You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
To call your APIs on behalf of your users, the MCP server needs to exchange the Auth0 access token it received from the MCP client (with the audience set to the MCP server itself) for a new Auth0 access token with the audience set to your API.
22
28
@@ -25,7 +31,7 @@ In Auth0, this is called Custom Token Exchange and uses [RFC 8693](https://www.r
25
31
By the end of this quickstart, you should have an MCP server that can:
26
32
27
33
* Exchange an Auth0 access token for another Auth0 access token with a different audience using Custom Token Exchange
28
-
* Verify the access token using the `@auth0/auth0-api-js` library (which uses `jose` under the hood) against your tenant JWKS, enforcing issuer, audience, and RS256
34
+
* Verify the access token using the `@auth0/auth0-api-js` library (which uses `jose` under the hood) or the `auth0-api-python` library for Python against your tenant JWKS, enforcing issuer, audience, and RS256
29
35
30
36
<MCPGetStartedPrerequisites />
31
37
@@ -84,173 +90,110 @@ auth0 api post resource-servers --data '{
84
90
85
91
Save the `Audience` from the command output; you'll need it in a later step.
86
92
87
-
93
+
## Sample app
88
94
<Tabs>
89
-
<Tabtitle="Use sample app (recommended)">
90
-
Start by downloading the sample app for this quickstart. The sample includes a FastMCP MCP server with an Auth0 integration and a protected API built with
91
-
[Fastify](https://fastify.dev/).
92
-
93
-
<DownloadQuickstartButton
94
-
category="auth-for-mcp"
95
-
framework="fastmcp-mcp-customtokenexchange-js"
96
-
/>
97
-
98
-
Once downloaded, extract the files and open the project in your preferred IDE.
99
-
</Tab>
100
-
<Tabtitle="Clone GitHub repository">
101
-
Clone the repository and navigate to the sample app folder which includes a FastMCP MCP server with an Auth0 integration and a protected API built with
cd auth0-ai-samples/auth-for-mcp/fastmcp-mcp-customtokenexchange-js
107
-
```
108
-
109
-
Once cloned, open the project in your preferred IDE.
110
-
</Tab>
111
-
</Tabs>
112
-
113
-
The sample app demonstrates custom token exchange with a `greet` tool that calls your protected API on behalf of the authenticated user.
114
-
115
-
## Install packages
116
-
117
-
Ensure you have npm installed or follow the instructions to [install npm](https://docs.npmjs.com/downloading-and-installing-node-js-and-npm) in its documentation. In the `fastmcp-mcp-customtokenexchange-js` directory, install the required packages:
118
-
119
-
```shell
120
-
npm install
121
-
```
122
-
123
-
## Create your environment file
124
-
125
-
In the `fastmcp-mcp-customtokenexchange-js` directory, run the following command to create a new `.env` file populated with all the required environment variables:
&&echo".env file created with your Auth0 details:" \
144
-
&& cat .env
145
-
```
146
-
147
-
To get your Auth0 application’s `AUTH0_DOMAIN`, run the following command:
148
-
149
-
```shell
150
-
auth0 tenants list
151
-
```
95
+
<Tabtitle="Javascript"icon="js">
96
+
<Tabs>
97
+
<Tabtitle="Use sample app (recommended)">
98
+
Start by downloading the sample app for this quickstart. The sample includes a FastMCP MCP server with an Auth0 integration and a protected API built with
99
+
[Fastify](https://fastify.dev/).
152
100
153
-
Copy the domain under `TENANT` from the output and update the corresponding variable in the `.env` file.
101
+
<DownloadQuickstartButton
102
+
category="auth-for-mcp"
103
+
framework="fastmcp-mcp-customtokenexchange-js"
104
+
/>
154
105
155
-
For `MCP_AUTH0_CLIENT_ID` and `MCP_AUTH0_CLIENT_SECRET` you will use the values obtained from the [Create an Application for your MCP server](./call-your-apis-on-users-behalf#create-an-application-for-your-mcp-server) step.
106
+
Once downloaded, extract the files and open the project in your preferred IDE.
107
+
</Tab>
108
+
<Tabtitle="Clone GitHub repository">
109
+
Clone the repository and navigate to the sample app folder which includes a FastMCP MCP server with an Auth0 integration and a protected API built with
cd auth0-ai-samples/auth-for-mcp/fastmcp-mcp-customtokenexchange-js
115
+
```
158
116
159
-
This Action is the server-side logic Auth0 executes to perform the token exchange. It is necessary because the MCP server receives an access token from the client (with the MCP server as its audience) and must exchange it for a new token (with the upstream API as the audience). This Action validates the original token and mints the new one.
117
+
Once cloned, open the project in your preferred IDE.
118
+
</Tab>
119
+
</Tabs>
160
120
161
-
The Custom Token Exchange Action is available as part of Custom Token Exchange Early Access. Navigate to [the On-behalf-of token exchange for first-party apps template available here](https://manage.auth0.com/#/actions/library/templates/templates/daeda4e8-8da2-4abb-afb5-ac09df0ebb2a) and click on **Use This Template**.
121
+
The sample app demonstrates custom token exchange with a `greet` tool that calls your protected API on behalf of the authenticated user.
162
122
163
-
<Frame>
164
-
<img
165
-
src="/img/mcp/cte_action_template_page.png"
166
-
alt="Action On-behalf-of token exchange for first-party apps template page"
167
-
/>
168
-
</Frame>
123
+
## Install packages
169
124
170
-
This will open a modal for you to name the action:
125
+
Ensure you have npm installed or follow the instructions to [install npm](https://docs.npmjs.com/downloading-and-installing-node-js-and-npm) in its documentation. In the `fastmcp-mcp-customtokenexchange-js` directory, install the required packages:
171
126
172
-
<Frame>
173
-
<img
174
-
class="img-sizing"
175
-
src="/img/mcp/cte_action_creation_modal.png"
176
-
alt="Action creation modal"
177
-
/>
178
-
</Frame>
127
+
```shell
128
+
npm install
129
+
```
179
130
180
-
Once the action is created, you can **Deploy** it. When you deploy the Action, Auth0 assigns it an Action ID. You still need to add your custom logic to the Action, but first, get the Action ID to create the Custom Token Exchange Profile.
131
+
## Create your environment file
132
+
<CreateEnvFile/>
181
133
182
-
## Set up the token exchange profile
134
+
## Use Custom Token Exchange Action
135
+
<CustomTokenExchangeAction/>
183
136
184
-
<CreateProfile />
137
+
## Set up the token exchange profile
138
+
<CreateProfile />
185
139
186
-
## Run the MCP server and the API
140
+
## Run the MCP server and the API
141
+
<RunMcpServerJs/>
187
142
188
-
Run this command to start your server:
143
+
## Exchange your access token
144
+
<ExchangeAccessTokenJs/>
145
+
</Tab>
189
146
190
-
```shell
191
-
npm run start
192
-
```
147
+
<Tabtitle="Python"icon="python">
148
+
<Tabs>
149
+
<Tabtitle="Use sample app (recommended)">
150
+
Start by downloading the sample app for this quickstart. The sample includes a FastMCP MCP server with an Auth0 integration and a protected Starlette-based API.
193
151
194
-
And in a separate window run this command to start the API:
Once downloaded, extract the files and open the project in your preferred IDE.
158
+
</Tab>
159
+
<Tabtitle="Clone GitHub repository">
160
+
Clone the repository and navigate to the sample app folder which includes a FastMCP MCP server with an Auth0 integration and a protected Starlette-based API.
cd auth0-ai-samples/auth-for-mcp/fastmcp-mcp-customtokenexchange-python
165
+
```
201
166
202
-
To call your APIs on behalf of your users, the MCP server needs to exchange the Auth0 access token it received from the MCP client (with the audience set to the MCP server itself) for a new Auth0 access token with the audience set to your API. In Auth0, this is called Custom Token Exchange and uses [RFC 8693](https://www.rfc-editor.org/rfc/rfc8693.html).
167
+
Once cloned, open the project in your preferred IDE.
168
+
</Tab>
169
+
</Tabs>
203
170
204
-
### The Orchestrator: `bearerForUpstream`
171
+
The sample app demonstrates custom token exchange with a `greet` tool that calls your protected API on behalf of the authenticated user.
205
172
206
-
The process begins with the `bearerForUpstream` function. Its main job is to take the initial token (the `subjectToken`), manage the exchange process, and handle any potential errors gracefully.
173
+
## Install packages
207
174
208
-
This function serves as a safe wrapper around our exchange logic.
175
+
Ensure you have poetry installed or follow the instructions to [install poetry](https://python-poetry.org/docs/) in its documentation. In the `fastmcp-mcp-customtokenexchange-python` directory, install the required packages:
if (!subjectToken) return { token: null, scopes: null };
177
+
```shell
178
+
poetry install
179
+
```
213
180
214
-
try {
215
-
const result = await exchangeCustomToken(subjectToken);
216
-
return {
217
-
token: result.accessToken,
218
-
scopes: result.scope,
219
-
}
220
-
} catch (err) {
221
-
console.error('Error during token exchange:', err);
222
-
throw err;
223
-
}
224
-
}
225
-
```
181
+
## Create your environment file
182
+
<CreateEnvFile/>
226
183
227
-
As you can see, it calls `exchangeCustomToken` and, on a successful exchange, returns the new `accessToken` and its associated scope. If the exchange fails, it logs the error and re-throws it to be handled upstream.
184
+
## Use Custom Token Exchange Action
185
+
<CustomTokenExchangeAction/>
228
186
229
-
### The core logic: `exchangeCustomToken`
187
+
## Set up the token exchange profile
188
+
<CreateProfile />
230
189
231
-
This function, located in`src/auth0.ts`, contains the actual token exchange logic. It uses the `ApiClient` from the `auth0-api-js` SDK to simplify the interaction with Auth0's `/oauth/token` endpoint.
190
+
## Run the MCP server and the API
191
+
<RunMcpServerPython/>
232
192
233
-
First, we initialize the `ApiClient` with the credentials of the application performing the exchange:
234
-
235
-
```javascript wrap lines
236
-
const exchangeClient = new ApiClient({
237
-
domain: AUTH0_DOMAIN,
238
-
audience: API_AUTH0_AUDIENCE,
239
-
clientId: MCP_AUTH0_CLIENT_ID,
240
-
clientSecret: MCP_AUTH0_CLIENT_SECRET,
241
-
});
242
-
```
243
-
With the client configured, the `exchangeCustomToken` function calls the `getTokenByExchangeProfile` method. This method implements the [Custom Token Exchange](https://auth0.com/docs/authenticate/custom-token-exchange) flow.
244
-
245
-
```javascript wrap lines
246
-
export async function exchangeCustomToken(subjectToken: string) {
From the root of your sample app directory, run the following command to create a new `.env` file populated with all the required environment variables:
This Action is the server-side logic Auth0 executes to perform the token exchange. It is necessary because the MCP server receives an access token from the client (with the MCP server as its audience) and must exchange it for a new token (with the upstream API as the audience). This Action validates the original token and mints the new one.
2
+
3
+
The Custom Token Exchange Action is available as part of Custom Token Exchange Early Access. Navigate to [the On-behalf-of token exchange for first-party apps template available here](https://manage.auth0.com/#/actions/library/templates/templates/daeda4e8-8da2-4abb-afb5-ac09df0ebb2a) and click on **Use This Template**.
4
+
5
+
<Frame>
6
+
<img
7
+
src="/img/mcp/cte_action_template_page.png"
8
+
alt="Action On-behalf-of token exchange for first-party apps template page"
9
+
/>
10
+
</Frame>
11
+
12
+
This will open a modal for you to name the action:
13
+
14
+
<Frame>
15
+
<img
16
+
class="img-sizing"
17
+
src="/img/mcp/cte_action_creation_modal.png"
18
+
alt="Action creation modal"
19
+
/>
20
+
</Frame>
21
+
22
+
Once the action is created, you can **Deploy** it. When you deploy the Action, Auth0 assigns it an Action ID. You still need to add your custom logic to the Action, but first, get the Action ID to create the Custom Token Exchange Profile.
To call your APIs on behalf of your users, the MCP server needs to exchange the Auth0 access token it received from the MCP client (with the audience set to the MCP server itself) for a new Auth0 access token with the audience set to your API. In Auth0, this is called Custom Token Exchange and uses [RFC 8693](https://www.rfc-editor.org/rfc/rfc8693.html).
2
+
3
+
### The Orchestrator: `bearerForUpstream`
4
+
5
+
The process begins with the `bearerForUpstream` function. Its main job is to take the initial token (the `subjectToken`), manage the exchange process, and handle any potential errors gracefully.
6
+
7
+
This function serves as a safe wrapper around our exchange logic.
console.error('Error during token exchange:', err);
21
+
throw err;
22
+
}
23
+
}
24
+
```
25
+
26
+
As you can see, it calls `exchangeCustomToken` and, on a successful exchange, returns the new `accessToken` and its associated scope. If the exchange fails, it logs the error and re-throws it to be handled upstream.
27
+
28
+
### The core logic: `exchangeCustomToken`
29
+
30
+
This function, located in `src/auth0.ts`, contains the actual token exchange logic. It uses the `ApiClient` from the `auth0-api-js` SDK to simplify the interaction with Auth0's `/oauth/token` endpoint.
31
+
32
+
First, we initialize the `ApiClient` with the credentials of the application performing the exchange:
33
+
34
+
```javascript wrap lines
35
+
constexchangeClient=newApiClient({
36
+
domain:AUTH0_DOMAIN,
37
+
audience:API_AUTH0_AUDIENCE,
38
+
clientId:MCP_AUTH0_CLIENT_ID,
39
+
clientSecret:MCP_AUTH0_CLIENT_SECRET,
40
+
});
41
+
```
42
+
With the client configured, the `exchangeCustomToken` function uses the client's `getTokenByExchangeProfile` method to perform the token exchange. This method implements the [Custom Token Exchange](https://auth0.com/docs/authenticate/custom-token-exchange) flow.
0 commit comments