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

# OAuth 2.0

> Enable secure and reliable access for advanced integrations

<Note>
  Note: OAuth access is not enabled by default for all merchants. Each application is reviewed and approved on a case-by-case basis.
</Note>

# What is OAuth 2.0?

OAuth 2.0 is an industry-standard authorization framework that enables secure, delegated access to resources without sharing credentials. It allows applications to obtain limited access to a user's account on an HTTP service, such as social media or cloud storage, on their behalf. Instead of sharing passwords, OAuth 2.0 issues tokens that grant specific permissions, enhancing security and user convenience.

# Before you begin

In order to start your integration please contact our support team to get set up. You need to provide the following information:

* Types of accounts you'd like to allow to connect Ziina wallets to your app: Personal, Business or both
* Redirect URI (explained below)
* Scopes you would like to request. See [available scopes](/developers/oauth-2.0#available-scopes)

You'll receive a `client_id`, `username` and `password` to use with our API.

# OAuth 2.0 token retrieval process

The API flow is captured in the following diagram:

```mermaid theme={null}
sequenceDiagram
    participant User
    participant YourApp
    participant ZiinaAuth

    User->>YourApp: 1. Initiates authorization from YourApp
    YourApp->>ZiinaAuth: 2. GET /oidc/auth
    ZiinaAuth->>User: 3. Prompts User for login and permissions grant
    User->>ZiinaAuth: 4. Authenticates and grants permissions
    ZiinaAuth->>YourApp: 5. Redirect to redirect_uri
    YourApp->>ZiinaAuth: 6. POST /oidc/token with Basic Auth Authorization header
    ZiinaAuth->>YourApp: 7. Response with access_token
    YourApp->>ZiinaAPI: 8. Make API calls with<br>Authorization: Bearer access_token
    ZiinaAPI->>YourApp: 9. Return API responses
```

<Steps>
  <Step title="User initiates authorization from YourApp" />

  <Step title="Navigate user to authentication service">
    ```
      https://auth.ziina.com/oidc/auth
      ?client_id=test
      &response_type=code
      &redirect_uri=https://example.com/callback
      &scope=read_account+write_payment_intents
      &state=xyz123
    ```

    * `client_id` you should obtain in advance (contact us)
    * `redirect_uri` – URI where user will be redirected after permissions have been granted. Should be shared with us in advance.
    * `response_type=code` for the Authorization Code grant. Must be always provided.
    * `state` an optional parameter to track the state between initiating and completing auth
    * `prompt` this field is optional, but if `offline_access` [scope](/developers/oauth-2.0#available-scopes) is required then this value must be set to `consent`
    * `scope` – Permissions you want to request. If you need to request multiple permissions you need to join them with `+` sign. Available scopes can be found [here](/developers/oauth-2.0#available-scopes)
  </Step>

  <Step title="Ziina asks user to grant access" />

  <Step title="User grants permissions at https://auth.ziina.com" />

  <Step title="User is redirected to your redirect_uri">
    Following query params added to your redirect\_uri

    * `iss=https://auth.ziina.com`
    * `code=${authorizationCode}` which you need to use to exchange for access and refresh tokens
    * `state=${state}` if this field was passed initially
  </Step>

  <Step title="Exchange code for access_token">
    Send

    ```http theme={null}
      POST /oidc/token?code=${authorizationCode}&redirect_uri=${redirectUri}&grant_type=authorization_code&scope=read_account+write_payment_intents HTTP/1.1
      Host: auth.ziina.com
      Content-Type: application/x-www-form-urlencoded
      Authorization: Basic dXNlcm5hbWU6cGFzc3dvcmQ=

      grant_type=authorization_code&code=${authorizationCode}&redirect_uri=${redirectUri}&scope=read_account+write_payment_intents
    ```

    * `authorizationCode` is the code, which you got at previous step. Its lifetime is 1 minute.
    * Use username and password provided by support to add basic authorization header
      with Base64-encoded `${username}:${password}` string prepended with the word `Basic`
  </Step>

  <Step title="Ziina responds with access_token">
    Example response

    ```json theme={null}
      {
        access_token: "123Abcdef....",
        expires_in: 9007199254740991,
        scope: "read_account write_payment_intents",
        token_type: "Bearer"
      }
    ```
  </Step>

  <Step title="Make API calls with the Bearer authorization header">
    API reference can be found [here](/api-reference/)
  </Step>
</Steps>

### Optional: refresh your access\_token

Once your `access_token` token expires you might want to get a new one. In order to do that you need
to send the following request:

```http theme={null}
POST /oidc/token?grant_type=refresh_token&refresh_token=123Abcdef HTTP/1.1
Host: auth.ziina.com
Content-Type: application/x-www-form-urlencoded
Authorization: Basic dXNlcm5hbWU6cGFzc3dvcmQ=

grant_type=refresh_token&refresh_token=123Abcdef
```

To create the Basic authorization header, encode the string `${username}:${password}` in Base64 and prepend it with the word `Basic`.

<Note>
  In order to get refresh\_token you need to add scope=offline\_access when you
  get access\_token
</Note>

### Available scopes

* `write_payment_intents`. Allows to create [payment intents](/api-reference/payment-intent/index) and accept payments on users behalf
* `write_refunds`. Allows to create and fetch [refunds](/api-reference/refund/get)
* `write_webhooks`. Allows to create and delete [webhooks](/api-reference/webhook/index)
* `write_transfers`. Allows to [transfer](/api-reference/transfer/create) money to Ziina users
* `offline_access`. Add this scope if you want to get `refresh_token`
* `read_account`. This scope is required if you want to [get user account information](/api-reference/account/get)

<Note>
  Tokens obtained at Ziina website on [business connect
  page](https://ziina.com/business/connect) have all available scopes assigned.
</Note>

### Example integration

1. Redirect the user to the authorization service as described in Step 1 above.
2. Use the code below to exchange the authorization code for an access token.

```js Example OAuth integration theme={null}
const express = require('express');
const app = express();

const username = "username_you_got_from_us";
const password = "password_you_got_from_us";
const base64Auth = Buffer.from(`${username}:${password}`).toString('base64');
// You can request only approved scopes
const scopes = [
  "read_account",
  "write_payment_intents",
  "write_webhooks",
];
const url = "https://auth.ziina.com/oidc/token";

async function sendTokenRequest(bodyParams) {
	const body = new URLSearchParams(bodyParams).toString();
	const response = await fetch(url, {
		method: "POST",
		headers: {
			"Content-Type": "application/x-www-form-urlencoded",
			Authorization: `Basic ${base64Auth}`,
		},
		body,
	});

	return response.json();
}

async function exchangeCodeForToken(code) {
  const params = {
    code,
    redirect_uri: "redirect_uri_you_provided_us",
    grant_type: "authorization_code",
    scope: scopes.join("+"),
  }
  
  return sendTokenRequest(params);
}

// Not required if you don't need to refresh your token
async function rotateTokens(refreshToken) {
  const params = {
    refresh_token: refreshToken,
    grant_type: "refresh_token",
  }

  return sendTokenRequest(params);
}

/*
  This endpoint handles redirects from the OAuth authorization flow.
  After a user grants permissions to your app, Ziina will redirect
  them back to this redirect_uri with an authorization code.
*/
app.get('/callback', async (req, res) => {
  // This response has access_token field. Use it to call Ziina API
  const response = await exchangeCodeForToken(req.query.code);

  res.send("Success");
});

app.listen(3000, () => {
  console.log('Server is running on port 3000');
});
```

## Need help?

If you have questions, visit our [help center](https://ziina.com/help-center) or contact us at [support@ziina.com](mailto:support@ziina.com).
