Mastodon
  • What is Mastodon?
  • Using Mastodon
    • Signing up for an account
    • Setting up your profile
    • Posting to your profile
    • Using the network features
    • Dealing with unwanted content
    • Promoting yourself and others
    • Set your preferences
    • More settings
    • Using Mastodon externally
    • Moving or leaving accounts
    • Running your own server
  • Running Mastodon
    • Preparing your machine
    • Installing from source
    • Configuring your environment
    • Configuring full-text search
    • Installing optional features
      • Object storage
      • Onion services
      • Captcha
      • Single Sign On
    • Setting up your new instance
    • Using the admin CLI
    • Upgrading to a new release
    • Backing up your server
    • Migrating to a new machine
    • Scaling up your server
    • Moderation actions
    • Troubleshooting errors
      • Database index corruption
    • Roles
  • Developing Mastodon apps
    • Getting started with the API
    • Playing with public data
    • Obtaining client app access
    • Logging in with an account
    • Libraries and implementations
  • Contributing to Mastodon
    • Technical overview
    • Setting up a dev environment
    • Code structure
    • Routes
    • Bug bounties and responsible disclosure
  • Spec compliance
    • ActivityPub
    • WebFinger
    • Security
    • Microformats
    • OAuth
    • Bearcaps
  • REST API
    • Datetime formats
    • Guidelines and best practices
    • OAuth Tokens
    • OAuth Scopes
    • Rate limits
  • API Methods
    • apps
      • oauth
      • emails
    • accounts
      • bookmarks
      • favourites
      • mutes
      • blocks
      • domain_blocks
      • filters
      • reports
      • follow_requests
      • endorsements
      • featured_tags
      • preferences
      • followed_tags
      • suggestions
      • tags
    • profile
    • statuses
      • media
      • polls
      • scheduled_statuses
    • timelines
      • conversations
      • lists
      • markers
      • streaming
    • grouped notifications
    • notifications
      • push
    • search
    • instance
      • trends
      • directory
      • custom_emojis
      • announcements
    • admin
      • accounts
      • canonical_email_blocks
      • dimensions
      • domain_allows
      • domain_blocks
      • email_domain_blocks
      • ip_blocks
      • measures
      • reports
      • retention
      • trends
    • proofs
    • oembed
  • API Entities
    • Account
    • AccountWarning
    • Admin::Account
    • Admin::CanonicalEmailBlock
    • Admin::Cohort
    • Admin::Dimension
    • Admin::DomainAllow
    • Admin::DomainBlock
    • Admin::EmailDomainBlock
    • Admin::Ip
    • Admin::IpBlock
    • Admin::Measure
    • Admin::Report
    • Announcement
    • Appeal
    • Application
    • Context
    • Conversation
    • CustomEmoji
    • DomainBlock
    • Error
    • ExtendedDescription
    • FamiliarFollowers
    • FeaturedTag
    • Filter
    • FilterKeyword
    • FilterResult
    • FilterStatus
    • IdentityProof
    • Instance
    • List
    • Marker
    • MediaAttachment
    • Notification
    • NotificationPolicy
    • NotificationRequest
    • Poll
    • Preferences
    • PreviewCard
    • PreviewCardAuthor
    • PrivacyPolicy
    • Quote
    • Reaction
    • Relationship
    • RelationshipSeveranceEvent
    • Report
    • Role
    • Rule
    • ScheduledStatus
    • Search
    • ShallowQuote
    • Status
    • StatusEdit
    • StatusSource
    • Suggestion
    • Tag
    • TermsOfService
    • Token
    • Translation
    • V1::Filter
    • V1::Instance
    • V1::NotificationPolicy
    • WebPushSubscription

Obtaining client app access

Getting accustomed to the basics of authentication and authorization.

    • Authentication and authorization
    • Creating our application
    • Example authentication code flow
    • What we can do with authentication

Authentication and authorization

Up until this point, we’ve been working with publicly available information, but not all information is public. Some information requires permission before viewing it, in order to audit who is requesting that information (and to potentially revoke or deny access).

This is where OAuth comes in. OAuth is a mechanism for generating access tokens that can be used to authenticate (verify) that a request is coming from a specific client, and ensure that the requested action is authorized (allowed) by the server’s access control policies.

Creating our application

The first thing we will need to do is to register an application, in order to be able to generate access tokens later. The application can be created like so:

curl -X POST \
	-F 'client_name=Test Application' \
	-F 'redirect_uris=urn:ietf:wg:oauth:2.0:oob' \
	-F 'scopes=read write push' \
	-F 'website=https://myapp.example' \
	https://mastodon.example/api/v1/apps

In the above example, we specify the client name and website, which will be shown on statuses if applicable. But more importantly, note the following two parameters:

  • redirect_uris has been set to the “out of band” token generation, which means that any generated tokens will have to be copied and pasted manually. The parameter is called redirect_uris because it is possible to define more than one redirect URI, but when generating the token, we will need to provide a URI that is included within this list.
  • scopes allow us to define what permissions we can request later. However, the requested scope later can be a subset of these registered scopes. See OAuth Scopes for more information.

You can also create applications by POSTing a JSON body to the same endpoint, as documented in POST /api/v1/apps.

As of Mastodon 4.3.0, you can discover which scopes the server supports along with other information by making a request to the /.well-known/oauth-authorization-server endpoint.

We should see a CredentialApplication entity returned, but for now, we only care about client_id and client_secret.

The client_id and client_secret values will be used to generate access tokens, so they should be cached for later use. See POST /api/v1/apps for more details on registering applications.

Treat the client_id and client_secret properties as if they are passwords. We recommend you encrypt these when storing in your cache, to prevent accidental credential exposure.

Example authentication code flow

Now that we have an application, let’s obtain an access token that will authenticate our requests as that client application. To do so, use POST /oauth/token like so:

curl -X POST \
	-F 'client_id=your_client_id_here' \
	-F 'client_secret=your_client_secret_here' \
	-F 'redirect_uri=urn:ietf:wg:oauth:2.0:oob' \
	-F 'grant_type=client_credentials' \
	https://mastodon.example/oauth/token

Note the following:

  • client_id and client_secret were provided in the response text when you registered your application.
  • redirect_uri must be one of the URIs defined when registering the application.
  • We are requesting a grant_type of client_credentials, which defaults to giving us the read scope.

The response of this method is a Token entity. We will need the access_token value. Once you have the access token, save it in your local cache.

Treat the access_token as if it were a password. We recommend you encrypt this value when storing in your cache, to prevent accidental credential exposure.

To use it in requests, add the HTTP header Authorization: Bearer <access_token> to any API call that requires OAuth (i.e., one that is not publicly accessible).

Let’s verify that our obtained credentials are working by calling GET /api/v1/apps/verify_credentials:

curl \
	-H 'Authorization: Bearer <access_token>' \
	https://mastodon.example/api/v1/apps/verify_credentials

If we’ve obtained our token and formatted our request correctly, we should see our details returned to us as an Application entity (without the client_secret property).

What we can do with authentication

With our authenticated client application, we can view relations of an account with GET /api/v1/accounts/:id/following and GET /api/v1/accounts/:id/followers. Also, some instances may require authentication for methods that would otherwise be public, so if you encountered any authentication errors while playing around with public methods, then those methods should now work.

Last updated October 10, 2024 · Improve this page

Sponsored by

Dotcom-Monitor LoadView Stephen Tures Swayable SponsorMotion

Join Mastodon · Blog ·

View source · CC BY-SA 4.0 · Imprint