├── 1-section ├── 3-exectution-context.js ├── 4-scope-chain.js ├── 1-global.js └── 2-hoisting.js ├── 4-section ├── 2-string-literal.js ├── 1-const-let.js ├── 4-object-literals.js ├── 3-fat-arrow.js └── 5-destructuring.js ├── 3-section ├── 3-apply-call-bind.js ├── 1-this.js └── 2-closure.js ├── 2-section ├── 1-functions.js └── 2-iifes.js ├── 6-section ├── 3-async-await.js ├── 1-callbacks.js └── 2-promises.js └── 5-section ├── 2-classes.js └── 1-prototypes.js /1-section/3-exectution-context.js: -------------------------------------------------------------------------------- 1 | // run the code and notice console output 2 | var color = 'red'; 3 | 4 | function first() { 5 | var color = 'green'; 6 | console.log(color); 7 | } 8 | 9 | first(); 10 | console.log(color); 11 | 12 | 13 | -------------------------------------------------------------------------------- /1-section/4-scope-chain.js: -------------------------------------------------------------------------------- 1 | //run the code and notice that red is logged twice - once by second and once by the last line 2 | var color = 'red'; 3 | 4 | function first() { 5 | var color = 'green'; 6 | console.log(color); 7 | second(); 8 | } 9 | 10 | function second() { 11 | console.log(color); 12 | } 13 | 14 | first(); 15 | console.log(color); 16 | -------------------------------------------------------------------------------- /1-section/1-global.js: -------------------------------------------------------------------------------- 1 | // check what window is 2 | window 3 | 4 | // check what this is 5 | this 6 | 7 | // verify that window and this are the same in global execution context 8 | window === this 9 | 10 | // add a variable to GEC and check if it's available on the window object 11 | var name = 'foo' 12 | 13 | // add a funcion to GEC and check if it's available on the window object 14 | function getName() { 15 | console.log(this.name); 16 | } -------------------------------------------------------------------------------- /4-section/2-string-literal.js: -------------------------------------------------------------------------------- 1 | '---------------------' 2 | // terrible ES5 syntax (string concat) 3 | '---------------------' 4 | 5 | var person = { 6 | firstName: 'Jane', 7 | lastName: 'Doe' 8 | } 9 | 10 | console.log('Hello, My name is ' + person.name + ' ' + person.lastName); 11 | 12 | '---------------------' 13 | // fix with template strings 14 | '---------------------' 15 | 16 | console.log(`Hello, My name is ${person.firstName} ${person.lastName}`); -------------------------------------------------------------------------------- /3-section/3-apply-call-bind.js: -------------------------------------------------------------------------------- 1 | function logTarget(message) { 2 | var logMessage = message || 'target is'; 3 | console.log(this); 4 | console.log(logMessage, this.target); 5 | } 6 | 7 | /* window.onclick = function(e) { 8 | var lg = logTarget.bind(e); 9 | lg(); 10 | } 11 | 12 | window.onclick = function(e) { 13 | logTarget.call(e, 'print call message'); 14 | } 15 | 16 | window.onclick = function(e) { 17 | logTarget.apply(e, ['print apply message']); 18 | } */ -------------------------------------------------------------------------------- /1-section/2-hoisting.js: -------------------------------------------------------------------------------- 1 | // run the following code and notice what's logged 2 | 3 | var name = 'foo'; 4 | 5 | function greet() { 6 | console.log('hello!'); 7 | } 8 | 9 | console.log(name); 10 | greet(); 11 | 12 | // now run the following code - notice that there was no error (js is aware of them) 13 | 14 | console.log(name); 15 | greet(); 16 | 17 | var name = 'foo'; 18 | 19 | function greet() { 20 | console.log('hello!'); 21 | 22 | } 23 | 24 | // notice that you can invoke the function before it's defined in the code 25 | // finally run the following code - notice that the difference in the 2 outputs 26 | 27 | console.log(name); 28 | var name = 'foo'; 29 | console.log(name); 30 | 31 | 32 | -------------------------------------------------------------------------------- /4-section/1-const-let.js: -------------------------------------------------------------------------------- 1 | '---------------------' 2 | // demo problem with using var 3 | '---------------------' 4 | 5 | function logVars() { 6 | var x = 1; 7 | console.log(x); 8 | 9 | if (true) { 10 | var x = 2; 11 | console.log(x); 12 | } 13 | 14 | console.log(x); 15 | } 16 | 17 | '---------------------' 18 | // fix with let 19 | '---------------------' 20 | 21 | function logVars() { 22 | var x = 1; 23 | console.log(x); 24 | 25 | if (true) { 26 | let x = 2; 27 | console.log(x); 28 | } 29 | 30 | console.log(x); 31 | } 32 | 33 | '---------------------' 34 | // demo const can't be re-assigned 35 | '---------------------' 36 | 37 | function logVars() { 38 | const x = 1; 39 | console.log(x); 40 | 41 | x = 2; 42 | 43 | console.log(x); 44 | } -------------------------------------------------------------------------------- /2-section/1-functions.js: -------------------------------------------------------------------------------- 1 | var obj = {}; 2 | 3 | console.log(obj); 4 | 5 | var obj2 = {}; 6 | var func = function() { 7 | console.log('hi from func!'); 8 | } 9 | 10 | obj2.func = func; 11 | 12 | console.log(obj2); 13 | 14 | // obj(); // error not a function 15 | 16 | // can be invoked 17 | obj2.func(); 18 | 19 | // since it's an object, you can access other properties 20 | console.log(func.name); 21 | 22 | 23 | // -------- 24 | 25 | // run the following code and check the error in the console 26 | sayHi(); 27 | sayHello(); 28 | 29 | // declaration 30 | function sayHi() { 31 | console.log('hi!'); 32 | } 33 | 34 | // expression 35 | var sayHello = function() { 36 | console.log('hello!'); 37 | } 38 | 39 | function caller(func) { 40 | if (typeof func === 'function') { 41 | func(); 42 | } else { 43 | console.log('not a function!'); 44 | } 45 | } -------------------------------------------------------------------------------- /3-section/1-this.js: -------------------------------------------------------------------------------- 1 | function func1() { 2 | console.log('func1', this); 3 | } 4 | 5 | var func2 = function() { 6 | console.log('func2', this); 7 | } 8 | 9 | (function() { 10 | console.log('IIFE', this); 11 | })(); 12 | 13 | var obj = { 14 | name: 'an object', 15 | func: function() { 16 | console.log('obj.func', this); 17 | } 18 | } 19 | 20 | obj.func(); 21 | 22 | // --- 23 | 24 | var obj = { 25 | name: 'an object', 26 | func: function() { 27 | function inFunc() { 28 | console.log('in func', this.name); // this will be pointing to window (js flaw?) 29 | } 30 | console.log('obj.func', this.name); 31 | inFunc(); 32 | } 33 | } 34 | 35 | obj.func(); 36 | 37 | // --- 38 | 39 | var obj = { 40 | name: 'an object', 41 | func: function() { 42 | var that = this; // remedy 43 | function inFunc() { 44 | console.log('in func', that); 45 | } 46 | console.log('obj.func', that); 47 | inFunc(); 48 | } 49 | } 50 | 51 | obj.func(); 52 | 53 | -------------------------------------------------------------------------------- /3-section/2-closure.js: -------------------------------------------------------------------------------- 1 | // 1. 2 | function makeFunc() { 3 | var name = 'Pearson'; 4 | function displayName() { 5 | console.log(name); 6 | } 7 | return displayName; 8 | } 9 | 10 | var myFunc = makeFunc(); 11 | console.log(myFunc); 12 | 13 | // run the following line in the console 14 | // myFunc(); 15 | 16 | // 2. 17 | 18 | function createClosure() { 19 | var name = 'Pearson'; 20 | 21 | setTimeout(function() { 22 | console.log('Timed out', name) 23 | }, 2000); 24 | 25 | console.log('I am done executing!'); 26 | } 27 | 28 | // createClosure(); 29 | 30 | // 3. 31 | 32 | for (var i = 0; i < 3; i++) { 33 | setTimeout(function() { 34 | console.log('Timed out', val) 35 | }, 2000); 36 | } 37 | 38 | for (var i = 0; i < 3; i++) { 39 | (function(i) { 40 | setTimeout(function() { 41 | console.log('Timed out', i) 42 | }, 2000) 43 | })(i); 44 | } 45 | 46 | for (var i = 0; i < 3; i++) { 47 | let j = i; 48 | setTimeout(function() { 49 | console.log('Timed out', j) 50 | }, 2000) 51 | } 52 | 53 | -------------------------------------------------------------------------------- /4-section/4-object-literals.js: -------------------------------------------------------------------------------- 1 | const firstName = 'jane'; 2 | const lastName = 'doe'; 3 | const age = 26; 4 | const city = 'Montreal'; 5 | 6 | '---------------------' 7 | // init 8 | '---------------------' 9 | 10 | const obj = { 11 | firstName, 12 | lastName, 13 | age, 14 | location 15 | } 16 | 17 | '---------------------' 18 | // method shorthand 19 | '---------------------' 20 | 21 | const obj = { 22 | firstName, 23 | lastName, 24 | age, 25 | location, 26 | getInfo() { //compare to getInfo: function() {} 27 | console.log(`Name: ${firstName} ${lastName}, Age: ${age}, Location: ${city}`); 28 | } 29 | } 30 | 31 | '---------------------' 32 | // dynamic key 33 | '---------------------' 34 | 35 | var key = 'country'; 36 | 37 | const obj = { 38 | firstName, 39 | lastName, 40 | age, 41 | location, 42 | [key]: 'Canada', //compare to obj.country = 'Canada' or obj[key] = 'Canada' 43 | getInfo() { 44 | console.log(`Name: ${firstName} ${lastName}, Age: ${age}, Location: ${city}`); 45 | } 46 | } 47 | 48 | 49 | 50 | -------------------------------------------------------------------------------- /6-section/3-async-await.js: -------------------------------------------------------------------------------- 1 | const longGET = (num) => { 2 | return new Promise((resolve, reject) => { 3 | setTimeout(() => { 4 | if (Math.random() <= 0.65 || true) { // remove true for error 5 | console.log(`GET: ${num}`); 6 | resolve(num) 7 | } else { 8 | console.log(`Error in GET: ${num}`); 9 | reject(num); 10 | } 11 | }, 1000); 12 | }) 13 | } 14 | 15 | '---------------------' 16 | // setup 17 | '---------------------' 18 | 19 | const executeGets = () => { 20 | let one = longGET(1); 21 | let two = longGET(++one); 22 | console.log('done with 1 and 2'); 23 | } 24 | 25 | executeGets(); 26 | 27 | '---------------------' 28 | // async/await 29 | '---------------------' 30 | 31 | const executeGets = async () => { 32 | let one = await longGET(1); 33 | let two = await longGET(++one); 34 | console.log('done with 1 and 2'); 35 | } 36 | 37 | executeGets(); 38 | 39 | '---------------------' 40 | // async/await - error handling 41 | '---------------------' 42 | 43 | const executeGets = async () => { 44 | try { 45 | let one = await longGET(1); 46 | let two = await longGET(++one); 47 | console.log('done with 1 and 2'); 48 | } catch (err) { 49 | console.log(`error in ${err}`); 50 | } 51 | } 52 | 53 | executeGets(); 54 | 55 | -------------------------------------------------------------------------------- /2-section/2-iifes.js: -------------------------------------------------------------------------------- 1 | // ---- game: part 1 ---- 2 | 3 | var game = (function createGame(initialScore) { 4 | var score = 0 || initialScore; 5 | 6 | function getScore() { 7 | console.log(score); 8 | } 9 | 10 | function incrementScore() { 11 | score++; 12 | getScore(); 13 | } 14 | 15 | return { 16 | getScore: getScore, 17 | incrementScore: incrementScore 18 | } 19 | 20 | })(5); 21 | 22 | game.getScore(); 23 | game.incrementScore(); 24 | 25 | 26 | // ---- game: part 2 ---- 27 | 28 | (function createGame() { 29 | var negative = 0; 30 | var positive = 0; 31 | 32 | function getScore() { 33 | console.clear(); 34 | console.log('Score: ' + (positive - negative)); 35 | } 36 | 37 | function printScoreTable() { 38 | console.table({positive, negative, score: (positive - negative)}); 39 | } 40 | 41 | function incrementScore() { 42 | positive++; 43 | getScore(); 44 | } 45 | 46 | function decrementScore() { 47 | negative++; 48 | getScore(); 49 | } 50 | 51 | window.onclick = function(e) { 52 | if (e.clientY <= 200) { 53 | decrementScore(); 54 | } else { 55 | incrementScore(); 56 | } 57 | } 58 | 59 | window.onkeypress = function(e) { 60 | if(e.key === 's') { 61 | printScoreTable(); 62 | } 63 | } 64 | 65 | })(); 66 | -------------------------------------------------------------------------------- /4-section/3-fat-arrow.js: -------------------------------------------------------------------------------- 1 | '---------------------' 2 | // all possible syntax 3 | '---------------------' 4 | 5 | '---------------------' 6 | // closure issue 7 | '---------------------' 8 | 9 | const loc = { 10 | country: 'Canada', 11 | city: 'Toronto', 12 | teams: ['Raptors', 'Blue Jays', 'Maple Leafs'], 13 | getInfo: function() { 14 | console.log(`Current location is ${this.city}, ${this.country}`); 15 | }, 16 | getTeamNames: function() { 17 | this.teams.map(function(team) { 18 | console.log(`${team} from ${this.city}, ${this.country}`); 19 | }) 20 | } 21 | } 22 | 23 | // loc.getInfo(); 24 | loc.getTeamNames(); 25 | 26 | '---------------------' 27 | // closure issue - fix (that/this) 28 | '---------------------' 29 | 30 | var that = this; 31 | this.teams.map(function(team) { 32 | console.log(`${team} from ${that.city}, ${that.country}`); 33 | }) 34 | 35 | '---------------------' 36 | // closure issue - fix (bind) 37 | '---------------------' 38 | 39 | this.teams.map((function(team) { 40 | console.log(`${team} from ${this.city}, ${this.country}`); 41 | }).bind(this)); 42 | 43 | '---------------------' 44 | // closure issue - fix (arrow) 45 | '---------------------' 46 | 47 | // fat arrow below will remember the enclosing 'this' 48 | this.teams.map((team) => { 49 | console.log(`${team} from ${this.city}, ${this.country}`); 50 | }) 51 | 52 | -------------------------------------------------------------------------------- /6-section/1-callbacks.js: -------------------------------------------------------------------------------- 1 | // what is a callback? 2 | // I will call you back! 3 | 4 | '---------------------' 5 | // second before first :( 6 | '---------------------' 7 | 8 | // long running function 9 | function first() { 10 | setTimeout(() => { 11 | console.log(1) 12 | }, 500); 13 | } 14 | 15 | function second() { 16 | console.log(2); 17 | } 18 | 19 | first(); 20 | second(); 21 | 22 | 23 | '---------------------' 24 | // accept callback 25 | '---------------------' 26 | 27 | // I take a long time to execute 28 | // I do not want to keep you waiting for me 29 | // Just let me know what I should do once I am done 30 | // You can move on to other things 31 | 32 | function first(callback) { 33 | setTimeout(() => { 34 | console.log(1) 35 | callback(); 36 | }, 500); 37 | } 38 | 39 | function second() { 40 | console.log(2); 41 | } 42 | 43 | first(second); 44 | console.log('moving on to other things..'); 45 | 46 | '---------------------' 47 | // callback hell 48 | '---------------------' 49 | 50 | function longGET(num, time, cb) { 51 | setTimeout(() => { 52 | console.log(`GET: ${num}`); 53 | cb(num); 54 | }, time); 55 | } 56 | 57 | // hell 58 | longGET(1, 500, function(num) { 59 | longGET(++num, 700, function(num) { 60 | longGET(++num, 300, function(num) { 61 | console.log('done') ; 62 | }) 63 | }) 64 | }) 65 | 66 | 67 | -------------------------------------------------------------------------------- /5-section/2-classes.js: -------------------------------------------------------------------------------- 1 | // a. 2 | function Watch(options) { 3 | this.brand = options.brand; 4 | } 5 | 6 | Watch.prototype.time = function() { 7 | console.log(new Date(Date.now()).toLocaleString()); 8 | } 9 | 10 | function SmartWatch(options) { 11 | Watch.call(this, options); 12 | this.type = 'smart'; 13 | } 14 | 15 | SmartWatch.prototype.steps = function() { 16 | console.log(Math.floor(Math.random() * 10000)); 17 | } 18 | 19 | // b. 20 | // fix inheritance 35,36 21 | function Watch(options) { 22 | this.brand = options.brand; 23 | } 24 | 25 | Watch.prototype.time = function() { 26 | console.log(new Date(Date.now()).toLocaleString()); 27 | } 28 | 29 | function SmartWatch(options) { 30 | Watch.call(this, options); 31 | this.type = 'smart'; 32 | } 33 | 34 | // inherit from Watch 35 | SmartWatch.prototype = Object.create(Watch.prototype); 36 | SmartWatch.prototype.constructor = SmartWatch; 37 | 38 | SmartWatch.prototype.steps = function() { 39 | console.log(Math.floor(Math.random() * 10000)); 40 | } 41 | 42 | // c. 43 | // es6 classes 44 | 45 | class Watch { 46 | constructor(options) { 47 | this.brand = options.brand; 48 | } 49 | 50 | time() { 51 | console.log(new Date(Date.now()).toLocaleString()); 52 | } 53 | } 54 | 55 | class SmartWatch extends Watch { 56 | constructor(options) { 57 | // super(options); 58 | this.type = 'smart'; 59 | } 60 | 61 | steps() { 62 | console.log(Math.floor(Math.random() * 10000)); 63 | } 64 | } -------------------------------------------------------------------------------- /5-section/1-prototypes.js: -------------------------------------------------------------------------------- 1 | //--- a. 2 | 3 | // run that in the console 4 | var person = {name: 'Jane'}; 5 | 6 | // now type - do you see any methods? where did they come from? 7 | person. 8 | 9 | // try 10 | person.hasOwnProperty('name'); //true 11 | person.hasOwnProperty('age'); //false 12 | 13 | //--- b. 14 | 15 | // run this in the console 16 | var arr = ['apples', 'oranges']; 17 | console.log(arr); 18 | 19 | // now try to find 'hasOwnProperty' method on prototype chain 20 | 21 | //--- c. 22 | 23 | // Everything is an object! 24 | 25 | const obj = {} 26 | const arr = [] 27 | console.log(obj.__proto__.constructor); 28 | console.log(arr.__proto__.constructor); 29 | console.log(arr.__proto__.__proto__.constructor); 30 | 31 | //--- d. 32 | 33 | function Person(name, age) { 34 | this.name = name; 35 | this.age = age; 36 | this.getInfo = function() { 37 | console.log(`Person info: Name -> ${this.name}, Age -> ${this.age}`); 38 | } 39 | } 40 | 41 | const p1 = new Person('Jane', '25'); 42 | const p2 = new Person('John', '52'); 43 | 44 | // both p1 and p2 get their own "getInfo" function 45 | // fix it with protoype 46 | 47 | function Person(name, age) { 48 | this.name = name; 49 | this.age = age; 50 | } 51 | 52 | Person.prototype.getInfo = function() { 53 | console.log(`Person info: Name -> ${this.name}, Age -> ${this.age}`); 54 | } 55 | 56 | const p1 = new Person('Jane', '25'); 57 | const p2 = new Person('John', '52'); 58 | 59 | // extend an existing API 60 | Array.prototype.first = function() { 61 | if (this.length) { 62 | console.log(`First element is ${this[0]}`); 63 | } else { 64 | console.log('Array is empty :(') 65 | } 66 | } 67 | 68 | var arr1 = ['apple', 'orange']; 69 | var arr2 = []; 70 | var arr3; 71 | 72 | arr1.first() 73 | arr2.first() 74 | arr3.first(); 75 | -------------------------------------------------------------------------------- /4-section/5-destructuring.js: -------------------------------------------------------------------------------- 1 | '---------------------' 2 | // destructuring objects 3 | '---------------------' 4 | 5 | const obj = { 6 | firstName: 'Jane', 7 | lastName: 'Doe', 8 | age: 26, 9 | location: 'Montreal', 10 | getInfo() { 11 | console.log(`Name: ${firstName} ${lastName}, Age: ${age}, Location: ${city}`); 12 | } 13 | } 14 | 15 | const {firstName, lastName} = obj; 16 | console.log('firstName:', firstName) 17 | console.log('lastName:', lastName) 18 | 19 | '---------------------' 20 | // destructuring objects (params) 21 | '---------------------' 22 | 23 | const func = (obj) => { 24 | const name = `${obj.firstName} ${obj.lastName}`; 25 | console.log(name); 26 | } 27 | 28 | func(obj); 29 | 30 | // same as below: 31 | 32 | const betterFunc = ({firstName, lastName}) => { 33 | const name = `${firstName} ${lastName}`; 34 | console.log(name); 35 | } 36 | 37 | betterFunc(obj) 38 | 39 | '---------------------' 40 | // destructuring arrays 41 | '---------------------' 42 | 43 | const arr = ['Jane', 'Doe', 26, 'Montreal']; 44 | const [firstName, lastName] = arr; 45 | 46 | console.log('firstName:', firstName); 47 | console.log('lastName:', lastName); 48 | 49 | '---------------------' 50 | // destructuring arrays (params) 51 | '---------------------' 52 | 53 | const func = (arr) => { 54 | const name = `${arr[0]} ${arr[1]}`; 55 | console.log(name); 56 | } 57 | 58 | func(arr); 59 | 60 | // same as below: 61 | 62 | const betterFunc = ([firstName, lastName]) => { 63 | const name = `${firstName} ${lastName}`; 64 | console.log(name); 65 | } 66 | 67 | betterFunc(arr); 68 | 69 | '---------------------' 70 | // rest params 71 | '---------------------' 72 | 73 | const restFunc = ([firstName, lastName, ...rest]) => { 74 | const name = `${firstName} ${lastName}`; 75 | console.log(name); 76 | console.log(rest); 77 | } 78 | 79 | restFunc(arr); -------------------------------------------------------------------------------- /6-section/2-promises.js: -------------------------------------------------------------------------------- 1 | // what is a Promise? 2 | // I promise that I will execute the code and let you know of the success/failure 3 | // Meanwhile, you can move on to other things 4 | 5 | '---------------------' 6 | // longGET 7 | '---------------------' 8 | 9 | const longGET = (num) => { 10 | return new Promise((resolve, reject) => { 11 | setTimeout(() => { 12 | if (Math.random() <= 0.65 || true) { // remove true for error 13 | console.log(`GET: ${num}`); 14 | resolve(num) 15 | } else { 16 | console.log(`Error in GET: ${num}`); 17 | reject(num); 18 | } 19 | }, 1000); 20 | }) 21 | } 22 | 23 | '---------------------' 24 | // syntax 25 | '---------------------' 26 | 27 | const one = longGET(1); // returns a promise 28 | 29 | one 30 | .then(() => { 31 | console.log('done'); 32 | }) 33 | .catch(() => { 34 | console.log('error'); 35 | }) 36 | 37 | console.log('moved on to other things') 38 | 39 | '---------------------' 40 | // sequence (error) 41 | '---------------------' 42 | 43 | const one = longGET(1); // returns a promise 44 | 45 | one 46 | .then((num) => { 47 | longGET(++num) 48 | console.log('done with 1 and 2'); 49 | }) 50 | .catch(() => { 51 | console.log('error'); 52 | }) 53 | 54 | '---------------------' 55 | // sequence (fixed) 56 | '---------------------' 57 | 58 | // When you return something from a then() callback, it's a bit magic. 59 | // If you return a value, the next then() is called with that value. 60 | // However, if you return something promise-like, the next then() waits on it, 61 | // and is only called when that promise settles (succeeds/fails). 62 | 63 | const one = longGET(1); // returns a promise 64 | 65 | one 66 | .then((num) => { 67 | return longGET(++num) 68 | }) 69 | .then((num) => { 70 | console.log('done with 1 and 2'); 71 | }) 72 | .catch(() => { 73 | console.log('error'); 74 | }) 75 | 76 | 77 | '---------------------' 78 | // finally 79 | '---------------------' 80 | 81 | const one = longGET(1); // returns a promise 82 | 83 | one 84 | .then((num) => { 85 | return longGET(++num) 86 | }) 87 | .then((num) => { 88 | console.log('done with 1 and 2'); 89 | }) 90 | .catch(() => { 91 | console.log('error'); 92 | }) 93 | .finally(() => { 94 | console.log('finally, finished executing!'); 95 | }) 96 | 97 | '---------------------' 98 | // parallel 99 | '---------------------' 100 | 101 | // start with all resolve 102 | // add a reject to see catch in action 103 | 104 | Promise.all([longGET(1), longGET(2)]) 105 | .then((results) => { 106 | console.log('done with 1 and 2', results); 107 | }) 108 | .catch((error) => { 109 | console.log(`error in ${error}`) 110 | }); 111 | 112 | --------------------------------------------------------------------------------