Django跨域资源共享(CORS)Access-Control-Allow-Origin缺失

16

我正在尝试在我的django应用程序中实现谷歌oauth2身份验证。我已按照文档中的所有步骤进行操作。

在浏览器地址栏中,如果我浏览此https://foo.bar.net/api/v1/auth/login/google-oauth2/链接,则它会通过google进行正确的身份验证,并将google-auth-token返回到指定的重定向url,并将其转换为普通令牌,然后以json格式将其发送给用户或前端。

但是,如果我尝试从我的js代码中发起GET请求到上述提到的url,则会显示

Reason: CORS header 'Access-Control-Allow-Origin' missing

在前端上完整的回溯看起来像这样:

GET https://foo.bar.net/api/v1/auth/login/google-oauth2/ 302 Found 718ms    
polyfil...ndle.js (line 7507)
GET https://accounts.google.com/o/oauth2/auth?client_...DW&response_type=code&scope=openid+email+profile 200 OK
Login Failed Response { _body=Event error,  status=0,  ok=false,  more...}
main.bundle.js (line 367)
Cross-Origin Request Blocked: The Same Origin Policy disallows reading the remote resource at https://accounts.google.com/o/oauth2/auth?client_id=kguygvh868697-khgkhvkgvkgkgv.apps.googleusercontent.com&redirect_uri=https://foo.bar.net/api/v1/auth/complete/google-oauth2/&state=Cbms1QhSQVzjO3xkjhkyuu&response_type=code&scope=openid+email+profile. (Reason: CORS header 'Access-Control-Allow-Origin' missing).

我在谷歌上搜索,发现需要安装djang-CORS-headers。我已经安装并配置了这个软件包。但是仍然出现相同的错误。

我的settings.py的一部分如下所示:

MIDDLEWARE = [
    'django.middleware.security.SecurityMiddleware',
    'django.contrib.sessions.middleware.SessionMiddleware',
    'corsheaders.middleware.CorsMiddleware',
    'django.middleware.common.CommonMiddleware',
    'django.middleware.csrf.CsrfViewMiddleware',
    'django.contrib.auth.middleware.AuthenticationMiddleware',
    'django.contrib.messages.middleware.MessageMiddleware',
    'django.middleware.clickjacking.XFrameOptionsMiddleware',
    'oauth2_provider.middleware.OAuth2TokenMiddleware',
]

INSTALLED_APPS = [
    'django.contrib.admin',
    'django.contrib.auth',
    'django.contrib.contenttypes',
    'django.contrib.sessions',
    'django.contrib.messages',
    'django.contrib.staticfiles',
    'rest_framework',
    'oauth2_provider',
    'corsheaders',
    'rest_framework_swagger',
]

CORS_ORIGIN_ALLOW_ALL = True
实际上,我们有两个独立的项目,一个是前端(ang),另一个是后端(django)。我同意ajax问题。所以我让Google OAuth网址在一个单独的窗口中打开。
在后端部分,我已经完成了获取服务器访问令牌并将其转换为我们应用程序的访问令牌。目前,我以json格式返回令牌详细信息。因此,这个json将显示在新打开的窗口中。但是不知道如何:
1.从窗口获取令牌并将其存储到浏览器的临时存储中。 2.在详细信息出现后关闭新窗口。 3.通过请求头传递令牌信息重定向到用户/配置文件页面。
不知道这个oauth流程是否正确。而且我不想让js部分包含完整的oauth流程(oauth implicit flow)。请指导我正确方向。

你不能在ajax中重定向到Google。 - charlietfl
@charlietfl 是的,实际上我是通过 Angular 进行 GET 请求。 - Avinash Raj
“跨源请求被阻止:同源策略不允许读取远程资源 https://accounts.google.com/o/oauth2/auth?…(原因:CORS头缺少'Access-Control-Allow-Origin')”,这表示问题并非因为您自己的服务器缺乏CORS支持,而是因为Google端点故意不支持从运行在浏览器中的前端JavaScript代码接收请求(通过XHR或Fetch API)。缺少Access-Control-Allow-Origin响应头不是疏忽; 缺少它意味着“不允许跨域请求”。 - sideshowbarker
1
需要在新窗口打开,并在返回的URL中使用一些JavaScript与打开的窗口通信,以便在OAuth返回令牌时进行通信。 - charlietfl
请查看 hello.js 库作为示例。 - charlietfl
显示剩余7条评论
1个回答

8

请问我在前端使用了授权码流程的地方在哪里? - Avinash Raj
1
你不应该在前端代码中获取访问令牌。 - RamiReddy P

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接