You're free to use your own username & password to access your own account and
to get started with the API. OAuth 2 is a simple protocol, but it's yet another
speed bump to getting an integration off the ground.

API Key

Remember that anyone who has your authentication token can see and change everything you have access to. So you want to guard that as well as you guard your username and password. If you come to fear that it has been compromised, just change your regular password and the authentication token will change too.

OAuth 2

For a full app integration, you wouldn't want to get into the business of asking
customers for their passwords -- or storing them! -- so we offer a simple way to
ask a user for access to his account. You get an API access token back without
ever having to see his password or ask him to copy/paste an API key.

Register your app at integrate.37signals.com. You'll be assigned a client_id and client_secret. You'll need to provide a redirect_uri: a URL where we can send a verification code. Just enter a dummy URL like http://myapp.com/oauth if you're not ready for this yet.

Configure your OAuth 2 library with your client_id, client_secret, and redirect_uri. Tell it to use https://launchpad.37signals.com/authorization/new to request authorization and https://launchpad.37signals.com/authorization/token to get access tokens.

Try making an authorized request to https://launchpad.37signals.com/authorization.json to dig in and test it out! Check out the Get authorization endpoint for a description of what this returns.

OAuth 2 from scratch

If you're going bare-metal and developing your own OAuth 2 client, you have a bit more work to do.

TL;DR request access, receive a verification code, trade it for an access token.

We implement draft 5 and will update our implementation as the final spec converges. Be prepared for changes along the way.

We support the web_server and user_agent flows, not the client_credentials or device flows.

We issue refresh tokens. Use them to request a new access token when it expires (2 week lifetime, currently).

We return more verbose errors than what's given in the spec to help with client development. We'll move these to a separate parameter later.

Get authorization

GET https://launchpad.37signals.com/authorization.json

GET https://launchpad.37signals.com/authorization.xml

This endpoint requires the Authorization header and returns the following:

A expires_at timestamp for when this token will expire, and you'll need to fetch a new one to authenticate requests

An identity, which is NOT used for determining who this user is within a specific application. The id field should NOT be used for submitting data within any application's API. This field can be used to get a user's name and email address quickly, and the id field could be used for caching on a cross-application basis if needed.

A list of accounts that this user has access to.

This endpoint should be first request made after you've obtained a user's authorization token via OAuth. You can pick which account to use for a given product, and then base where to make requests to from the chosen account's href field.

Who am I?

So you've picked the product, have the href to request to, and now what? Depending on what your API integration needs, you may need to know who the current user is within that product. For example, if you were working with the Basecamp API this is how you would obtain the id field to submit a todo assigned to the current user.

Here's links to the endpoints in our products that you'll need to hit: