Skip to content

Pinia 是什麼?Vue 官方推薦的狀態管理工具全攻略

Pinia 介紹:createPinia 與核心概念

在開發 Vue 專案時,如何高效管理跨元件的資料一直是核心課題。Pinia 作為 Vue 的官方推薦狀態管理工具(State Management Tool),已正式取代 Vuex 成為開發者的首選方案。它不僅設計更簡潔,更完美契合 Vue 3 的 Composition API 生態。

為什麼需要 Pinia 或 Vuex?

在小型專案中,您可以用 props 傳資料、emit() 傳事件、provide/injectcomposable。但當專案變大時會出現問題,例如:多層元件傳 props 很痛苦、多個頁面需要共用資料、API 資料需要快取、使用者登入狀態需要全域共享、多個模組之間要互相影響。這時候就需要一個 集中管理狀態 的工具 PiniaVuex

這時,集中管理狀態(Global State Management) 的工具如 Pinia 就能發揮作用,將資料與邏輯抽離,讓專案結構更清晰。

但也不必一開始就用

引入狀態管理是有成本的,資料被搬到 store 之後,追蹤來源會多繞一層。可以照這個順序判斷:

情境建議做法
父子之間傳值propsemit
跨越幾層但範圍固定,例如:主題設定provide / inject
邏輯需要複用,但資料各自獨立Composable
同一份資料被多個無關頁面共用Pinia

判斷句:資料需要 被很多不相干的地方讀寫 時,才交給 Pinia。

Pinia vs. Vuex:為什麼您該選擇 Pinia?

雖然 Vuex 在 Vue 2 時代是主流,但在 Vue 3 推出後,官方更推薦使用 Pinia。以下是兩者的直觀比較:

比較項目Pinia(推薦)Vuex
語法設計簡潔、直覺較為冗長複雜
Mutation不需要 (直接在 action 修改)必須 (區分同步與非同步)
TypeScript原生支援,體驗極佳設定較麻煩,型別推導不完整
結構彈性高,支援多個 Store 平級管理嚴格,模組巢狀結構複雜
適用版本Vue 3 (最佳) / Vue 2Vue2 為主

Pinia 的核心概念:state、getters、actions

store 是保存全域狀態的實體,您可以把它想像成一個不帶 UI 的元件。它由三個核心部分組成:

  • state:定義資料的地方(類似元件的 data)。
  • getters:計算屬性,根據 state 衍生出的資料(類似元件的 computed)。
  • actions:修改資料的方法,支援 同步非同步 操作(類似元件的 methods)。

若把它對照回元件的語法會更好記:

Store對應元件中的說明
stateref / reactive資料本體
getterscomputed由既有資料衍生、有快取
actions一般函式修改資料,可以是非同步

store 的資料重新整理就會消失

store 活在記憶體裡,按下 F5 就回到初始值。登入狀態這類需要保留的資料,仍要寫進 localStorage 或重新向 API 取得,也可以使用社群的持久化外掛處理。

store 檔案結構建議

為了保持程式碼的可維護性,建議在 src/stores 資料夾下,依據功能領域拆分不同的 store 檔案:

src/
 ├─ stores/
 │   ├─ user.js       # 使用者登入、權限
 │   ├─ cart.js       # 購物車內容
 │   └─ product.js    # 產品清單、快取
 ├─ App.vue
 └─ main.js

Pinia 的 store 是 平級 的,沒有 Vuex 那種巢狀模組。需要互相取用時,直接在一個 store 裡呼叫另一個 store 即可。

如何開始使用 Pinia?

安裝套件

使用 npm 即可輕鬆安裝:

bash
npm install pinia
# 或簡寫
npm i pinia

在專案中註冊 (main.js)

在 Vue 入口檔案中引入並掛載 Pinia

js
import { createApp } from 'vue';
import { createPinia } from 'pinia';
import App from './App.vue';

const app = createApp(App);
const pinia = createPinia();

app.use(pinia);
app.mount('#app');

app.use() 的機制與 Vue Router 的註冊方式相同,都是透過 建立應用程式 的外掛安裝入口。

總結

Pinia 的出現大幅簡化了 Vue 開發者的工作流程,透過更現代化的 API 設計與 TypeScript 的加持,它已成為 Vue 生態系中不可或缺的一環。如果您正準備開啟一個新的 Vue 3 專案,Pinia 絕對是您的不二之選。

接下來請看 Pinia 語法,了解兩種 store 寫法與解構時最常見的響應式陷阱。

常見問題

什麼時候才真的需要 Pinia?

當同一份資料被多個彼此無關的頁面使用,例如:登入資訊、購物車、共用的設定與快取時。若只是父子之間傳值,用 propsemit 就好;跨層級但範圍固定,可以用 provide / inject

Pinia 與 Vuex 最大的差別是什麼?

Pinia 移除了 mutation,直接在 action 修改狀態,同步與非同步不再分開寫;同時採用多個平級 store 而非巢狀模組,TypeScript 的型別推導也完整得多。

Vuex 還需要學嗎?

新專案不必,官方已建議使用 Pinia。但若要維護 Vue 2 時期的舊專案,仍需要看得懂 Vuex 的 mutation 與模組結構。

Pinia 的資料重新整理後會消失嗎?

會,store 存在記憶體中,重新整理就會回到初始值。需要保留的資料要自行寫入 localStorage 或改由 API 重新取得,也可以使用持久化的社群外掛。

store 檔案要怎麼拆分?

依業務領域拆,例如:usercartproduct 各一個檔案。Pinia 的 store 是平級的,需要互相取用時直接在一個 store 裡呼叫另一個 store 即可。

延伸閱讀