Skip to content
This repository has been archived by the owner on Dec 13, 2018. It is now read-only.

Commit

Permalink
more documentation updates
Browse files Browse the repository at this point in the history
  • Loading branch information
Robert committed Nov 6, 2015
1 parent ebf6f6f commit 48be3e7
Show file tree
Hide file tree
Showing 3 changed files with 151 additions and 89 deletions.
30 changes: 15 additions & 15 deletions README.md
Expand Up @@ -76,9 +76,10 @@ Follow these steps to add Stormpath user authentication to your Express.js app.
}));
```

If your app is a single page application (Angular, React), you will need to
tell our library where the root file is. For example, if your Angular app is
in the `client/` folder in your project:
**If your app is a single page application (Angular, React)**

You will need to tell our library where the root file is. For example, if
your Angular app is in the `client/` folder in your project:

```javascript
app.use(stormpath.init(app, {
Expand All @@ -89,17 +90,6 @@ Follow these steps to add Stormpath user authentication to your Express.js app.
}));
```

**If your app is an API service:**

If your application is an API service that requires the use of OAuth Bearer
Tokens, then enable the API option:

```javascript
app.use(stormpath.init(app, {
api: true
}));
```

*[Read more about the initialization in the documentation →][]*

8. **Wait For The SDK**
Expand All @@ -116,14 +106,24 @@ Follow these steps to add Stormpath user authentication to your Express.js app.

9. **Protect Your Routes**

Use `stormpath.loginRequired` as a middleware to protect your routes:
For websites and Single-Page Apps, use `stormpath.loginRequired` as a
middleware to protect your routes:

```javascript
app.get('/secret', stormpath.loginRequired, function (req, res) {
//...
});
```

For API services that use HTTP Basic Auth or OAuth2, use
`stormpath.apiAuthenticationRequired`:

```javascript
app.get('/secret', stormpath.apiAuthenticationRequired, function (req, res) {
//...
});
```

If the user tries to access this route without being logged in, they will be redirected to the login page.

10. **Login**
Expand Down
145 changes: 92 additions & 53 deletions docs/authentication.rst
Expand Up @@ -3,19 +3,19 @@
Authentication
==============

This library offers several options for securing your server and authenticating
your users. Which strategy should you use? The answer depends on your use
case, and we'll discuss each one in detail. But at a high level, your choices
look like this:
This library offers several options for securing your application and
authenticating your users. Which strategy should you use? The answer depends
on your use case, and we'll discuss each one in detail. But at a high level,
your choices look like this:

* If you are building a traditional web app or single page application, you
should use **Cookie Authentication**.

* If you are building a mobile application, you should use the **OAuth2
Password Grant**.

* If you are building an API service, you can **HTTP Basic Authentication** or
**OAuth2 Client Credentials**.
* If you are building an API service, you can use
**HTTP Basic Authentication** or **OAuth2 Client Credentials**.



Expand All @@ -36,27 +36,26 @@ To use cookie authentication, simply use the ``loginRequired`` middleware::
res.send('Hello, ' + req.user.fullname);
});

Behind the scenes we are using OAuth2 Access Tokens, and storing them in the
cookies. The lifetime of the cookies is controlled by the OAuth Policy of
your Stormpath Application. By default the cookies will expire after 60 days.
Behind the scenes we are issuing a OAuth2 Access Token and Refresh token for
the user, and storing them in secure, HTTPS-Only cookies. The maximum
lifetime of the cookies is controlled by the expiration time of the Refresh
Token.

If you need to change the expiration time of the cookies, please login to the
Stormpath Admin Console and find the OAuth policy inside of your Stormpath
Application. Then change the expiration time of the Refresh Token.
If you need to change the expiration time of the Refresh Token, please login
to the Stormpath Admin Console and navigate to the OAuth policy of your
Stormpath Application. Then change the expiration time of the Refresh Token.

.. note::
Express-Stormpath's session management will not interfere with any existing
session middleware you might have. The sessions that Stormpath uses are
exclusively used for Stormpath's purposes, so it's safe you create your own
separate sessions.

This works by utilizing the Express `router`_.
exclusively used for Stormpath's purposes, so it's safe to create your own
separate sessions if needed.


Issuing API Keys
----------------

If you are building an API service you will need to distribute API keys to your
If you are building an API service, you will need to distribute API keys to your
developers. They will then use these keys to authenticate with your API, either
via HTTP Basic Auth or OAuth2 Access tokens. We'll cover those strategies in
the next sections, but we need to provision API keys for your developers first.
Expand All @@ -66,7 +65,7 @@ basic website that developers can use to obtain their keys. Here is an example
of how you can create an API Key for the currently logged in user::

app.post('/apiKeys', stormpath.loginRequired, function (req, res) {
req.user.createApiKey(function (err,apiKey){
req.user.createApiKey(function (err, apiKey) {
if (err) {
res.status(400).end('Oops! There was an error: ' + err.userMessage);
}else{
Expand All @@ -75,24 +74,12 @@ of how you can create an API Key for the currently logged in user::
});
});

This is a naive example which simply prints out the API Keys for them, but
This is a naive example which simply prints out the API Keys for the user, but
once they have the keys they will be able to authenticate with your API.

For more information on API Keys, please see
`Using Stormpath for API Authentication`_

Enabling API Authentication
---------------------------

Regardless of the authentication strategy that you choose, you will need to
enable the API Authentication features by configuring your server with the
``api`` option::

app.use(stormpath.init(app, {
api: true
}));


HTTP Basic Authentication
-------------------------

Expand All @@ -101,17 +88,35 @@ not have complex needs around authorization and resource control. This strategy
is simple because the developer simply supplies their API keys on every request
to your server.

Once the developer has the API keys, they will use them to authenticate with your
Once the developer has their API keys, they will use them to authenticate with your
API. For each request they will set the ``Authorization`` header, like this::

Authorization: Basic <Base64UrlSafe(apiKeyId:apiKeySecret)>

How this is done will depend on what tool or library they are using. For example,
if using curl::
if using curl:

.. code-block:: sh
curl -v --user apiKeyId:apiKeySecret http://localhost:3000/secret
$ curl -v --user apiKeyId:apiKeySecret http://localhost:3000/secret
Or if you're using the ``request`` library:

You will need to tell your server that you want to secure your endpoints and
.. code-block:: javascript
var request = require('request');
request({
url: 'http://localhost:3000/secret',
auth: {
user: 'apiKeyId',
pass: 'apiKeySecret'
}
}, function (err, res){
console.log(res.body);
});
You will need to tell your application that you want to secure this endpoint and
allow basic authentication. This is done with the ``apiAuthenticationRequired``
middleware::

Expand All @@ -128,8 +133,8 @@ OAuth2 Client Credentials
If you are building an API service and you have complex needs around
authorization and security, this strategy should be used. In this situation
the developer does a one-time exchange of their API Keys for an access token.
This access token is time limited and must be periodically renewed. This adds a
layer of security, but at the cost of being less simple than HTTP Basic
This access token is time limited and must be periodically refreshed. This adds a
layer of security, at the cost of being less simple than HTTP Basic
Authentication.

If you're not sure which strategy to use, it's best to start with HTTP Basic
Expand All @@ -156,9 +161,29 @@ parts you need to know are:
* The Authorization header must be Basic and contain the Base64 Url-Encoded
values of the Api Key Pair.

If you were doing this request with curl, it would look like this::
If you were doing this request with curl, it would look like this:

.. code-block:: sh
curl -X POST --user api_key_id:api_key_secret http://localhost:3000/oauth/token -d grant_type=client_credentials
curl -X POST --user api_key_id:api_key_secret http://localhost:3000/oauth/token -d grant_type=client_credentials
Or if using the ``request`` library:

.. code-block:: javascript
request({
url: 'http://localhost:3000/oauth/token',
method: 'POST',
auth: {
user: '1BWQHHJCOW90HI7HFQ5LTD6O0',
pass: 'zzeu+NwmicjtJ9yDJ2KlRguC+8uTjKVm3AMs80ah6hw'
},
form: {
'grant_type': 'client_credentials'
}
},function (err,res) {
console.log(res.body);
});
If the credentials are valid, you will get an access token response that looks
like this::
Expand All @@ -177,11 +202,26 @@ The response is a JSON object which contains:
- ``expires_in`` - This is the amount of seconds (*as an integer*) for which
this token is valid.

With that token you can now make requests of your API. This request is simpler,
the only thing you need to do is supply the token in the ``Authorization`` header
as a bearer token. If you are using curl, that request looks like this::
With this token you can now make requests to your API. This request is simpler,
as only thing you need to supply is ``Authorization`` header with the access
token as a bearer token. If you are using curl, that request looks like this:

$ curl -v -H "Authorization: Bearer eyJ0eXAiOiJKV1QiL..." http://localhost:3000/secret
.. code-block:: sh
curl -v -H "Authorization: Bearer eyJ0eXAiOiJKV1QiL..." http://localhost:3000/secret
Or if using the ``request`` library:

.. code-block:: javascript
request({
url: 'http://localhost:3000/secret',
auth: {
'bearer': 'eyJ0eXAiOiJKV1QiL...'
}
}, function (err, res){
console.log(res.body);
});
In order to protect your API endpoint and allow this form of authenetication,
you need to use the ``apiAuthenticationRequired`` middleware::
Expand All @@ -198,14 +238,13 @@ configuration, like this::


app.use(stormpath.init(app, {
"api": true,
"web": {
"oauth2":{
"client_credentials": {
"accessToken": {
"ttl": 3600 // your custom TTL, in seconds, goes here
web: {
oauth2: {
client_credentials: {
accessToken: {
ttl: 3600 // your custom TTL, in seconds, goes here
}
},
}
}
}
}));
Expand All @@ -217,7 +256,7 @@ OAuth2 Password Grant
This is the authentication strategy that you will want to use for mobile clients.
In this situation the end-user supplies their username and password to your
mobile application. The mobile application sends that username and password to
your server, which then verifies the password with Stormpath.
your Express application, which then verifies the password with Stormpath.

If the account is valid and the password is correct, Stormpath will generate
an access token for the user. Your server gets this access token from Stormpath
Expand All @@ -228,7 +267,7 @@ uses it for future requests to your API. Every time the mobile application uses
this access token your server will verify that it's still valid, using Stormpath.

When a user wants to login to your mobile application, the mobile application
should make this request to your server::
should make this request to your Express application::

POST /oauth/token HTTP/1.1
Host: myapi.com
Expand All @@ -252,7 +291,7 @@ token to your mobile application. The response will look like this::
Your mobile application should store the access token and refresh token. By
default the access token is valid for 1 hour and the refresh token for 60 days.
When the access token expires you can get a new access token by using the
refresh token::
refresh token, making this request to your Express application::

POST /oauth/token HTTP/1.1
Host: myapi.com
Expand Down

0 comments on commit 48be3e7

Please sign in to comment.