Is it possible to initialize store state with async function ?
Hello friends,
I am trying to set up my store from indexedDb.
I've seen an example with useLocalStorage from vueUse, but how can I make it works with custom function ?
Thank for the help
5 Replies
import { skipHydrate } from "pinia";
const key = "item";
export const useItemStore = defineStore(key, {
state: () => ({
itemtypes: new Map(),
fetching: false,
}),
actions: {
async fetch() {
return new Promise(async function (resolve, reject) {
if (process.client) {
console.log("process client");
const db = await getIdb.value;
console.log(db);
const data_trans = db
.transaction("test")
.objectStore("test")
.get(key);
data_trans.onsuccess = async (event) => {
try {
console.log("success");
let buffer = data_trans.result;
console.log(buffer);
resolve(
new Map<number, string>(
buffer.map((raw) => {
return [raw.id, raw.title];
})
)
);
} catch (error) {
console.log("error", error);
const buffer: any = await $fetch(
`https://jsonplaceholder.typicode.com/posts/`,
{
headers: { "Content-Type": "application/json" },
method: "GET",
}
);
db.transaction("test", "readwrite")
.objectStore("test")
.put(buffer, key);
resolve(
new Map<number, string>(
buffer.map((raw) => {
return [raw.id, raw.title];
})
)
);
}
};
data_trans.onerror = async (event) => {
console.log(data_trans.error);
};
}
});
},
hydrate(state, initialState) {
console.log("hydrating !!!");
this.actions.fetch().then((value) => (state.itemtypes = value));
},
});
import { skipHydrate } from "pinia";
const key = "item";
export const useItemStore = defineStore(key, {
state: () => ({
itemtypes: new Map(),
fetching: false,
}),
actions: {
async fetch() {
return new Promise(async function (resolve, reject) {
if (process.client) {
console.log("process client");
const db = await getIdb.value;
console.log(db);
const data_trans = db
.transaction("test")
.objectStore("test")
.get(key);
data_trans.onsuccess = async (event) => {
try {
console.log("success");
let buffer = data_trans.result;
console.log(buffer);
resolve(
new Map<number, string>(
buffer.map((raw) => {
return [raw.id, raw.title];
})
)
);
} catch (error) {
console.log("error", error);
const buffer: any = await $fetch(
`https://jsonplaceholder.typicode.com/posts/`,
{
headers: { "Content-Type": "application/json" },
method: "GET",
}
);
db.transaction("test", "readwrite")
.objectStore("test")
.put(buffer, key);
resolve(
new Map<number, string>(
buffer.map((raw) => {
return [raw.id, raw.title];
})
)
);
}
};
data_trans.onerror = async (event) => {
console.log(data_trans.error);
};
}
});
},
hydrate(state, initialState) {
console.log("hydrating !!!");
this.actions.fetch().then((value) => (state.itemtypes = value));
},
});
1) I'd go for setup stores
2) Then expose an async init function
3) call the init function on the server side (just once) if you need SSR
when you say a init function, is it like literally a function named init ?
Since I want to check the indexedDb only on the client, I've had some issue with the hydration. when I use skipHydrate, I have a cannot stringify non pogo error
can be named as you want
Well not sure why it works, but it seems to work perfect with either hydration and mount and ssr.
Thanks for the advice !
I watched a lot of your useFetch & co video, it helped me a lot ! thanks for that also
import { skipHydrate } from "pinia";
import { useAsyncState } from "@vueuse/core";
const key = "job";
export const useJobStore = defineStore(key, () => {
const { state, isReady, isLoading } = useAsyncState(
ifetch().then((data) => data),
{ id: null }
);
async function ifetch() {
return new Promise(async function (resolve, reject) {
if (process.client) {
console.log("process client");
const db = await getIdb.value;
console.log(db);
const data_trans = db.transaction("test").objectStore("test").get(key);
data_trans.onsuccess = async (event) => {
try {
console.log("success");
let buffer = data_trans.result;
console.log(buffer);
resolve(
new Map<number, string>(
buffer.map((raw) => {
return [raw.id, raw.title];
})
)
);
} catch (error) {
console.log("error", error);
const buffer: any = await $fetch(
`https://jsonplaceholder.typicode.com/posts/`,
{
headers: { "Content-Type": "application/json" },
method: "GET",
}
);
db.transaction("test", "readwrite")
.objectStore("test")
.put(buffer, key);
resolve(
new Map<number, string>(
buffer.map((raw) => {
return [raw.id, raw.title];
})
)
);
}
};
data_trans.onerror = async (event) => {
console.log(data_trans.error);
};
}
});
}
return { state};
});
import { skipHydrate } from "pinia";
import { useAsyncState } from "@vueuse/core";
const key = "job";
export const useJobStore = defineStore(key, () => {
const { state, isReady, isLoading } = useAsyncState(
ifetch().then((data) => data),
{ id: null }
);
async function ifetch() {
return new Promise(async function (resolve, reject) {
if (process.client) {
console.log("process client");
const db = await getIdb.value;
console.log(db);
const data_trans = db.transaction("test").objectStore("test").get(key);
data_trans.onsuccess = async (event) => {
try {
console.log("success");
let buffer = data_trans.result;
console.log(buffer);
resolve(
new Map<number, string>(
buffer.map((raw) => {
return [raw.id, raw.title];
})
)
);
} catch (error) {
console.log("error", error);
const buffer: any = await $fetch(
`https://jsonplaceholder.typicode.com/posts/`,
{
headers: { "Content-Type": "application/json" },
method: "GET",
}
);
db.transaction("test", "readwrite")
.objectStore("test")
.put(buffer, key);
resolve(
new Map<number, string>(
buffer.map((raw) => {
return [raw.id, raw.title];
})
)
);
}
};
data_trans.onerror = async (event) => {
console.log(data_trans.error);
};
}
});
}
return { state};
});