part 2

Agenda
-
Review classes, this, promises, async/await
-
Destructuring and spread operator
-
Iterators, Generators & Iterables
-
Unit testing
-
Routing & MVC
What are we building?
a company directory with skills
Repository
git clone git@github.com:goofyahead/NodeJS-crash-course.git
Review
https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Classes
https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Promise
https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Functions/Arrow_functions
http://openmymind.net/mongodb.pdf
Classes
class Person {
constructor (){
this.age
this.name
}
fun() {
console.log('internal fun')
}
getAge() {
const fun = () => {
this.age = 32
}
fun()
this.fun()
return this.age
}
static staticFun () {
console.log('static call')
}
}
const person1 = new Person()
person1.age = 12
person1.name = 'alfredo'
console.log(person1.age)
console.log(person1.name)
console.log(person1.getAge())
Person.staticFun()this / self / scope
constructor (){
this.db = null
const self = this
MongoClient.connect(url, function(err, client) {
console.log("Connected successfully to server");
self.db = client.db(dbName);
});
}constructor (){
this.db = null
MongoClient.connect(url, function(err, client) {
console.log("Connected successfully to server");
this.db = client.db(dbName);
});
}constructor (){
this.db = null
MongoClient.connect(url,(err, client) => {
console.log("Connected successfully to server");
this.db = client.db(dbName);
});
}Promises & async/await
class Person {
constructor() {
this.age
this.name
}
async asyncAge() {
console.log('internal fun')
setTimeout(() => {
return this.age
}, 1000)
}
}
const person1 = new Person()
const asyncBlock = async () => {
const age = await person1.asyncAge()
console.log('age', age)
}
asyncBlock()Promises & async/await
class Person {
constructor() {
this.age
this.name
}
async asyncAge() {
console.log('internal fun')
return new Promise((resolve, reject) => {
setTimeout(() => {
resolve(111)
}, 3000)
})
}
}
const person1 = new Person()
const asyncBlock = async () => {
const age = await person1.asyncAge()
console.log('age', age)
}
asyncBlock()Run mongo on a folder
mkdir data/db
mongod --dbpath data/db
CRUD
mongo mydb
db.stats()
//Insertion
db.people.insert({name: 'alex'})
//Find
db.people.find({age: {$gt: 20}})
//Update
db.people.update({name: 'alex'}, {likes: ['cookies']})//Update
db.people.update({name: 'alex'}, {$set: {likes: ['cookies']}})Good to go!

Destructuring and spread
https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/Destructuring_assignment
Spread & Destructuring
[a, b] = [10, 20];
console.log(a);
// expected output: 10
console.log(b);
// expected output: 20
[a, b, ...rest] = [10, 20, 30, 40, 50];
console.log(rest);
// expected output: [30,40,50]
var o = {p: 42, q: true};
var {p, q} = o;
console.log(p); // 42
console.log(q); // trueSpread
const person = { name: 'David Walsh', gender: 'Male' };
const tools = { computer: 'Mac', editor: 'Atom' };
const summary = {...person, ...tools};
/*
Object {
"computer": "Mac",
"editor": "Atom",
"gender": "Male",
"name": "David Walsh",
}
*/Destructuring
function drawES6Chart({size = 'big', cords = {x: 0, y: 0}, radius = 25} = {}) {
console.log(size, cords, radius);
// do some chart drawing
}
drawES6Chart({
cords: {x: 18, y: 30},
radius: 30
});
drawES6Chart()function drawES5Chart(options) {
options = options === undefined ? {} : options;
var size = options.size === undefined ? 'big' : options.size;
var cords = options.cords === undefined ? {x: 0, y: 0} : options.cords;
var radius = options.radius === undefined ? 25 : options.radius;
console.log(size, cords, radius);
}
drawES5Chart({
cords: {x: 18, y: 30},
radius: 30
});Destructuring
var metadata = {
title: 'Scratchpad',
translations: [
{
locale: 'de',
localization_tags: [],
last_edit: '2014-04-14T08:43:37',
url: '/de/docs/Tools/Scratchpad',
title: 'JavaScript-Umgebung'
}
],
url: '/en-US/docs/Tools/Scratchpad'
};
var {title: englishTitle, translations: [{title: localeTitle}]} = metadata;
console.log(englishTitle); // "Scratchpad"
console.log(localeTitle); // "JavaScript-Umgebung"Destructuring
var people = [
{
name: 'Mike Smith',
family: {
mother: 'Jane Smith',
father: 'Harry Smith',
sister: 'Samantha Smith'
},
age: 35
},
{
name: 'Tom Jones',
family: {
mother: 'Norah Jones',
father: 'Richard Jones',
brother: 'Howard Jones'
},
age: 25
}
];
for (var {name: n, family: {father: f}} of people) {
console.log('Name: ' + n + ', Father: ' + f);
}
Iterators generators & iterables

https://developer.mozilla.org/en-US/docs/Web/JavaScript/Guide/Iterators_and_GeneratorsIterators
function makeIterator(array) {
var nextIndex = 0;
return {
next: function() {
return nextIndex < array.length ?
{value: array[nextIndex++], done: false} :
{done: true};
}
};
}var it = makeIterator(['yo', 'ya']);
console.log(it.next().value); // 'yo'
console.log(it.next().value); // 'ya'
console.log(it.next().done); // trueGenerators *
function* idMaker() {
var index = 0;
while(true)
yield index++;
}
var gen = idMaker();
console.log(gen.next().value); // 0
console.log(gen.next().value); // 1
console.log(gen.next().value); // 2
// ...Iterables
var myIterable = {};
myIterable[Symbol.iterator] = function* () {
yield 1;
yield 2;
yield 3;
};
for (let value of myIterable) {
console.log(value);
}
Unit testing

mocha
npm install mocha --save-devvar assert = require('assert');
describe('Array', function() {
describe('#indexOf()', function() {
it('should return -1',() => {
assert.equal([1,2,3].indexOf(4), -1);
});
});
});test script
{
"name": "myawesomeapp",
"version": "1.0.0",
"description": "my awesome app",
"main": "index.js",
"scripts": {
"start": "node index.js",
"test": "mocha test/* --recursive",
"debug": "node --inspect-brk index.js"
},
"keywords": [
"rest",
"mongodb"
],
"author": "alex",
"license": "ISC",
"dependencies": {
"handlebars": "^4.0.11",
"hapi": "^17.5.1",
"mongodb": "^3.0.10",
"vision": "^5.3.2"
},
"devDependencies": {
"mocha": "^5.2.0"
}
}
coverage
{
"name": "myawesomeapp",
"version": "1.0.0",
"description": "my awesome app",
"main": "index.js",
"scripts": {
"start": "node index.js",
"test": "nyc mocha test/* --recursive",
"debug": "node --inspect-brk index.js"
},
"keywords": [
"rest",
"mongodb"
],
"author": "alex",
"license": "ISC",
"dependencies": {
...
},
"devDependencies": {
"mocha": "^5.2.0",
"nyc": "^12.0.2"
}
}npm install nyc --save-dev
Refactor! To MVC

Refactor! To MVC
server.route(PeopleController.getPeople)
server.route(PeopleController.getPerson)
server.route(PeopleController.renderPerson)server.route({
method: 'GET',
path: '/people',
handler: (request) => {
return Db.getPeople()
}
})
server.route({
method: 'GET',
path: '/people/{name}',
handler: (request) => {
return Db.getPerson(request.params.name)
}
})
server.route({
method: 'GET',
path: '/render/people/{name}',
handler: async (request, h) => {
const person = await Db.getPerson(request.params.name)
return h.view('person', {
message: 'Hello Handlebars!',
person: person
});
}
})

Questions?

Homework
- Play around with this (promises and =>)
- Understand module.exports
- Allow insertion of people REST
- Form to perform insert with
body - Go to MDN and node website!

NodeJS part 2
By Alejandro Vidal Rodriguez
NodeJS part 2
- 37