0

I have high volume multi threaded java based application which needs to call REST based endpoints running on Microsoft cloud with Authorization token in the header retrieved using "Azure ADAL AcquireToken". I am using "AzureAD/azure-activedirectory-library-for-java" (Code sample below). Questions I have are -

  1. Do I need to make a call to retrieve the token using acquireToken method for each and every REST call I am going to make? If yes, then I believe the token I am going to get with latest call may change, then in that case are the requests if I have requests already made with previously retrieved tokens going to fail or Azure ADAL will still going to honor all the previously generated tokens?
  2. If token retrieved previously are not expected to be honored by Azure ADAL then what options I have to manage single token at a time and then making sure at a time only one token is used by all the requests? Do I need to implement some kind of single threaded cache to retrieve a token, maintain that token until it expires, make a call to get new token if expired and make all my multi threaded requests go through this single threaded cache to get the latest token? Any suggestions on this. If this is the case then its seems like a huge bottleneck in high volume multi threaded multi jvm application as far as scalability goes.

My code below. When I called the acquireToken method from a loop inside the main method, I mostly got 3 different types of token in 10 calls and all 3 different tokens seemed to work, but not sure if that how it should be called in a multi threaded applications.

package com.mycompany.msft.auth;

import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;

import com.microsoft.aad.adal4j.AuthenticationContext;
import com.microsoft.aad.adal4j.AuthenticationResult;
import com.microsoft.aad.adal4j.ClientCredential;

public class ApplicationAuthExample {
    private final static String AUTHORIZATION_ENDPOINT = "https://login.microsoftonline.com/";
    private final static String ARM_ENDPOINT = "https://myendpoint";


    private static String credential = "my credential";
    private static String clientId = "my client id";
    private static String tenantId = "my tenant id";

    private static String url = AUTHORIZATION_ENDPOINT + tenantId ;

    AuthenticationContext context = null;
    AuthenticationResult result = null;
    ExecutorService service = null;

    public  AuthenticationResult getAuthToken() {
        try {
            service = Executors.newFixedThreadPool(1);


            context = new AuthenticationContext(url, false, service);

            Future<AuthenticationResult> future = null;


                ClientCredential cred = new ClientCredential(clientId, credential);
                future = context.acquireToken(ARM_ENDPOINT, cred, null);


            result = future.get();
        } catch (Exception ex) {
            System.out.println("Exception occurred:");
            ex.printStackTrace();
            System.exit(1);
        } finally {
            service.shutdown();
        }
        return result;
    }

    public static void main(String[] args) throws Exception {

        ApplicationAuthExample auth = new ApplicationAuthExample();

        for (int i =0 ; i< 10 ; i++) {
            AuthenticationResult result = auth.getAuthToken();
            // use adal to Authenticate

            System.out.println (i+ " Authorization" + "Bearer " + result.getAccessToken());
            System.out.println (i + " getExpiresOn" + result.getExpiresOn());

            //This token comes different in different calls. Which one should I use and which one not. 
            System.out.println (i+ " getExpiresOn" + result.getRefreshToken());


            System.out.println (i+" getExpiresOn" + result.getUserInfo());
            }

    }
}
akg
  • 3
  • 3

1 Answers1

0

Per my experience, I think the key of the issue is the expiration time of the token. You can use the token as your wish after it expire. You can refer to the section Claims in id_tokens of https://azure.microsoft.com/en-us/documentation/articles/active-directory-v2-tokens/ to know that the token claim the time include Issued At, Expriation Time & `Not Before.

So you will need to use adal4j to acquire the token and request a refresh token when the previous one expires.

The lifetime of a default security token for a claims-based authentication deployment using AD FS 2.0 is 60 minutes.

If you want to increase the token expiration time of Azure AD, you can try to refer to the doc https://technet.microsoft.com/en-us/library/gg188586.aspx to configure the relying party token lifetime.

Peter Pan
  • 23,476
  • 4
  • 25
  • 43
  • Thank you Peter! Does this mean we (consumer of token) needs to maintain first token and then refresh of token logic? – akg Jan 25 '16 at 21:13
  • @akg Yes. We need to maintain the token. When a token was invalid, we need to request a new one. – Peter Pan Jan 29 '16 at 01:58