[{"data":1,"prerenderedAt":-1},["ShallowReactive",2],{"question-rest-api-kak-obespechit-obratnuyu-sovmestimost-rest-api":3},{"id":4,"slug":5,"topicId":6,"topicSlug":7,"topicName":8,"topicEmoji":9,"question":10,"answer":11,"codeLang":12,"codeSrc":12,"important":12,"commonMistakes":12,"modernUsage":12,"difficulty":13,"tags":14,"related":16,"progress":17,"seo":18},1231,"kak-obespechit-obratnuyu-sovmestimost-rest-api",34,"rest-api","REST API","🌐","Как обеспечить обратную совместимость REST API?","Обратная совместимость (backward compatibility) — свойство API, при котором обновлённая версия продолжает корректно работать с существующими клиентами без необходимости их изменения.\n\n### Неломающие изменения (non-breaking)\n\n- Добавление нового поля в ответ — клиенты игнорируют неизвестные поля (tolerant reader).\n- Добавление нового endpoint-а.\n- Добавление нового опционального параметра запроса.\n- Добавление нового значения enum (в ответе).\n- Расширение допустимого диапазона значений.\n\n### Ломающие изменения (breaking)\n\n- Удаление или переименование поля из ответа.\n- Изменение типа поля (`\"age\": 30` -> `\"age\": \"30\"`).\n- Удаление endpoint-а.\n- Добавление обязательного параметра.\n- Изменение кода ответа.\n\n### Стратегии обеспечения совместимости\n\n| Стратегия | Описание |\n|-----------|----------|\n| Версионирование (URL\u002FHeader) | `\u002Fapi\u002Fv1\u002Fusers` и `\u002Fapi\u002Fv2\u002Fusers` работают параллельно |\n| Deprecation + Sunset (RFC 8594, 8977) | Заголовки уведомляют о плановом удалении |\n| Tolerant Reader (Закон Постела) | Клиент игнорирует неизвестные поля, не зависит от порядка |\n| API Evolution | Постепенное развитие: добавление новых полей, deprecated для старых |\n| Feature Flags | Управление поведением через заголовки |\n\n### Tolerant Reader Pattern\n\n> «Будь консервативен в том, что отправляешь, и либерален в том, что принимаешь.»\n\n```java\n\u002F\u002F Настройка Jackson для игнорирования неизвестных полей\n@JsonIgnoreProperties(ignoreUnknown = true)\npublic record UserDto(Long id, String name, String email) {}\n\n\u002F\u002F Или глобально\nObjectMapper mapper = new ObjectMapper();\nmapper.configure(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES, false);\n```\n\n\u003Cdetails>\u003Csummary>Примеры реализации\u003C\u002Fsummary>\n\nЗаголовки Deprecation и Sunset:\n```java\n@GetMapping(\"\u002Fapi\u002Fv1\u002Fusers\")\npublic ResponseEntity\u003CList\u003CUserV1Dto>> getUsersV1() {\n    List\u003CUserV1Dto> users = userService.findAllV1();\n    return ResponseEntity.ok()\n        .header(\"Deprecation\", \"true\")\n        .header(\"Sunset\", \"Sat, 01 Nov 2026 00:00:00 GMT\")\n        .header(\"Link\", \"\u003C\u002Fapi\u002Fv2\u002Fusers>; rel=\\\"successor-version\\\"\")\n        .body(users);\n}\n```\n\nПаттерн эволюции API:\n```java\n\u002F\u002F Шаг 1: Добавляем новое поле, старое оставляем\npublic record UserDto(\n    Long id,\n    String name,\n    String email,\n    @Deprecated String userName,    \u002F\u002F старое поле (deprecated)\n    String displayName              \u002F\u002F новое поле\n) {\n    @JsonProperty(\"userName\")\n    public String getUserName() {\n        return displayName != null ? displayName : name;\n    }\n}\n\n\u002F\u002F Шаг 2: Через несколько релизов удаляем старое поле\n```\n\nАвтоматическое обнаружение несовместимых изменений:\n```bash\nopenapi-diff --fail-on-incompatible \\\n  api-spec-v1.yaml \\\n  api-spec-v2.yaml\n```\n\n\u003C\u002Fdetails>\n\n### Частые ошибки\n\n- Удаление полей без предварительного deprecated-периода.\n- Изменение типа поля без версионирования.\n- Добавление обязательного параметра в существующий endpoint.\n- Отсутствие автоматической проверки совместимости в CI\u002FCD.\n- Бесконечная поддержка всех версий — вовремя удаляйте старые версии.\n\n### Как используется в 2026\n\n- openapi-diff и Optic интегрируются в CI\u002FCD для автоматической проверки совместимости.\n- API lifecycle management — платформы (Backstage, Kong) управляют жизненным циклом API.\n- Contract testing (Pact, Spring Cloud Contract) — стандарт для проверки совместимости.\n- Тренд на API Evolution вместо строгого версионирования.\n\n> **На собеседовании:** ключевое — разделить изменения на ломающие и неломающие, знать Tolerant Reader и заголовки Deprecation\u002FSunset. Частая ошибка — не упомянуть автоматическую проверку совместимости в CI\u002FCD.","","senior",[15],"rest",[],null,{"title":19,"description":20,"ogTitle":19,"ogDescription":21,"keywords":22,"schemaAnswer":23,"featuredSnippetReady":24},"Как обеспечить обратную совместимость REST API? — Gymterview","Обратная совместимость (backward compatibility) — свойство API, при котором обновлённая версия продолжает корректно работать с существующими клиентами без необх","Обратная совместимость (backward compatibility) — свойство API, при котором обновлённая версия продолжает корректно рабо",[15,13],"Обратная совместимость (backward compatibility) — свойство API, при котором обновлённая версия продолжает корректно работать с существующими клиентами без необходимости их изменения.",true]