Jetzt verfügbar:  Berichte für DRACOONMehr Infos

OAuth in Access Code Mode - staying authorized

Kommentare

7 Kommentare

  • Avatar
    Mathias Schreiner

    Hey Nick,

    you can do this in the way described below:

    ```

    // First time authorization

    DracoonClient client1 = null;
    String authCode = authorizeClient(CLIENT_ID, CLIENT_SECRET);
    DracoonAuth auth1 = new DracoonAuth(CLIENT_ID, CLIENT_SECRET, authCode);
    client1 = new DracoonClient.Builder(new URL(SERVER_URL)).auth(auth1).build();
    client1.account().getUserAccount();

    // If you have authorized for the first time you can access the tokens this way

    String accessToken = client1.getAuth().getAccessToken();
    String refreshToken = client1.getAuth().getRefreshToken();

    // TODO persist tokens

    // You can then initialize the client on subsequent runs this way

    // TODO read tokens

    DracoonAuth auth2 = new DracoonAuth(CLIENT_ID, CLIENT_SECRET, ACCESS_TOKEN, REFRESH_TOKEN);
    DracoonClient client2 = new DracoonClient.Builder(new URL(SERVER_URL)).auth(auth2).build();
    client2.account().getUserAccount();

    ```
    0
    Aktionen für Kommentare Permalink
  • Avatar
    Nick Horatiu

    Hello Mathias,

    Thank you for your prompt reply. 

    I have already tried to take that approach and got "null" result for those two calls despite internal member fields corresponding to tokens being initialized as you can see in the screenshot below. 

    In this example, I'm making a call to the API with the access code, the internal class member do get populated with tokens but I'm not able to retrieve them and use them as indicated. 

     

    0
    Aktionen für Kommentare Permalink
  • Avatar
    Mathias Schreiner

    You are right, this seems to be an issue on the master branch from which the current maven artifact is build.

    It's fixed on the develop branch:
    https://github.com/dracoon/dracoon-java-sdk/blob/develop/src/main/java/com/dracoon/sdk/internal/DracoonClientImpl.java#L293

    0
    Aktionen für Kommentare Permalink
  • Avatar
    Nick Horatiu

    Thanks, Mathias, I've made the necessary corrections in the source code of the SDK library.

    Refreshing the access token will probably happen each time the app is restarted because the field mOAuthLastRefreshTime will be 0L on a new app start and this condition will always be true: 

    // If OAuth tokens validity has been exceeded: Refresh tokens
    long nextRefreshTime = mOAuthLastRefreshTime +
    DracoonConstants.AUTHORIZATION_REFRESH_INTERVAL;
    long currentTime = System.currentTimeMillis();
    if (nextRefreshTime < currentTime) {
          refreshOAuthTokens();
    }

    However, I suppose refresh token, even though a long lived token, will have to be refreshed from time to time. This is most likely done via reauthorization using web browser. However, how can I detect programmatically that this is indeed the case? Will I get a specific exception when making any of the calls requiring authentication (e.g. client.nodes().getNodes(0L) ) ?

    0
    Aktionen für Kommentare Permalink
  • Avatar
    Mathias Schreiner

    If both access token and refresh token are invalid the next request will throw an exception.

    0
    Aktionen für Kommentare Permalink
  • Avatar
    Bernd Hort

    Maybe it would a good idea to update the sample class OAuthExamples from the SDK. The call

    client.account().getUserAccount();

    is far from being intuitive. Specially since there is no member information in UserAccount regarding the access token or refresh token.

    Also an enhancement to the code would be to give a log warning in client.getAuth().getAccessToken() if access token is null in the form
    "access token will be retrieved via client.account.getUserAccount()".

    0
    Aktionen für Kommentare Permalink
  • Avatar
    Matthias Kellnhofer

    The OAuth tokens aren't retrieved by calling getUserAccount(). They are retrieved when the first API call is made.

    Maybe we should move this initialization to a separate method (e.g. DracoonClient::init()) and allow users/developers to call it before using the client to make API calls.

    Thanks for the feedback!

    0
    Aktionen für Kommentare Permalink

Bitte melden Sie sich an, um einen Kommentar zu hinterlassen.