> ## Documentation Index
> Fetch the complete documentation index at: https://docs.msu.io/llms.txt
> Use this file to discover all available pages before exploring further.

# Token Issuance & Refresh

> Issue a new Access Token and Refresh Token using an Authorization Code, or refresh an expired Access Token using a Refresh Token.

Issues a new Access Token and Refresh Token using an Authorization Code (`authorization_code`), or refreshes an expired Access Token using a Refresh Token (`refresh_token`).

## Header parameters

<ParamField header="Content-Type" type="string" required>
  Must be `application/x-www-form-urlencoded`.
</ParamField>

<ParamField header="Authorization" type="string" required>
  Client credentials encoded in Base64: `Basic base64({CLIENT_ID}:{CLIENT_SECRET})`.
</ParamField>

## Body parameters

<ParamField body="grant_type" type="string" required>
  Token grant type. Must be `authorization_code` or `refresh_token`.
</ParamField>

<ParamField body="code" type="string">
  Required when `grant_type=authorization_code`. The Authorization Code received from `/oauth/authorize`.
</ParamField>

<ParamField body="redirect_uri" type="string">
  Required when `grant_type=authorization_code`. Must exactly match the URI used in the Authorization Code request.
</ParamField>

<ParamField body="refresh_token" type="string">
  Required when `grant_type=refresh_token`. The Refresh Token to use for renewal.
</ParamField>

<ParamField body="code_verifier" type="string">
  PKCE code verifier. Required if a `code_challenge` was provided in the Authorization Code request.
</ParamField>

## Response

<ResponseField name="access_token" type="string">
  Access Token. Used as a Bearer token in API calls.
</ResponseField>

<ResponseField name="token_type" type="string">
  Token type. Always `Bearer`.
</ResponseField>

<ResponseField name="expires_in" type="integer">
  Access Token validity period in seconds (600 seconds = 10 minutes).
</ResponseField>

<ResponseField name="refresh_token" type="string">
  Refresh Token. Used to renew the Access Token. Valid for 3 hours.
</ResponseField>

<ResponseField name="scope" type="string">
  Space-separated list of granted permission scopes.
</ResponseField>

<RequestExample>
  ```bash cURL (Authorization Code) theme={null}
  curl --request POST \
    --url 'https://oauth.msu.io/oauth/token' \
    --header 'Content-Type: application/x-www-form-urlencoded' \
    --header 'Authorization: Basic base64({CLIENT_ID}:{CLIENT_SECRET})' \
    --data 'grant_type=authorization_code&code={AUTHORIZATION_CODE}&redirect_uri={REDIRECT_URI}'
  ```

  ```bash cURL (Refresh Token) theme={null}
  curl --request POST \
    --url 'https://oauth.msu.io/oauth/token' \
    --header 'Content-Type: application/x-www-form-urlencoded' \
    --header 'Authorization: Basic base64({CLIENT_ID}:{CLIENT_SECRET})' \
    --data 'grant_type=refresh_token&refresh_token={REFRESH_TOKEN}'
  ```

  ```javascript JavaScript theme={null}
  const response = await fetch('https://oauth.msu.io/oauth/token', {
    method: 'POST',
    headers: {
      'Content-Type': 'application/x-www-form-urlencoded',
      'Authorization': `Basic ${btoa('{CLIENT_ID}:{CLIENT_SECRET}')}`
    },
    body: new URLSearchParams({
      grant_type: 'authorization_code',
      code: '{AUTHORIZATION_CODE}',
      redirect_uri: '{REDIRECT_URI}'
    })
  });
  const data = await response.json();
  ```

  ```python Python theme={null}
  import requests
  import base64

  credentials = base64.b64encode(b'{CLIENT_ID}:{CLIENT_SECRET}').decode()

  response = requests.post(
    'https://oauth.msu.io/oauth/token',
    headers={
      'Content-Type': 'application/x-www-form-urlencoded',
      'Authorization': f'Basic {credentials}'
    },
    data={
      'grant_type': 'authorization_code',
      'code': '{AUTHORIZATION_CODE}',
      'redirect_uri': '{REDIRECT_URI}'
    }
  )
  data = response.json()
  ```
</RequestExample>

<ResponseExample>
  ```json Response theme={null}
  {
    "access_token": "eyJhbGciOiJSUzI1NiIsImtpZCI6Im1zdS1vYXV0aCIsInR5cCI6IkpXVCJ9...",
    "token_type": "Bearer",
    "expires_in": 600,
    "refresh_token": "eyJhbGciOiJSUzI1NiIsImtpZCI6Im1zdS1vYXV0aCIsInR5cCI6IkpXVCJ9...",
    "scope": "enhancement"
  }
  ```
</ResponseExample>
