Reputation: 63
I have recently started learning Sveltekit and am working on a very basic project to practise. Here is the structure of the project:
|-routes/
| |-nextpage/
| └ +page.svelte
|+page.svelte
|+page.server.js
I got stuck trying to pass data from the +page.server.js to the +page.svelte located inside the nextpage/ route and I have no idea what to do.
In the main +page.svelte there is a component with a button that when pressed sends a FormData via POST request to the /results endpoint, triggering a server action called results within the +page.server.js. Then redirects to /nextpage.
Component in +page.svelte:
let myObject = {
//stuff
}
const handleSubmit = () => {
const formData = new FormData();
for(const name in myObject){
formData.append(name, myObject[name]);
}
let submit = fetch('?/results', {
method: 'POST',
body: formData
})
.finally(() => console.log("done"))
window.location = "/nextpage";
}
+page.server.js:
let myObject = {};
export const load = () => {
return {
myObject
}
}
export const actions = {
results: async({ request }) => {
const formData = await request.formData();
formData.forEach((value, key) => (myObject[key] = value));
console.log(myObject);
}
}
Now I would like to be able to show myObject in the +page.svelte in /nextpage, but the usual export let data
does not work:
/nextpage +page.svelte:
<script>
export let data;
</script>
{data.myObject} //undefined`
What can I do? Thank you for your help.
Upvotes: 3
Views: 7632
Reputation: 326
A store would be perfect to pass data from one component to the next or to any other component. You can save the object, or almost any data, to a store variable in the component. On the first component save the object to the store before you switch components. Then when the second component loads you can easily retrieve whatever data is needed, in your case the object. This is also a handy thing you could use in modals, or when you have multiple components that are not children of the main component on a page. When storing or accessing store data make sure to put a $ before the variable to make it accessible. I also liket to put store at the end of the variable to know it's a store variable. So I would name your variable objectStore, which I would be able to access in the components as $objectStore.
Component in +page.svelte:
<script>
//import the 'objectStore' variable from the store
import {objectStore} from 'path/to/store'
let myObject = {
//stuff
}
const handleSubmit = () => {
const formData = new FormData();
for(const name in myObject){
formData.append(name, myObject[name]);
}
let submit = fetch('?/results', {
method: 'POST',
body: formData
})
.finally(() => console.log("done"))
//set store value as your object
$objectStore = myObject
window.location = "/nextpage";
}
</script>
Then just import the object from the store /nextpage +page.svelte:
<script>
//import the 'objectStore' variable from the store
import {objectStore} from 'path/to/store'
</script>
Upvotes: 0
Reputation: 1
You can use +layout.js
or sveltkit/stores
.
sveltekit/stores
are above the layout layer because they don't depend on the flow of the pages compared to the +layout.js
layer which does depend.
cookies
are processed locally.
Upvotes: 0
Reputation: 63
OK guys, I guess all I needed was to use cookies. Since the object I was trying to pass between pages didn't need to be stored for longer than a page load, I don't think it would make sense to save it in a database. Instead, what did it in my case was to set a cookie with cookies.set('name', JSON.stringify(obj));
inside the action function in the main +page.server.js, and then get it back inside the load function of the /nextpage +page.server.js with const obj = cookies.get('name');
. I'm not sure it was the cleanest way to do it, but it worked for me.
Upvotes: 1
Reputation: 184526
That does not work. Pages are fully separate, you cannot load data from one page into another.
If you want to share loaded data use a layout load function.
Upvotes: 0