Call an Identity Provider API

Call an Identity Provider API

Once you successfully authenticate a user with an external Identity Provider (IdP), such as Facebook or GitHub, the IdP often includes an Access Token in the user profile it returns to Auth0.

You can retrieve and use this token to call the IdP's API.

The process you will follow differs depending on whether your code runs in the backend or the frontend:

  • If your code runs in the backend, then we can assume that your server is trusted to safely store secrets (as you will see, we use a secret in the backend scenario). If that's the case, proceed to the backend section of this article.

  • If your code runs in the frontend (for example, it's a SPA, native desktop, or mobile app), then your app cannot hold credentials securely and has to follow an alternate approach. In this case, proceed to the frontend section of this article.

From the backend

Once you authenticate a user, the IdP often includes an Access Token in the user profile it returns to Auth0.

For security and compliance reasons, Auth0 does not send this token to your app as part of the user profile. To get it, you must access the Auth0 Management API and retrieve the full user's profile:

  1. Get an Access Token that allows you to call the Auth0 Management API.

  2. Call the Auth0 Management API's Get Users by ID endpoint using the Access Token obtained in step one. This endpoint returns the full user's profile, which contains the IdP Access Token.

  3. Extract the IdP Access Token from the response and use it to call the IdP's API.

Step 1: Get a Token

You will need an Access Token to call the Management API.

Create a test application for the Management API

If this is the first time you are requesting a Management APIv2 Token, you will need to create and configure an application that can be used to call the Management API:

  1. Navigate to Auth0 Dashboard > Applications > APIs, and select the Auth0 Management API.

  2. Select the API Explorer view, and click Create & Authorize a Test Application.

This will create a new application and grant all scopes of the Management API, which means that the tokens generated for this application will be able to access all Management API endpoints.

Can't see the button?

If you don't see this button, it means that you already have at least one authorized application for the Management API. In this case, you can either update the scopes of the existing application and use that, or create a new one following these steps:

  1. Navigate to Auth0 Dashboard > Applications > Applications, and select Create Application.

  2. Select Machine to Machine Applications, and then Create.

  3. From the Select an API dropdown, select Auth0 Management API.

  4. Enable required scopes, and select Authorize.

  5. Select the APIs view, and enable the toggle for Auth0 Management API.

To grant or remove scopes from the registered Auth0 Management API, select the Machine to Machine Applications view:

Edit the scopes granted to the Application

Get the Management API Token

You are now done with configuration and are ready to get your Management API token:

  1. From the registered Auth0 Management API, select the Test view.

  2. Choose your application from the Application dropdown to pre-populate the ready-to-use snippets with customized variables.

  3. Choose your language of preference for the snippet, and copy and run it.

  4. Extract the access_token property from the response. This is what you will use to access the Management API.

What are the snippets doing?

The snippets make a POST operation to the /oauth/token endpoint of the Auth0 Authentication API, using the OAuth 2.0 Client Credentials grant. This is the grant that machine-to-machine processes use to access an API. To learn more about the flow, read Client Credentials Flow.

Token expiration

By default, the token you received expires in 24 hours (86,400 seconds). To change this:

  1. Navigate to Auth0 Dashboard > Applications > APIs, and select the Auth0 Management API.

  2. Select the Settings view, locate the Token Expiration (Seconds) field, enter a new value, and click Save. The maximum value you can set is 2,592,000 seconds (30 days), though we recommend that you keep the default value.

The next token you generate will use the updated expiration time.

Step 2: Get the full User Profile

To get a user's profile, call the Get a User endpoint of the Management API using the Access Token you extracted in the previous section:


curl --request GET \
  --url 'https://{yourDomain}/api/v2/users/%7BuserId%7D' \
  --header 'authorization: Bearer {yourAccessToken}'

Was this helpful?

/
var client = new RestClient("https://{yourDomain}/api/v2/users/%7BuserId%7D");
var request = new RestRequest(Method.GET);
request.AddHeader("authorization", "Bearer {yourAccessToken}");
IRestResponse response = client.Execute(request);

Was this helpful?

/
package main

import (
	"fmt"
	"net/http"
	"io/ioutil"
)

func main() {

	url := "https://{yourDomain}/api/v2/users/%7BuserId%7D"

	req, _ := http.NewRequest("GET", url, nil)

	req.Header.Add("authorization", "Bearer {yourAccessToken}")

	res, _ := http.DefaultClient.Do(req)

	defer res.Body.Close()
	body, _ := ioutil.ReadAll(res.Body)

	fmt.Println(res)
	fmt.Println(string(body))

}

Was this helpful?

/
HttpResponse<String> response = Unirest.get("https://{yourDomain}/api/v2/users/%7BuserId%7D")
  .header("authorization", "Bearer {yourAccessToken}")
  .asString();

Was this helpful?

/
var axios = require("axios").default;

var options = {
  method: 'GET',
  url: 'https://{yourDomain}/api/v2/users/%7BuserId%7D',
  headers: {authorization: 'Bearer {yourAccessToken}'}
};

axios.request(options).then(function (response) {
  console.log(response.data);
}).catch(function (error) {
  console.error(error);
});

Was this helpful?

/
#import <Foundation/Foundation.h>

NSDictionary *headers = @{ @"authorization": @"Bearer {yourAccessToken}" };

NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:[NSURL URLWithString:@"https://{yourDomain}/api/v2/users/%7BuserId%7D"]
                                                       cachePolicy:NSURLRequestUseProtocolCachePolicy
                                                   timeoutInterval:10.0];
[request setHTTPMethod:@"GET"];
[request setAllHTTPHeaderFields:headers];

NSURLSession *session = [NSURLSession sharedSession];
NSURLSessionDataTask *dataTask = [session dataTaskWithRequest:request
                                            completionHandler:^(NSData *data, NSURLResponse *response, NSError *error) {
                                                if (error) {
                                                    NSLog(@"%@", error);
                                                } else {
                                                    NSHTTPURLResponse *httpResponse = (NSHTTPURLResponse *) response;
                                                    NSLog(@"%@", httpResponse);
                                                }
                                            }];
[dataTask resume];

Was this helpful?

/
$curl = curl_init();

curl_setopt_array($curl, [
  CURLOPT_URL => "https://{yourDomain}/api/v2/users/%7BuserId%7D",
  CURLOPT_RETURNTRANSFER => true,
  CURLOPT_ENCODING => "",
  CURLOPT_MAXREDIRS => 10,
  CURLOPT_TIMEOUT => 30,
  CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
  CURLOPT_CUSTOMREQUEST => "GET",
  CURLOPT_HTTPHEADER => [
    "authorization: Bearer {yourAccessToken}"
  ],
]);

$response = curl_exec($curl);
$err = curl_error($curl);

curl_close($curl);

if ($err) {
  echo "cURL Error #:" . $err;
} else {
  echo $response;
}

Was this helpful?

/
import http.client

conn = http.client.HTTPSConnection("")

headers = { 'authorization': "Bearer {yourAccessToken}" }

conn.request("GET", "/{yourDomain}/api/v2/users/%7BuserId%7D", headers=headers)

res = conn.getresponse()
data = res.read()

print(data.decode("utf-8"))

Was this helpful?

/
require 'uri'
require 'net/http'
require 'openssl'

url = URI("https://{yourDomain}/api/v2/users/%7BuserId%7D")

http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
http.verify_mode = OpenSSL::SSL::VERIFY_NONE

request = Net::HTTP::Get.new(url)
request["authorization"] = 'Bearer {yourAccessToken}'

response = http.request(request)
puts response.read_body

Was this helpful?

/
import Foundation

let headers = ["authorization": "Bearer {yourAccessToken}"]

let request = NSMutableURLRequest(url: NSURL(string: "https://{yourDomain}/api/v2/users/%7BuserId%7D")! as URL,
                                        cachePolicy: .useProtocolCachePolicy,
                                    timeoutInterval: 10.0)
request.httpMethod = "GET"
request.allHTTPHeaderFields = headers

let session = URLSession.shared
let dataTask = session.dataTask(with: request as URLRequest, completionHandler: { (data, response, error) -> Void in
  if (error != nil) {
    print(error)
  } else {
    let httpResponse = response as? HTTPURLResponse
    print(httpResponse)
  }
})

dataTask.resume()

Was this helpful?

/

Replace these values:

  • {userId}: ID of the user for whom you want to call the IdP's API.

  • {yourAccessToken}: Access Token you extracted in the previous section.

Where do I find the User ID?

  • For your implementation, you can either extract the user ID from the sub claim in the ID Token, or call the /userinfo endpoint of the Authentication API and extract it from the user_id response property.

Step 3: Extract the IdP Access Token

You can find the Access Token used to call the IdP's API within the user's identities array: user.identities[0].access_token.

In most cases, the user will only have one identity, but if the user has signed in multiple times through different connections and you have used account linking, there may be more.

In this sample response, we see that our user has only one identity: google-oauth2.

{
  "email": "john.doe@test.com",
  "email_verified": true,
  "name": "John Doe",
  "given_name": "John",
  "family_name": "Doe",
  "picture": "https://myavatar/photo.jpg",
  "gender": "male",
  "locale": "en",
  "updated_at": "2017-03-15T07:14:32.451Z",
  "user_id": "google-oauth2|111199914890750704174",
  "nickname": "john.doe",
  "identities": [
    {
      "provider": "google-oauth2",
      "access_token": "ya29.GlsPBCS6ahokDlgCYnVLnDKNE71HBXPEzNhAPoKJLAGKDSe1De3_xclahNcdZXoU-26hCpa8h6240TV86dtaEQ4ZWoeeZduHDq_yeu9QyQqUr--S9B2CR9YJrLTD",
      "expires_in": 3599,
      "user_id": "111199914890750704174",
      "connection": "google-oauth2",
      "isSocial": true
    }
  ],
  "created_at": "2017-03-15T07:13:41.134Z",
  "last_ip": "127.0.0.1",
  "last_login": "2017-03-15T07:14:32.451Z",
  "logins_count": 99
}

Was this helpful?

/

You are now ready to call the IdP's API. Please refer to the IdP's documentation for specifics on how to do so.

From the frontend

If you are working with a public application (SPA, native desktop, or mobile app), then this is the place to be.

When working with a frontend app, the process for calling IdP APIs differs from the backend process because frontend apps are public applications that cannot hold credentials securely. Because SPA code can be viewed and altered, and native/mobile apps can be decompiled and inspected, they cannot be trusted to hold sensitive information like secret keys or passwords.

Specifically, they cannot securely hold the Client Secret for the Machine to Machine Application, which you use to call /oauth/token during the first step of the backend process.

Instead, you must build a proxy for your backend and expose it to your application as an API.

Build a proxy

First, you will build a process in your backend that will implement the steps included in the backend section of this article, and expose it to your application as an API.

You will call the IdP's API from the same backend process, so the Access Token is never exposed to your public application.

Then, you will call your proxy API from your public application using the Authorization Code Flow with Proof Key for Code Exchange (PKCE).

Show me how

If you haven't implemented this before, you might find our Single-page Applications (SPA) with API architecture scenario useful. It covers a different scenario, but it explains how to configure Auth0, how to call an API from a SPA, and how to implement API validations. It comes with a sample that uses Angular 2 and Node.js.

We also offer a Mobile Applications with API variation (the sample uses Android and Node.js).