2017-12-31 45 views
0

Ich habe zwei Domänen senden:Quer (sub) Domain jQuery.ajax Abfrage App Flasche erhält Cookies, kann sie aber nicht

https://localhost.com  # SPA served via Nginx 
https://api.localhost.com # Flask API proxied by nginx (uwsgi_pass) 

und fügte hinzu, beide meine Gastgeber über 127.0.0.1 localhost.com api.localhost.com Datei.

Ich habe Server-Seite oauth2 über GitHub OAUTH Dienst hinzugefügt und ich kann authentifizieren (ich erhalte ein Zugriffs-Token und kann die GitHub API abfragen). Dies ist die "flow":

user calls: https://localhost.com 
ajax: https://api.localhost.com/v1/login # gets the app's Github OAuth url 
             # sets a session cookie for 
             # localhost.com 
user calls: https://github.com/...  # gets redirected to log in ect. 
redirect: https://api.localhost.com/callback 
             # github redirects to the callback 
             # can access some session cookie 
             # (I assume) from localhost.com 
redirect: https://localhost.com   # now has two session cookies: 
             # localhost.com 
             # api.localhost.com 
ajax: https://api.localhost.com/v1/username 
             # this is where it breaks 

I beide gesetzt, die serverseitige CORS Header für api.localhost.com (Schnipsel aus nginx.conf)

add_header 'Access-Control-Allow-Origin' "https://localhost.com"; 
    add_header 'Access-Control-Allow-Credentials' 'true'; 
    add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS'; 
    add_header 'Access-Control-Allow-Headers' 'Content-Type, *'; 

und den withCredentials Parametern in den Abfragen:

$.getJSON("https://api.localhost.com/v1/login", 
    { 
     xhrFields: { withCredentials: true }, 
    }, 
    (response) => { 
     this.login_url = response; 
    }); 
    $.getJSON("https://api.localhost.com/v1/username", 
    { 
     xhrFields: { withCredentials: true }, 
    }, 
    (response) => { 
     console.log(response) 
     this.username = response; 
    }); 

Die erste Cross-Domain ajax: https://api.localhost.com/v1/login Werke und setzt ein Cookie, so dass ich denke, es ist richtig konfiguriert ist. (Ich könnte falsch sein.) jedoch die zweiten ajax: https://api.localhost.com/v1/username scheint nicht die Session-Cookie zu senden, wie ich mit einer leeren Sitzung in der Flasche gelassen bin:

from flask import session 

# [ ... ] 

def username_get(): 
    return str(list(session.keys())) # returns "[]" 

ich beiden Session-Cookies manuell entschlüsseln kann (localhost.com und api.localhost.com). Sie haben beide den gleichen Inhalt (Benutzername, Zugriffstoken und oauth_state [erforderlich während GitHub OAuth]) und zeigen an, dass die Authentifizierung erfolgreich war.

Was ich nicht verstehe, ist:

  1. Warum erhalte ich zwei Cookies, insbesondere, warum die Session-Cookie von ajax: https://api.localhost.com/v1/login in localhost.com gespeichert und nicht api.localhost.com?

  2. Github OAuth funktioniert, dh redirect: https://api.localhost.com/callback empfängt den Sitzungscookie, der von https://api.localhost.com/v1/login festgelegt wurde, und kann die Daten (oauth_state) verwenden. Das folgende ajax: https://api.localhost.com/v1/Username sendet jedoch den Sitzungscookie nicht. Warum?

Ich hoffe, ich habe alle notwendigen Bits enthalten. Dies ist ein sehr rätselhaftes Problem und keine der vorhandenen SO-Fragen hat mir über diesen Punkt hinweg geholfen. JEDE Hilfe oder Hinweise werden sehr geschätzt.

Antwort

0

(2) Ich habe $.getJSON falsch verwendet. Es ist so einfach, dass es weh tut.

Als per the documentation:

jQuery.getJSON(url [, data ] [, success ]) 

und Daten werden als Abfrageparameter an die URL angehängt werden. Damit das Gespräch zu ersetzen mit

$.ajax({ 
     dataType: "json", 
     url: "https://api.localhost.com/v1/username", 
     xhrFields: { withCredentials: true }, 
     success: (response) => 
     { 
      this.username = response; 
     } 
     }); 

(nicht dem Kurz verwendet) setzt die entsprechenden xhrField und sendet nun korrekt das Cookie.

(1) Wahrscheinlich durch Zwischenspeichern oder einige temporäre Dateien verursacht. Ich habe den gesamten Server heruntergefahren, alle temporären Dateien gelöscht und dasselbe mit meinem Browser (Chrome) gemacht.Nach dem Neustart erhalte ich nur einen einzigen Session-Cookie für api.localhost.com, was das erwartete Verhalten ist.

Verwandte Themen