Skip to content

Використання сховища поза компонентом

Сховища Pinia покладаються на екземпляр pinia для спільного використання одного екземпляра сховища для всіх викликів. У більшості випадків це працює з коробки, просто викликаючи вашу функцію useStore(). Наприклад, у setup() вам більше нічого не потрібно робити. Але поза компонентом все трохи інакше. За лаштунками useStore() вводить екземпляр pinia, який ви надали своєму app. Це означає, що якщо екземпляр pinia не може бути автоматично введений, ви маєте вручну надати його функції useStore(). Ви можете вирішити це по-різному залежно від типу застосунку, який ви пишете.

Односторінкові застосунки

Якщо ви не виконуєте SSR (рендеринг на стороні серверу), будь-який виклик useStore() після встановлення плагіна pinia за допомогою app.use(pinia) працюватиме:

js
import { useUserStore } from '@/stores/user'
import { createPinia } from 'pinia';
import { createApp } from 'vue'
import App from './App.vue'

// ❌  завершиться невдало, тому що воно викликано до створення pinia
const userStore = useUserStore()

const pinia = createPinia()
const app = createApp(App)
app.use(pinia)

// ✅ працює, оскільки екземпляр pinia зараз активний
const userStore = useUserStore()
import { useUserStore } from '@/stores/user'
import { createPinia } from 'pinia';
import { createApp } from 'vue'
import App from './App.vue'

// ❌  завершиться невдало, тому що воно викликано до створення pinia
const userStore = useUserStore()

const pinia = createPinia()
const app = createApp(App)
app.use(pinia)

// ✅ працює, оскільки екземпляр pinia зараз активний
const userStore = useUserStore()

Найпростіший спосіб переконатися, що це завжди застосовується, це відкласти виклики useStore() шляхом розміщення їх у функціях, які завжди запускатимуться після встановлення pinia.

Давайте подивимося на цей приклад використання сховища всередині навігаційного охоронця за допомогою Vue Router:

js
import { createRouter } from 'vue-router'
const router = createRouter({
  // ...
})

// ❌ Залежно від порядку імпорту це не вдасться
const store = useStore()

router.beforeEach((to, from, next) => {
  // ми хотіли скористатися сховищем тут
  if (store.isLoggedIn) next()
  else next('/login')
})

router.beforeEach((to) => {
  // ✅ Це спрацює, оскільки маршрутизатор починає свою навігацію після
  // встановлення маршрутизатора, а pinia також буде встановлено
  const store = useStore()

  if (to.meta.requiresAuth && !store.isLoggedIn) return '/login'
})
import { createRouter } from 'vue-router'
const router = createRouter({
  // ...
})

// ❌ Залежно від порядку імпорту це не вдасться
const store = useStore()

router.beforeEach((to, from, next) => {
  // ми хотіли скористатися сховищем тут
  if (store.isLoggedIn) next()
  else next('/login')
})

router.beforeEach((to) => {
  // ✅ Це спрацює, оскільки маршрутизатор починає свою навігацію після
  // встановлення маршрутизатора, а pinia також буде встановлено
  const store = useStore()

  if (to.meta.requiresAuth && !store.isLoggedIn) return '/login'
})

SSR застосунки

При роботі з рендерингом на стороні сервера вам доведеться передати екземпляр pinia в useStore(). Це перешкоджає pinia обмінюватися глобальним станом між різними екземплярами програми.

У посібнику з SSR цьому присвячений цілий розділ, це лише коротке пояснення.

Released under the MIT License.