1# MCP and Connectors1# MCP servers
2 2
3> For the complete documentation index, see [llms.txt](/llms.txt). Markdown versions of documentation pages are available by appending `.md` to the page URL.3> For the complete documentation index, see [llms.txt](/llms.txt). Markdown versions of documentation pages are available by appending `.md` to the page URL.
4 4
5In addition to tools you make available to the model with [function calling](https://developers.openai.com/api/docs/guides/function-calling), you can give models new capabilities using **connectors** and **remote MCP servers**. These tools give the model the ability to connect to and control external services when needed to respond to a user's prompt. These tool calls can either be allowed automatically, or restricted with explicit approval required by you as the developer.5In addition to tools you make available to the model with [function calling](https://developers.openai.com/api/docs/guides/function-calling), you can give models new capabilities using **remote MCP servers** or **Secure MCP Tunnel**. These tools give the model the ability to connect to and control external services when needed to respond to a user's prompt. These tool calls can either be allowed automatically, or restricted with explicit approval required by you as the developer.
6 6
7- **Connectors** are OpenAI-maintained MCP wrappers for popular services like Google Workspace or Dropbox, like the connectors available in [ChatGPT](https://chatgpt.com).
8- **Remote MCP servers** can be any server on the public Internet that implements a remote [Model Context Protocol](https://modelcontextprotocol.io/introduction) (MCP) server.7- **Remote MCP servers** can be any server on the public Internet that implements a remote [Model Context Protocol](https://modelcontextprotocol.io/introduction) (MCP) server.
9 8
10This guide will show how to use both remote MCP servers and connectors with the Responses API. For Agents API sessions, see [MCP connections](https://developers.openai.com/api/docs/guides/agents-api/tools/mcp), which covers connections from the managed service or from your sandbox.9- **Secure MCP Tunnel** connects a local or private MCP server without exposing it to the public internet.
10
11This guide shows how to use MCP tools with the Responses API. Built-in connectors remain supported for existing models; see [Legacy connectors](#connectors) for the deprecation policy and compatibility examples. For Agents API sessions, see [MCP connections](https://developers.openai.com/api/docs/guides/agents-api/tools/mcp), which covers connections from the managed service or from your sandbox.
11 12
12## Secure MCP Tunnel13## Secure MCP Tunnel
13 14
15 16
16## Quickstart17## Quickstart
17 18
18Check out the examples below to see how remote MCP servers and connectors work through the [Responses API](https://developers.openai.com/api/reference/resources/responses/methods/create). Both connectors and remote MCP servers can be used with the `mcp` built-in tool type.19Use the `mcp` tool type in the [Responses API](https://developers.openai.com/api/reference/resources/responses/methods/create). Set `server_url` for a remote MCP server, or use `tunnel_id` for a local MCP server through [Secure MCP Tunnel](https://developers.openai.com/api/docs/guides/secure-mcp-tunnels). Depending on the server, you may also need an OAuth access token in the `authorization` parameter.
19
20
21
22Using remote MCP servers
23
24
25 20
26 Remote MCP servers require a `server_url`. Depending on the server,21Using a remote MCP server in the Responses API
27 you may also need an OAuth `authorization` parameter containing an
28 access token.
29
30
31
32 Using a remote MCP server in the Responses API
33 22
34```bash23```bash
35curl https://api.openai.com/v1/responses \ 24curl https://api.openai.com/v1/responses \
196```185```
197 186
198 187
199 It is very important that developers trust any remote MCP server they use with188It is very important that developers trust any remote MCP server they use with
200 the Responses API. A malicious server can exfiltrate sensitive data from189 the Responses API. A malicious server can exfiltrate sensitive data from
201 anything that enters the model's context. Carefully review the 190 anything that enters the model's context. Carefully review the
202 **Risks and Safety** section below before using this tool.191 **Risks and Safety** section below before using this tool.
203 192
204 193The API will return new items in the `output` array of the model response. If the model decides to use an MCP server, it will first make a request to list available tools from the server, which will create a `mcp_list_tools` output item. From the remote MCP server example above, it contains only one tool definition:
205
206
207
208
209Using connectors
210
211
212
213 Connectors require a `connector_id` parameter, and an OAuth access
214 token provided by your application in the `authorization` parameter.
215
216
217
218 Using connectors in the Responses API
219
220```bash
221curl https://api.openai.com/v1/responses \
222-H "Content-Type: application/json" \
223-H "Authorization: Bearer $OPENAI_API_KEY" \
224-d '{
225 "model": "gpt-6-astra",
226 "tools": [
227 {
228 "type": "mcp",
229 "server_label": "Dropbox",
230 "connector_id": "connector_dropbox",
231 "authorization": "<oauth access token>",
232 "require_approval": "never"
233 }
234 ],
235 "input": "Summarize the Q2 earnings report."
236 }'
237```
238
239```javascript
240import OpenAI from "openai";
241const client = new OpenAI();
242
243const resp = await client.responses.create({
244 model: "gpt-6-astra",
245 tools: [
246 {
247 type: "mcp",
248 server_label: "Dropbox",
249 connector_id: "connector_dropbox",
250 authorization: "<oauth access token>",
251 require_approval: "never",
252 },
253 ],
254 input: "Summarize the Q2 earnings report.",
255});
256
257console.log(resp.output_text);
258```
259
260```python
261import os
262
263from openai import OpenAI
264
265client = OpenAI()
266connector_authorization = os.environ["OPENAI_CONNECTOR_AUTHORIZATION"]
267
268resp = client.responses.create(
269 model="gpt-6-astra",
270 tools=[
271 {
272 "type": "mcp",
273 "server_label": "Dropbox",
274 "connector_id": "connector_dropbox",
275 "authorization": connector_authorization,
276 "require_approval": "never",
277 },
278 ],
279 input="Summarize the Q2 earnings report.",
280)
281
282print(resp.output_text)
283```
284
285```go
286package main
287
288import (
289 "context"
290 "fmt"
291
292 "github.com/openai/openai-go/v3"
293 "github.com/openai/openai-go/v3/responses"
294)
295
296func main() {
297 client := openai.NewClient()
298 tool := responses.ToolParamOfMcp("Dropbox")
299 tool.OfMcp.ConnectorID = "connector_dropbox"
300 tool.OfMcp.Authorization = openai.String("<oauth access token>")
301 tool.OfMcp.RequireApproval = responses.ToolMcpRequireApprovalUnionParam{OfMcpToolApprovalSetting: openai.String("never")}
302
303 response, err := client.Responses.New(context.Background(), responses.ResponseNewParams{
304 Model: "gpt-6-astra",
305 Tools: []responses.ToolUnionParam{tool},
306 Input: responses.ResponseNewParamsInputUnion{OfString: openai.String("Summarize the Q2 earnings report.")},
307 })
308 if err != nil {
309 panic(err)
310 }
311 fmt.Println(response.OutputText())
312}
313```
314
315```java
316import com.openai.client.OpenAIClient;
317import com.openai.client.okhttp.OpenAIOkHttpClient;
318import com.openai.models.responses.ResponseCreateParams;
319import com.openai.models.responses.Tool;
320
321String oauthAccessToken = "<oauth access token>";
322
323ResponseCreateParams params =
324 ResponseCreateParams.builder()
325 .model("gpt-6-astra")
326 .input("Summarize the Q2 earnings report.")
327 .addTool(
328 Tool.Mcp.builder()
329 .serverLabel("Dropbox")
330 .connectorId(Tool.Mcp.ConnectorId.of("connector_dropbox"))
331 .authorization(oauthAccessToken)
332 .requireApproval(Tool.Mcp.RequireApproval.McpToolApprovalSetting.NEVER)
333 .build())
334 .build();
335
336client.responses().create(params).output().stream()
337 .flatMap(item -> item.message().stream())
338 .flatMap(message -> message.content().stream())
339 .flatMap(content -> content.outputText().stream())
340 .forEach(text -> System.out.println(text.text()));
341```
342
343```csharp
344using OpenAI.Responses;
345#pragma warning disable OPENAI001
346
347string dropboxToken =
348 Environment.GetEnvironmentVariable("DROPBOX_OAUTH_ACCESS_TOKEN")!;
349string key = Environment.GetEnvironmentVariable("OPENAI_API_KEY")!;
350ResponsesClient client = new(key);
351
352CreateResponseOptions options = new() { Model = "gpt-6-astra" };
353options.Tools.Add(
354 ResponseTool.CreateMcpTool(
355 serverLabel: "Dropbox",
356 connectorId: McpToolConnectorId.Dropbox,
357 authorizationToken: dropboxToken,
358 toolCallApprovalPolicy: DefaultMcpToolCallApprovalPolicy.NeverRequireApproval
359 )
360);
361options.InputItems.Add(
362 ResponseItem.CreateUserMessageItem("Summarize the Q2 earnings report.")
363);
364
365ResponseResult response = await client.CreateResponseAsync(options);
366
367Console.WriteLine(response.GetOutputText());
368```
369
370```ruby
371require "openai"
372
373client = OpenAI::Client.new
374response = client.responses.create(
375 model: "gpt-6-astra",
376 input: "Summarize the Q2 earnings report.",
377 tools: [
378 {
379 type: :mcp,
380 server_label: "Dropbox",
381 connector_id: "connector_dropbox",
382 authorization: "<oauth access token>",
383 require_approval: :never
384 }
385 ]
386)
387
388puts(response.output_text)
389```
390
391
392
393The API will return new items in the `output` array of the model response. If the model decides to use a Connector or MCP server, it will first make a request to list available tools from the server, which will create a `mcp_list_tools` output item. From the remote MCP server example above, it contains only one tool definition:
394 194
395```json195```json
396{196{
437 237
438## How it works238## How it works
439 239
440The MCP tool (for both remote MCP servers and connectors) is available in the [Responses API](https://developers.openai.com/api/reference/resources/responses/methods/create) in most recent models. Check MCP tool compatibility for your model [here](https://developers.openai.com/api/docs/models). When you're using the MCP tool, you only pay for [tokens](https://developers.openai.com/api/docs/pricing) used when importing tool definitions or making tool calls. No additional fees apply per tool call.240The MCP tool is available in the [Responses API](https://developers.openai.com/api/reference/resources/responses/methods/create) in most recent models. Check MCP tool compatibility for your model [here](https://developers.openai.com/api/docs/models). When you're using the MCP tool, you only pay for [tokens](https://developers.openai.com/api/docs/pricing) used when importing tool definitions or making tool calls. No additional fees apply per tool call.
441 241
442Below, we'll step through the process the API takes when calling an MCP tool.242Below, we'll step through the process the API takes when calling an MCP tool.
443 243
1292 1092
1293To prevent the leakage of sensitive tokens, the Responses API does not store the value you provide in the `authorization` field. This value will also not be visible in the Response object created. Because of this, you must send the `authorization` value in every Responses API creation request you make.1093To prevent the leakage of sensitive tokens, the Responses API does not store the value you provide in the `authorization` field. This value will also not be visible in the Response object created. Because of this, you must send the `authorization` value in every Responses API creation request you make.
1294 1094
1295## Connectors1095<a id="connectors"></a>
1096
1097## Legacy connectors
1098
1099`connector_id` is deprecated for models released after September 1,
1100 2026. Use `server_url` to connect to a remote MCP server, or
1101 `tunnel_id` to connect to a local MCP server through
1102 [Secure MCP Tunnel](https://developers.openai.com/api/docs/guides/secure-mcp-tunnels). Existing
1103 models retain connector support. The examples in this section use
1104 `gpt-5.2`, which predates the cutoff.
1296 1105
1297The Responses API has built-in support for a limited set of connectors to third-party services. These connectors let you pull in context from popular applications, like Dropbox and Gmail, to allow the model to interact with popular services.1106The Responses API has built-in support for a limited set of connectors to third-party services. These connectors let you pull in context from popular applications, like Dropbox and Gmail, to allow the model to interact with popular services.
1298 1107
1299Connectors can be used in the same way as remote MCP servers. Both let an OpenAI model access additional third-party tools in an API request. However, instead of passing a `server_url` as you would to call a remote MCP server, you pass a `connector_id` which uniquely identifies a connector available in the API.1108Connectors can be used in the same way as remote MCP servers. Both let an OpenAI model access additional third-party tools in an API request. However, instead of passing a `server_url` as you would to call a remote MCP server, you pass a `connector_id` which uniquely identifies a connector available in the API.
1300 1109
1110Connectors require an OAuth access token provided by your application in the `authorization` parameter.
1111
1112Use a legacy connector with GPT-5.2
1113
1114```bash
1115curl https://api.openai.com/v1/responses \
1116-H "Content-Type: application/json" \
1117-H "Authorization: Bearer $OPENAI_API_KEY" \
1118-d '{
1119 "model": "gpt-5.2",
1120 "tools": [
1121 {
1122 "type": "mcp",
1123 "server_label": "Dropbox",
1124 "connector_id": "connector_dropbox",
1125 "authorization": "<oauth access token>",
1126 "require_approval": "never"
1127 }
1128 ],
1129 "input": "Summarize the Q2 earnings report."
1130 }'
1131```
1132
1133```javascript
1134import OpenAI from "openai";
1135const client = new OpenAI();
1136
1137const resp = await client.responses.create({
1138 model: "gpt-5.2",
1139 tools: [
1140 {
1141 type: "mcp",
1142 server_label: "Dropbox",
1143 connector_id: "connector_dropbox",
1144 authorization: "<oauth access token>",
1145 require_approval: "never",
1146 },
1147 ],
1148 input: "Summarize the Q2 earnings report.",
1149});
1150
1151console.log(resp.output_text);
1152```
1153
1154```python
1155import os
1156
1157from openai import OpenAI
1158
1159client = OpenAI()
1160connector_authorization = os.environ["OPENAI_CONNECTOR_AUTHORIZATION"]
1161
1162resp = client.responses.create(
1163 model="gpt-5.2",
1164 tools=[
1165 {
1166 "type": "mcp",
1167 "server_label": "Dropbox",
1168 "connector_id": "connector_dropbox",
1169 "authorization": connector_authorization,
1170 "require_approval": "never",
1171 },
1172 ],
1173 input="Summarize the Q2 earnings report.",
1174)
1175
1176print(resp.output_text)
1177```
1178
1179```go
1180package main
1181
1182import (
1183 "context"
1184 "fmt"
1185
1186 "github.com/openai/openai-go/v3"
1187 "github.com/openai/openai-go/v3/responses"
1188)
1189
1190func main() {
1191 client := openai.NewClient()
1192 tool := responses.ToolParamOfMcp("Dropbox")
1193 tool.OfMcp.ConnectorID = "connector_dropbox"
1194 tool.OfMcp.Authorization = openai.String("<oauth access token>")
1195 tool.OfMcp.RequireApproval = responses.ToolMcpRequireApprovalUnionParam{OfMcpToolApprovalSetting: openai.String("never")}
1196
1197 response, err := client.Responses.New(context.Background(), responses.ResponseNewParams{
1198 Model: "gpt-5.2",
1199 Tools: []responses.ToolUnionParam{tool},
1200 Input: responses.ResponseNewParamsInputUnion{OfString: openai.String("Summarize the Q2 earnings report.")},
1201 })
1202 if err != nil {
1203 panic(err)
1204 }
1205 fmt.Println(response.OutputText())
1206}
1207```
1208
1209```java
1210import com.openai.client.OpenAIClient;
1211import com.openai.client.okhttp.OpenAIOkHttpClient;
1212import com.openai.models.responses.ResponseCreateParams;
1213import com.openai.models.responses.Tool;
1214
1215String oauthAccessToken = "<oauth access token>";
1216
1217ResponseCreateParams params =
1218 ResponseCreateParams.builder()
1219 .model("gpt-5.2")
1220 .input("Summarize the Q2 earnings report.")
1221 .addTool(
1222 Tool.Mcp.builder()
1223 .serverLabel("Dropbox")
1224 .connectorId(Tool.Mcp.ConnectorId.of("connector_dropbox"))
1225 .authorization(oauthAccessToken)
1226 .requireApproval(Tool.Mcp.RequireApproval.McpToolApprovalSetting.NEVER)
1227 .build())
1228 .build();
1229
1230client.responses().create(params).output().stream()
1231 .flatMap(item -> item.message().stream())
1232 .flatMap(message -> message.content().stream())
1233 .flatMap(content -> content.outputText().stream())
1234 .forEach(text -> System.out.println(text.text()));
1235```
1236
1237```csharp
1238using OpenAI.Responses;
1239#pragma warning disable OPENAI001
1240
1241string dropboxToken =
1242 Environment.GetEnvironmentVariable("DROPBOX_OAUTH_ACCESS_TOKEN")!;
1243string key = Environment.GetEnvironmentVariable("OPENAI_API_KEY")!;
1244ResponsesClient client = new(key);
1245
1246CreateResponseOptions options = new() { Model = "gpt-5.2" };
1247options.Tools.Add(
1248 ResponseTool.CreateMcpTool(
1249 serverLabel: "Dropbox",
1250 connectorId: McpToolConnectorId.Dropbox,
1251 authorizationToken: dropboxToken,
1252 toolCallApprovalPolicy: DefaultMcpToolCallApprovalPolicy.NeverRequireApproval
1253 )
1254);
1255options.InputItems.Add(
1256 ResponseItem.CreateUserMessageItem("Summarize the Q2 earnings report.")
1257);
1258
1259ResponseResult response = await client.CreateResponseAsync(options);
1260
1261Console.WriteLine(response.GetOutputText());
1262```
1263
1264```ruby
1265require "openai"
1266
1267client = OpenAI::Client.new
1268response = client.responses.create(
1269 model: "gpt-5.2",
1270 input: "Summarize the Q2 earnings report.",
1271 tools: [
1272 {
1273 type: :mcp,
1274 server_label: "Dropbox",
1275 connector_id: "connector_dropbox",
1276 authorization: "<oauth access token>",
1277 require_approval: :never
1278 }
1279 ]
1280)
1281
1282puts(response.output_text)
1283```
1284
1285
1301### Available connectors1286### Available connectors
1302 1287
1303- Dropbox: `connector_dropbox`1288- Dropbox: `connector_dropbox`
1334 -H "Content-Type: application/json" \1319 -H "Content-Type: application/json" \
1335 -H "Authorization: Bearer $OPENAI_API_KEY" \1320 -H "Authorization: Bearer $OPENAI_API_KEY" \
1336 -d '{1321 -d '{
1337 "model": "gpt-6-astra",1322 "model": "gpt-5.2",
1338 "tools": [1323 "tools": [
1339 {1324 {
1340 "type": "mcp",1325 "type": "mcp",
1353const client = new OpenAI();1338const client = new OpenAI();
1354 1339
1355const resp = await client.responses.create({1340const resp = await client.responses.create({
1356 model: "gpt-6-astra",1341 model: "gpt-5.2",
1357 tools: [1342 tools: [
1358 {1343 {
1359 type: "mcp",1344 type: "mcp",
1377authorization = os.environ["GOOGLE_CALENDAR_OAUTH_ACCESS_TOKEN"]1362authorization = os.environ["GOOGLE_CALENDAR_OAUTH_ACCESS_TOKEN"]
1378 1363
1379resp = client.responses.create(1364resp = client.responses.create(
1380 model="gpt-6-astra",1365 model="gpt-5.2",
1381 tools=[1366 tools=[
1382 {1367 {
1383 "type": "mcp",1368 "type": "mcp",
1412 tool.OfMcp.RequireApproval = responses.ToolMcpRequireApprovalUnionParam{OfMcpToolApprovalSetting: openai.String("never")}1397 tool.OfMcp.RequireApproval = responses.ToolMcpRequireApprovalUnionParam{OfMcpToolApprovalSetting: openai.String("never")}
1413 1398
1414 response, err := client.Responses.New(context.Background(), responses.ResponseNewParams{1399 response, err := client.Responses.New(context.Background(), responses.ResponseNewParams{
1415 Model: "gpt-6-astra",1400 Model: "gpt-5.2",
1416 Tools: []responses.ToolUnionParam{tool},1401 Tools: []responses.ToolUnionParam{tool},
1417 Input: responses.ResponseNewParamsInputUnion{OfString: openai.String("What's on my Google Calendar for today?")},1402 Input: responses.ResponseNewParamsInputUnion{OfString: openai.String("What's on my Google Calendar for today?")},
1418 })1403 })
1433 1418
1434ResponseCreateParams params =1419ResponseCreateParams params =
1435 ResponseCreateParams.builder()1420 ResponseCreateParams.builder()
1436 .model("gpt-6-astra")1421 .model("gpt-5.2")
1437 .input("What's on my Google Calendar for today?")1422 .input("What's on my Google Calendar for today?")
1438 .addTool(1423 .addTool(
1439 Tool.Mcp.builder()1424 Tool.Mcp.builder()
1460string key = Environment.GetEnvironmentVariable("OPENAI_API_KEY")!;1445string key = Environment.GetEnvironmentVariable("OPENAI_API_KEY")!;
1461ResponsesClient client = new(key);1446ResponsesClient client = new(key);
1462 1447
1463CreateResponseOptions options = new() { Model = "gpt-6-astra" };1448CreateResponseOptions options = new() { Model = "gpt-5.2" };
1464options.Tools.Add(1449options.Tools.Add(
1465 ResponseTool.CreateMcpTool(1450 ResponseTool.CreateMcpTool(
1466 serverLabel: "google_calendar",1451 serverLabel: "google_calendar",
1483 1468
1484client = OpenAI::Client.new1469client = OpenAI::Client.new
1485response = client.responses.create(1470response = client.responses.create(
1486 model: "gpt-6-astra",1471 model: "gpt-5.2",
1487 input: "What's on my Google Calendar for today?",1472 input: "What's on my Google Calendar for today?",
1488 tools: [1473 tools: [
1489 {1474 {