Skip to main content
Glama
priority-mcp

Priority REST API MCP Server

by priority-mcp

Priority REST API MCP Server

MCP-сервер, который подключает ИИ-ассистентов — Claude и другие — напрямую к ERP-системе Priority. Каждая операция OData (запрос, создание, обновление, удаление, пакетная обработка, вложения, текстовые поля) представлена как инструмент MCP, поэтому ИИ-агенты могут читать и записывать оперативные бизнес-данные без написания пользовательского интеграционного кода.

Версия: 0.2.0 · Транспорт: Streamable HTTP (SSE опционально) · Среда выполнения: Node.js 18 · Инструменты: 19


Быстрый старт

1. Клонируйте репозиторий и установите зависимости

git clone https://github.com/priority-mcp/priority-odata-mcp priority-mcp
cd priority-mcp
npm install

2. Создайте файл .env из примера

cp .env.example .env

Как минимум задайте эти четыре переменные:

PRIORITY_BASE_URL=https://<host>/odata/Priority/<tabula.ini>/<company>/
PRIORITY_AUTH_TYPE=basic
PRIORITY_USERNAME=myuser
PRIORITY_PASSWORD=mypassword

3. Запустите сервер

# Development (from source)
node src/index.js

# Production (bundled)
npm run build
node dist/index.js

При первом запуске, если ODATA_MCP_TOKEN не задан, генерируется случайный Bearer-токен и выводится в stdout. Скопируйте его для следующего шага.

4. Подключитесь из Claude Code

Добавьте в конфигурацию MCP:

{
  "mcpServers": {
    "priority": {
      "type": "http",
      "url": "http://localhost:3000/mcp",
      "headers": {
        "Authorization": "Bearer <ODATA_MCP_TOKEN>"
      }
    }
  }
}

Related MCP server: mcp_sdk_eyra_accelerator

Транспорт

Сервер использует Streamable HTTP в качестве основного транспорта — каждый запрос POST /mcp полностью не сохраняет состояние. Новые McpServer и StreamableHTTPServerTransport создаются для каждого запроса и уничтожаются после его завершения.

Конечная точка

Метод

Назначение

/mcp

POST

Основная конечная точка MCP (Streamable HTTP)

/sse

GET

SSE-поток — требует SSE_ENABLED=true

/sse

POST

JSON-RPC-сообщения для SSE-клиентов

/health

GET

Проверка работоспособности — возвращает версию и статус

/.well-known/oauth-authorization-server

GET

Обнаружение OAuth 2.1 (требуется Claude Code ≥2.1.92)

/authorize, /token, /register

GET/POST

Поток PKCE OAuth 2.1 — автоматически одобряет запросы

Примечание: Конечные точки OAuth 2.1 существуют для удовлетворения процедуры установления соединения Streamable HTTP в Claude Code. Они автоматически одобряют все запросы и не предназначены для реального контроля доступа — эту функцию выполняет ODATA_MCP_TOKEN.


Аутентификация

Аутентификация работает на двух независимых уровнях.

Уровень 1 — защита этого сервера

Все маршруты (кроме /health и конечных точек OAuth) требуют:

Authorization: Bearer <ODATA_MCP_TOKEN>

Задайте ODATA_MCP_TOKEN в файле .env. Если он отсутствует, при запуске генерируется случайный UUID и выводится в stdout.

Уровень 2 — вызовы Priority ERP

Управляется переменной PRIORITY_AUTH_TYPE:

  • basic — базовая HTTP-аутентификация с использованием PRIORITY_USERNAME + PRIORITY_PASSWORD

  • pat — Bearer-токен через PRIORITY_PAT

  • oauth2 — то же, что и pat (передайте PAT как Bearer-токен)

  • none — без заголовка аутентификации (только для локального тестирования)

Операции записи (POST/PATCH/DELETE) автоматически получают и повторяют запрос с заголовком X-CSRF-Token, если первоначальный запрос отклонён, следуя схеме защиты CSRF в Priority.

Опциональные заголовки лицензии приложения отправляются с каждым запросом к Priority, если заданы PRIORITY_APP_ID и PRIORITY_APP_KEY (X-App-Id / X-App-Key).


Конфигурация

Скопируйте .env.example в .env. Сервер ищет файл .env в следующем порядке: ENV_FILE_PATH./mcp-servers/Priority-REST-API-MCP-Server/.env./.env.

Обязательные параметры

Переменная

Описание

PRIORITY_BASE_URL

Корневой URL OData — формат: https://<host>/odata/Priority/<tabula.ini>/<company>/

PRIORITY_AUTH_TYPE

basic | pat | oauth2 | none

PRIORITY_USERNAME

Имя пользователя — обязательно при AUTH_TYPE=basic

PRIORITY_PASSWORD

Пароль — обязателен при AUTH_TYPE=basic

Аутентификация Priority (опционально)

Переменная

Описание

ODATA_MCP_TOKEN

Bearer-токен, защищающий /mcp. Если не задан, используется случайный UUID.

PRIORITY_PAT

Персональный токен доступа (при AUTH_TYPE=pat или oauth2)

PRIORITY_APP_ID

Идентификатор лицензии приложения — отправляется как заголовок X-App-Id

PRIORITY_APP_KEY

Ключ лицензии приложения — отправляется как заголовок X-App-Key

PRIORITY_LANGUAGE

Переопределяет заголовок Accept-Language (например, en)

HTTP-сервер

Переменная

По умолчанию

Описание

HTTP_HOST

0.0.0.0

Адрес привязки

HTTP_PORT

3000

Порт прослушивания

SSE_ENABLED

false

Включить конечную точку /sse

Тайм-ауты и TLS

Переменная

По умолчанию

Описание

PRIORITY_HTTP_TIMEOUT_MS

30000

Тайм-аут чтения для вызовов API Priority (мс)

MCP_WRITE_TIMEOUT

15000

Тайм-аут для операций POST/PATCH/DELETE (мс)

MCP_PROC_TIMEOUT

45000

Тайм-аут для пакетных операций (мс)

TLS_REJECT_UNAUTHORIZED

false

Установите true в production, чтобы отклонять самоподписанные сертификаты

Отладка

Переменная

По умолчанию

Описание

LOG_LEVEL

INFO

DEBUG записывает каждый запрос и ответ

MCP_DEBUG

false

Выводит полные URL OData, параметры, количество результатов

PRIORITY_ENABLE_TRACE

false

Добавляет X-App-Trace: 1 к каждому запросу к Priority

STRICT_DATA_INTEGRITY

true

Вызывает ошибку при пустых/фиктивных ответах API — отключайте только для тестирования

ENV_FILE_PATH

Переопределяет путь к файлу .env (полезно для развёртывания в подмодулях)


Инструменты

Все 19 инструментов определены в src/tools/ и зарегистрированы в src/tools/priorityTools.js.

Система и метаданные

Инструмент

Описание

Параметры

version_get

Получить версию службы Priority и заголовки ответа

metadata_entities_list

Вывести список всех наборов сущностей OData; фильтровать только формы с поддержкой REST

apiOnly?, includeMetadata?

metadata_schema_get

Получить схему полей сущности, запросив образец записи. Автоматически перенаправляет имена подформ на родительскую + $expand

entity, sample?, top?

metadata_refresh

Очистить и обновить серверный кэш метаданных. Всегда выполняет полную очистку (см. «Известные ограничения»)

entity?

Запросы

Инструмент

Описание

Параметры

entity_get

Получить одну запись по ключу или поиску, с опциональными $expand и $select

entity, key, lookup, select?, expand?

query_run

Выполнить запрос OData с полной поддержкой filter/select/top/skip/orderby/expand/count. Проверяет результаты фильтрации по дате после получения

entity, filter?, select?, top?, skip?, orderby?, expand?, count?, deltaToken?

safe_query_run

Как query_run, но сначала автоматически обнаруживает допустимые поля и проверяет имена полей $select перед выполнением — предотвращает ошибки 400 из-за недопустимых имён столбцов

entity, filter?, select?, top?, skip?, expand?, count?

query_sum

Вычислить сумму числового поля по сущности с опциональным фильтром. Сначала пробует $apply=aggregate; при неудаче выполняет полное сканирование с разбиением на страницы

entity, field?, filter?

Создание / Обновление / Удаление

Инструмент

Описание

Параметры

entity_create

Создать новую запись. Поддерживает создание подформ через parentEntity + parentKey + subform

entity, data, parentEntity?, parentKey?, parentLookup?, subform?

entity_update

Обновить запись через PATCH с If-Match: *. Поддерживает составные ключи

entity, key, data, parentEntity?, parentKey?, subform?

entity_delete

Удалить запись через DELETE с If-Match: *. Поддерживает удаление подформ

entity, key, parentEntity?, parentKey?, subform?

batch_operations

Выполнить несколько операций POST/PATCH/DELETE в одном запросе $batch с цепочками зависимостей

requests[] (id, method, url, body?, dependsOn?)

Текстовые поля

Инструмент

Описание

Параметры

entity_text_get

Получить содержимое форматированного текста подресурса /Text записи

entity, key

entity_text_create

Отправить POST с новым текстовым содержимым на /Entity(Key)/Text

entity, key, textData

entity_text_update

Отправить PATCH с существующим текстовым содержимым на /Entity(Key)/Text

entity, key, textData

Вложения

Инструмент

Описание

Параметры

entity_attachments_get

Вывести список вложений записи

entity, key

entity_attachments_upload

Загрузить файл в подресурс /Attachments записи как multipart/form-data. fileData должен быть в кодировке base64

entity, key, fileData, fileName, contentType?

Конфигурация и справка

Tool

Description

Parameters

instructions_get

Возвращает полное руководство по эксплуатации: синтаксис OData, шаблоны подформ, лимиты троттлинга, правила обработки дат, известные сценарии сбоев и примеры архитектуры. Вызывайте первым при изучении незнакомой сущности

config_restflag_update

Устанавливает RESTFLAG=Y или N в таблице FORMLIMITED, чтобы включить или отключить доступ к REST API для формы Priority

formName, restFlag, formType?


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

Сервер регистрирует MCP промпты (многоразовые шаблоны инструкций) и ресурсы (живые конечные точки данных).

Промпты (src/prompts/)

Имя

Назначение

query_priority_entity

Руководство по построению OData-запросов к сущности

explore_entity_relationships

Объясняет иерархию подформ для заданной сущности

modify_priority_data

Руководство по операциям создания, обновления и удаления

date_handling_guide

Критические правила для фильтров по датам — формат ISO, проверка операторов

known_failure_patterns

Документированные сценарии 404/501/400 и их обходные решения

pagination_guide

Объясняет шаблоны $top/$skip и подсчёта

Ресурсы (src/resources/)

URI

Назначение

priority://entities/list

Живой список всех сущностей с включённым REST (RESTFLAG=Y)

priority://entity-schema/{entity}

Схема для конкретной сущности (шаблонный URI)

priority://queries/common

Библиотека готовых примеров запросов

priority://subforms/reference

Справочное руководство по шаблонам подформ и операциям


Пример вызова инструмента

Запросить три самых последних заказа на продажу для клиента 1011 — отправлено как JSON-RPC 2.0 на POST /mcp:

{
  "jsonrpc": "2.0",
  "id": 1,
  "method": "tools/call",
  "params": {
    "name": "query_run",
    "arguments": {
      "entity":  "ORDERS",
      "filter":  "CUSTNAME eq '1011'",
      "select":  ["ORDNAME", "CUSTNAME", "CURDATE", "TOTPRICE"],
      "top":     3,
      "orderby": "CURDATE desc"
    }
  }
}

Сервер выдаёт:

GET /odata/Priority/.../ORDERS?$format=json&$filter=CUSTNAME+eq+'1011'
  &$select=ORDNAME,CUSTNAME,CURDATE,TOTPRICE&$top=3&$orderby=CURDATE+desc

Ответ:

{
  "jsonrpc": "2.0",
  "id": 1,
  "result": {
    "content": [{
      "type": "text",
      "text": "{\"value\":[{\"ORDNAME\":\"SO25000001\",\"CUSTNAME\":\"1011\",\"CURDATE\":\"2025-07-15T00:00:00+03:00\",\"TOTPRICE\":15000.0},...],\"_mcp_metadata\":{\"entity\":\"ORDERS\",\"resultCount\":2,\"filterApplied\":true}}"
    }],
    "isError": false
  }
}

Формат даты: Priority возвращает даты в формате ISO 8601 со смещением часового пояса (например, 2025-07-15T00:00:00+03:00), а не в UTC Z. Используйте синтаксис CURDATE ge 2025-01-01 в фильтрах по датам — не формат ISO-Z.


Развёртывание

Docker

# Build
docker build -t priority-mcp .

# Run
docker run --env-file .env -p 3000:3000 priority-mcp

Dockerfile использует node:18-slim, выполняет npm run build для сборки src/dist/ через esbuild, затем запускает dist/index.js. Конфигурация Docker Compose и локальный генератор TLS-сертификатов находятся в deployment/local/.

Контрольный список для продакшена

  • Установите ODATA_MCP_TOKEN явно — не полагайтесь на автоматически сгенерированный

  • Установите TLS_REJECT_UNAUTHORIZED=true

  • Установите STRICT_DATA_INTEGRITY=true (по умолчанию)

  • Установите LOG_LEVEL=INFO (по умолчанию — подавляет служебный шум)

  • Привяжите HTTP_HOST к конкретному интерфейсу, если не публикуете наружу


Известные ограничения

Особенности поведения Priority ERP, о которых стоит знать перед разработкой.

Ограничение частоты запросов — 100 вызовов/минуту на пользователя Priority Cloud ограничивает до 100 вызовов API в минуту на пользователя, максимум 10 параллельных запросов, тайм-аут 3 минуты на вызов. Проектируйте агентов так, чтобы по возможности группировать операции.

Ограничение ответа — MAXFORMLINES Priority молча обрезает ответы на уровне системной константы MAXFORMLINES независимо от $top. Используйте пагинацию на основе $skip, если нужны все записи.

Подформы не являются самостоятельными сущностями Прямой запрос PORDERITEMS_SUBFORM возвращает HTTP 404. Доступ к подформам должен осуществляться через родительскую сущность с $expand=PORDERITEMS_SUBFORM. metadata_schema_get автоматически определяет это и перенаправляет.

$apply=aggregate не поддерживается query_sum всегда переключается на полное сканирование с пагинацией, поскольку $apply=aggregate(...) не поддерживается в этой версии Priority.

GET /ENTITY/$count возвращает 500 Вместо этого используйте ?$top=0&$count=true. Внутренне tryEstimateCount() сначала пробует /$count, затем выполняет пагинацию пакетами по 500 записей (с ограничением 10 000).

contains()/startswith() не поддерживаются для некоторых полей EPROG.ENAME и EREP.ENAME поддерживают только точное совпадение eq — строковые функции возвращают HTTP 501.

Обновление метаданных на уровне сущности возвращает 400 metadata_refresh игнорирует аргумент entity и всегда выполняет полный сброс кэша, поскольку Priority отклоняет запросы на очистку кэша в рамках одной сущности.

Кодирование URL в пакетных запросах URL-адреса внутри запросов batch_operations никогда не кодируются автоматически. Пробелы и специальные символы должны быть вручную закодированы в процентах (пробелы → %20).

Составные ключи Некоторые сущности используют составные ключи, например FORMLIMITED: ENAME='X',TYPE='F'; AINVOICES: IVNUM='T9696',IVTYPE='A',DEBIT='D'. Передавайте полную строку составного ключа в entity_update и entity_delete.


Структура проекта

/
├── src/
│   ├── index.js                    Entry point — creates and starts PriorityMCPServer
│   ├── server.js                   Express app, all routes, auth guard, OAuth 2.1 PKCE
│   ├── sseServer.js                SSE connection manager
│   ├── config.js                   Reads all env vars, resolves .env path
│   ├── version.js                  SERVER_VERSION, KNOWN_ISSUES list
│   │
│   ├── priority/
│   │   └── client.js               PriorityClient — axios instance, auth headers,
│   │                               all API methods (runQuery, createEntity, …)
│   │
│   ├── mcp/
│   │   ├── handler.js              JSON-RPC 2.0 dispatcher (SSE path)
│   │   ├── registry.js             ToolRegistry — registerTool, callTool, listTools
│   │   ├── prompt-registry.js
│   │   ├── resource-registry.js
│   │   ├── priority-mcp-sdk-server.js   Wires registries into McpServer (SDK path)
│   │   ├── tool-call-runner.js          Executes tool, wraps result for MCP response
│   │   └── json-schema-to-zod.js        JSON Schema → Zod conversion
│   │
│   ├── tools/                      One file per tool + priorityTools.js (registration)
│   ├── prompts/                    One file per prompt + priorityPrompts.js
│   ├── resources/                  One file per resource + priorityResources.js
│   └── utils/
│       ├── data-integrity.js       ensureNoMockData(), validateApiResponse()
│       ├── date-handling.js        Date parsing and validation helpers
│       ├── errors.js               createPriorityApiError(), FilterNotAppliedError
│       ├── filter-resolver.js      OData filter string building
│       ├── expand-resolver.js      $expand normalization
│       ├── entity-resolver.js      Entity name / subform name resolution
│       ├── resolve-query-args.js
│       └── subform-query-resolver.js
│
├── data/
│   └── entity-relationships.json   Hardcoded subform map (PORDERS, ORDERS, …)
│
├── tests/
│   ├── scripts/                    Manual test scripts
│   └── results/                    Saved JSON/Markdown test output
│
├── docs/                           Design docs (DATA_INTEGRITY_POLICY, DATE_HANDLING_RULES, …)
├── postman/                        Postman collection for manual API testing
├── deployment/local/               Docker Compose + TLS cert generator
├── build.js                        esbuild bundler: src/ → dist/
└── .env.example                    All env vars documented with descriptions

Тесты

Автоматизированного тестового раннера нет. Тесты — это ручные скрипты, требующие живого подключения к Priority:

# Read operations
node tests/scripts/test-priority-operations.js

# Write operations (interactive — asks for confirmation)
node tests/scripts/test-write-operations.js

# Test all 19 MCP tools via the running server
node tests/scripts/test-all-mcp-tools-via-server.js

# Standalone resolver smoke tests
node test-keyresolver.js
node test-resolver.js

Предупреждение: Тесты на запись создают, обновляют и удаляют реальные записи. Запускайте только на компании для разработки.


Технологический стек

  • Среда выполнения: Node.js 18, ES-модули ("type": "module")

  • MCP SDK: @modelcontextprotocol/sdk ^1.29.0

  • HTTP-сервер: express ^4.21.1

  • HTTP-клиент: axios ^1.7.7

  • Проверка схем: zod ^4.3.6

  • Сборщик: esbuild ^0.25.0 (через npm run build)

  • Прочее: cors, dotenv, form-data, uuid, http-errors

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

Maintenance

Maintainers
Response time
Release cycle
Releases (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
    Not graded
    quality
    C
    maintenance
    A generic MCP server that dynamically converts OpenAPI-defined REST APIs into tools for LLMs like Claude. It supports multiple authentication methods and transport protocols, enabling seamless interaction with any OpenAPI-compliant API.
    18
    MIT
  • F
    license
    Not graded
    quality
    D
    maintenance
    A standalone MCP server that exposes API endpoints as tools for AI assistants by proxying requests to a target API defined in an OpenAPI specification. It supports various authentication methods and utilizes Server-Sent Events (SSE) to facilitate integration with clients like Claude and ChatGPT.
  • A
    license
    C
    quality
    D
    maintenance
    An MCP server that bridges AI agents to the eyeot ERP, exposing ~600 business actions (CRM, sales, stock, HR, finance, etc.) as MCP tools over stdio via OAuth 2.1 authentication.
    33
    1
    MIT
  • A
    license
    Not graded
    quality
    D
    maintenance
    A config-driven MCP server that exposes OData and REST APIs as MCP tools, enabling AI assistants to query, manage, and monitor SAP backends through natural language.
    45
    27
    MIT

View all related MCP servers

Related MCP Connectors

  • MCP server for Argo RPG Platform — connects AI assistants to campaign data via OAuth2

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

  • Self-hosted MCP gateway: turn any API, database or MCP server into AI connectors — no code.

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/priority-mcp/priority-odata-mcp'

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