Основные отличия между методами PUT и PATCH

Чем put отличается от patch

Чем put отличается от patch

Методы PUT и PATCH относятся к числу стандартных HTTP-операций, используемых для изменения состояния ресурса в REST API, однако их назначение и последствия применения существенно различаются. Ошибочный выбор между ними приводит к перезаписи данных, конфликтам версий и неожиданному поведению серверной логики. Понимание различий важно при проектировании API, интеграции клиентских приложений и отладке сетевых запросов.

PUT предполагает передачу полного представления ресурса. Сервер воспринимает запрос как команду заменить текущее состояние ресурса на переданное, даже если часть полей отсутствует. Это означает, что клиент обязан знать актуальную структуру объекта и отправлять все атрибуты, включая неизменённые. Такой подход тесно связан с идемпотентностью и часто используется в сценариях синхронизации данных.

PATCH решает другую задачу – точечное изменение. Клиент передаёт только те поля, которые требуется обновить, не затрагивая остальные. Это снижает риск случайной потери данных и уменьшает объём передаваемой информации. При этом формат тела запроса может различаться: от частичного JSON-объекта до специальных форматов вроде JSON Patch, что напрямую влияет на серверную реализацию.

Выбор между PUT и PATCH должен основываться на модели данных, требованиях к конкурентному доступу и уровне доверия к клиенту. В API с частыми обновлениями отдельных полей и несколькими потребителями PATCH позволяет избежать лишних конфликтов. PUT оправдан, когда клиент управляет ресурсом целиком и несёт ответственность за его текущее состояние.

Как PUT обрабатывает полную замену ресурса на сервере

Метод PUT интерпретируется сервером как команда полностью заменить текущее состояние ресурса данными, переданными в теле запроса. Сервер не анализирует, какие поля были изменены намеренно, а какие пропущены случайно. Если атрибут отсутствует в payload, он считается удалённым или сброшенным в значение по умолчанию, в зависимости от реализации.

Клиент, отправляющий PUT-запрос, обязан передавать полную модель ресурса в актуальном формате. Это особенно критично при наличии необязательных полей, вложенных объектов и серверных значений, которые не возвращаются в ответах API. При несоответствии схемы возможна потеря данных, даже если цель запроса заключалась в изменении одного параметра.

На уровне серверной логики PUT часто реализуется как последовательность операций: валидация входных данных, удаление или перезапись текущей версии ресурса и сохранение новой. При использовании ORM это может выражаться в полном обновлении записи без учёта предыдущего состояния, что напрямую влияет на связанные сущности и триггеры.

Состояние ресурса Поле A Поле B Поле C
До PUT значение значение значение
Тело PUT новое значение новое значение
После PUT новое значение удалено / null новое значение

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

Как PATCH выполняет частичное обновление отдельных полей

Как PATCH выполняет частичное обновление отдельных полей

Метод PATCH применяется, когда требуется изменить строго определённые поля ресурса, не затрагивая остальные данные. Сервер рассматривает тело запроса как набор инструкций для обновления, а не как новую версию объекта. Поля, отсутствующие в запросе, сохраняют своё текущее значение независимо от структуры ресурса.

Наиболее распространённый сценарий – передача JSON-объекта с изменяемыми свойствами. Сервер выполняет операцию слияния: существующая модель загружается из хранилища, затем указанные поля перезаписываются новыми значениями. Такой подход требует явной обработки null-значений, поскольку они могут означать как намеренное очищение поля, так и ошибку клиента.

Для сложных структур часто используется формат JSON Patch, описывающий изменения через последовательность операций. Это позволяет адресно работать с вложенными объектами и элементами массивов, например изменять одно значение без пересборки всей структуры. Сервер при этом обязан проверять корректность путей и допустимость операций, иначе возрастает риск нарушения целостности данных.

PATCH не предполагает повторяемого результата при идентичных запросах, поэтому при проектировании API важно учитывать конкурентные обновления. Рекомендуется применять контроль версий ресурса или условные заголовки, чтобы предотвратить перезапись изменений, внесённых другим клиентом между запросами.

Использование PATCH оправдано, когда клиент не располагает полной моделью ресурса или работает с ограниченным набором полей. Это снижает сетевую нагрузку и упрощает обновление данных в распределённых системах, где состояние ресурса может часто меняться.

Поведение PUT и PATCH при отсутствии ресурса

При обращении к несуществующему ресурсу метод PUT может приводить к его созданию, если сервер поддерживает такую семантику. Спецификация HTTP допускает этот сценарий при условии, что клиент указывает целевой идентификатор ресурса в URL. В этом случае сервер сохраняет переданное представление и возвращает код ответа 201 или 200, в зависимости от реализации.

Создание ресурса через PUT требует полной и валидной модели данных. Если тело запроса неполное или содержит ошибки, сервер обязан отклонить запрос с кодом 400 или 422. Поэтому PUT в режиме создания подходит только для случаев, когда клиент полностью контролирует структуру и идентификаторы ресурсов.

Метод PATCH при отсутствии ресурса ведёт себя иначе. Поскольку его смысл заключается в модификации существующего состояния, большинство серверов возвращают ошибку 404. Создание нового ресурса через PATCH считается неоднозначным и усложняет серверную логику, так как невозможно применить частичные изменения к объекту, которого ещё нет.

Некоторые API допускают расширенную интерпретацию PATCH с созданием ресурса по умолчанию, однако такой подход требует чёткой документации и дополнительной валидации. Без этих мер клиенты не могут предсказать результат запроса, что повышает риск логических ошибок.

При проектировании API рекомендуется использовать PUT для явного создания или полной замены ресурса и отклонять PATCH-запросы к несуществующим URL. Это упрощает контракт между клиентом и сервером и делает поведение методов предсказуемым.

Требования к телу запроса для PUT и PATCH

Тело запроса для PUT должно содержать полное представление ресурса в формате, поддерживаемом сервером. Любое отсутствие обязательного поля интерпретируется как ошибка или намеренное удаление данных, поэтому клиент обязан формировать payload строго по актуальной схеме.

  • включение всех обязательных и необязательных полей ресурса;
  • передача корректных значений для вложенных объектов и коллекций;
  • учёт серверных полей, которые не заполняются автоматически;
  • соответствие версии схемы, используемой сервером.

Для PATCH тело запроса описывает только изменяемые элементы. Сервер не ожидает полной структуры и не должен требовать присутствия неизменяемых полей. Это упрощает формирование запросов, но накладывает дополнительные требования на интерпретацию входных данных.

  1. передача только тех полей, которые подлежат изменению;
  2. явное использование null для очистки значений, если это предусмотрено контрактом;
  3. поддержка форматов частичного обновления, например JSON Patch;
  4. строгая валидация допустимых операций и типов данных.

Для обоих методов рекомендуется явно указывать заголовок Content-Type и документировать правила обработки отсутствующих полей. Это снижает количество ошибок интеграции и упрощает поддержку API при изменении модели данных.

Риски потери данных при использовании PUT

Риски потери данных при использовании PUT

Основной риск при работе с PUT связан с тем, что сервер воспринимает запрос как полную замену ресурса. Если клиент передаёт неполный набор полей, отсутствующие значения удаляются или сбрасываются. Это часто происходит при использовании устаревших моделей данных или при ручном формировании запросов.

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

Дополнительный риск возникает при наличии серверных полей, которые не возвращаются в ответах API, например вычисляемых значений или служебных флагов. Если клиент не включает их в тело PUT-запроса, сервер может считать эти поля удалёнными, даже если они критичны для бизнес-логики.

Для снижения потерь рекомендуется использовать условные запросы с проверкой версии ресурса, заголовки If-Match или предварительное получение актуального состояния перед обновлением. В сценариях частичных изменений предпочтительнее применять PATCH, ограничивая область воздействия запроса.

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

Когда выбирать PUT или PATCH в REST API

Когда выбирать PUT или PATCH в REST API

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

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

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

PATCH снижает риск перезаписи несвязанных данных и упрощает поддержку API при частых изменениях структуры ресурса. Однако серверу необходимо явно контролировать конкурентные обновления и корректность частичных изменений.

При проектировании REST API рекомендуется чётко разграничивать области применения методов: использовать PUT для полной замены или создания ресурса и PATCH для адресных изменений. Это делает контракт API прозрачным и уменьшает количество логических ошибок на стороне клиентов.

Вопрос-ответ:

Почему PUT может удалить данные, которые я не собирался менять?

PUT воспринимается сервером как полная замена ресурса. Если в теле запроса отсутствуют какие-либо поля, сервер считает, что клиент больше не хочет хранить эти значения. Это типично для API, где PUT напрямую маппится на перезапись записи в базе данных без учёта предыдущего состояния.

Можно ли безопасно использовать PATCH для обновления одного поля?

Да, при корректной серверной реализации PATCH изменяет только переданные поля. Остальные данные остаются без изменений. Безопасность такого обновления зависит от обработки null-значений, проверки типов и наличия механизма контроля конкурентных изменений.

Что произойдёт, если отправить PATCH на ресурс, которого ещё нет?

Большинство API вернёт ошибку 404, так как PATCH рассчитан на изменение существующего состояния. Создание ресурса через PATCH встречается редко и требует специальной логики, иначе результат запроса становится непредсказуемым для клиента.

Зачем использовать PUT, если PATCH выглядит менее рискованным?

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

Какой метод лучше подходит для публичного API с большим числом клиентов?

Чаще выбирают PATCH, так как клиенты обычно изменяют отдельные поля и не имеют доступа ко всей структуре ресурса. Это снижает вероятность перезаписи данных, добавленных другими участниками, и упрощает развитие схемы ресурса без нарушения существующих интеграций.

Как выбор между PUT и PATCH влияет на версионирование ресурса?

PUT часто используется вместе с жёстким контролем версии, так как клиент отправляет полное состояние ресурса. При несоответствии версии сервер может отклонить запрос и избежать перезаписи чужих изменений. PATCH чаще применяется с мягкими проверками, где версия используется для обнаружения конфликтов при частичном обновлении, особенно если несколько клиентов работают с разными полями одного объекта.

Можно ли комбинировать PUT и PATCH для одного и того же ресурса?

Да, такой подход распространён. PUT применяют для сценариев полной замены или начальной загрузки данных, а PATCH — для последующих точечных правок. При этом контракт API должен явно описывать, какие поля допускают частичное обновление и какие проверки выполняются сервером, чтобы оба метода не приводили к противоречивому состоянию ресурса.

Ссылка на основную публикацию