Session Sapper/svelte3会话在没有页面重新加载的情况下不同步
我无法让Sapper在没有页面加载的情况下同步服务器端路由中所做的会话更改。我的示例场景是,我在会话中没有用户的情况下加载应用程序,我的服务器端登录路由将用户设置为会话,我使用Session Sapper/svelte3会话在没有页面重新加载的情况下不同步,session,sapper,svelte-3,Session,Sapper,Svelte 3,我无法让Sapper在没有页面加载的情况下同步服务器端路由中所做的会话更改。我的示例场景是,我在会话中没有用户的情况下加载应用程序,我的服务器端登录路由将用户设置为会话,我使用goto进入仪表板 问题是没有填充仪表板预加载函数中的会话参数。如果我使用的是window.location.href='/dashboard',它就是,因为它正在Sapper的应用程序中运行。但是如果我只重定向客户端,Sapper不会将更新的会话发送到客户端 有办法吗?我用错工具了吗 注意:我正在使用connectpgs
goto
进入仪表板
问题是没有填充仪表板预加载函数中的会话
参数。如果我使用的是window.location.href='/dashboard'
,它就是,因为它正在Sapper的应用程序中运行。但是如果我只重定向客户端,Sapper不会将更新的会话发送到客户端
有办法吗?我用错工具了吗
注意:我正在使用connectpgsimple和express会话,设置sapper如下:sapper.middleware({session:(req,res)=>req.session.public})
我在
会话
包含服务器上的种子数据。它是一个可写存储,这意味着您可以使用新数据更新它(例如,在用户登录后),您的应用程序将被刷新
这表明你的应用程序必须手动同步你的会话数据
这里的解决方案是使用webhook连接、响应头或响应数据中的键手动将会话数据同步到客户端
我有一个用于创建服务器路由处理程序的装饰器,在其中我将会话数据添加到响应中。以下是一个简化版本:
const createHandler = getData => (req, res) => {
res.status(200).json({data: getData(req.body), session: req.session.public})
}
很明显,还有更多,例如错误处理,但你明白了。在客户机上,我将fetch
包装在一个helper函数中,我总是使用该函数来获取json、设置正确的头等等。在该函数中,我查看响应,如果有session
属性,我将其设置到会话存储中,以便在preload
中可用
import {stores} from "@sapper/app"
const myFetch = (...args) => fetch(...args).then(r => r.json()).then(body => {
if (body.session) stores().session.set(body.session)
return body.data
})
简单地说,在您的会话状态从前端更改后(用户刚刚登录,或者您刚刚使其登录无效),您应该更新前端上的会话存储
<script>
import { goto, stores } from '@sapper/app';
const { session } = stores();
const loginBtnHandler = () => {
const req = await fetch('/api/login', {
method: 'POST',
credentials: 'same-origin', // (im using cookies in this example)
headers: {
'Content-Type': 'application/json',
},
body: JSON.stringify({ ........ })
});
if (req.ok) {
// here is where you refresh the session on the client right after you log in
$session.loggedIn = true; // or your token or whatever
// next page will properly read the session
goto('/');
return;
}
...
}
</script>
从'@sapper/app'导入{goto,stores};
const{session}=stores();
const loginBtnHandler=()=>{
const req=wait fetch('/api/login'{
方法:“POST”,
凭证:'相同来源',//(本例中我使用cookie)
标题:{
“内容类型”:“应用程序/json”,
},
正文:JSON.stringify({……..})
});
如果(请求ok){
//在这里,您可以在登录后立即刷新客户端上的会话
$session.loggedIn=true;//或您的令牌或其他
//下一页将正确阅读会话
后藤(“/”);
返回;
}
...
}
谢谢您的回答。我有点理解你的答案,但我无法通过预加载来传递数据。您是否介意发布一个预加载“export async function preload(){}的示例,以查看如何在stores()中设置会话?这是一个大问题,我看到不止一个帖子请求帮助,但没有人提供帮助。似乎rich是唯一回答这个问题的人,我们需要一个可行的例子。不幸的是,我无法使预加载工作正常进行(会话是问题的一部分,我认为还有其他问题),因此我没有工作示例。回答得很好,谢谢。请看: