Mở đầu:
Mỗi một Vue instance sẽ phải thông qua nhiều bước trước khi nó được khởi tạo, ví dụ khi ban khai báo một instance mới thì instance đó sẽ phải thông qua bước như: thiết lập cài đặt dữ liệu, biên dịch template, liên kết với DOM, cập nhật giá trị của DOM khi dữ liệu thay đổi. Trong suốt quá trình đó Vue instance sẽ phải gọi ra một số lifecycle hooks. Bây giờ chắc hẳn bạn sẽ thắc mắc là lifecycle hooks là gì phải không nào?
Lifecycle hooks là gì?
Lifecycle hooks chính là những hàm, phương thức đặc biệt xử lý cho một chức năng nào đó. Ví dụ khi Vue instance được khởi tạo thì chúng ta có hook tên là created, hook này sẽ được gọi khi instance khởi tạo xong. Nếu bạn đã từng tìm hiểu qua WordPress thì chắc chắn sẽ biết khái niệm này bởi WordPress hoạt động chủ yếu dựa vào hai cơ chế là Hooks và Action.
Để hiểu rõ hơn thì bạn có thể tham khảo thêm mô hình hoạt động của 1 Vue Instance và thời điểm các scope event được gọi.
Khởi tạo component
Hook khởi tạo là phương thức dùng để can thiệp vào quá trình đầu tiên khi component chạy, chúng cho phép thực hiện các hành động trước khi component được đưa vào cây DOM. Không giống như các hook khác, hook khởi tạo cũng chạy trong quá trình render phía server. Sử dụng hook khởi tạo nếu bạn muốn thiết lập những gì liên quan trong component trong suốt quá trình render ở client và server. Bạn sẽ không thể truy xuất vào DOM hoặc phần tử được mouting (this.$el) trong hook khởi tạo.
beforeCreate
Được gọi khi chúng ta khởi tạo vue.js và trước khi thực hiện tiến trình observe Data và init Events.
Ví dụ:
<script>
export default { beforeCreate() { console.log('Nothing gets called before me!') }
}
</script>
created
Được gọi khi tiến trình observe Data và init Events hoàn thành.
Ví dụ:
<script>
export default { data() { return { property: 'Blank' } }, computed: { propertyComputed() { console.log('I change when this.property changes.') return this.property } }, created() { this.property = 'Example property update.' console.log('propertyComputed will update, as this.property is now reactive.') }
}
</script>
Chèn phần tử DOM
Hook trong giai đoạn chèn thêm phần tử DOM thường được sử dụng nhiều nhất, ở giai đoạn này mọi việc không quá sớm cũng như quá muộn. Chúng cho phép bạn truy xuất vào component ngay lập tức trước và sau khi component render lần đầu. Tuy nhiên, hook này không chạy khi render phía server.
Sử dụng hook này nếu bạn muốn truy xuất hoặc thay đổi DOM của component ngay trước hoặc sau khi khởi tạo render.
Không sử dụng nếu bạn muốn lấy dữ liệu từ component khi khởi tạo. Thay vào đó sử dụng created() (hoặc created() và actived() với keep-alive component), đặc biệt khi bạn cần dữ liệu trong quá trình render phía server.
beforeMount
Được gọi ngay sau khi tiến trình render function hoàn tất.
Ví dụ:
<script>
export default { beforeMount() { console.log(`this.$el doesn't exist yet, but it will soon!`) }
}
</script>
mounted
Được gọi khi tiến trình replace el hoàn tất.
Ví dụ:
<template> <p>I'm text inside the component.</p>
</template> <script>
export default { mounted() { console.log(this.$el.textContent) // I'm text inside the component. }
}
</script>
Re-render
Hook này của component được gọi khi các thuộc tính “phản ứng” của component thay đổi và nó cũng chính là nguyên nhân mọi thứ re-render. Chúng cho phép bạn hook vào vòng watch-compute-render trong component. Sử dụng nếu bạn muốn biết khi nào component được re-rend. Không sử dụng nếu bạn muốn biết khi nào thuộc tính “phản ứng” trên component của bạn thay đổi. Thay vào đó sử dụng các thuộc tính computed hoặc watcher.
beforeUpdate
Được gọi khi data có sự thay đổi, và trước khi visualDOM re-rendered.
Ví dụ:
<script>
export default { data() { return { counter: 0 } }, beforeUpdate() { console.log(this.counter) // Logs the counter value every second, before the DOM updates. }, created() { setInterval(() => { this.counter++ }, 1000) }
}
</script>
updated
Được gọi khi data đã được thay đổi.
Ví dụ:
<template> <p ref="dom-element">{{counter}}</p>
</template>
<script>
export default { data() { return { counter: 0 } }, updated() { // Fired every second, should always be true console.log(+this.$refs['dom-element'].textContent === this.counter) }, created() { setInterval(() => { this.counter++ }, 1000) }
}
</script>
Destruction
Hook Destruction cho phép bạn thực hiện các hành đồng khi component được hủy bỏ. Chúng được gọi khi component được remove khỏi DOM.
beforeDestroy
Được gọi ngay trước khi vue instance được destroy.
Ví dụ:
<script>
export default { data() { return { someLeakyProperty: 'I leak memory if not cleaned up!' } }, beforeDestroy() { // Perform the teardown procedure for someLeakyProperty. // (In this case, effectively nothing) this.someLeakyProperty = null delete this.someLeakyProperty }
}
</script>
destroyed
Được gọi khi vue instance đã được destroy.
Ví dụ:
<script>
import MyCreepyAnalyticsService from './somewhere-bad' export default { destroyed() { console.log(this) // There's practically nothing here! MyCreepyAnalyticsService.informService('Component destroyed. All assets move in on target on my mark.') }
}
</script>
Các hook khác
Còn một số các hook khác như actived(), deactived()… nó được sử dụng trong keep-alive component và ngoài phạm vi của bài viết này. Nó cho phép bạn phát hiện một component được bao quanh bởi thẻ <keep-alive>. Bạn cũng có thể sử dụng chúng để lấy dữ liệu cho component hoặc quản lý thay đổi trạng thái mà không cần rebuild lại component.
Kết luận:
Qua bài này đã giới thiệu với các bạn khái niệm về lifecycle và các hooks. Hy vọng rằng bài viết sẽ giúp các bạn hiểu hơn về ý nghĩa của từng thành phần trên.
Tham khảo:
https://alligator.io/vuejs/component-lifecycle/