Dùng để khai báo hằng số, không thể khai báo lại, gán lại gía trị cho hằng số, hằng số đó không thay đổi nhưng có gía trị của nó có thể thay đổi
"use stric"
var user_name = "JOE";
const NAME = user_name;
console.log(NAME);
// JOE
user_name = "JOE LEONA";
console.log(NAME);
// JOE --> Gía trị hằng số không đổi
var user_information = {
age : 20,
student : true,
dob : "01/01/2000"
}
const INFORMATION = user_information;
console.log(INFORMATION);
// { age: 20, student: true, dob: '01/01/2000' }
user_information.age = 25;
user_information.student = false;
console.log(INFORMATION);
// { age: 25, student: false, dob: '01/01/2000' } ---> Đối tượng thay đổi thuộc tính và gía trị của hằng thay đổi theo
Hằng số chỉ sử có gía trị trong block { ... } nó được khai báo
{
const name = 'JOE';
console.log(name);
// JOE
}
{
console.log(name);
// name is not defined
}
Tuy không thể khai báo đè vào hằng số đã khai báo nhưng hằng số vẫn có thể sử dụng trong vòng lặp (do mỗi vòng lặp là 1 block riêng)
'use stric'
var arr = [2,3,5,7,11,13];
for(item of arr) {
const message = "Hi!, I'm " + item;
console.log(message);
}
// Hi!, I'm 2
// Hi!, I'm 3
// Hi!, I'm 5
// Hi!, I'm 7
// Hi!, I'm 11
// Hi!, I'm 13
Sử dụng từ khóa let để tạo biến cục bộ tương tự như từ khóa var nhưng phạm vi sử dụng nhỏ hơn (chỉ có thể sử dụng trong block - code trong đoạn { ... }) let sử dụng để khai báo các biến tạm thời,
Từ khóa var phân biệt phạm vi thông qua hàm, khai báo trong hàm thì là biến cục bộ trong hàm đó và khai báo ngoài hàm thì là biến toàn cục đối với hàm đó
Từ khóa let phân biẹt phạm vi bằng block - tức là đoạn code bên trong { ..... }
if (true) {
var name = "JOE"
}
console.log(name)
// JOE
if (true) {
let name = "JOE"
}
console.log(name)
// nill
Khi gọi hàm sẽ ưu tiên gọi hàm trong block đó
"use stric"
{
function foo () { return 1 }
{
function foo () { return 2 }
console.log(foo())
// 2
}
console.log(foo())
// 1
}
Dùng arrow function để khai báo cấu trúc hàm
// Cú pháp chuẩn
var functionName = (val1, val2) => { // do anything }
// Hàm có 1 tham số
var functionName = val => { // do anything }
// Hàm không có tham số
var functionName = () => { // do anything }
// Hàm chỉ có 1 câu lệnh
var functionName = (val1, val2) => console.log('Hello !')
Ký tự => phải cùng hàng với tên hàm
Viết ngắn không cần sử dụng return
var flowers = [rose, sakura]
console.log( flowers.map( flower => flower + " so beauty !" ) )
// [ 'rose so beauty !', 'sakura so beauty !' ]
var numbers = [1, 2, 3];
console.log( numbers.map( number => ({ next: number + 1, previous: number - 1 })) )
// [ { next: 2, previous: 0 }, { next: 3, previous: 1 }, { next: 4, previous: 2 } ]
Thay thế bind() trong việc gỉai quyết khó khăn khi việc sử dụng this
// Dùng `bind()`
'use stric'
var developer = {
name : 'Joe',
age : 20,
showInformation : function(callback) {
callback();
},
render : function(){
this.showInformation(function() {
console.log('Hi! ' + this.name + ', ' + this.age + ' years old' )
}.bind(this))
}
}
developer.render()
// Hi! Joe, 20 years old
// Dùng `=>`
'use stric'
var developer = {
name : 'Joe',
age : 20,
showInformation : function(callback) {
callback();
},
render : function(){
this.showInformation(( () => console.log('Hi! ' + this.name + ', ' + this.age + ' years old' )))
}
}
developer.render()
// Hi! Joe, 20 years old
Khai báo gía trị mặc định ngay trong tham số của hàm
// 1 tham số
'use stric'
var samuraiName = (name = 'Minato') => 'Hello ' + name;
console.log(samuraiName())
// Hello Minato
console.log(samuraiName('Odame'))
// Hello Odame
// nhiều tham số
var sum = (x = 3, y = 1, z = 3) => x + y + z;
console.log(sum(1))
// 5
console.log(sum( 0 , 3))
// 6
Dùng khi cần khai báo 1 hàm với số lượng tham số chưa biết trước (không xác định), hay là có thể khai báo hàm với số lượng tham số vô hạn
'use stric'
var sum = (x, y, ...z) => {
let sumz = 0;
// z là mảng các tham số còn lại
z.map(item => sumz += item);
return x + y + sumz
}
console.log(sum(1,2,10,11,13))
// 37
Spread Operator cho phép chuyển đổi một chuỗi thành nhiều tham số (đối với hàm) và một chuỗi thành nhiều phần tử (đối với mảng)
'use stric'
var arr = [2,3,5,7,11,13];
var sendUser = (x, y, ...z) => {
let sumz = 0;
z.map(item => sumz += item);
return x + y + sumz
}
console.log(sendUser(...arr))
// 41
Ghép mảng
'use stric'
var arr1 = [2,3,5,7,11,13];
var arr2 = [2,3,5,7,11,13];
var sumarr = [...arr1, ...arr2]
console.log(sumarr)
// [ 2, 3, 5, 7, 11, 13, 2, 3, 5, 7, 11, 13 ]
Từ chuỗi tạo thành mảng
'use stric'
var string = "LEONA";
console.log([...string]);
// [ 'L', 'E', 'O', 'N', 'A' ]
Là việc khai báo string mới, ở đây có thể sử dụng multi-line, biến, hàm, biểu thức bên trong string mà không cần đến nối string
'use stric'
var name = 'Joe'
var string = `My name is ${name}`
console.log(string)
// My name is Joe
Bên trong ${ } có thể là hàm, chuỗi, biến, biểu thức
'use stric'
var name = () => 'Joe'
var string = `My name is ${name()}`
console.log(string)
// My name is Joe
Cho phép tạo ra chuỗi nguyên mẫu
console.log("Hello \n You")
// Hello
// You
console.log(String.raw `Hello \n You`)
// Hello \n You
Cho phép chuyển trực tiếp từ hệ cơ số 2, 8, 16 về hệ cơ số 10
0xFF
// 255 >> 16
0b10
// 2 >> 2
0o10
// 8 >> 8
Ngoài ra còn có thể sử dụng toString() để chuyển về cơ số bất kì
(255).toSring(16)
// 'FF'
'use stric'
var arr = [..."日本語"];
[..."日本語"].map( character => {
console.log((character.codePointAt(0)).toString(16))
})
// 65e5
// 672c
// 8a9e
Cho phép mô tả object đơn gỉan hơn
Việc khai báo thuộc tính có thể rút gọn thông qua tên biến gán gía trị
'use stric'
var createDeveloper = (name, age, main_lang) => {
return {
name,
age,
main_lang
}
}
let developer = createDeveloper('Joe', 22, 'Ruby');
console.log(developer)
// { name: 'Joe', age: 22, main_lang: 'Ruby' }
console.log(developer.name)
// Joe
Giúp việc đặt tên thuộc tính cho đối tượng linh hoạt hơn
'use stric'
var createDeveloper = (name, salary) => {
return {
name,
['salary_of' + name] : salary
}
}
let developer = createDeveloper('Joe', 2000);
console.log(developer)
// { name: 'Joe', salary_ofJoe: 2000 }
console.log(developer.salary_ofJoe)
// 2000
Tương tự như Property Shorthand, giúp việc mô tả method của object đơn giản hơn
'use stric'
var createDeveloper = (name, salary) => {
return {
name,
salary,
reward() {
this.salary *= 1.15
}
}
}
let developer = createDeveloper('Joe', 2000);
console.log(developer.salary);
// 2000
developer.reward();
// 2300
console.log(developer.salary)
Là cách tách mảng hoặc object thành nhiều biến một cách đơn gỉan
'use stric'
let date = [18, 08, 2017]
let [d, m, y] = date;
console.log(d);
// 18
console.log(m);
// 08
console.log(y);
// 2017
Quan trọng là thứ tự các biến ứng với từng thành phần cua mảng, nếu không muốn lấy thì bỏ trống
'use stric'
let date = [18, 08, 2017]
let [d, , y] = date;
console.log(d);
// 18
// console.log(m);
// m is not defined
console.log(y);
// 2017
'use stric'
let a = 10;
let b = 5;
[a, b] = [b, a];
console.log(a);
// 5
console.log(b);
// 10
Tương tự với mảng, cũng có thể áp dụng Destructuring Asignments với đối tượng (với điều kiện phải trùng thuộc tính - key và không phụ thuộc vào thứ tự, nếu không dùng thông qua key thì tương tự như mảng, phụ thuộc vào thứ tự)
'use stric'
let date = {
day : 18,
month : 08,
year : 2018
}
let {day : d, month : m, year : y} = date;
console.log(d);
// 18
console.log(m);
// 08
console.log(y);
// 2017
'use stric'
let date = {
day : 18,
month : 08,
years : 2018
}
let {day : d, month : m, year : y} = date;
console.log(d);
// 18
console.log(m);
// 08
console.log(y);
// undefined
Có thể gán 1 phần các thuộc tính của đối tượng bằng cách chỉ sử dụng key chưa value cần
'use stric'
let date = {
day : 18,
month : 08,
year : 2018
}
let {month : m} = date;
console.log(m);
// 08
Biến được gán sẽ mang kiểu dữ liệu của value tương ứng với key
'use stric'
var developer = {
name: 'Joe',
age: 20,
exp: {
php: 1,
ruby: 2,
js: 3
}
}
let {exp: expObj} = developer;
console.log(expObj)
// { php: 1, ruby: 2, js: 3 }
Nếu cố gắng gán 1 key không tồn tại, thì sẽ trả về undefined như ở phần trên, hoặc nếu số phần sử của mảng muốn gán lớn hơn số phần tử của mảng đã có thì cũng trả về undefined, muốn khắc phục có thể set Default Values
'use stric'
let dev = ['joe', 'leona']
let [a, b, c] = dev
console.log(a)
// joe
console.log(b)
// leona
console.log(c)
// undefined
'use stric'
let dev = ['joe', 'leona']
let [a, b, c = 'bill'] = dev
console.log(a)
// joe
console.log(b)
// leona
console.log(c)
// bill
'use stric'
let date = {
day : 18,
month : 08,
year : 2018
}
let {month : m, hour: h = 12 } = date;
console.log(m);
// 08
console.log(h);
// 12
'use stric'
let sum = ([a, b]) => console.log(a, b);
sum([1,2])
// 1 2
let sum = ({ a: n, b: m }) => console.log(n, m);
sum({a: 'beep', b: 12})
// beep 12
let sum = ({ n, m }) => console.log(n, m);
sum({n: 'beep', m: 12})
// beep 12
'use stric'
let sum = ({ n, m }) => console.log(n, m);
sum({n: 'beep', m: null})
// beep null
Fail-Soft: Nếu cố gắng gán 1 key không tồn tại, hoặc nếu số phần sử của mảng muốn gán lớn hơn số phần tử của mảng đã có thì trả về undefined thay vì gây ra lỗi chương trình như Fail-Hard
'use stric'
let dev = ['joe', 'leona']
let [a, b, c] = dev
console.log(a)
// joe
console.log(b)
// leona
console.log(c)
// undefined
Export riêng từng hàm ở ở cuối file (named export - do ta định nghĩa tên của đối tượng được export khi đang export)
// lib/math.js
'use strict'
let sum = (x, y) => x + y;
let divide = (n, m) => n/m;
export {sum, divide}
// app1.js
import * as math from "lib/math"
console.log("Sum 10 and 5 is:" + math.sum(10, 5))
// Sum 10 and 5 is: 15
// app2.js
import { sum, divide } from "lib/math"
console.log("Divide 10 and 5 is:" + divide(10, 5))
// Divide 10 and 5 is: 2.0
Hoặc export trực tiếp hàm, đối tượng
export var sum = (x, y) => x + y;
export var car = {price: 2000, color: 'green'};
Một file có thể không có hoặc có duy nhất 1 Default export
// export
'use strict'
export default function foo() {
return 'default foo';
}
export function bar() { return 'bar'; };
// import
// chỉ import foo() -- default export
import mylib from 'foobar';
import {default as mylib} from 'foobar';
console.log(mylib())
// default foo
import mylib, {bar} from 'foobar';
console.log(bar())
// bar
Có thể sử dụng namespace khác mylib thay cho foo vì foo là default export
Trong express app trước đây của em không sử dụng import và export thay vào đó là sử dụng require và module.exports Code không chạy là do không hỗ trợ ES6
Muốn sử dụng ES6 thì cần dùng thêm babel
ES6 cho phép tạo class trực tiếp bằng từ khóa class
'use strict';
class Person {
constructor(name,birthYear) {
this.name = name;
this.birthYear = birthYear;
}
getAge() {
return new Date().getFullYear() - this.birthYear;
}
}
let ngoctrinh = new Person('Ngoc Trinh', 2000);
console.log(ngoctrinh.getAge())
// 17
ES6 cũng hỗ trợ việc kế thừa class, thông qua từ khóa extends
'use strict';
class Person {
constructor(name) {
this.name = name;
}
getMessage() {
return `Wellcome ${this.name}`
}
}
class Singer extends Person {
constructor(name, salary) {
super(name);
this.salary = salary;
}
getSalary() {
return this.salary;
}
}
let leroi = new Singer('Le roi', 15000000)
console.log(leroi.name)
// Le roi
console.log(leroi.getSalary())
// 15000000
console.log(leroi.getMessage())
// Wellcome Le roi
var Foo = class {
constructor() {}
bar() {
return 'Hello World!';
}
};
var instance = new Foo();
console.log(instance.bar());
// "Hello World!"
console.log(Foo.name);
// "Foo"
'use strict';
class Personal {
constructor (name, age) {
this.name = name;
this.age = age;
}
getMessage() {
return `Wellcome ${this.name}, ${this.age} years old`
}
}
class Singer extends Personal {
constructor(name, age, salary) {
super(name, age);
this.salary = salary;
}
getMessage() {
return `Wellcome singer ${this.name}, ${this.age} years old, with $${this.salary}`
}
}
var ngoctrinh = new Singer('Ngoc Trinh', 25, 25000);
console.log(ngoctrinh.getMessage())
// Wellcome singer Ngoc Trinh, 25 years old, with $25000
'use strict';
class Message {
static getMessage() {
return `Wellcome !`
}
}
console.log(Message.getMessage())
// Wellcome !
'use strict';
class Personal {
constructor (name, age) {
this._name = name;
this._age = age;
}
set name( name ) { this._name = name }
get name() { return this._name }
set age( age ) { this._age = age }
get age() { return this._age }
}
var people = new Personal('Joe', 23);
console.log(people.name);
// Joe
people._name = 'Leona'
console.log(people.name)
// Leona
Symbol là kiểu dữ liệu dạng primitive type (dữ liệu nguyên thủy), nó sẽ tạo ra các ký tự duy nhất, không phải 1 chuỗi mà là 1 dạng object , cho nên không thể thấy được gía trị thực của nó. (thích hợp vào việc gỉai quyết bài toán mang tính duy nhất)
'use strict';
// khai báo symbol
let sb1 = Symbol();
// khai báo symbol với tham số truyền vào ( được hiểu như secret key)
let sb2 = Symbol('sb2');
let sb3 = Symbol('sb2');
console.log(sb2 === sb3)
// false
console.log(typeof sb1);
// symbol
Do tính không trùng lặp của symbol nên ta có thể dùng symbol như 1 key của object, và sẽ không sợ bị trùng key
'use strict';
const obj_key = Symbol();
let obj = {
[obj_key]: 123
};
console.log(obj[obj_key])
// 132
Ép kiểu symbols
'use strict';
let sb1 = Symbol('Sb1');
let sb2 = Symbol('Sb1');
console.log(Boolean(sb1));
// true
console.log(Number(sb1))
// TypeError: Cannot convert a Symbol value to a number
console.log(String(sb1));
// Symbol(Sb1)
let st1 = String(sb1);
let st2 = String(sb2);
console.log(sb1 == sb2);
// false
console.log(st1 === st2)
// true
'use strict';
let sb1 = Symbol;
let sb2 = Symbol.for('sb2');
let sb3 = Symbol.for('sb2');
console.log(sb2 === sb3)
// true
console.log(Symbol.keyFor(sb1))
// underfined
console.log(Symbol.keyFor(sb2))
// sb2
Iterators là một bộ duyệt để duyệt mảng, danh sách, collection mà mỗi lần duyệt sẽ lưu lại vị trí đã duyệt trước đó.
Iterators trong JS có cung cấp thêm 1 phương thức next() nó sẽ return phần tử kế tiếp đồng thời ghi nhận luôn phần tử đã lấy ra là phần tử next() và trả về là object
'use strict';
let arr = ['a', 'b', 'c'];
var iterator = arr[Symbol.iterator]();
console.log(iterator.next());
// { value: 'a', done: false }
console.log(iterator.next());
// { value: 'b', done: false }
console.log(iterator.next());
// { value: 'c', done: false }
console.log(iterator.next());
// { value: undefined, done: true }
Generator Function không đảm bảo tính run-to-completion của function thông thường
// run-to-completion
var x = 1;
function foo() {
x++;
bar();
console.log( "x:", x );
}
function bar() {
x++;
}
foo();
// x: 3
// Generator Function
'use strict';
var x = 1;
function *foo() {
x++;
yield;
console.log( "x:", x );
}
function bar() {
x++;
}
var it = foo();
// ở đây không thực thi foo() ngay lập tức mà tạo ra một interator để kiểm soát quá trình thực thi này
it.next();
// Đầu tiên bắt đầu chạy generator thực hiện `x++`, generator dừng lại khi gặp `yield`, tại thời điểm này generator vẫn đang hoạt động nhưng chuyển sang trạng thái dừng, sau câu lệnh x = 2
console.log(x);
// 2
bar();
// chạy bar()
console.log(x);
// 3
it.next();
// sau khi chạy xong câu lệnh `next()` thì generator hoạt động trở lại và tiếp tục thực hiện câu lệnh in ra màn hình
// x: 3
class Clz {
* bar () {
…
}
}
let Obj = {
* foo () {
…
}
}
Là dữ liệu kiểu tập hợp, và không lặp lại (nếu cố tình thêm dữ liệu lặp lại thì sẽ chỉ lưu 1 lần) và có thể lưu cả function, object, class
'use strict';
var numbers = new Set([1,2,3,3,4])
console.log(numbers)
// Set { 1, 2, 3, 4 }
numbers.add(5);
console.log(numbers)
// Set { 1, 2, 3, 4, 5 }
numbers.add(1);
console.log(numbers)
// Set { 1, 2, 3, 4, 5 }
numbers.delete(1)
console.log(numbers)
// Set { 2, 3, 4, 5 }
numbers.delete(6)
console.log(numbers)
// Set { 2, 3, 4, 5 }
console.log(numbers.has(1))
// false
console.log(numbers.has(3))
// true
console.log(numbers.size)
// 4
for (let number of numbers){
console.log(number);
}
// 2
// 3
// 4
// 5
console.log([...numbers])
// [ 2, 3, 4, 5 ]
console.log(new Set([10,20,30,40,50]))
// Set { 10, 20, 30, 40, 50 }
let newnap = [...numbers].map( number => number*2);
console.log(newnap)
// [ 4, 6, 8, 10 ]
let newfilt = [...numbers].filter( number => number%2 == 0)
console.log(newfilt)
// [ 2, 4 ]
numbers.clear();
console.log(numbers)
// Set {}
Tương tự như Set, Map có kiểu key => value và có key không trùng lặp, Nếu cố ý ghi đè trùng key thì sẽ lấy value của lần ghi cuối cùng
'use strict';
let map = new Map([['name', 'Joe'], ['age', 23], ['language', 'PHP']]);
console.log(map);
// Map { 'name' => 'Joe', 'age' => 23, 'language' => 'PHP' }
map.set('salary', '$2500');
console.log(map);
// Map { 'name' => 'Joe', 'age' => 23, 'language' => 'PHP', 'salary' => '$2500' }
map.delete('salary');
console.log(map);
// Map { 'name' => 'Joe', 'age' => 23, 'language' => 'PHP' }
console.log(map.has('name'));
// true
console.log(map.size);
// 3
map.clear();
console.log(map);
// Map {}
key trong map có thể là string, number, object , const, NaN, unicode string, object
'use strict';
let map = new Map([
['name', 'Joe'],
['age', 23]
]);
for (let key of map.keys()) {
console.log(key);
}
// name
// age
for (let value of map.values()) {
console.log(value);
}
// Joe
// 23
for (let entry of map.entries()) {
console.log(entry);
}
// [ 'name', 'Joe' ]
// [ 'age', 23 ]
for (var [key, value] of map){
console.log(key + ' - ' + value);
}
// name - Joe
// age - 23
map.forEach((value, key) => {
console.log(key + ' - ' + value);
})
// name - Joe
// age - 23
let newmap = [...map].map( ([key, value]) => `${key} - ${value}` );
console.log(newmap);
// [ 'name - Joe', 'age - 23' ]
let newfilt = [...map].filter( ([key, value]) => key === 'name' );
console.log(newfilt);
// [ [ 'name', 'Joe' ] ]
Tương tự như Map, nhưng key của WeakMap phải là 1 biến và biến đó phải là 1 Object
Tương tự với Set nhưng phần tử nhập vào phải là 1 đối tượng, object, function, class, và bắt buộc phải tạo biến trước khi lưu vào Set, biến đó được coi như key
Object.assign() Là một phương thức giúp, coppy tất cả các gía trị của các thuộc tính liệt kê từ một hoặc nhiều nguồn object khác nhau lên 1 object, kết quả trả về là 1 Object đã đưọc thêm thuộc tính.
Object mục tiêu sẽ bị ghi đè các thuộc tính chung khóa, theo thứ tự object đem ra ghi đè lên. String và Symbol đều có thể được sao chép, nhưng null và underfined thì không coppy được
'use strict';
let personal = { 'name': 'Joe', 'age': 23, 'job': 'Teacher' };
let developer = { 'job': 'PHP developer', 'salary': '$2500' };
let PHPDeveloper1 = Object.assign({}, personal, createDeveloper);
console.log(PHPDeveloper1);
// { name: 'Joe', age: 23, job: 'PHP developer', salary: '$2500' }
let PHPDeveloper2 = Object.assign({}, personal, developer, null);
console.log(PHPDeveloper2);
// { name: 'Joe', age: 23, job: 'PHP developer', salary: '$2500' }
let PHPDeveloper1 = Object.assign({}, personal, developer, true, false);
console.log(PHPDeveloper1);
// { name: 'Joe', age: 23, job: 'PHP developer', salary: '$2500' }
find() và findIndex() cho phép tìm phần tử và index của phần tử, find() và findIndex() sẽ trả về phần tử đầu tiên tìm thấy trong mảng
'use strict';
let arr1 = [1,2,3,4,5,6,7,1]
let el1 = arr1.find(x => x === 1)
console.log(el1);
// 1
let tmp = arr1.findIndex(x => x === 1)
console.log(tmp)
// 0
'use strict';
var string = 'ha '.repeat(10);
console.log(string)
// ha ha ha ha ha ha ha ha ha ha
'use strict';
console.log("hello".startsWith("ello", 1))
// true
console.log("hello".endsWith("hell", 4))
// true
console.log("hello".includes("ell"))
// true
console.log("hello".includes("ell", 1))
// true
console.log("hello".includes("ell", 2))
// false
'use strict';
console.log(Number.isSafeInteger(42));
// true
console.log(Number.isSafeInteger(9999999999999995145515));
// false
console.log(Number.isSafeInteger('npm install express'));
// false
console.log(Number.isSafeInteger(null));
// false
'use strict';
console.log(Math.trunc(42.7))
// 42
console.log(Math.trunc( 0.1))
// 0
console.log(Math.trunc(-0.1))
// -0
console.log(Math.trunc(-1.1))
// -1
console.log(Math.trunc(null))
// 0
console.log(Math.trunc(NaN))
// NaN
console.log(Math.sign(7))
// 1
console.log(Math.sign(0))
// 0
console.log(Math.sign(-0))
// -0
console.log(Math.sign(-7))
// -1
console.log(Math.sign(NaN))
// NaN
Promise dùng để xử lý kết quả của hành động cụ thể (kết quả của hành động có thể là thành công hoặc thất bại)
Khi 1 Promise được khởi tạo thì nó có một trong 3 trạng thái:
- Fulfilled : Hành động được xử lý xong và thành công.
- Rejected : Hành động được xử lý xong và thất bại.
- Pending : Hành động đang chờ xử lý hoặc bị từ chối.
Trong đó Fulfilled và Rejected ta gọi là Settled, có nghĩa là hành động đó đã được xử lý xong (thành công hoặc thất bại)
'use strict';
var promise = new Promise(function(resolve, reject){
reject('Error !');
resolve('Success!');
});
promise.then(
function(success){
console.log(success);
},
function(error){
console.log(error);
}
);
// Error !
hai hàm callback chỉ xảy ra 1 trong 2 mà thôi, điều này tương ứng với trong Promise sẽ khai báo, một là Resolve, hai là Reject, nếu khai báo cả hai thì nó chỉ có tác dụng với khai báo đầu tiên
có thể dùng promise.then().catch(); để bắt lỗi
'use strict';
var promise = new Promise(function(resolve, reject){
reject('Error!');
});
promise
.then(function(message){
console.log(`${message} with then`);
})
.catch(function(message){
console.log(`${message} with catch`);
});
// Error! with catch
'use strict';
var promise = new Promise(function(resolve, reject){
reject('Error!');
});
promise
.then(function(success){
console.log(`${success} with then success`);
}, function (error) {
console.log(`${error} with then error`);
})
.catch(function(message){
console.log(`${message} with catch`);
});
// Error! with then error
Nếu truyền cả callback error và catch thì callback error sẽ được chạy và catch không được chạy
Pending là trạng thái chưa sử dụng resolve và reject.
'use strict';
var promise = new Promise(function(resolve, reject){
});
console.log(promise);
// Promise {[[PromiseStatus]]: "pending", [[PromiseValue]]: undefined}
Fulfilled là trạng thái của Promise đã thành công , tức là trạng thái này xảy ra khi đã sử dụng resolve
'use strict';
var promise = new Promise(function(resolve, reject){
resolve();
});
console.log(promise);
// Promise {[[PromiseStatus]]: "resolved", [[PromiseValue]]: undefined}
Rejected là trạng thái của Promise đã thất bại, tức là sử dụng đến reject, nhưng khi đã sử dụng reject thì bắt buộc phải khai báo hành động xử lý cho nó, then hoặc catch
'use strict';
var promise = new Promise(function(resolve, reject){
reject();
});
promise.catch(function(){
// Something
});
console.log(promise);
// Promise {[[PromiseStatus]]: "rejected", [[PromiseValue]]: undefinedƯ
Có thể sử dụng then liên tiếp (do then nhận vào 1 promise và nó cũng trả về 1 promise)
'use strict';
var promise = new Promise(function(resolve, reject){
resolve();
});
promise
.then(function(){
console.log(1);
})
.then(function(){
console.log(2);
})
.then(function(){
console.log(3);
});
// 1
// 2
// 3
nếu then lồng nhau, và trong chuỗi then đó có 1 then nào đó sử dụng đến callback reject, điều đó tương đương với việc những then ở sau đó promise sẽ là một Fulfilled. và nó sẽ chạy ở callback resolve
'use strict';
var promise = new Promise(function(resolve, reject){
reject();
});
promise
.then(function(){
console.log(1);
})
.then(function(){
console.log(2);
}, function(){
console.log('Error!')
})
.then(function(){
console.log(3);
});
// Error!
// 3
Nếu dùng catch để bắt lỗi thì chỉ có catch hoạt động
'use strict';
var promise = new Promise(function(resolve, reject){
reject();
});
promise
.then(function(){
console.log(1);
})
.then(function(){
console.log(2);
})
.then(function(){
console.log(3);
})
.catch(function(){
console.log('Error!')
});
// Error !