Skip to main content
Glama
EuKennedy

mcpkit

by EuKennedy

mcpkit

ci release license node

TypeScript-инструментарий для создания MCP-серверов без лишнего шаблонного кода.

Определите инструмент с помощью схемы Zod и обработчика. Получите готовый сервер Model Context Protocol — генерация схемы, валидация входных данных, конверты ошибок, настройка транспорта — всё уже сделано.

import { defineServer, defineTool } from 'mcpkit';
import { z } from 'zod';

const server = defineServer({
  name: 'demo',
  version: '0.1.0',
  tools: [
    defineTool({
      name: 'add',
      description: 'Add two numbers.',
      input: z.object({ a: z.number(), b: z.number() }),
      handler: ({ a, b }) => `${a + b}`,
    }),
  ],
});

await server.start();

Это настоящий, работающий MCP-сервер. Запустите его с помощью mcpkit dev и подключите к нему любой MCP-совместимый клиент.


зачем это нужно

Написание MCP-сервера с использованием официального SDK — это нормально, но вам приходится выполнять одну и ту же рутинную работу каждый раз:

  • объявление списка инструментов в одном месте

  • объявление отдельной JSON-схемы для каждого инструмента

  • написание конструкции switch для имен инструментов в обработчике вызовов

  • приведение возвращаемых значений обработчика к конверту содержимого протокола

  • настройка транспорта

  • перехват ошибок и преобразование их в правильный формат isError

mcpkit сводит всё это к defineTool + defineServer. Схема генерируется из вашего типа Zod, валидация выполняется до вашего обработчика, ошибки превращаются в корректные ответы протокола, а возвращаемая строка становится блоком текстового содержимого. Вы остаетесь на том уровне, который действительно важен — что делает инструмент — и пропускаете тот, который не важен.

Related MCP server: MCP Base Server

с vs без

Один и тот же инструмент, написанный с использованием «голого» SDK и с помощью mcpkit:

const server = new Server(
  { name: 'demo', version: '0.1.0' },
  { capabilities: { tools: {} } },
);

server.setRequestHandler(
  ListToolsRequestSchema,
  async () => ({
    tools: [
      {
        name: 'add',
        description: 'Add two numbers.',
        inputSchema: {
          type: 'object',
          properties: {
            a: { type: 'number' },
            b: { type: 'number' },
          },
          required: ['a', 'b'],
        },
      },
    ],
  }),
);

server.setRequestHandler(
  CallToolRequestSchema,
  async (req) => {
    if (req.params.name === 'add') {
      const { a, b } = req.params.arguments as {
        a: number; b: number;
      };
      return {
        content: [{ type: 'text', text: `${a + b}` }],
      };
    }
    throw new Error('unknown tool');
  },
);

await server.connect(new StdioServerTransport());
const server = defineServer({
  name: 'demo',
  version: '0.1.0',
  tools: [
    defineTool({
      name: 'add',
      description: 'Add two numbers.',
      input: z.object({
        a: z.number(),
        b: z.number(),
      }),
      handler: ({ a, b }) => `${a + b}`,
    }),
  ],
});

await server.start();

Правый столбец обладает тем же поведением на уровне протокола, плюс валидация входных данных, плюс типизированные аргументы обработчика, плюс конверт isError при необработанных исключениях.

установка

npm install mcpkit zod

Или создайте новый проект (рекомендуется для первого сервера):

npx mcpkit create my-server
cd my-server
npm run dev

Вы получите небольшой проект с работающим stdio-сервером, тремя примерами инструментов и tsconfig.json, настроенным на строгий режим. Замените примеры инструментов своими и выпускайте.

cli

mcpkit create [target]   scaffold a new server from a template
mcpkit dev               run with hot reload (uses tsx under the hood)
mcpkit build             compile to dist/
mcpkit inspect           launch the official inspector against your server

create поставляется с четырьмя шаблонами:

шаблон

что вы получаете

stdio-basic

локальный MCP-сервер через stdio. большинство клиентов хотят именно это.

http-streaming

доступный по сети сервер через потоковый HTTP-транспорт.

with-fetch

stdio-сервер с инструментами для HTTP-запросов (тайм-ауты настроены).

with-sqlite

stdio-сервер с примером CRUD на базе SQLite (better-sqlite3, WAL).

api

defineTool

defineTool({
  name: string,            // [a-zA-Z0-9_-]+
  description: string,     // shown to the client / LLM
  input: z.ZodType,        // Zod schema; converted to JSON Schema for you
  handler: (input) => string | ToolContent | ToolContent[] | { content, isError? }
})

Входные данные обработчика полностью типизированы через z.infer. Возврат строки оборачивает её в виде единого блока текстового содержимого — это типичный случай. Выброс исключения внутри обработчика автоматически превращается в ответ isError: true; если вы хотите настроить сообщение об ошибке, передайте обработчик onToolError в defineServer.

defineServer

defineServer({
  name: string,
  version: string,
  description?: string,
  tools?: ToolDefinition[],
  resources?: ResourceDefinition[],
  prompts?: PromptDefinition[],
  onToolError?: (err, toolName) => ToolResult,
  onEvent?: (event: ServerEvent) => void,
})

Возвращает DefinedServer с методами:

  • .start({ transport: 'stdio' }) — подключить транспорт и запустить сервер.

  • .connect(transport) — подключить экземпляр транспорта, который вы создали самостоятельно (HTTP, пользовательский, любой, который ведет себя как Transport).

  • .stop() — закрыть активный транспорт и базовый сервер.

  • .raw — базовый Server из SDK, если вам нужно сделать что-то нестандартное.

ресурсы и промпты

Такая же декларативная форма:

defineResource({
  uri: 'file:///etc/hosts',
  name: 'hosts',
  mimeType: 'text/plain',
  read: async () => ({ text: await fs.readFile('/etc/hosts', 'utf8') }),
});

definePrompt({
  name: 'summarize',
  description: 'Summarize a chunk of text.',
  arguments: z.object({ text: z.string() }),
  build: ({ text }) => ({
    messages: [{ role: 'user', content: { type: 'text', text: `Summarize:\n${text}` } }],
  }),
});

наблюдаемость

onEvent получает структурированный обратный вызов для каждого вызова инструмента, чтения ресурса и получения промпта — время начала, время окончания, задержка, ошибка, requestId для каждого вызова для корреляции. Вы можете подключить его к чему угодно: pino, console, OpenTelemetry, вашему собственному агрегатору. Также есть встроенное решение для простого случая:

import { defineServer, consoleLogger, jsonLogger } from 'mcpkit';

const server = defineServer({
  name: 'demo',
  version: '0.1.0',
  onEvent: consoleLogger(),    // → pretty stderr lines
  // or: onEvent: jsonLogger() // → one JSON object per line, on stderr
  tools: [...]
});

Логирование всегда идет в stderr — stdout зарезервирован для трафика протокола на stdio-транспортах.

тестирование

mcpkit/testing предоставляет внутрипроцессный клиент, который общается с вашим сервером через транспорт в оперативной памяти — никаких подпроцессов, никаких stdio-каналов, никаких проблем с завершением процессов. Тот же клиент, который использовал бы реальный потребитель, просто маршрутизируется через RAM.

import { describe, it, expect } from 'vitest';
import { createTestClient, expectToolError, snapshotTools } from 'mcpkit/testing';
import { server } from '../src/index.js';

describe('add', () => {
  it('adds', async () => {
    const client = await createTestClient(server);
    const result = await client.callTool('add', { a: 2, b: 3 });
    expect(result.text).toBe('5');
    expect(result.isError).toBe(false);
    await client.close();
  });

  it('rejects bad input', async () => {
    const client = await createTestClient(server);
    const text = await expectToolError(client, 'add', { a: 'nope', b: 1 });
    expect(text).toMatch(/invalid/i);
    await client.close();
  });

  it("doesn't drift its public surface", () => {
    expect(snapshotTools(server)).toMatchSnapshot();
  });
});

важные проектные решения

Zod, а не «сырая» JSON-схема. Вы пишете тип один раз. Валидация, сгенерированная JSON-схема для протокола и вывод типов TypeScript для обработчика — всё это получается из одного источника. Попытка синхронизировать три определения — это тот самый шаблонный код, который этот проект призван удалить.

Ошибки — это значения, а не исключения. Обработчик, который выбрасывает исключение, становится конвертом содержимого isError: true. Клиент видит разумный ответ вместо сбоя на уровне транспорта. Если вы предпочитаете форматировать ошибку самостоятельно, переопределите onToolError.

Ядро, не зависящее от транспорта. Один и тот же defineServer работает через stdio, потоковый HTTP-транспорт, внутрипроцессный тестовый транспорт или что угодно другое, что реализует интерфейс Transport из SDK. Шаблон http-streaming показывает, как это настроить.

Строгий режим по умолчанию. Шаблоны поставляются с strict: true и noUncheckedIndexedAccess. Сама библиотека компилируется с теми же настройками. Если вы найдете дыру в типах, это баг.

Ошибки слушателей игнорируются. Если ваш обработчик onEvent выбрасывает исключение, ваши вызовы инструментов продолжают работать. Баги наблюдаемости не должны быть критическими.

faq

Привязывает ли меня это к mcpkit навсегда? Нет. У каждого помощника есть «аварийный выход» — server.raw дает вам базовый Server из SDK, и вы можете напрямую вызвать setRequestHandler на нем, если вам нужно что-то, что комплект еще не моделирует. Комплект — это слой поверх, а не замена.

Почему Zod 3, а не 4? Zod 4 великолепен, но экосистема (в частности zod-to-json-schema) всё еще догоняет. Мы перейдем, когда он станет стабильным в продакшене. Если вы уже используете Zod 4, интерфейсы схем достаточно совместимы — создайте issue, если столкнетесь с проблемой.

Поддерживает ли он ресурсы и промпты, а не только инструменты? Да. defineResource и definePrompt являются первоклассными гражданами. Они используются реже, чем инструменты, поэтому большинство примеров начинаются с инструментов, но настройка идентична.

Потоковый HTTP, SSE, оба? Потоковый HTTP. Старый вариант HTTP+SSE все еще есть в SDK, но он постепенно выводится из эксплуатации — если у вас есть причина использовать его, defineServer не зависит от транспорта, и вы можете передать любой экземпляр Transport через .connect().

Готов к продакшену? Библиотека небольшая, и область применения намеренно узкая. Официальный SDK выполняет всю тяжелую работу под капотом. Зафиксируйте версию, напишите тесты для своих инструментов (внутрипроцессный клиент делает это простым), и вы готовы.

чем это не является

  • не хостинговый сервис. вы создаете, вы развертываете.

  • не агентский фреймворк. он создает серверную сторону MCP, а не клиентскую.

  • не навязывает мнение о вашей предметной области. инструменты — это функции; что они делают — ваша проблема.

дорожная карта

  • больше шаблонов (защищенные oauth, edge runtime, drizzle/postgres).

  • команда mcpkit publish, которая выполняет линтинг + упаковку + тегирование релиза.

  • более богатые помощники для тестирования (фаззинг входных данных инструмента, сравнение схемы с базовой линией).

  • опциональный адаптер OpenTelemetry для onEvent.

Если чего-то не хватает, откройте issue с наброском API, который вы хотели бы видеть.

лицензия

MIT.

A
license - permissive license
Not graded
quality - not tested
C
maintenance

Maintenance

Maintainers
Response time
Release cycle
1Releases (12mo)
Commit activity

Resources

Unclaimed servers have limited discoverability.

Looking for Admin?

If you are the server author, to access and configure the admin panel.

Related MCP Servers

  • A
    license
    C
    quality
    D
    maintenance
    A lightweight and extendable MCP server toolkit that allows developers to build and integrate custom tools with AI assistants through automatic tool discovery from local directories or npm packages.
    2
    18
    MIT
  • A
    license
    Not graded
    quality
    D
    maintenance
    A TypeScript-based template for rapidly developing MCP servers with modular tool architecture, built-in validation using Zod schemas, and comprehensive error handling.
    9
    MIT
  • A
    license
    B
    quality
    D
    maintenance
    A TypeScript-based boilerplate for building Model Context Protocol (MCP) servers using the official SDK and Zod. It provides a structured foundation with a decoupled architecture to simplify the creation and registration of custom MCP tools.
    1
    16
    ISC

View all related MCP servers

Related MCP Connectors

  • Markdown-first MCP server for Notion API with 8 composite tools and 39 actions.

  • MCP server for Clipkit — gives AI agents a video toolbox via the Clipkit schema.

  • MCP server for secureFlows: token-free URL builders and integration-linting tools for AI agents.

View all MCP Connectors

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/EuKennedy/mcpkit'

If you have feedback or need assistance with the MCP directory API, please join our Discord server