Dropbox integration using OAuth 2.0 authentication
Like many web services, Dropbox API allows its clients to use OAuth 2.0 as an authentication method. Let's dive in a tutorial on how to authenticate yourself to Dropbox to make your user Dropbox account accessible from your processes, and leverage the tools provided by the RunMyProcess platform to manage easily your OAuth 2.0 credentials.
Since OAuth 2.0 is a standard now, you will be able to use the techniques described in this tutorial to access many other OAuth 2.0 compatible web services (Google, Microsoft, ...).
Setting up your Dropbox application
The first step to be able to access the Dropbox API using OAuth 2.0 is to register your application to Dropbox, that will allow you to get some id, passwords (secrets) and other information (called credentials in this document) needed to create tokens that will be used to eventually access the API. These credentials should be stored in a secure environment (for example your project vault, more on that later). The tokens created using these credentials are unique for each user accessing the API and should also be kept in a secure place, like the OAuth service tokens store, another service provided by the platform.
To create your new Dropbox application, please go to the Dropbox developer app console, and click the Create app
button, then fill in the required information (what kind of app are you creating (surely a Dropbox API app), what kind of documents your app will access/create, and of course the name of your application !)
When your app is created, you are able to access its information page, where you can get your app key and app secret, and set your OAuth 2.0 redirect URIs, but before using that we need to create a couple of web interfaces in our Dropbox RunMyProcess project.
Setting up your RunMyProcess application
If needed, create a new project, that will host our web interfaces, processes and composite APIs used to access our Dropbox files. The first web interface will be used to ask a user of your application to authorize your Dropbox application to access his/her Dropbox, basically it is used to redirect the user to the Dropbox authorize page, passing some useful parameters. When this redirection is done, the user is presented an authorize page, hosted by Dropbox, showing him/her the name of the application that is asking for the access, and the rights/permissions that this application is asking for, something like :
1 |
|
If the user agrees to this, Dropbox will redirect him/her to the specified redirect URI
(a parameter sent by the first web interface during the first redirect), this URI points to the second web interface that we will have to design. This second web interface will be called with some codes, that we will have to convert to some access token and then store these tokens to access the Dropbox API later on. And yes, this redirect URI must be in the configured redirect URIs list in your Dropbox project app console configuration page.
Are you still reading ? ;-)
Well OAuth 2.0 may seem a little bit complex at first sight, but everything will be clear when all our resources are up and running.
To make things even simpler, we will need the url of the second web interface, in the first web interface, and in the Dropbox app console, so we will start by designing this second interface first !
Web interface callback and associated composite API
This web interface will be called by Dropbox after the user has authorized our Dropbox application to access his/her files. The access token will be generated by using a code that is provided in the query string of the callback url, and we will have to store this token in the OAuth service store of the user. We can do that by calling a composite API, from the web interface. To convert the returned code to an access token, we will need to send a request to Dropbox OAuth 2.0 API, to do that, let's create a new connector:
- From your project home page, create a new web service provider by clicking the
New...
button and selectingProvider
, name itDropbox OAuth
for example, - Set the url for each mode to : https://
api.dropbox.com/1/oauth2/
- Set the
Authentication scheme
for each mode to :Login / Password
- Set the
Login
field for each mode to your application key, found in the developer app console - Set the
Password
field for each mode to your application secret, found in the developer app console
- Save the provider, and click on the
New Connector
button - Set the name of the connector to
Dropbox OAuth Token
for example - Set the connector url to :
token?code=${authorization_code}&grant_type=authorization_code&redirect_uri=yourCallbackUrl
, do not forget to replace theyourCallbackUrl
placeholder with your own callback url, that we will get in a few steps (yes there is an egg and chicken problem here ;-)) - Set the
Method
,Result format
,Accept media type
andContent-type
as shown in the screenshot below:
Now let's create the CAPI:
- From your project home page, create a new composite API by clicking the
New...
button and selectingComposite API
, name this CAPIDropbox OAuth Token Registration
for example, - Make sure to set the
Accept media type
,Input validation
,Result media type
andResult transformation
fields of theConfiguration
tab as shown in the screenshot below :
Here we have created a new CAPI, that will be called using a POST method, its expecting a Json object in the request body, with one field : code
.
- The design of the CAPI cannot be much simpler :
Here we have only two tasks, the first one will call the Dropbox OAuth API to convert the code to an access token, then this token is saved into the current user OAuth service token vault by calling the P_save_oauth2_token()
method. Once done, the tokens associated to the current user are kept in a secure place, and will be easily retrieved by a connector configured to access the user's Dropbox. Of course here we have used dropbox
as a service name, but you can use any name you want.
So now, we have all the needed resources to design our callback web interface, that will be called by Dropbox after the user has authorized our application to access his/her files.
- From your project home page, create a new web interface by clicking the
New...
button and selectingWeb interface
, name itDropbox OAuth Token Authorize Callback
for example, - Go to the
API listener
tab, and add an API listener by choosing ourDropbox OAuth Token Registration
CAPI, - Select the
Manually via Javascript
method call - Make sur that the API listener id is
id_dropbox_oauth_token
:
- And now, the web interface design, from the
Design
tab:- Add a static text area, fill it with some greetings text to inform the user that he/she has sucessfully authorized the application to access his/her Dropbox files,
- Add a Javascript component, with an empty name to make it invisible
Set its script to :
1 2 3 4 5 6 7 8 |
|
Basically here we are triggering the registration CAPI with some parameters. Dropbox will pass the code
via the url query string in a parameter named code
and we are setting the refresh_token
to an empty value (more on this later). A successful call will be silent, but a failure will display an alert box to inform the user. Of course this is a very simplistic way of handling the registration, feel free to add/change the web interface to adapt it to your case.
- Your web interface should look like this :
That's it for the web interface callback, now let's design the first web interface, the one we will use to redirect the user to the Dropbox authorize page.
By the way, do not forget to replace the yourCallbackUrl
placeholder of the Dropbox OAuth Token
connector url, with the url of this new web interface.
Go to Dropbox authorize page web interface
This web interface only purpose is to redirect the user to the authorize Dropbox page. If the user is not already logged to his/her Dropbox account, a login page will be displayed before the authorize page, otherwise the authorize page is displayed right away, asking the user if he/she is with the fact that our Dropbox application will be able to access his/her Dropbox files.
The redirection url must contain three parameters: a client id which is the Dropbox application key shown in the Dropbox developer application console, and a redirection URI, which must be one of the redirection URI listed in the same Dropbox developer application console, if the URI doesn't match a listed URI Dropbox will refuse to display the authorize page, to avoid to send an access token to an unknown URI. In our case this redirection URI is, of course, the url of our Dropbox callback web interface.
Please note that, as usual, you can get an url per execution mode of the web interface, so be careful when you configure your URIs in the developer application console. During the development period you should use the TEST mode url, and when the Dropbox application is set to production, you can switch to the LIVE mode url (you can also list the three urls (LIVE, ACCEPTANCE, TEST) in the application console).
The third parameter, named state
is sent to Dropbox, and will be sent back by Dropbox, as a parameter to the web interface callback, this can be used to retrieve some contextual information or check that the callback is really related to an authorization initiated by us.
So let's create this web interface !
- From your project home page, create a new web interface by clicking the
New...
button and selectingWeb interface
, name itDropbox OAuth Token Redirector
for example, - Go to the
design
tab, and add an statix text area, fill it in with some text to explain the user that he/she will be redirected to his/her Dropbox account to authorize the application to access his/her files, - Add a button, name it
Authorize
for example, and set its action toExecute script
, set itson click
action toRedirect
Use this code in the script
settings of the button:
1 |
|
Here we are encoding the callback url to use it in a request query string, so do not forget to adapt the code and use your own web interface callback (created above) url, specifically replace the yourCustomerId
and yourCallbackId
placeholders.
Use this in the url
settings of the button:
1 |
|
Do not forget to replace the yourAppKey
placeholder, using your own app key found in the Dropbox developer application console.
- Your web interface should look like this :
Well done ! So now we have everything to generate a Dropbox access token:
- Launch the Dropbox OAuth Token Redirector
web interface
- Click on the Authorize
button
- Sign in to your Dropbox account if needed
- Authorize the Dropbox application to access your files
- When the Dropbox OAuth Token Callback
web interface is called, the access token is save into your OAuth 2.0 Service Token vault, you can check that in your settings view :
- Go to My Settings
view, and click on the OAuth2 Services
tab :
This view lists the known OAuth 2.0 services, that is the service names used with the P_save_oauth2_token()
function.
Please note that deleting a token from this list, does not revoke the access token, to do that you have to go to your service account page, and revole the access from there. For example, to revoke a Dropbox access token, go to your Dropbox account security page.
Let's use this access token now !
Dropbox connector with OAuth 2.0 authentication
At last ! here is the acme of this tutorial: we will access our Dropbox data ! Now that we have an OAuth 2.0 access token, securely stored into our OAuth service tokens vault, let's use it in a web connector.
- From your project home page, create a new web service provider by clicking the
New...
button and selectingProvider
, name itDropbox Account
for example, - Set the url for each mode to : https://
api.dropbox.com/1/account/
- Set the
Authentication scheme
for each mode to :OAuth v2
- Set the
Access
token field for each mode to :${P_get_oauth2_token('dropbox').access_token}
- Save the provider, and click on the
New Connector
button - Set the name of the connector to
Dropbox Account Information
for example - Set the connector url to :
info
- Set the
Method
,Result format
andAccept media type
as shown in the screenshot below:
And now ! the best part of this tutorial ! Click on the Launch Test
link and then on the Launch Test
button, and if everything goes well you should receive some JSON with your own Dropbox account information.
Well, no magic here ;-) we are just calling a Dropbox API using an OAuth 2.0 access token, retrieved from our OAuth service tokens vault, using the P_get_oauth2_token()
method.
Refreshing an access token
Well that was a lot of things to get into, and we are now nearly at the end of this tutorial. But we have still one more thing to deal with: in some case you will have to refresh your access token. Indeed, some services will send you an access token with a limited validity lifetime, when this period is over you will have to use the refresh token sent to you, at the same time you got the access token, to get a new access token.
Dropbox OAuth implementation does not use refresh tokens (an access token is then valid until its owner revoke it), so we will use an example based on Google OAuth 2.0 web services.
In our tutorial, in the Dropbox OAuth Token Registration
CAPI, when we have converted the code to an access token, we have just received an access token, no refresh token. Imagine that instead of that, we had received an access token and a refresh token, and saved both of them in our 'dropbox' OAuth token vault (in fact we have done that, but with an empty ""
refresh token value, so you can use this same code, but with a real value).
The RunMyProcess platform provides some tools to easily use the refresh token. The first one is of course the OAuth service tokens vault, that can hold an access token and a refresh token:
1 2 |
|
The second one, is the possibility to assign a composite API to the authentication method of an OAuth 2.0 connector :
This CAPI will be called in cases where a first try to call the connector will result in a 401/Access unauthorized
HTTP result code. This is the result code received when we try to use an outdated access token. It is time then to refresh the access token, using the refresh token.
The refresh token CAPI will have exactly the same design as the token registration CAPI: a call to the web service provider refresh token service, then we save the new access token, received as a result from this service call (we save the new access token to make it available for a future call of the OAuth 2.0 authenticated connector, via the P_get_oauth2_token('dropbox').access_token
instruction), and the CAPI has to return a JSONObject with one mandatory field : access_token
that will be used during the second try to call the connector. If this fails, then the connector call returns with a failure message.
Let's have a look at such a composite API, designed to refresh a Google API access token.
First we need to configure a new provider and an associated connector, to call the refresh token service provided by Google.
- From your Google OAuth 2.0 project home page (yes we are now using Google OAuth 2.0 services, so let's do this in an appropriate project), create a new web service provider by clicking the
New...
button and selectingProvider
, name itGoogle OAuth 2.0
for example, - Set the url for each mode to : https://
www.googleapis.com/oauth2/v3/
- Set the
Authentication scheme
for each mode to :None
- Save the provider, and click on the
New Connector
button - Set the name of the connector to
Google OAuth 2.0 Token
for example - Set the connector url to :
token
- Set the
Method
,Result format
,Accept media type
,Content-type
andContent
as shown in the screenshot below:
Let's have a closer look at the content of the connector :
1 |
|
These are the mandatory parameters we have to send to the token service, as documented in the Google OAut 2.0 API official page.
We have to pass some credentials (client_id
and client_secret
(called app key
and app secret
in the Dropbox world)), the refresh_token
of course and ask google to send us a new access_token
by setting the grant_type
parameter to refresh_token
.
Our refresh token is securely stored in our OAuth2 service tokens vault, so we could also retrieve it from there :
1 |
|
The client_id
and client_secret
can also be saved in a secure place : the Project Vault. This vault can contain a JSONObject of any form, and its content is crypted so that you can put some credentials in it. We could have filled in this vault just after creating our new Google OAuth 2.0 application with the client_id and client_secret information grouped in a googleapi
field, then use this content in our token connector :
1 |
|
Ok, now we can design our Google OAuth 2.0 Refresh Token
CAPI :
- From your Google OAuth 2.0 project home page, create a new composite API by clicking the
New...
button and selectingComposite API
, name this CAPIGoogle OAuth 2.0 Refresh Token
for example, - Make sure to set the
Method
,Result media type
andResult transformation
fields of theConfiguration
tab as shown in the screenshot below :
Here we have created a new CAPI, that will be called using a GET
method.
The result of the CAPI will be a JSONObject, with only one field : access_token
which value will be found in the CAPI computed variables (see below)
- The design of the CAPI is again very simple :
Here we have only two tasks, the first one will call the Google OAuth API to convert a refresh token to an access token, then this token is saved into the current user OAuth service token vault by calling the P_save_oauth2_token()
method, after updating the current service tokens retrieved by calling P_get_oauth2_token()
.
You just have to associate this CAPI to the Google API providers you want to use, and in case of an outdated access token, it will be refreshed automatically.
Wow ! There are a lot of things to digest here, but everything is now in place to leverage OAuth 2.0 authenticated web services, so now it is your turn !
See also
The official OAuth 2.0 specifications
The official OAuth 2.0 web site
The Dropbox blog explaining how to use OAuth 2.0 with Dropbox API
The Dropbox developer site
The Dropbox developer App console
The Dropbox core api documentation
The RunMyProcess Freemarker API documentation, where you can find the documentation of the project vault API and OAuth service tokens API in the Request section.
Please give details of the problem