Chào mừng đến với Cafedev! Trong bài viết hôm nay, chúng ta sẽ cùng nhau khám phá về chủ đề Pinia Vuejs với xử lý Composables. Cùng với sự phát triển của Vue.js, việc sử dụng Composables đã trở thành một phần không thể thiếu trong quá trình phát triển ứng dụng web. Cafedev sẽ hướng dẫn bạn cách xử lý Composables trong Vue Router một cách hiệu quả nhất. Hãy cùng đồng hành và khám phá những điều thú vị về chủ đề này ngay bây giờ!

Composables là những hàm sử dụng Vue Composition API để đóng gói và tái sử dụng logic có trạng thái. Cho dù bạn viết code của riêng mình, bạn sử dụng thư viện bên ngoài hoặc cả hai, bạn đều có thể sử dụng sức mạnh của Composables đầy đủ trong các store của pinia.

1. Các Store Tùy chọn

Khi định nghĩa một store tùy chọn, bạn có thể gọi một composable bên trong thuộc tính state:

export const useAuthStore = defineStore('auth', {
  state: () => ({
    user: useLocalStorage('pinia/auth/login', 'bob'),
  }),
})

Hãy nhớ rằng bạn chỉ có thể trả về trạng thái có thể ghi được (ví dụ: một ref()). Dưới đây là một số ví dụ về composables mà bạn có thể sử dụng:
useLocalStorage
useAsyncState
Dưới đây là một số ví dụ về composables mà không thể được sử dụng trong các store tùy chọn (nhưng có thể được sử dụng với các store setup):
useMediaControls: tiếp cận các hàm
useMemoryInfo: tiếp cận dữ liệu chỉ có thể đọc
useEyeDropper: tiếp cận dữ liệu chỉ có thể đọc và các hàm

2. Các Store Setup

Trong khi đó, khi định nghĩa một store setup, bạn có thể sử dụng gần như bất kỳ composable nào vì mỗi thuộc tính được phân biệt thành trạng thái, action hoặc getter:

import { defineStore, skipHydrate } from 'pinia'
import { useMediaControls } from '@vueuse/core'

export const useVideoPlayer = defineStore('video', () => {
  // we won't expose (return) this element directly
  const videoElement = ref<HTMLVideoElement>()
  const src = ref('/data/video.mp4')
  const { playing, volume, currentTime, togglePictureInPicture } =
    useMediaControls(videoElement, { src })

  function loadVideo(element: HTMLVideoElement, src: string) {
    videoElement.value = element
    src.value = src
  }

  return {
    src,
    playing,
    volume,
    currentTime,

    loadVideo,
    togglePictureInPicture,
  }
})

Cảnh báo: Khác biệt so với trạng thái thông thường, ref() chứa một tham chiếu không thể được serialize đến phần tử DOM. Đây là lý do tại sao chúng tôi không trả nó trực tiếp. Vì nó là trạng thái chỉ tồn tại trên client, chúng tôi biết rằng nó sẽ không được đặt trên máy chủ và sẽ luôn bắt đầu là undefined trên client.

3. SSR

Khi xử lý Server Side Rendering, bạn cần chú ý một số bước phụ thêm để sử dụng composables trong các store của bạn.
Trong Store Tùy chọn, bạn cần định nghĩa một hàm hydrate(). Hàm này được gọi khi store được khởi tạo trên client (trình duyệt) khi có trạng thái ban đầu có sẵn vào thời điểm store được tạo. Lý do chúng ta cần định nghĩa hàm này là vì trong tình huống như vậy, state() không được gọi.

import { defineStore, skipHydrate } from 'pinia'
import { useLocalStorage } from '@vueuse/core'

export const useAuthStore = defineStore('auth', {
  state: () => ({
    user: useLocalStorage('pinia/auth/login', 'bob'),
  }),

  hydrate(state, initialState) {
    // in this case we can completely ignore the initial state since we
    // want to read the value from the browser
    state.user = useLocalStorage('pinia/auth/login', 'bob')
  },
})

Trong Store Setup, bạn cần sử dụng một helper có tên là skipHydrate() trên bất kỳ thuộc tính trạng thái nào không nên được lấy từ trạng thái ban đầu. Khác biệt so với các store tùy chọn, các store setup không thể đơn giản là bỏ qua việc gọi state(), vì vậy chúng ta đánh dấu các thuộc tính không thể được hydrate với skipHydrate(). Lưu ý rằng điều này chỉ áp dụng cho các thuộc tính reactive có thể ghi được:

import { defineStore, skipHydrate } from 'pinia'
import { useEyeDropper, useLocalStorage } from '@vueuse/core'

export const useColorStore = defineStore('colors', () => {
  const { isSupported, open, sRGBHex } = useEyeDropper()
  const lastColor = useLocalStorage('lastColor', sRGBHex)
  // ...
  return {
    lastColor: skipHydrate(lastColor), // Ref<string>
    open, // Function
    isSupported, // boolean (not even reactive)
  }
})

Cảm ơn bạn đã đồng hành cùng Cafedev trong hành trình tìm hiểu về Pinia Vuejs với Xử lý Composables. Chúng ta đã cùng nhau thảo luận về cách sử dụng Composables trong Vue Pinia và các kỹ thuật xử lý hiệu quả. Hy vọng rằng thông tin và kiến thức mà chúng tôi chia sẻ đã giúp bạn hiểu rõ hơn về chủ đề này. Đừng quên tiếp tục theo dõi các bài viết mới nhất trên Cafedev để cập nhật thông tin và kỹ năng công nghệ hàng ngày. Hẹn gặp lại trong những bài viết tiếp theo của chúng tôi!

Tham khảo thêm: MIỄN PHÍ 100% | Series tự học Vuejs từ cơ bản tới nâng cao

Các nguồn kiến thức MIỄN PHÍ VÔ GIÁ từ cafedev tại đây

Nếu bạn thấy hay và hữu ích, bạn có thể tham gia các kênh sau của CafeDev để nhận được nhiều hơn nữa:

Chào thân ái và quyết thắng!

Đăng ký kênh youtube để ủng hộ Cafedev nha các bạn, Thanks you!