Skip to content

Fixed issue with missing files from 06 Code Quality. #7

Merged
merged 2 commits into from
Sep 20, 2019
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions 06 Code Quality.md
Original file line number Diff line number Diff line change
Expand Up @@ -244,7 +244,7 @@ In the example above we store the data returned from the `getData` promise in th

### 6.4 Test Your Knowledge

Run the `promises.js` script, its functionality should be familiar to the `currency.js` script you worked with in chapter 3.
Run the `promises.js` script located in the otherScripts folder. Its functionality should be familiar to the `currency.js` script you worked with in chapter 3.

Open the `promises.js` script and study the code carefully. Notice that it defines 5 promises and chains them together. You are going to extend the functionality by defining some additional promises and adding them to the promise chain.

Expand Down Expand Up @@ -376,7 +376,7 @@ both `printObjectPromise` and `printObjectAsync` behave in exactly the same mann

### 7.3 Test Your Knowledge

Run the `asyncFunctions.js` script. Note that it works in the same way as the previous ones. Open the script and study it carefully.
Run the `asyncFunctions.js` script, located in the otherScripts folder. Note that it works in the same way as the previous ones. Open the script and study it carefully.

1. modify the script to ask for the currency to convert to and display only the one conversion rate.
2. instead of printing the exchange rate, ask for the amount to be converted and them return the equivalent in the chosen currency
Expand Down
32 changes: 32 additions & 0 deletions exercises/07_unit_testing/otherScripts/addressFinder.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@

'use strict'

const request = require('request')

try {
if (process.argv.length < 3) {
throw 'missing parameter'
}
let address = process.argv[2]
/* we need to remove the single quotes from the string */
address = address.replace(/'/g,'')
console.log(address)
const url = `https://maps.googleapis.com/maps/api/geocode/json?region=gb&units=metric&appid=44c39f3fa462f86b3fc88f5678e5c5ff&address=${address}`
console.log(url)
request.get( url, (err, res, body) => {
if (err) {
throw 'could not complete request'
}
const json = JSON.parse(body)
console.log(JSON.stringify(json, null, 2))
try {
if (json.status === 'ZERO_RESULTS') {
throw 'no results found'
}
} catch(err) {
console.log(err)
}
})
} catch(err) {
console.log(err)
}
41 changes: 41 additions & 0 deletions exercises/07_unit_testing/otherScripts/arrowFunctions.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@

'use strict'

/* eslint no-magic-numbers: 0, arrow-body-style: 0 */

// all four of these functions contain the same functionality.

// traditional JavaScript function that takes an ECMA rest param and returns the total
// no use made of functional programming principles.
function add(...num) {
let total = 0

for (let i=0; i< num.length; i++) {
total += num[i]
}
return total
}

// simple ECMAScript 5 compatible anonymous function assigned to a constant.
// Array.prototype.reduce used to eliminate the loop from the previous example.
const add2 = function(...num) {
return num.reduce( (acc, val) => acc + val)
}

// arrow function syntax used instead of the traditional anonymous function declaration.
// normally a single parameter would not be enclosed in braces but these are needed for rest params.
const add3 = (...num) => {
return num.reduce( (acc, val) => acc + val)
}

// if the body of the function contains a single line of code that returns a value
// the braces and return statement are not required.
const add4 = (...num) => num.reduce( (acc, val) => acc + val)

console.log(add(1, 2, 3))

console.log(add2(1, 2, 3))

console.log(add3(1, 2, 3))

console.log(add4(1, 2, 3))
35 changes: 35 additions & 0 deletions exercises/07_unit_testing/otherScripts/asyncDemo.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@

'use strict'

const asyncFunc = (name, callback) => {
const names = ['colin', 'bob']
if (names.indexOf(name) > -1) {
// success
const result = 'found'
return callback(null, result)
} else {
// error
const message = 'name not found'
return callback(message)
}
}

// check username exists
const check = name => {
asyncFunc(name, (err, result) => {
if (err) {
// it didn't work i.e. not found
console.error(err)
throw new Error('broke looking for name')
} else {
// success: i.e. result has a value
console.log('It was found.')
console.log(result)
}
})
}

check('colin')
check('nobody')

// (err, data) => {} is common callback signature
50 changes: 50 additions & 0 deletions exercises/07_unit_testing/otherScripts/asyncFunctions.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@

'use strict'

const request = require('request')

async function main() {
try {
const base = await getInput('enter base currency')
await checkValidCurrencyCode(base)
const data = await getData(`http://api.fixer.io/latest?base=${base}`)
await printObject(data)
process.exit()
} catch (err) {
console.log(`error: ${err.message}`)
}
}

const getInput = prompt => new Promise( (resolve) => {
process.stdin.resume()
process.stdin.setEncoding('utf8')
process.stdout.write(`${prompt}: `)
process.stdin.on('data', text => resolve(text))
})

const checkValidCurrencyCode = code => new Promise( (resolve, reject) => {
code = code.trim()
request('http://api.fixer.io/latest', (err, res, body) => {
if (err) reject(new Error('invalid API call'))
const rates = JSON.parse(body).rates
if (!rates.hasOwnProperty(code)) it.throw(new Error(`invalid currency code ${code}`))
resolve()
})
})

const getData = url => new Promise( (resolve, reject) => {
request(url, (err, res, body) => {
if (err) reject(new Error('invalid API call'))
resolve(body)
})
})

const printObject = data => new Promise( (resolve) => {
const indent = 2
data = JSON.parse(data)
const str = JSON.stringify(data, null, indent)
console.log(str)
resolve()
})

main()
25 changes: 25 additions & 0 deletions exercises/07_unit_testing/otherScripts/books.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
#!/usr/bin/env node

'use strict'

function Book(isbn, title) {
this.isbn = isbn
this.title = title
this.year = null
Object.defineProperty(this, 'published', {
get: () => this.year,
set: year => this.year = year
})
Object.defineProperty(this, 'summary', {
get: () => `${this.title} (${this.isbn}). Published ${this.year}.`
})
}

const b = new Book('1491943122', 'Learning Node')
if (b instanceof Book) console.log('its a Book')
console.log(`the b object is a '${typeof b}'`)
console.log(b.published) // prints null
b.year = 2016
console.log(b.published) // prints 2016
console.log(b)
console.log(b.summary)
20 changes: 20 additions & 0 deletions exercises/07_unit_testing/otherScripts/classes/employee.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
#!/usr/bin/env node
/* eslint no-magic-numbers: 0 */

'use strict'

const Person = require('./person')

module.exports = class Employee extends Person {

constructor(firstname, lastname, grade = 1) {
super(firstname, lastname)
this.joinedDate = new Date()
this.grade = grade
}

calculateSalary(months = 1) {
return this.grade * 1000 * months
}

}
22 changes: 22 additions & 0 deletions exercises/07_unit_testing/otherScripts/classes/employeeTest.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
#!/usr/bin/env node
/* eslint no-magic-numbers: 0 */

'use strict'

const Employee = require('./employee')

try {
const worker = new Employee('John', 'Doe')
console.log(worker.name)

const salary = worker.calculateSalary()
console.log(salary)

const manager = new Employee('Peter', 'Piper', 4)
console.log(manager.name)
console.log(manager.calculateSalary(6))
console.log(manager)

} catch(err) {
console.log(`ERROR: ${err}`)
}
45 changes: 45 additions & 0 deletions exercises/07_unit_testing/otherScripts/classes/person.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
#!/usr/bin/env node

'use strict'

/** Class representing a person */
module.exports = class Person {

/**
* Create a person
* @param {string} firstname - the person's first name
* @param {string} lastname - the person's last name
*/
constructor(firstname, lastname) {
if (firstname === undefined || lastname === undefined) {
throw new Error('missing parameter')
}
this.first = firstname
this.last = lastname
}

/**
* Set the person's first name
* @param {string} name - the person's first name
*/
set firstName(name) {
this.first = name
}

/**
* Set the person's last name
* @param {string} name - the person's last name
*/
set lastName(name) {
this.last = name
}

/**
* Get the person's full name
* @return {string} the person's full name
*/
get name() {
return `${this.first} ${this.last}`
}

}
16 changes: 16 additions & 0 deletions exercises/07_unit_testing/otherScripts/classes/personTest.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
#!/usr/bin/env node

'use strict'

const Person = require('./person')
try {
const person = new Person('Andy', 'Capp')
console.log(person.name)
person.lastName = 'Pandy'
console.log(JSON.stringify(person, null, 2))

const badPerson = new Person('anon')
console.log(badPerson)
} catch(err) {
console.log(`ERROR: ${err}`)
}
73 changes: 73 additions & 0 deletions exercises/07_unit_testing/otherScripts/coffee/betterCoffee.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,73 @@
#!/usr/bin/env node

'use strict'

/* eslint no-magic-numbers: 0 */

function Coffee(roast, ounces = 8) {

const privateData = {}

privateData.size = {
small: 8,
medium: 12,
large: 16
}

if (roast === undefined) {
throw new Error('missing roast type')
}

privateData.roast = roast
privateData.ounces = ounces

function getSize() {
if (this.ounces === this.size.small) {
return 'small'
} else if (this.ounces === this.size.medium) {
return 'medium'
} else if (this.ounces === this.size.large) {
return 'large'
}
}

return {
order: {
get: () => {
let msg
switch (getSize()) {
case 'small':
case 'medium':
case 'large':
msg = `You've ordered a ${getSize()} ${this.roast} coffee.`
break
default:
msg = `We don't have a ${this.roast} in that size!`
break
}
return msg
}
}
}

} // end function Coffee

try {
const coffee = new Coffee('House Blend', 12)
console.log(coffee.order)
console.log(coffee)

const darkRoast = new Coffee('Dark Roast', 16)
console.log(darkRoast.order)

const specialBlend = new Coffee('Special Blend', 200)
console.log(specialBlend.order)

const kenyan = new Coffee('Kenyan')
console.log(kenyan.order)

const anon = new Coffee()
console.log(anon.order)
} catch(err) {
console.log(`ERROR: ${err}`)
}
Loading