Edited at

【初心者向け】Vue.jsでコンポーネントごとにデータの永続化を行うサンプル

こんにちは、@y_temp4です。

Vue.js でコンポーネントごとにデータの永続化を行うサンプルを作りましたので、ご紹介します。


実装(CodePen)


See the Pen
Vue Client-Side Storage Sample
by Yuki Terashima (@y-temp4)
on CodePen.

こちらは JS 部分のコードの抜粋です。

new Vue({

el: '#root',
data: {
app: {
counter1: 0,
counter2: 0
}
},
mounted() {
const app = localStorage.app
if (app) this.app = JSON.parse(app)
},
methods: {
addCounter1() {
this.app.counter1++
},
addCounter2() {
this.app.counter2++
},
},
watch: {
app: {
handler: newState => {
localStorage.app = JSON.stringify(newState)
},
deep: true
}
},
template: `<div>
<p>{{ app.counter1 }}</p>
<button @click="addCounter1">addCounter1</button>
<p>{{ app.counter2 }}</p>
<button @click="addCounter2">addCounter2</button>
</div>`

})


解説

データの永続化を行う際には localStorage を利用します。

コンポーネント単位とはいえ、それぞれの data のキーに対して localStorage の値をセットするのはだるいので、何らかのオブジェクトとして全体をラップして(今回は app で囲っています)、それを watch で監視するという方式を取っています。

こうすることによって、キーが増えてもこのコンポーネント内では localStorage への保存のために他に watch する対処が増えないので便利です。

Vue でオブジェクトの値の変更を検知するためには、検知したいオブジェクトに handler を指定した上で deep: true を指定する必要があります。

...

watch: {
app: {
handler: newState => {
localStorage.app = JSON.stringify(newState)
},
deep: true
}
},
...

(localStorage は文字列しか受け取らないので、保存時には JSON.stringify、読み込み時には JSON.parse を忘れずに。)

localStorage はクライアントでしか使えないので、mounted 時に保存したデータの読み込みを行います。

addCounter1 や 2 を何度か押したあと、リロードしても値が保持されていることが確認できるかと思います。


さいごに

Vuex のデータの永続化だと vuex-persistedstate あたりが有名かと思いますが、コンポーネントレベルでの永続化の例はあまり見当たらなかったので試しに書いてみました。

もしこの記事が参考になったら、いいねしていただけると嬉しいです😄


参考