or run

npx @tessl/cli init
Log in

Version

Tile

Overview

Evals

Files

Files

docs

auth-tokens.mdbatch.mdcaching.mdchat.mdclient.mdcontent-generation.mdembeddings.mdfile-search-stores.mdfiles.mdfunction-calling.mdimage-generation.mdindex.mdlive.mdmcp.mdmodels.mdoperations.mdtuning.mdvideo-generation.md

mcp.mddocs/

0

# MCP Integration (Experimental)

1

2

The MCP (Model Context Protocol) integration allows you to convert MCP clients and tools into Gemini-compatible tools for extended functionality and interoperability.

3

4

## Capabilities

5

6

### mcpToTool

7

8

Convert MCP clients or tools to Gemini CallableTool interface.

9

10

```typescript { .api }

11

/**

12

* Convert MCP clients/tools to Gemini tools

13

* @param mcpClientOrTools - MCP client or tools array

14

* @param config - Tool configuration

15

* @returns Promise resolving to callable tool

16

*/

17

function mcpToTool(

18

mcpClientOrTools: McpClient | McpTool[],

19

config?: CallableToolConfig

20

): Promise<CallableTool>;

21

22

interface CallableToolConfig {

23

/** Tool display name */

24

displayName?: string;

25

/** Tool description */

26

description?: string;

27

/** Additional configuration */

28

[key: string]: unknown;

29

}

30

```

31

32

**Usage Examples:**

33

34

```typescript

35

import { GoogleGenAI, mcpToTool } from '@google/genai';

36

import { McpClient } from '@modelcontextprotocol/sdk';

37

38

const client = new GoogleGenAI({ apiKey: 'YOUR_API_KEY' });

39

40

// Connect to MCP server

41

const mcpClient = new McpClient({

42

serverUrl: 'http://localhost:3000'

43

});

44

45

await mcpClient.connect();

46

47

// Convert MCP client to Gemini tool

48

const mcpTool = await mcpToTool(mcpClient, {

49

displayName: 'External MCP Tools',

50

description: 'Tools provided by MCP server'

51

});

52

53

// Use in generation with automatic function calling

54

const response = await client.models.generateContent({

55

model: 'gemini-2.0-flash',

56

contents: 'Use the available tools to complete this task',

57

config: {

58

tools: [mcpTool],

59

automaticFunctionCalling: {

60

maximumRemoteCalls: 10

61

}

62

}

63

});

64

65

console.log('Response:', response.text);

66

67

// Close MCP connection

68

await mcpClient.disconnect();

69

```

70

71

## Types

72

73

### McpClient

74

75

MCP client interface (from @modelcontextprotocol/sdk).

76

77

```typescript { .api }

78

interface McpClient {

79

/** Connect to MCP server */

80

connect(): Promise<void>;

81

/** Disconnect from MCP server */

82

disconnect(): Promise<void>;

83

/** List available tools */

84

listTools(): Promise<McpTool[]>;

85

/** Call a tool */

86

callTool(name: string, args: Record<string, unknown>): Promise<unknown>;

87

}

88

```

89

90

### McpTool

91

92

MCP tool definition.

93

94

```typescript { .api }

95

interface McpTool {

96

/** Tool name */

97

name: string;

98

/** Tool description */

99

description?: string;

100

/** Input schema */

101

inputSchema?: {

102

type: string;

103

properties?: Record<string, unknown>;

104

required?: string[];

105

};

106

}

107

```

108

109

### CallableTool

110

111

Gemini callable tool interface.

112

113

```typescript { .api }

114

interface CallableTool {

115

/** Get tool declaration */

116

tool(): Promise<Tool>;

117

/** Execute function calls */

118

callTool(functionCalls: FunctionCall[]): Promise<Part[]>;

119

}

120

```

121

122

## Complete Examples

123

124

### Connect to MCP Server

125

126

```typescript

127

import { GoogleGenAI, mcpToTool } from '@google/genai';

128

import { McpClient } from '@modelcontextprotocol/sdk';

129

130

const client = new GoogleGenAI({ apiKey: 'YOUR_API_KEY' });

131

132

// Create and connect MCP client

133

const mcpClient = new McpClient({

134

serverUrl: 'http://localhost:3000',

135

apiKey: 'MCP_SERVER_KEY'

136

});

137

138

await mcpClient.connect();

139

console.log('Connected to MCP server');

140

141

// List available tools

142

const tools = await mcpClient.listTools();

143

console.log('Available MCP tools:');

144

tools.forEach(tool => {

145

console.log(` - ${tool.name}: ${tool.description}`);

146

});

147

148

// Convert to Gemini tool

149

const geminiTool = await mcpToTool(mcpClient);

150

151

// Use in generation

152

const response = await client.models.generateContent({

153

model: 'gemini-2.0-flash',

154

contents: 'Search for information about AI',

155

config: {

156

tools: [geminiTool]

157

}

158

});

159

160

// Handle function calls manually

161

if (response.functionCalls) {

162

console.log('MCP tools were called:', response.functionCalls);

163

}

164

165

// Cleanup

166

await mcpClient.disconnect();

167

```

168

169

### Use Specific MCP Tools

170

171

```typescript

172

import { McpTool } from '@modelcontextprotocol/sdk';

173

174

// Define specific MCP tools

175

const mcpTools: McpTool[] = [

176

{

177

name: 'search_database',

178

description: 'Search the database',

179

inputSchema: {

180

type: 'object',

181

properties: {

182

query: { type: 'string' },

183

limit: { type: 'number' }

184

},

185

required: ['query']

186

}

187

},

188

{

189

name: 'get_weather',

190

description: 'Get weather information',

191

inputSchema: {

192

type: 'object',

193

properties: {

194

location: { type: 'string' }

195

},

196

required: ['location']

197

}

198

}

199

];

200

201

// Convert tools (not client)

202

const geminiTool = await mcpToTool(mcpTools, {

203

displayName: 'Database and Weather Tools'

204

});

205

206

// Use in generation

207

const response = await client.models.generateContent({

208

model: 'gemini-2.0-flash',

209

contents: 'Search the database for AI papers and check weather in San Francisco',

210

config: {

211

tools: [geminiTool],

212

automaticFunctionCalling: {

213

maximumRemoteCalls: 5

214

}

215

}

216

});

217

218

console.log('Response:', response.text);

219

```

220

221

### MCP with Streaming

222

223

```typescript

224

// Connect MCP client

225

const mcpClient = new McpClient({

226

serverUrl: 'http://localhost:3000'

227

});

228

229

await mcpClient.connect();

230

231

// Convert to tool

232

const mcpTool = await mcpToTool(mcpClient);

233

234

// Stream with MCP tools

235

const stream = await client.models.generateContentStream({

236

model: 'gemini-2.0-flash',

237

contents: 'Use the tools to gather information',

238

config: {

239

tools: [mcpTool]

240

}

241

});

242

243

for await (const chunk of stream) {

244

if (chunk.text) {

245

process.stdout.write(chunk.text);

246

}

247

248

// Check for function calls

249

if (chunk.functionCalls) {

250

console.log('\nMCP tools invoked:', chunk.functionCalls);

251

}

252

}

253

254

await mcpClient.disconnect();

255

```

256

257

### MCP in Chat Session

258

259

```typescript

260

// Setup MCP

261

const mcpClient = new McpClient({

262

serverUrl: 'http://localhost:3000'

263

});

264

265

await mcpClient.connect();

266

const mcpTool = await mcpToTool(mcpClient);

267

268

// Create chat with MCP tools

269

const chat = client.chats.create({

270

model: 'gemini-2.0-flash',

271

config: {

272

tools: [mcpTool],

273

systemInstruction: 'You are a helpful assistant with access to external tools.'

274

}

275

});

276

277

// Multi-turn conversation with MCP

278

const r1 = await chat.sendMessage({

279

message: 'Search for recent AI developments'

280

});

281

console.log('Assistant:', r1.text);

282

283

const r2 = await chat.sendMessage({

284

message: 'Get more details about the first result'

285

});

286

console.log('Assistant:', r2.text);

287

288

// Cleanup

289

await mcpClient.disconnect();

290

```

291

292

### Multiple MCP Servers

293

294

```typescript

295

// Connect to multiple MCP servers

296

const mcpClient1 = new McpClient({

297

serverUrl: 'http://localhost:3000'

298

});

299

300

const mcpClient2 = new McpClient({

301

serverUrl: 'http://localhost:4000'

302

});

303

304

await Promise.all([

305

mcpClient1.connect(),

306

mcpClient2.connect()

307

]);

308

309

// Convert each to tool

310

const [tool1, tool2] = await Promise.all([

311

mcpToTool(mcpClient1, { displayName: 'Database Tools' }),

312

mcpToTool(mcpClient2, { displayName: 'API Tools' })

313

]);

314

315

// Use both in generation

316

const response = await client.models.generateContent({

317

model: 'gemini-2.0-flash',

318

contents: 'Use both database and API tools to gather information',

319

config: {

320

tools: [tool1, tool2],

321

automaticFunctionCalling: {

322

maximumRemoteCalls: 10

323

}

324

}

325

});

326

327

console.log('Response:', response.text);

328

329

// Cleanup

330

await Promise.all([

331

mcpClient1.disconnect(),

332

mcpClient2.disconnect()

333

]);

334

```

335

336

### MCP with Custom Tool Implementation

337

338

```typescript

339

import { CallableTool, Tool, FunctionCall, Part } from '@google/genai';

340

import { McpClient } from '@modelcontextprotocol/sdk';

341

342

// Custom wrapper for MCP client

343

class CustomMcpTool implements CallableTool {

344

constructor(private mcpClient: McpClient) {}

345

346

async tool(): Promise<Tool> {

347

// Get tools from MCP server

348

const mcpTools = await this.mcpClient.listTools();

349

350

// Convert to Gemini format

351

const functionDeclarations = mcpTools.map(mcpTool => ({

352

name: mcpTool.name,

353

description: mcpTool.description,

354

parametersJsonSchema: mcpTool.inputSchema

355

}));

356

357

return {

358

functionDeclarations

359

};

360

}

361

362

async callTool(functionCalls: FunctionCall[]): Promise<Part[]> {

363

const results: Part[] = [];

364

365

for (const fc of functionCalls) {

366

try {

367

console.log(`Calling MCP tool: ${fc.name}`);

368

369

// Call MCP server

370

const result = await this.mcpClient.callTool(fc.name!, fc.args || {});

371

372

results.push({

373

functionResponse: {

374

name: fc.name,

375

response: { result },

376

id: fc.id

377

}

378

});

379

} catch (error) {

380

console.error(`MCP tool error: ${fc.name}`, error);

381

382

results.push({

383

functionResponse: {

384

name: fc.name,

385

response: {

386

error: error.message

387

},

388

id: fc.id

389

}

390

});

391

}

392

}

393

394

return results;

395

}

396

}

397

398

// Use custom wrapper

399

const mcpClient = new McpClient({ serverUrl: 'http://localhost:3000' });

400

await mcpClient.connect();

401

402

const customTool = new CustomMcpTool(mcpClient);

403

404

const response = await client.models.generateContent({

405

model: 'gemini-2.0-flash',

406

contents: 'Use the tools',

407

config: {

408

tools: [customTool],

409

automaticFunctionCalling: {

410

maximumRemoteCalls: 5

411

}

412

}

413

});

414

```

415

416

### Error Handling with MCP

417

418

```typescript

419

// MCP connection with error handling

420

async function connectMcpWithRetry(

421

config: { serverUrl: string },

422

maxRetries: number = 3

423

): Promise<McpClient> {

424

const mcpClient = new McpClient(config);

425

426

for (let attempt = 1; attempt <= maxRetries; attempt++) {

427

try {

428

await mcpClient.connect();

429

console.log('Connected to MCP server');

430

return mcpClient;

431

} catch (error) {

432

console.error(`Connection attempt ${attempt} failed:`, error);

433

434

if (attempt === maxRetries) {

435

throw new Error('Failed to connect to MCP server after retries');

436

}

437

438

await new Promise(resolve => setTimeout(resolve, 2000));

439

}

440

}

441

442

throw new Error('Unexpected error');

443

}

444

445

// Use with error handling

446

try {

447

const mcpClient = await connectMcpWithRetry({

448

serverUrl: 'http://localhost:3000'

449

});

450

451

const mcpTool = await mcpToTool(mcpClient);

452

453

const response = await client.models.generateContent({

454

model: 'gemini-2.0-flash',

455

contents: 'Use the MCP tools',

456

config: {

457

tools: [mcpTool]

458

}

459

});

460

461

console.log('Response:', response.text);

462

463

await mcpClient.disconnect();

464

} catch (error) {

465

console.error('MCP error:', error);

466

}

467

```

468

469

### MCP Tool Discovery

470

471

```typescript

472

// Discover and document MCP tools

473

async function discoverMcpTools(mcpClient: McpClient): Promise<void> {

474

await mcpClient.connect();

475

476

const tools = await mcpClient.listTools();

477

478

console.log(`Discovered ${tools.length} MCP tools:\n`);

479

480

tools.forEach((tool, index) => {

481

console.log(`${index + 1}. ${tool.name}`);

482

console.log(` Description: ${tool.description || 'N/A'}`);

483

484

if (tool.inputSchema?.properties) {

485

console.log(' Parameters:');

486

Object.entries(tool.inputSchema.properties).forEach(([name, schema]: [string, any]) => {

487

const required = tool.inputSchema?.required?.includes(name) ? '(required)' : '(optional)';

488

console.log(` - ${name}: ${schema.type} ${required}`);

489

if (schema.description) {

490

console.log(` ${schema.description}`);

491

}

492

});

493

}

494

495

console.log('');

496

});

497

498

await mcpClient.disconnect();

499

}

500

501

// Discover tools

502

const mcpClient = new McpClient({

503

serverUrl: 'http://localhost:3000'

504

});

505

506

await discoverMcpTools(mcpClient);

507

```

508

509

### MCP with Function Calling Mode

510

511

```typescript

512

import { FunctionCallingConfigMode } from '@google/genai';

513

514

// Connect MCP

515

const mcpClient = new McpClient({

516

serverUrl: 'http://localhost:3000'

517

});

518

519

await mcpClient.connect();

520

const mcpTool = await mcpToTool(mcpClient);

521

522

// Force model to use MCP tools

523

const response = await client.models.generateContent({

524

model: 'gemini-2.0-flash',

525

contents: 'Get information',

526

config: {

527

tools: [mcpTool],

528

toolConfig: {

529

functionCallingConfig: {

530

mode: FunctionCallingConfigMode.ANY // Must call at least one tool

531

}

532

}

533

}

534

});

535

536

console.log('Response:', response.text);

537

538

await mcpClient.disconnect();

539

```

540

541

### MCP Health Check

542

543

```typescript

544

// Monitor MCP server health

545

class McpHealthMonitor {

546

private mcpClient: McpClient;

547

private isHealthy: boolean = false;

548

549

constructor(serverUrl: string) {

550

this.mcpClient = new McpClient({ serverUrl });

551

}

552

553

async check(): Promise<boolean> {

554

try {

555

await this.mcpClient.connect();

556

557

// Try to list tools as health check

558

const tools = await this.mcpClient.listTools();

559

560

this.isHealthy = tools.length >= 0;

561

562

await this.mcpClient.disconnect();

563

564

return this.isHealthy;

565

} catch (error) {

566

console.error('MCP health check failed:', error);

567

this.isHealthy = false;

568

return false;

569

}

570

}

571

572

async waitUntilHealthy(timeoutMs: number = 30000): Promise<void> {

573

const startTime = Date.now();

574

575

while (Date.now() - startTime < timeoutMs) {

576

const healthy = await this.check();

577

578

if (healthy) {

579

console.log('MCP server is healthy');

580

return;

581

}

582

583

await new Promise(resolve => setTimeout(resolve, 1000));

584

}

585

586

throw new Error('MCP server health check timeout');

587

}

588

589

isServerHealthy(): boolean {

590

return this.isHealthy;

591

}

592

}

593

594

// Use health monitor

595

const monitor = new McpHealthMonitor('http://localhost:3000');

596

597

await monitor.waitUntilHealthy();

598

599

if (monitor.isServerHealthy()) {

600

// Proceed with MCP integration

601

const mcpClient = new McpClient({

602

serverUrl: 'http://localhost:3000'

603

});

604

605

await mcpClient.connect();

606

const mcpTool = await mcpToTool(mcpClient);

607

608

// Use tool...

609

610

await mcpClient.disconnect();

611

}

612

```

613

614

### Combined Native and MCP Tools

615

616

```typescript

617

import { Type } from '@google/genai';

618

619

// Define native Gemini tool

620

const nativeTool = {

621

functionDeclarations: [{

622

name: 'calculate',

623

description: 'Perform calculation',

624

parameters: {

625

type: Type.OBJECT,

626

properties: {

627

expression: { type: Type.STRING }

628

}

629

}

630

}]

631

};

632

633

// Setup MCP tool

634

const mcpClient = new McpClient({

635

serverUrl: 'http://localhost:3000'

636

});

637

638

await mcpClient.connect();

639

const mcpTool = await mcpToTool(mcpClient);

640

641

// Use both together

642

const response = await client.models.generateContent({

643

model: 'gemini-2.0-flash',

644

contents: 'Calculate 2+2 and search for information',

645

config: {

646

tools: [nativeTool, mcpTool],

647

automaticFunctionCalling: {

648

maximumRemoteCalls: 10

649

}

650

}

651

});

652

653

console.log('Response:', response.text);

654

655

await mcpClient.disconnect();

656

```

657

658

## Notes

659

660

- MCP integration is experimental and requires the @modelcontextprotocol/sdk package

661

- MCP servers must implement the Model Context Protocol specification

662

- Connection management and error handling are critical for reliable MCP integration

663

- MCP tools are automatically converted to Gemini's function calling format

664

- Supports both automatic and manual function calling modes

665

- Can combine MCP tools with native Gemini tools in the same request

666