Development / OAuth2
OAuth2 is a protocol that lets external applications request authentication of the user and authorization to perform actions using the web service on their behalf without getting their password. It is an alternative to HTTP Digest Access Authentication that MusicBrainz currently uses.
Basic steps
Registering an application
All developers need to register their application before getting started. A registered OAuth application is assigned a unique Client ID and Client Secret. The OAuth protocol recognizes two types of applications:
- Confidential - Applications that can keep secrets. Typically web applications, running on a server.
- Public - Applications that have their code exposed to the public and therefore cannot keep secrets. There are typically installed desktop applications or web applications running in the browser.
The Client Secret assigned to Confidential applications should not be shared. This does not apply to Public applications, in which case the assigned Client Secret is not treated as a secret and can be embedded in the application code.
Obtaining access token
The general work-flow for obtaining an access token is the following:
- Redirect the user to the OAuth authorization page with the appropriate parameters. From a desktop application, you need to open a browser with the URL for the user.
- After the user authorizes the request, you will receive an authorization code. The authorization code is either delivered to the configured redirect URL or the user copies it to the application manually if using the out-of-band (OOB) method.
- Send a request exchange the authorization code for an access token and optionally a refresh token.
Details of the steps are explained below.
Using access token
After an application has obtained an access token, it may use the token in the web service to get user details or submit data to MusicBrainz on the user's behalf. MusicBrainz currently only supports Bearer tokens, which are very easy to use but can only be sent over HTTPS.
Refreshing access token
Access tokens have a limited life-time. During the authorization process, application receives a refresh token, in addition to the first access token. This refresh token allows applications to obtain new access tokens.
Authorization
Authorization request
The authorization sequence starts by redirecting the user to the authorization endpoint with a set of query string parameters describing the authorization request. The endpoint is located at https://musicbrainz.org/oauth2/authorize
and is only accessible over HTTPS. HTTP connections are refused.
The following set of query string parameters is supported by the MusicBrainz authentication endpoint:
response_type
- Must be always set to
code
. client_id
- Client ID assigned to your application. You can find it on the website in your list of registered applications.
redirect_uri
- URL where clients should be redirected after authorization. This must match exactly the URL you entered when registering your application. Desktop applications can use either
urn:ietf:wg:oauth:2.0:oob
orhttp://localhost
with a custom port. scope
- Space delimited list of scopes the application requests. See below for a list of all available scopes.
state
(optional)- Any string the application wants passed back after authorization. For example, this can be a CSRF token from your application. This parameter is optional, but strongly recommended.
code_challenge
(optional)- MusicBrainz supports the use of "Proof Key for Code Exchange" (PKCE) by clients. This is strongly recommended to avoid authorization code interception attacks. See RFC 7636 for the process of generating a
code_verifier
and then acode_challenge
(passed here) based on that. code_challenge_method
(optional)- Either
S256
(recommended) orplain
(the default if not specified).
There are two extra parameters applicable only to web server applications:
access_type
(optional)- Indicates if your application needs to access the API when the user is not present at the browser. This parameter defaults to
online
. If your application needs to refresh access tokens when the user is not present at the browser, then useoffline
. This will result in your application obtaining a refresh token the first time your application exchanges an authorization code for a user. approval_prompt
(optional)- Indicates if the user should be re-prompted for consent. The default is
auto
, so a given user should only see the consent page for a given set of scopes the first time through the sequence. If the value isforce
, then the user sees a consent page even if they have previously given consent to your application for a given set of scopes.
For example, a complete authorization request from a web application requesting permissions to read the user's private tags and ratings would look like this:
https://musicbrainz.org/oauth2/authorize? response_type=code& client_id=k1Mm4xTmAh5zhXtiPEQekViNbgMT8_RG& redirect_uri=http%3A%2F%2Fwww.example.com.com%2Fauth2callback& scope=tag%20rating& state=1351449443
The response to the authorization request will be sent to the URL indicated in the redirect_uri
parameter. The authorization endpoint will redirect the user to this URL with a set of specific query string parameters indicating the result. If the user does not approve the request or there is a problem with the request, it will return an error describing the problem. Otherwise it will return an authorization code that can be exchanged for an access token by the token endpoint.
In case of an error, the response will look like this:
http://www.example.com/oauth2callback?state=1351449443&error=access_denied
Possible error codes are unsupported_response_type
, invalid_scope
and access_denied
. If there is a problem with the client_id
or redirect_uri
parameters, the authorization endpoint will not redirect back to your application and only inform the user about the problem.
A successful authorization response:
http://www.example.com/oauth2callback?state=1351449443&code=4-H4vg4V2kEEhHPM7kWpN18d9trJenOp
Exchanging authorization code for an access token
Once your application receives an authorization code, it can send a POST request the token endpoint located at https://musicbrainz.org/oauth2/token
, to exchange the code for an access token. As before, this endpoint is only avilable over HTTPS and HTTP requests will be refused.
The requires parameters for exchanging the authorization code are:
grant_type
- Must be set to
authorization_code
. code
- Authorization code from the initial request.
client_id
- Client ID assigned to your application.
client_secret
- Client secret assigned to your application.
redirect_uri
- Redirect URL registered with the application.
token_type
(optional)- Only
bearer
is allowed to be passed here. code_verifier
(optional)- If you're using PKCE, pass the
code_verifier
here. We'll reject the access token request if it doesn't agree with thecode_challenge
andcode_challenge_method
sent with the initial request tohttps://musicbrainz.org/oauth2/authorize
. The process is described in detail by RFC 7636.
An example of an authorization code exchange would look like this:
POST /oauth2/token HTTP/1.1 Host: musicbrainz.org Content-Type: application/x-www-form-urlencoded grant_type=authorization_code& code=4-H4vg4V2kEEhHPM7kWpN18d9trJenOp& client_id=k1Mm4xTmAh5zhXtiPEQekViNbgMT8_RG& client_secret=2dj1b7PvccAkDLxIebEIFTGGO_eETc7K& redirect_uri=http%3A%2F%2Fwww.example.com.com%2Fauth2callback
In case the authorization code and the client credentials were all valid, the server would respond with a JSON document in this format:
{ "access_token":"UF7GvG2pl70jTogIwOhD32BhI_aIevPF", "expires_in":3600, "token_type":"Bearer", "refresh_token":"GjSCBBjp4fnbE0AKo3uFu9qq9K2fFm4u" }
Refreshing an access token
If you have an installed application, or web application with offline access, you have received a refresh token during the authorization process. This token can be used to get a new access token without any user interaction. Access tokens have a limited life-time, but the refresh token stays valid until the user manually revokes it.
The required parameters for refreshing an access token are:
grant_type
- Must be set to
refresh_token
. refresh_token
- Refresh token received during the authorization process.
client_id
- Client ID assigned to your application.
client_secret
- Client secret assigned to your application.
token_type
(optional)- Only
bearer
is allowed to be passed here.
An example of an authorization code exchange would look like this:
POST /oauth2/token HTTP/1.1 Host: musicbrainz.org Content-Type: application/x-www-form-urlencoded grant_type=refresh_token& refresh_token=GjSCBBjp4fnbE0AKo3uFu9qq9K2fFm4u& client_id=k1Mm4xTmAh5zhXtiPEQekViNbgMT8_RG& client_secret=2dj1b7PvccAkDLxIebEIFTGGO_eETc7K
In case the refresh token and the client credentials were all valid, the server would respond with a JSON document in this format:
{ "access_token":"GjtKfJS6G4lupbQcCOiTKo4HcLXUgI1p", "expires_in":3600, "token_type":"Bearer", "refresh_token":"GjSCBBjp4fnbE0AKo3uFu9qq9K2fFm4u" }
Revoking a token
If a refresh or access token is no longer needed, e.g. when the end user logs out, changes identity, or uninstalls your application, you should notify us to remove the unused token. MusicBrainz implements a token revocation endpoint (RFC 7009) at https://musicbrainz.org/oauth2/revoke
. The only supported method is POST
. Once again, it's only available over HTTPS.
The required parameters for revoking a token are:
token
- Either a refresh token or access token.
client_id
- Client ID assigned to your application.
client_secret
- Client secret assigned to your application.
If your application is installed or offline and token
is a refresh token, we'll revoke the entire authorization grant associated with that token. If it's an access token, we'll only revoke the access token given; any associated refresh token can still be used to request a new access token.
If your application is web-based or online, revoking the access token will revoke the entire authorization grant, as there's no refresh token in this case.
An example of a token revocation would look like this:
POST /oauth2/revoke HTTP/1.1 Host: musicbrainz.org Content-Type: application/x-www-form-urlencoded token=GjSCBBjp4fnbE0AKo3uFu9qq9K2fFm4u& client_id=k1Mm4xTmAh5zhXtiPEQekViNbgMT8_RG& client_secret=2dj1b7PvccAkDLxIebEIFTGGO_eETc7K
If all parameters are present and the client credentials are okay, then a 200 OK response with no body is returned. The response status will indicate success even if the token was invalid (as the client wouldn't be able to handle such an error in a reasonable way).
Scopes
Authorization requests have a limited scope. You should request only the scopes that your application necessarily needs. The following scopes are available in the MusicBrainz OAuth implementation:
profile
- View the user's public profile information (username, age, country, homepage).
email
- View the user's email.
tag
- View and modify the user's private tags.
rating
- View and modify the user's private ratings.
collection
- View and modify the user's private collections.
submit_isrc
- Submit new ISRCs to the database.
submit_barcode
- Submit barcodes to the database.
Access token usage
MusicBrainz supports one type of access token: Bearer tokens.
Bearer tokens
Bearer tokens are very easy to use and consist only of one component, which you should treat as a password. For this reason, it is only possible to use them over HTTPS. If you try to send them over plain HTTP, they will be ignored.
The preferred method to use bearer tokens is via the Authorization
header. An authenticated request would look like the following:
GET /oauth2/userinfo HTTP/1.1 Host: musicbrainz.org Authorization: Bearer dFngty-XelYCQpveDtCXT_1NWxtH5OPA
You can try it with the curl command line application:
curl -H 'Authorization: Bearer dFngty-XelYCQpveDtCXT_1NWxtH5OPA' https://musicbrainz.org/oauth2/userinfo
If you can't use the Authorization
header, there is an alternative in which you perform a POST
request and pass the access_token
in the body that way:
POST /oauth2/userinfo HTTP/1.1 Host: musicbrainz.org Content-Type: application/x-www-form-urlencoded access_token=dFngty-XelYCQpveDtCXT_1NWxtH5OPA
An example of that, using curl again:
curl -X POST -d 'access_token=dFngty-XelYCQpveDtCXT_1NWxtH5OPA' 'https://musicbrainz.org/oauth2/userinfo'
There is one last option suitable for testing only, and that is passing the access_token
in the URI as a query parameter. You should avoid this unless the previous two methods are impossible, because it increases the likelihood of the token being logged by web servers and history data.
GET https://musicbrainz.org/oauth2/userinfo?access_token=dFngty-XelYCQpveDtCXT_1NWxtH5OPA
With curl, that's just:
curl 'https://musicbrainz.org/oauth2/userinfo?access_token=dFngty-XelYCQpveDtCXT_1NWxtH5OPA'
Bearer tokens are specified in RFC 6750.