使用NextAuth跨多个域进行身份验证(CORS)

gpfsuwkq  于 2024-01-07  发布在  其他
关注(0)|答案(2)|浏览(114)

我想做一个XHR从www.example.com到www.example.com。domain2.com是一个使用NextAuth的NextJS应用程序。
问题是,当我执行此请求时,domain2的cookie不包含在内。我的代码是:

  1. var httpRequest = new XMLHttpRequest();
  2. httpRequest.onreadystatechange = function(){
  3. if (httpRequest.readyState === XMLHttpRequest.DONE) {
  4. if (httpRequest.status === 200) {
  5. alert('send successful')
  6. } else {
  7. alert('Error:' + httpRequest.responseText)
  8. }
  9. }
  10. };
  11. httpRequest.withCredentials = true;
  12. httpRequest.open('GET', url, true);
  13. httpRequest.send();

字符串
服务器代码:

  1. const session = await getSession({ req })
  2. if(session == undefined || session.accessToken == undefined) {
  3. res.statusCode = 500;
  4. res.send(JSON.stringify({'error': 'Not logged in'}));
  5. return;
  6. }


我该怎么做?

kqqjbcuj

kqqjbcuj1#

不幸的是,目前NextAuth.js还没有明确支持这一点。
您可以设置自定义cookie策略以支持子域(例如auth.example.com,www.example.com,cdn.example.com),但对于完全唯一的域,目前您需要为每个域设置不同的站点。
这是由一些平台支持的,如Auth 0作为“静默登录”,通常涉及跨域iframe在不同域的网站之间传递消息(其中一个域是“标准”)。这是一个计划中的功能,可能不太可能在今年年底前放弃。
注意事项:对于某些OAuth提供程序,您可以使用具有相同OAuth Client/Secret的不同域,但并非所有提供程序都是如此,但是如果您只使用支持此功能的提供程序,则可以将所有示例指向同一数据库。
附言:如果你对如何实现这一点感兴趣,从技术上讲,你可以自己实现这一点(使用或不使用NextAuth.js),使用postMessage API从屏幕外的iframe返回一个令牌,该令牌指向你选择登录的“规范”URL上的页面;然后你可以读取该令牌以确定用户是否有会话。
这并不复杂,但复杂的地方在于安全地执行此操作,因为这意味着什么取决于场景(例如,它是具有多个有效域和可能不同内容的一个web应用,或者是多个完全独立的网站在不同的域,你会高兴与客户端只cookie)这是一个棘手的问题,提供一个单一的解决方案,为每个人都工作得很好,我不知道这将是什么样子的NextAuth.js尚未。

slsn1g29

slsn1g292#

下面是一个解决方案,当同一个应用程序在多个域上使用nextAuth /app路由器时,它可以正常工作。

  1. // app/api/auth/[...nextauth]/route.js
  2. const authOptions = (req, res) => {
  3. const auth_url = req.nextUrl.searchParams.get('auth_url');
  4. if (auth_url) {
  5. const authUrlObject = new URL(auth_url);
  6. if (authUrlObject.hostname === 'url1.domain1.com') {
  7. process.env.NEXTAUTH_URL = 'https://url1.domain1.com/api/auth';
  8. } else if (authUrlObject.hostname === 'url2.domain2.com') {
  9. process.env.NEXTAUTH_URL = 'https://url2.domain2.com/api/auth';
  10. }
  11. }
  12. return {
  13. providers: [
  14. GoogleProvider({ ...})
  15. ]
  16. }

字符串
和出口

  1. const handler = async (req, res) => {
  2. return await NextAuth(req, res, authOptions(req));
  3. };
  4. export { handler as GET, handler as POST };


并在客户端的SignIn中传递auth_url

  1. await signIn('google', null, {auth_url: `${window.location.origin}${window.location.pathname}/` }

展开查看全部

相关问题