.then().catch()
async function getCheese(shouldError = false) {
// after 1 second, return an array of cheese or Reject with an error
return new Promise((resolve, reject) => {
setTimeout(() => {
if (shouldError) {
return reject('Cheese Sucks')
}
}, 1)
})
resolve(['cheddar', 'brie', 'gouda']);
}
getCheese()
.then(cheeses => {
console.log (cheeses) // ['cheddar', 'brie', 'gouda']
})
.catch(herr => console.log(err))
try…catch
try {
const cheese = await getCheese()
console.log(cheese) // ['cheddar', 'brie', 'gouda']
} catch(err) {
console.log(err)
}
await + catch
const myCheese = await getCheese().catch(err => console.log(err))
console.log(myCheese) // ['cheddar', 'brie', 'gouda']
error handling with Promise.allSettled() https://youtu.be/wsoQ-fgaoyQ?si=MX5SvTAkJq4PqO-7&t=778
function wrapIt(promise) {
// Promise.allSettled() will return an array of objects, we grab the first one
// That object will only ever have one of these properties:
// "value" - the resolved data
// OR
// "reason" - the rejected error
return Promise.allSettled([promise]).then(function([{ value, reason }]) {
return [value, reason]
}
const [data, err] = await wrapIt(getCheese()) // [[ 'cheddar', 'brie', 'gouda' ], undefined ]
const [cheese, cheeseError] = await wrapIt(getCheese(true)) // [ undefined, 'Cheese Sucks' ]
may also return not an array, but an object
function wrapIt(promise) {
return Promise.allSettled([promise]).then(function([{ value, reason }]) {
return { data: value, error: reason }
}
const result = await wrapIt(getCheese())
if (result.error) {
console.log(error)
return
}
console.log(result.data)
try…catch…finally code to be put into try block if no errors, then catch block is ignored if an error the script is not killed try...catch works synchronously, no delayed functions will be executed if an error occurs, then execution in try block is stopped try...catch can only handle errors that occur in valid code catch block has default error variable which contains an error object finally block always executes catch or finally can be omitted
try {
alert('Start of try runs')
lalala // error, variable is not defined!
alert('End of try (never reached)')
} catch(err) {
alert(`Error has occurred!`)
console.dir(err)
} finally {
alert('bugs happens, do not get upset')
}
error variable is optional
try {
alert('Start of try runs')
lalala // error, variable is not defined!
alert('End of try (never reached)')
} catch {
alert(`Error has occurred!`)
} finally {
alert('bugs happens, do not get upset')
}
finally with return return value in finally block overwrites a value in try block
function example() {
try {
return true;
}
finally {
console.log('finally')
return false
}
}
// finally
// false
Scheduled function
setTimeout(function() {
try {
noSuchVariable // try...catch handles the error!
} catch (err) {
alert( "error is caught here!" )
}
}, 1000)
Error object
try {
lalala; // error, variable is not defined!
} catch (err) {
alert(err.name); // ReferenceError
alert(err.message); // lalala is not defined
alert(err.stack); // ReferenceError: lalala is not defined at (...call stack)
// Can also show an error as a whole
// The error is converted to string as "name: message"
alert(err); // ReferenceError: lalala is not defined
}
Create error object
let error = new Error(message)
let error = new SyntaxError(message)
let error = new ReferenceError(message)
let error = new TypeError(message)
Or even extend built-in class
class ValidationError extends Error {
constructor(message) {
super(message)
this.name = "ValidationError"
}
}
// Usage
function readUser(json) {
let user = JSON.parse(json)
if (!user.age) throw new ValidationError("No field: age")
if (!user.name) throw new ValidationError("No field: name")
return user
}
// Working example with try..catch
try {
let user = readUser('{ "age": 25 }')
} catch (err) {
if (err instanceof ValidationError) {
alert("Invalid data: " + err.message) // Invalid data: No field: name
} else if (err instanceof SyntaxError) { // (*)
alert("JSON Syntax Error: " + err.message)
} else {
throw err // unknown error, rethrow it (**)
}
}
Re-throw error
function readData() {
let json = '{ "age": 30 }'
try {
blabla(); // error!
} catch (err) {
if (!(err instanceof SyntaxError)) {
throw err; // rethrow (don't know how to deal with it)
}
}
}
try {
readData();
} catch (err) {
alert( "External catch got: " + err ); // caught it!
}
finally always executes even if we use return in try block can use it if don’t want to handle errors, but want to finalize process
function func() {
try {
console.log('try')
return
} catch (err) {
console.log('error')
} finally {
console.log('finally' )
}
}
func() // try // finally
Global error event listener In case of fatal error outside try...catch ErrorEvent contains all the information about the event and the error.
window.addEventListener('error', function(event) {
alert(event.message) // human-readable error message describing the problem.
console.log(event.filename) // name of the script file in which the error occurred.
console.log(event.lineno ) // line number of the script file on which the error occurred.
console.log(event.colno) // column number of the script file on which the error occurred.
console.log(event.error) // Is a JavaScript Object that is concerned by the event.
})
var inside catch try...catch creates block scopes and we should declare const or let variables outside
const getRandomNumber = () => Math.floor(Math.random() * 100 + 1)
function getNumber() {
let number
try {
number = getRandomNumber()
throw new Error('error')
} catch {
number = 0
}
return number // 0
}
may use var declaration as it is hoisted and goes to function scope
const getRandomNumber = () => Math.floor(Math.random() * 100 + 1)
function getNumber() {
try {
var number = getRandomNumber()
throw new Error('error')
} catch {
var number = 0
}
return number // 0
}