Skip to main content

Documentation Index

Fetch the complete documentation index at: https://mintlify.com/disgoorg/disgo/llms.txt

Use this file to discover all available pages before exploring further.

The oauth2 package provides a client for implementing Discord’s OAuth2 flow, allowing you to authenticate users and access their Discord data.

Installation

import "github.com/disgoorg/disgo/oauth2"

Client

New

Creates a new OAuth2 client.
func New(id snowflake.ID, secret string, opts ...ConfigOpt) *Client
id
snowflake.ID
required
Your application’s client ID
secret
string
required
Your application’s client secret
opts
...ConfigOpt
Optional configuration options

Client type

type Client struct {
    ID              snowflake.ID
    Secret          string
    Rest            rest.OAuth2
    StateController StateController
}
ID
snowflake.ID
The application’s client ID
Secret
string
The application’s client secret
Rest
rest.OAuth2
The REST client for OAuth2 endpoints
StateController
StateController
Manages OAuth2 state parameters for security

Authorization flow

GenerateAuthorizationURL

Generates an authorization URL for users to authenticate.
func (c *Client) GenerateAuthorizationURL(params AuthorizationURLParams) string

GenerateAuthorizationURLState

Generates an authorization URL and returns both the URL and state parameter.
func (c *Client) GenerateAuthorizationURLState(params AuthorizationURLParams) (string, string)
params
AuthorizationURLParams
required
Parameters for generating the authorization URL

AuthorizationURLParams

type AuthorizationURLParams struct {
    RedirectURI        string
    Permissions        discord.Permissions
    GuildID            snowflake.ID
    DisableGuildSelect bool
    IntegrationType    discord.ApplicationIntegrationType
    Scopes             []discord.OAuth2Scope
}
RedirectURI
string
required
The redirect URI registered with your application
Permissions
discord.Permissions
Permissions to request if adding a bot
GuildID
snowflake.ID
Pre-select a specific guild
DisableGuildSelect
bool
Disable the guild selection dropdown
IntegrationType
discord.ApplicationIntegrationType
The integration type for the authorization
Scopes
[]discord.OAuth2Scope
required
OAuth2 scopes to request

StartSession

Exchanges an authorization code for an access token and starts a session.
func (c *Client) StartSession(
    code string,
    state string,
    opts ...rest.RequestOpt
) (Session, *discord.IncomingWebhook, error)
code
string
required
The authorization code from the OAuth2 callback
state
string
required
The state parameter from the OAuth2 callback
opts
...rest.RequestOpt
Optional request options
Returns the session, an optional webhook (if webhook scope was requested), and any error.

Session management

Session

Represents an OAuth2 session with an access token.
type Session struct {
    AccessToken  string
    RefreshToken string
    Scopes       []discord.OAuth2Scope
    TokenType    discord.TokenType
    Expiration   time.Time
}
AccessToken
string
The access token for making API requests
RefreshToken
string
The refresh token for obtaining a new access token
Scopes
[]discord.OAuth2Scope
The granted OAuth2 scopes
TokenType
discord.TokenType
The token type (usually “Bearer”)
Expiration
time.Time
When the access token expires

RefreshSession

Refreshes an expired session using the refresh token.
func (c *Client) RefreshSession(
    session Session,
    opts ...rest.RequestOpt
) (Session, error)

VerifySession

Verifies a session and refreshes it if expired.
func (c *Client) VerifySession(
    session Session,
    opts ...rest.RequestOpt
) (Session, error)

Session.Expired

Checks if the session has expired.
func (s Session) Expired() bool

User data

GetUser

Retrieves the authenticated user’s information. Requires the identify scope.
func (c *Client) GetUser(
    session Session,
    opts ...rest.RequestOpt
) (*discord.OAuth2User, error)

GetMember

Retrieves the authenticated user’s guild member information. Requires the guilds.members.read scope.
func (c *Client) GetMember(
    session Session,
    guildID snowflake.ID,
    opts ...rest.RequestOpt
) (*discord.Member, error)

GetGuilds

Retrieves the authenticated user’s guilds. Requires the guilds scope.
func (c *Client) GetGuilds(
    session Session,
    opts ...rest.RequestOpt
) ([]discord.OAuth2Guild, error)

GetConnections

Retrieves the authenticated user’s connections. Requires the connections scope.
func (c *Client) GetConnections(
    session Session,
    opts ...rest.RequestOpt
) ([]discord.Connection, error)

GetApplicationRoleConnection

Retrieves the user’s role connection for an application. Requires the role_connections.write scope.
func (c *Client) GetApplicationRoleConnection(
    session Session,
    applicationID snowflake.ID,
    opts ...rest.RequestOpt
) (*discord.ApplicationRoleConnection, error)

UpdateApplicationRoleConnection

Updates the user’s role connection for an application. Requires the role_connections.write scope.
func (c *Client) UpdateApplicationRoleConnection(
    session Session,
    applicationID snowflake.ID,
    update discord.ApplicationRoleConnectionUpdate,
    opts ...rest.RequestOpt
) (*discord.ApplicationRoleConnection, error)

Configuration

WithLogger

Sets a custom logger.
func WithLogger(logger *slog.Logger) ConfigOpt

WithRestClient

Sets a custom REST client.
func WithRestClient(restClient rest.Client) ConfigOpt

WithRestClientConfigOpts

Sets REST client configuration options.
func WithRestClientConfigOpts(opts ...rest.ClientConfigOpt) ConfigOpt

WithOAuth2

Sets a custom OAuth2 REST interface.
func WithOAuth2(oauth2 rest.OAuth2) ConfigOpt

WithStateController

Sets a custom state controller.
func WithStateController(stateController StateController) ConfigOpt

WithStateControllerOpts

Sets state controller configuration options.
func WithStateControllerOpts(opts ...StateControllerConfigOpt) ConfigOpt

State controller

The state controller manages OAuth2 state parameters for security.

StateController interface

type StateController interface {
    // NewState generates a new random state to be used as a state
    NewState(redirectURI string) string

    // UseState validates a state and returns the redirect url or empty string if invalid
    UseState(state string) string
}

NewStateController

Creates a new state controller.
func NewStateController(opts ...StateControllerConfigOpt) StateController

State controller configuration

WithStateControllerLogger

Sets the logger for the state controller.
func WithStateControllerLogger(logger *slog.Logger) StateControllerConfigOpt

WithStates

Loads states from an existing map.
func WithStates(states map[string]string) StateControllerConfigOpt

WithNewStateFunc

Sets the function used to generate new random states.
func WithNewStateFunc(newStateFunc func() string) StateControllerConfigOpt

WithMaxTTL

Sets the maximum time to live for a state.
func WithMaxTTL(maxTTL time.Duration) StateControllerConfigOpt

Errors

var (
    // ErrStateNotFound is returned when the state is not found in the StateController
    ErrStateNotFound = errors.New("state could not be found")

    // ErrSessionExpired is returned when the Session has expired
    ErrSessionExpired = errors.New("access token expired. refresh the session")

    // ErrMissingOAuth2Scope is returned when a specific OAuth2 scope is missing
    ErrMissingOAuth2Scope = func(scope discord.OAuth2Scope) error {
        return fmt.Errorf("missing '%s' scope", scope)
    }
)

Example usage

package main

import (
    "fmt"
    "log"
    "net/http"
    "os"

    "github.com/disgoorg/disgo/discord"
    "github.com/disgoorg/disgo/oauth2"
    "github.com/disgoorg/snowflake/v2"
)

var client *oauth2.Client

func main() {
    clientID, _ := snowflake.Parse(os.Getenv("CLIENT_ID"))
    clientSecret := os.Getenv("CLIENT_SECRET")

    client = oauth2.New(clientID, clientSecret)

    http.HandleFunc("/login", handleLogin)
    http.HandleFunc("/callback", handleCallback)

    log.Fatal(http.ListenAndServe(":8080", nil))
}

func handleLogin(w http.ResponseWriter, r *http.Request) {
    authURL := client.GenerateAuthorizationURL(oauth2.AuthorizationURLParams{
        RedirectURI: "http://localhost:8080/callback",
        Scopes: []discord.OAuth2Scope{
            discord.OAuth2ScopeIdentify,
            discord.OAuth2ScopeGuilds,
        },
    })

    http.Redirect(w, r, authURL, http.StatusTemporaryRedirect)
}

func handleCallback(w http.ResponseWriter, r *http.Request) {
    code := r.URL.Query().Get("code")
    state := r.URL.Query().Get("state")

    session, _, err := client.StartSession(code, state)
    if err != nil {
        http.Error(w, err.Error(), http.StatusBadRequest)
        return
    }

    user, err := client.GetUser(session)
    if err != nil {
        http.Error(w, err.Error(), http.StatusInternalServerError)
        return
    }

    fmt.Fprintf(w, "Hello, %s!", user.Username)
}