Files
mdm-ordinis/docs/integration/api/read-endpoints.md
T
Zimin A.N. b601c4636f feat(swagger): OAuth2/Keycloak PKCE flow в Swagger UI + docs links
OpenApiConfig:
- Добавлена OAuth2 security scheme (authorization_code flow с Keycloak
  realm `nstart`). Auth/token URLs из ordinis.openapi.oauth.issuer-uri
  configuration property (default: auth.nstart.space/realms/nstart).
- BearerAuth scheme сохранён secondary — для pre-issued tokens из CI/scripts.
- Servers list переупорядочен — prod первый, staging второй.
- Description обновлён с pointer на /docs/ для full integration guide.

application.yml:
- springdoc.swagger-ui.oauth: client-id (env override), use-pkce-with-
  authorization-code-grant=true. Public client `ordinis-swagger`
  настраивается отдельно в Keycloak — see keycloak-setup-swagger-client.md
  в ordinis-infra repo.
- ORDINIS_OPENAPI_OAUTH_ISSUER_URI env var для override realm на разных
  окружениях.

docs/integration/api/read-endpoints.md:
- Swagger UI section обновлён: акцент на Authorize button + Keycloak
  PKCE login (no client_secret needed), tip про bearerAuth fallback.

docs/index.md:
- Добавлен tab "Я хочу пощупать API" с link на Swagger UI.

После deploy:
- https://ordinis.k8s.264.nstart.cloud/swagger-ui.html  — Swagger UI
- https://ordinis.k8s.264.nstart.cloud/v3/api-docs      — OpenAPI spec
Authorize → выбрать oauth2 → Keycloak login (PKCE) → Try it out с JWT.
2026-05-08 00:08:29 +03:00

6.0 KiB
Raw Blame History

Read-side endpoints

Read-API в Ordinis — отдельный deployable (ordinis-read-api, scaled 2× в проде) работающий на Postgres replica. Запросы из read-api не блокируют writer'а.

Base URL:

Среда URL
prod https://ordinis.k8s.264.nstart.cloud/api/v1
staging https://ordinis.k8s.265.nstart.cloud/api/v1

Все endpoints требуют JWT (см. Авторизация).

OpenAPI / Swagger UI

Interactive playground с Keycloak login (PKCE flow, без client_secret):

  • Swagger UI: https://ordinis.k8s.264.nstart.cloud/swagger-ui.html → нажми Authorize → выбери oauth2 → войдёшь через Keycloak. После login каждый "Try it out" автоматически добавит JWT.
  • Spec JSON: https://ordinis.k8s.264.nstart.cloud/v3/api-docs
  • Spec YAML: https://ordinis.k8s.264.nstart.cloud/v3/api-docs.yaml

{% note tip %}

Если у тебя уже есть pre-issued service token (например для CI scripts) — выбери схему bearerAuth в Authorize dialog и paste'ни raw JWT. PKCE flow тогда не нужен.

{% endnote %}

Из spec'а можно generate'ить клиент:

openapi-generator-cli generate \
  -i https://ordinis.k8s.264.nstart.cloud/v3/api-docs \
  -g python \
  -o ./altum-backend/clients/ordinis

Поддерживаются: Python, TypeScript, Go, Java, Kotlin, Ruby и др.

GET /api/v1/dictionaries

Список доступных справочников (фильтрован по scope JWT'а).

curl -H "Authorization: Bearer $TOKEN" \
  https://ordinis.k8s.264.nstart.cloud/api/v1/dictionaries

Response:

[
  {
    "name": "spacecraft",
    "displayName": "Космические аппараты",
    "scope": "PUBLIC",
    "schemaVersion": "1.0.0",
    "recordsCount": 4
  },
  {
    "name": "mission",
    "displayName": "Миссии / программы",
    "scope": "PUBLIC",
    "schemaVersion": "1.0.0",
    "recordsCount": 9
  }
]

GET /api/v1/{name}/records

{% note warning %}

БЕЗ префикса /dictionaries/! Read-api сидит на /api/v1/{name}/records. Префикс /api/v1/dictionaries/... — это admin write controller (CRUD), у него нет bulk-list эндпоинта.

{% endnote %}

Активные записи на момент at (default: сейчас).

Параметры

Параметр Тип Пример Назначение
lang string ru-RU, en-US Flatten i18n полей в строку. Короткие ru/en тоже.
at ISO 8601 2026-05-04T12:00:00+03:00 Bitemporal query — активные на момент.
as_scope string PUBLIC,INTERNAL Legacy для anonymous + allowQueryScope=true.

Пример

curl -H "Authorization: Bearer $TOKEN" \
  "https://ordinis.k8s.264.nstart.cloud/api/v1/spacecraft/records?lang=ru-RU"

Response:

[
  {
    "businessKey": "RESURS-P-3",
    "displayKey": "Ресурс-П № 3",
    "scope": "PUBLIC",
    "validFrom": "2025-01-01T00:00:00+03:00",
    "validTo": "9999-12-31T23:59:59+03:00",
    "data": {
      "name": "Ресурс-П № 3",
      "satelliteTypeCode": "EARTH-OBSERVATION-OPTICAL",
      "launchDate": "2024-12-25",
      "status": "active"
    },
    "version": 2
  }
]

Без ?lang (raw i18n)

"name": { "ru-RU": "Ресурс-П № 3", "en-US": "Resurs-P No.3" }

С ?lang=ru-RU:

"name": "Ресурс-П № 3"

Если запрошенного языка нет — fallback к default_locale (обычно ru-RU).

GET /api/v1/{name}/records/{businessKey}

Одна запись. Параметры те же что у list.

curl -H "Authorization: Bearer $TOKEN" \
  "https://ordinis.k8s.264.nstart.cloud/api/v1/spacecraft/records/RESURS-P-3?lang=ru"

404 Not Found — запись либо не существует, либо закрыта на момент at, либо вне scope JWT'а (Ordinis скрывает существование).

GET /api/v1/{name}/records/{businessKey}/history

Все версии записи (включая закрытые) для построения истории изменений в UI.

[
  {
    "version": 1,
    "validFrom": "2024-06-01T00:00:00+03:00",
    "validTo": "2025-01-01T00:00:00+03:00",
    "data": {...},
    "txTime": "2024-06-01T10:23:45+03:00",
    "changedBy": "admin@nstart.space",
    "changeReason": "initial"
  },
  {
    "version": 2,
    "validFrom": "2025-01-01T00:00:00+03:00",
    "validTo": "9999-12-31T23:59:59+03:00",
    "data": {...},
    "txTime": "2024-12-30T14:11:22+03:00",
    "changedBy": "admin@nstart.space",
    "changeReason": "Обновление статуса после успешного запуска"
  }
]

Для consumers history endpoint обычно не нужен — это UI-feature.

Spatial filters (geometry)

Если справочник имеет geometry поля (spacecraft.aoi, mission.coverage_area), поддерживаются bbox + polygon фильтры:

?bbox= (bounding box)

GET /api/v1/spacecraft/records?bbox=37.0,55.0,38.0,56.0

Format: min_lon,min_lat,max_lon,max_lat (WGS84). Возвращает записи где geometry пересекает bbox через PostGIS ST_Intersects + GiST index.

?polygon= (GeoJSON)

GET /api/v1/spacecraft/records?polygon={"type":"Polygon","coordinates":[[[37,55],[38,55],[38,56],[37,56],[37,55]]]}

Polygon — GeoJSON object (URL-encoded). Сложнее bbox, точнее.

Дальше