oasdiff

Дано:

  • Две версии одного приложения: A и B.
  • Обе версии предоставляют контракт, описанный с помощью OpenAPI.
  • У приложения есть пользователи, соблюдающие текущий контракт.

Задача:

  • Выяснить, имеются ли обратно несовместимые изменения в контракте новой версии.
  • Выяснить, какие дополнительные изменения произошли в контракте.

Почему бы просто не вызывать diff и не изучить различия?

  • Спецификация достаточно большая, чтобы можно было разобрать отличия “глазами” за один проход.
  • Выявить обратно несовместимые изменения “на глаз” очень сложно.
  • Форматирование одинаковых элементов меняется в зависимости от версии генератора, например, в одной версии массив может быть описан в одну строку, в другой — в несколько, или же элементы могут быть переставлены в другом порядке. Это увеличивает размер diff‘а, и не упрощает задачу.

Решить последний пункт не так уж и сложно с помощью jq --sort-keys. Приведу простой пример:

diff \
    <(jo foo=1 bar=2 baz=3 | jq --sort-keys) \
    <(jo baz=4 foo=1 bar=2 | jq --sort-keys)
3c3
<   "baz": 3,
---
>   "baz": 4,

Однако это не ускоряет и не упрощает решение основной проблемы.

Нужно найти или реализовать инструмент, который бы показывал в понятном формате изменения в двух версиях одной и той же спецификации.

К счастью, такие решения существуют. Поверхностно обратим внимание на те инструменты, которые попали в исследование.

redskap/swagger-brake 1

  • java;
  • хорошая документация;
  • не смог прожевать переданные схемы.

civisanalytics/swagger-diff 2

  • ruby;
  • хороший README;
  • спотыкается на переданных схемах, останавливаясь с ошибкой.

Sayi/swagger-diff 3

  • java;
  • для сборки рабочего jar из исходного кода потребуется править pom.xml;
  • не смог переварить переданные схемы.

atlassian/openapi-diff 4

  • ts;
  • с задачей справляется;
  • выводит json и текстовые фрагменты в stdout, делая вывод непригодным к машинному анализу.

Tufin/oasdiff — ✅ 5

  • go;
  • хороший README;
  • справился с задачей;
  • настраиваемый формат вывода (текстовый или json);
  • имеет отдельный веб-сервис, где можно провести сравнение онлайн;
  • активно развивается автором.

Именно oasdiff и был выбран в качестве основного инструмента поиска различий в контрактах OpenAPI.

Вот, например, как можно вывести список обратно несовместимых изменений:

oasdiff breaking \
    spec1.json \
    spec2.json

Напоследок хочу заметить, что задача перехода с одной версии на другую решается не только с помощью понимания изменений в контракте, но и хорошим комплектом e2e-тестов.