Привет! Меня зовут Сергей, я ведущий разработчик в Lad. В этой статье речь пойдет об опыте работы с Payload.
В нашей компании мы использовали Payload для создания быстрых прототипов и MVP-проектов. Payload мы выбрали как весьма гибкий и интересный инструмент, предоставляющий большой функционал из коробки, админ-панель и базовую работу с пользователями.
В основном статья будет касаться взаимодействия со стороны backend-части.
Плюсы и преимущества Payload
- Упрощает разработку проекта, а это быстрая и простая начальная установка и готовая структура проекта (что в целом может быть и минусом). 
- Поддержка мультиязычности из коробки. 
- Предоставляет авторизацию из коробки. 
- Аутентификация происходит по классической связке «email — password». 
Для авторизации используется Bearer-токен.

Сразу весь необходимый набор ручек работы с пользователем:

Также это может быть расширено посредством PassportJs, но на практике у нас не было необходимости его использовать.
- Access control на CRUD операции. 
- Удобен для быстрого прототипирования. Если хочется за 30 минут запустить проект, описать несколько сущностей — решение крайне удобно. 
- Предоставляет базовый CRUD. 
После описания сущности для нее создается набор рутов, готовый для работы:

- 
Query-запросы (GraphQL). Со стороны frontend появляется возможность выполнять простые запросы, включая сортировки и фильтрацию (equals, less_then, in и т. д.). 
- Стандартизация запросов. Ошибки, пагинация, ответы и прочее — все находится в едином стиле. 
- Поддержка Mongodb и Postgres и простая быстрая базовая работа с ними (в нашем случае мы использовали только mongo). 
- Быстрое описание коллекции и генерация интерфейсов на ее основе: 
export const Clients: CollectionConfig = {
 slug: 'clients',
 auth: {
   depth: 1,
   tokenExpiration: 28800,
   maxLoginAttempts: 5,
   lockTime: 30 * 1000,
 },
 labels: {
   plural: 'Клиенты',
   singular: 'Клиент',
 },
 admin: {
   useAsTitle: 'name',
 },
 fields: [
   {
     name: 'name',
     type: 'text',
     label: 'Имя',
   },
   {
     name: 'favoriteNumber',
     type: 'number',
     label: 'Любимое число',
   },
   {
     type: 'date',
     label: 'Дата рождения',
     name: 'dateOfBirth',
   },
 ],
};Интерфейс на выходе:
/**
* This interface was referenced by `Config`'s JSON-Schema
* via the `definition` "clients".
*/
export interface Client {
 id: string;
 name?: string | null;
 favoriteNumber?: number | null;
 dateOfBirth?: string | null;
}- Хорошая и удобная админка из коробки: 

- Система предоставляет множество хуков на сущности и на поля. Часто это может быть очень удобно. 
hooks: {
  afterRead: [afterReadUser], 
  afterDelete: [afterDeleteUser],
}С какими минусами Payload мы столкнулись
Из некоторых плюсов вытекают минусы.
- 
Проблема хуков. Система предоставляет несколько уровней хуков. Одни хуки на уровне полей, вторые — на уровне коллекций. В нашей воле описать хуки на создание, изменение и удаление. Звучит весьма неплохо. Но на определенном этапе работы с проектом выходит так, что не все вещи удобно и возможно делать через хуки + их становится слишком много. Это начинает выглядеть как усложнение. Встает проблема с тем, что приходится помнить и следить за всеми описанными хуками. Похоже на проблему с колбэками — это некая непредсказуемость кода: в какой момент и что выполнится? Все слишком нелинейно. Слишком запутанно. 
- Типы и поля. Больше похоже на то, что они заточены на админ-панель, а не на бэкенд-часть. Яркий пример — это тип boolean, который здесь называется checkbox: 

- Проблема с mongoose. На момент разработки Payload использовал старый драйвер mongoDb. Обновить его просто так нельзя. Возникают различные проблемы, особенно проблемы, связанные с типами. 
- Базы данных. Слишком высокий уровень абстракции. БД — mongoose — обертка на Payload. Появляется некая непредсказуемость того, что может произойти. 
- Концепция Payload заставляет писать БД в стиле ближе к реляционному с огромным количеством таблиц и связей между ними. 
- Если нужны более сложные запросы, то они будут работать в обход хуков. Приходится очень внимательно следить за этим. Часто это сильно усложняет и замедляет процесс разработки. 
- 
Мелкие проблемы, которые возникают в процессе работы: - невозможно типизировать JSON-тип; 
- нельзя указать минимальное значение массива 0; 
- и многие другие моменты, которые не являются критичными, но весьма раздражают в процессе работы. 
 
- Если нужно сделать более сложную валидацию и проверку данных, то приходится делать кастомный контроллер либо оборачивать дополнительными хуками. Но тогда как будто ломается концепция чего-то «быстрого из коробки». 
- Приходится использовать самописные вещи для валидации или проводить проверку полей в самом handler. 
- Из-за специфичной архитектуры невозможно говорить о микросервисах. 
- В версии до 2.0 graphQl был старый и deprecated, и ты ничего не мог с этим поделать. 
- Невозможно переписать handler для ошибок. 
- Форум (community help) в целом заточен на вопросы frontend-части и для backend достаточно бесполезен. 
Выводы
При работе с Payload следует учитывать, что могут возникнуть некоторые проблемы, когда мы хотим функционал чуть больший, чем представляется из коробки. Ограничения версий, самописный код может начать конфликтовать с тем, что есть в системе или могут возникнуть другие ситуации, описанные в статье. Но все эти минусы присущи не только Payload, а любым «коробочным решениям».
Если резюмировать весь опыт взаимодействия с Payload, то нужно отметить, что это действительно весьма удобный инструмент для создания прототипов и MVP. В нашем случае он позволил создать два крупных качественных MVP с большим количеством функционала за сжатые сроки.
Комментарии (2)
 - MrCooger11.07.2024 11:26- Ну многие ходят на работу из-за, внезапно, денег, а не интересных задач и работы по 12+ часов и пятилетки за 4, а интенсивный труд приводит только к ментальным проблемам в таком случае. Нормальная тенденция, чтобы была возможность жизнь прожить, а не проработать 
 
           
 
HEXFFFFFFFF
Современная разработка мне напоминает дилог с кучером из "формулы любьви"
– Степан, у гостя карета сломалась…
– Вижу, барин. Ось полетела, да спицы менять надо.
– Починить сможешь?
– За день сделаю.
– А за два?
Степан глянул на барина, перевел взгляд на карету:
– Можно и за два.
– А за пять?.
Степан задумчиво почесал в затылке:
– Трудновато, барин. Но ежели постараться, можно и за пять…
– А за десять дней? Степан аж крякнул:
– Ну, барин, тут тогда самому не справиться. Помощник нужен. Хомо сапиенс!