7

Nie mogę pobrać identyfikatora użytkownika id_token (https://developers.google.com/accounts/docs/CrossClientAuth) z interfejsu API tożsamości Chrome (https://developer.chrome.com/apps/identity).Czy można uzyskać token identyfikatora za pomocą aplikacji Chrome Indentity Api?

mogę dostać access_token stosując próbkę tożsamości chrom gdy sekcja OAuth w manifeście jest:

"oauth2": { 
    "client_id": "<chrome-app-client-id>.apps.googleusercontent.com", 
    "scopes": ["https://www.googleapis.com/auth/plus.login"] 
} 

Ale gdy próbuję uzyskać id_token ten sam sposób mam to na moim android klienta GET błąd:

"żądanie OAuth2 nie powiodło się: Usługa odpowiedział z błędem: 'nieprawidłowy zakres: {0}'"}

manifest sekcja jest teraz:

"oauth2": { 
    "client_id": "<chrome-app-client-id>.apps.googleusercontent.com", 
    "scopes": ["audience:server:client_id:<app-engine-client-id>.apps.googleusercontent.com"] 
} 

Na Androidzie otrzymuję identyfikator id_token, przekazując ten sam ciąg zasięgu do android.gms.auth.GoogleAuthUtil.getToken(), ale nie mogę uruchomić go za pomocą interfejsu API Chrome.

Czy można uzyskać identyfikator id_token za pomocą aplikacji Chrome Indentity Api? Jeśli nie, w jaki sposób mogę uzyskać identyfikator id_token dla mojej aplikacji Chrome?

Dzięki za pomoc!

+0

Terminologia z OAuth jest szalony. W swoim poście odwołujesz się do "id użytkownika", "id_klienta", "tokena identyfikatora" i "id". Czy możesz dokładnie określić, co dokładnie chcesz uzyskać? (Wiem kilka rzeczy o "id_klienta", "id" jest zbyt ogólna, aby je zrozumieć, i nie jestem pewien, co to jest "identyfikator użytkownika".) –

+0

Zgadzam się, istnieje kilka terminów, które musisz zachować oddzielny. Edytowano post dla jasności. Identyfikator klienta jest wymieniony na pierwszym łączu w poście, jest potrzebny do określenia odbiorców w id_token. Myślę, że jasne jest, że chcę id_token, który można zweryfikować, gdy zostanie dołączony do https://www.googleapis.com/oauth2/v1/tokeninfo?id_token= – chris

+0

Czy próbowałeś dodać 'openid' do zakresów? Zwykle jest to wskazówka, aby serwer przeszedł w tryb OpenID Connect i wydał Token ID. –

Odpowiedz

-1

Po pierwsze, zakładam, że w twoim fragmencie manifest.json nie masz na myśli, że twój identyfikator klienta jest dosłownie: "<chrome-app-client-id>.apps.googleusercontent.com. Powinno to być coś w stylu: 9414861317621.apps.googleusercontent.com - coś, co otrzymałeś z Konsoli programisty lub jakiejkolwiek strony Google, której użyłeś do zarejestrowania aplikacji.

Zakładając, że powyższe informacje są poprawne, a użytkownik ma prawo id_klienta, a prawy zasięg, otrzymuje to, co jest nazywane tokenem dostępu OAuth2, z numerem telefonu chrome.identity.getAuthToken. Ponieważ nie pokazujesz nam żadnego kodu JavaScript, nie mogę stwierdzić, czy to właśnie robisz. Otrzymujesz token dostępu, który musisz zapisać do kolejnego użycia, gdy zadzwonisz do funkcji API. Na przykład:

var access_token; 

chrome.identity.getAuthToken(
    { 
     'interactive': true 
    }, 
    function(token) { 
     access_token = token; 
     // do something if you like to indicate 
     // that the app is authorized 
    } 
); 

Następnie, po dokonaniu połączenia API, podać, że dostęp do tokena, tak:

var url = 'https://www.googleapis.com/' + method; 
Ajax.ajaxSend(url, "json", 
    function (status, response) { 
     if (response && response.error && response.error.message) 
      errorCallback(response.error.message); 
     else if (status == 200) 
      successCallback(response); 
     else 
      errorCallback('Result code: ' + status); 
    }, 
    function (e) { 
     if (errorCallback) 
      errorCallback('Communication error'); 
    }, 
    { 
     Authorization: 'Bearer ' + access_token 
    } 
); 

Ajax.ajaxSend jest moja własna funkcja:

var Ajax = (function() { 
    var api = { 
     ajaxSend: function (url, responseType, successCallback, errorCallback, headers) { 
      var req = new XMLHttpRequest(); 
      req.onload = function (e) { 
       successCallback(req.status, req.response); 
      }; 
      req.onerror = errorCallback; 
      req.responseType = responseType ? responseType : "text"; 
      req.open("get", url); 
      if (headers) 
       for (var v in headers) 
        req.setRequestHeader(v, headers[v]); 
      req.send(); 
     } 
    }; 
    return api; 
})(); 

Inny niezdefiniowane funkcje również są tym, czego można się spodziewać. Trzeci argument do Ajax.ajaxSend jest nagłówkiem do wysłania. (Niestety, nie mam czasu na opracowanie samodzielnego kodu dla tej odpowiedzi.)

Mam nadzieję, że powyższe jest przydatne.

+1

Dzięki za pomoc, ale to nie jest odpowiedź na moje pytanie. W moim pytaniu na linii 3 mówię, że wiem, jak uzyskać access_token (uwzględniłem to, aby uniknąć odpowiedzi wyjaśniających, jak je zdobyć). Próbuję uzyskać identyfikator id_token (token, który można zweryfikować po dołączeniu do tego adresu URL: "googleapis.com/oauth2/v1/tokeninfo?id_token=") – chris

+0

Czy zdarzyło Ci się to zrozumieć? Próbuję też zrobić to samo. Dzięki. – rsb

+0

nadal zmaga się z tym:/ – kidCoder

5

Wczoraj doszłam do tego samego problemu, a ponieważ znalazłem rozwiązanie, równie dobrze mógłbym go udostępnić, ponieważ nie było to takie oczywiste. O ile mi wiadomo Google nie zapewnia bezpośredniego i udokumentowanego sposobu, aby to zrobić, ale możesz użyć funkcji chrome.identity.launchWebAuthFlow().

Najpierw należy utworzyć aplikację Web poświadczenia w konsoli google i dodaj następujący adres URL jako ważnego Authorized redirect URI: https://<EXTENSION_OR_APP_ID>.chromiumapp.org. Identyfikator URI nie musi istnieć, chrome po prostu złapie przekierowanie do tego adresu URL i wywoła później funkcję zwrotną.

manifest.json:

{ 
    "manifest_version": 2, 
    "name": "name", 
    "description": "description", 
    "version": "0.0.0.1", 
    "background": { 
    "scripts": ["background.js"] 
    }, 
    "permissions": [ 
    "identity" 
    ], 
    "oauth2": { 
    "client_id": "<CLIENT_ID>.apps.googleusercontent.com", 
    "scopes": [ 
     "openid", "email", "profile" 
    ] 
    } 
} 

background.js:

// Using chrome.identity 
var manifest = chrome.runtime.getManifest(); 

var clientId = encodeURIComponent(manifest.oauth2.client_id); 
var scopes = encodeURIComponent(manifest.oauth2.scopes.join(' ')); 
var redirectUri = encodeURIComponent('https://' + chrome.runtime.id + '.chromiumapp.org'); 

var url = 'https://accounts.google.com/o/oauth2/auth' + 
      '?client_id=' + clientId + 
      '&response_type=id_token' + 
      '&access_type=offline' + 
      '&redirect_uri=' + redirectUri + 
      '&scope=' + scopes; 

chrome.identity.launchWebAuthFlow(
    { 
     'url': url, 
     'interactive':true 
    }, 
    function(redirectedTo) { 
     if (chrome.runtime.lastError) { 
      // Example: Authorization page could not be loaded. 
      console.log(chrome.runtime.lastError.message); 
     } 
     else { 
      var response = redirectedTo.split('#', 2)[1]; 

      // Example: id_token=<YOUR_BELOVED_ID_TOKEN>&authuser=0&hd=<SOME.DOMAIN.PL>&session_state=<SESSION_SATE>&prompt=<PROMPT> 
      console.log(response); 
     } 
    } 
); 

Google OAuth2 API (dla OpenID Połącz) dokumentację można znaleźć tutaj: https://developers.google.com/identity/protocols/OpenIDConnect#authenticationuriparameters

PS : Jeśli nie potrzebujesz sekcji oauth2 w twoim manifeście. Możesz go bezpiecznie pominąć i podać identyfikatory i zakresy tylko w kodzie.

EDYCJA: Dla zainteresowanych nie potrzebujesz interfejsu API tożsamości. Możesz nawet uzyskać dostęp do tokena za pomocą małej sztuczki z interfejsem API. Kod jest trochę dłuższy, ale masz lepsze komunikaty o błędach i kontrolę. Pamiętaj, że w poniższym przykładzie musisz utworzyć poświadczenia Chrome App.

manifest.json:

{ 
    "manifest_version": 2, 
    "name": "name", 
    "description": "description", 
    "version": "0.0.0.1", 
    "background": { 
    "scripts": ["background.js"] 
    }, 
    "permissions": [ 
    "tabs" 
    ], 
    "oauth2": { 
    "client_id": "<CLIENT_ID>.apps.googleusercontent.com", 
    "scopes": [ 
     "openid", "email", "profile" 
    ] 
    } 
} 

background.js:

// Using chrome.tabs 
var manifest = chrome.runtime.getManifest(); 

var clientId = encodeURIComponent(manifest.oauth2.client_id); 
var scopes = encodeURIComponent(manifest.oauth2.scopes.join(' ')); 
var redirectUri = encodeURIComponent('urn:ietf:wg:oauth:2.0:oob:auto'); 

var url = 'https://accounts.google.com/o/oauth2/auth' + 
      '?client_id=' + clientId + 
      '&response_type=id_token' + 
      '&access_type=offline' + 
      '&redirect_uri=' + redirectUri + 
      '&scope=' + scopes; 

var RESULT_PREFIX = ['Success', 'Denied', 'Error']; 
chrome.tabs.create({'url': 'about:blank'}, function(authenticationTab) { 
    chrome.tabs.onUpdated.addListener(function googleAuthorizationHook(tabId, changeInfo, tab) { 
     if (tabId === authenticationTab.id) { 
      var titleParts = tab.title.split(' ', 2); 

      var result = titleParts[0]; 
      if (titleParts.length == 2 && RESULT_PREFIX.indexOf(result) >= 0) { 
       chrome.tabs.onUpdated.removeListener(googleAuthorizationHook); 
       chrome.tabs.remove(tabId); 

       var response = titleParts[1]; 
       switch (result) { 
        case 'Success': 
         // Example: id_token=<YOUR_BELOVED_ID_TOKEN>&authuser=0&hd=<SOME.DOMAIN.PL>&session_state=<SESSION_SATE>&prompt=<PROMPT> 
         console.log(response); 
        break; 
        case 'Denied': 
         // Example: error_subtype=access_denied&error=immediate_failed 
         console.log(response); 
        break; 
        case 'Error': 
         // Example: 400 (OAuth2 Error)!!1 
         console.log(response); 
        break; 
       } 
      } 
     } 
    }); 

    chrome.tabs.update(authenticationTab.id, {'url': url}); 
}); 
+0

Cześć Piotr. Próbowałem Twojego rozwiązania, ale dostaję * Nie można załadować strony autoryzacji * błąd. Robię dokładnie to, co robisz, z tymi samymi zakresami w manifeście. –

+0

Witaj @ Egidius, wymyśliłeś to? Mam ten sam problem. Dzięki. – rsb

+0

@Aegidius, to samo tutaj, nie jestem pewien, czy ta metoda jest nadal ważna? – seesoe