Svelte + Houdini客户端渲染无法自动发送Cookie问题求助
我在SvelteKit项目中使用Houdini进行GraphQL操作,SvelteKit运行在localhost:5000,GraphQL服务器运行在localhost:4000,服务器依赖Cookie完成身份验证。我配置的HoudiniClient如下:
// client.ts declare namespace App { interface Session { token?: string } } export default new HoudiniClient({ url: 'http://localhost:4000/graphql', fetchParams({ session }) { const {token } = session as App.Session return { headers: { cookie: `token=${token}` } } } })
路由中通过+page.gql获取数据时,服务端渲染(SSR)场景能正常工作,但客户端渲染(如页面跳转)时,请求未携带Cookie——即便Cookie已设置为SameSite=Lax、HttpOnly=false、Secure=false。我尝试使用_houdini_beforeLoad和Svelte的load方法,均无法获取客户端Cookie,请问这一问题的原因是什么?
1. SvelteKit客户端session的局限性
当前配置依赖fetchParams中的session参数,但客户端环境下SvelteKit的session不会自动同步浏览器Cookie。SSR时session从服务端请求上下文获取,能拿到Cookie中的token,但客户端没有这个上下文,session对象大概率为空,导致生成的cookie头无效。
2. 跨端口属于跨域场景
虽然都是localhost,但端口5000和4000属于不同的源。浏览器默认不会自动将5000域下的Cookie发送到4000的请求中,SameSite=Lax规则仅适用于同一顶级域名下的不同子域名,跨端口仍属于跨域范畴,需要明确配置凭证携带规则。
3. Houdini请求未开启凭证模式
你的fetchParams仅手动拼接cookie头,但浏览器在跨域请求时默认不会发送Cookie,除非请求明确设置credentials: 'include'(跨场景需用include,同域可用same-origin)。另外,客户端load方法运行在隔离环境(部分场景为Web Worker),无法直接访问document.cookie,手动读取的方式本身就不生效。
- 修改HoudiniClient配置,分环境处理请求参数
区分SSR和客户端环境,客户端请求开启凭证模式,让浏览器自动处理Cookie携带:export default new HoudiniClient({ url: 'http://localhost:4000/graphql', fetchParams({ session }) { // SSR环境使用session中的token if (typeof window === 'undefined') { const { token } = session as App.Session return { headers: { cookie: `token=${token}` } } } // 客户端环境开启凭证模式 return { credentials: 'include' } } }) - 配置GraphQL服务器跨域规则
服务器需设置Access-Control-Allow-Origin为http://localhost:5000(不能用*,否则credentials会失效),同时添加Access-Control-Allow-Credentials: true响应头。
内容的提问来源于stack exchange,提问作者Aviad Ben Dov

