Skip to content

Instantly share code, notes, and snippets.

@martdn
Last active October 23, 2019 07:32
Show Gist options
  • Save martdn/8f9cfb91fe5e122376a570e7b83de56c to your computer and use it in GitHub Desktop.
Save martdn/8f9cfb91fe5e122376a570e7b83de56c to your computer and use it in GitHub Desktop.
Sprint11. Rework order backend

Description

Если коротко

Была создана новая структура для хранения заказа, соответственно под неё были переарботаны фронтенд и бэкенд. На фронте были переписаны на vue страницы создания заказа и список заказов пользователя.

Подробнее

  • load-user.ts в @/application/actions/admin/middleware и @/application/actions/main/middleware были переименованы в is-user-authenticated т к никакого получения юзера там не происходит - лишь проверка на существование пользователя с хэшем из сессии - если есть пропускать дальше, иначе редирект на логин. 2 версии мидлваре из за того что перенаправлять надо на разные роуты - в мейне на форму авторизации сайта, в админке на форму авторизации админки

  • в backend/application/actions/**/index.ts урлы экшенов были перенесены в урл генераторы, чтобы в коде можно было работать с урлами не как со строками, а с автокомплитом. Получилось 3 урл генератора, по одному на секцию: {Main|Admin|Api}UrlGenerator.

  • @/application/models/Order - старая монго модель заказа (удалил), там же был интерфейс описывающий заказ. Вместо всего этого был создан модуль @/components/order. @/components/order/mongo-order-repository/mongo-order (монго модель), @/components/order/order (типы, имющие отношение к заказу). Созданы 2 типа - NewOrder (новый заказ, с указанием кол-ва пассажиров, без статуса и номера) и Order (с заполненными пассажирами, номером, статусом и датой создания). Order это созданный заказ который будем хранить. NewOrder - это полуфабрикат для заказа. Так же был создан order-repo с монго реализацией. Во всех метсах где использовалась старая монго модель - заменил на новую или на использование репозитория. Для репозитория есть "фабрика" - @/application/services/order-repo

  • папку со старыми монго моделями @/application/models переименовал в @/application/model

  • @/application/utils/create-hash который используется для создания хэшей паролей в нескольких местах переместил в @/components/create-hash. Нашел дублирующую его реализацию в юзере (@/components/user), заменил на использование @/components/create-hash. В общем во всех местах где создается хэш пароля использую теперь @/components/create-hash

  • backend/application/actions/admin/request-handlers/orders/**, backend/application/actions/admin/request-handlers/users/display-user-page.ts - переделал на использование @/components/order

  • backend/application/actions/api/index.ts, backend/application/actions/main/index.ts обработчики запросов, которые возвращают Promise обернул в wrapAsync из @rimiti/express-async. Вот пакет https://github.com/rimiti/express-async, вот объяснение зачем это надо https://dimsolution.com/blog/2019-02-12/how-to-use-async-await-functions-with-express/. Если вкратце - хэндлеры бы и без этого работали, но ошибки в асинхронных хэндлерах ловятся как то не правильно без обертки, с оберткой ошибки ловятся как надо.

  • backend/application/actions/api/request-handlers/check-user-hash.ts использовад UserRepo и переделал на async/await (в роутере при этом надо оборачивать хэндлер во wrapAsync, см выше)

  • backend/application/actions/api/request-handlers/confirm-order.ts переименовал в backend/application/actions/api/request-handlers/create-order.ts использовал в нем CreateOrderInteractor

  • backend/application/services/mysql.ts - вместо пакета mysql использовал пакет mysql2, тк он поддерживает Promise. Жаль что тайпингов для него нет.

  • @/components/ticket-repository переименовал в @/components/ticket, по аналогии с пакетами рядом, там ведь в самом деле не только репозиторий

  • backend/application/actions/main/request-handlers/notification.ts оч странный хэндлер, не нашел на него обращений на фронте. Может стоит удалить его. Код исправил под новый order, но там логика требует уточнений - если не будем его удалять - надо фиксить. Логика требует уточнения т к у заказа есть сатус заказа и статус платежа, а в новом заказе только 1 статус. Надо уточнить что с этим делать - если конечно нельзя просто удалить этот хэндлер.

  • backend/application/actions/main/request-handlers/profile/display-user-orders.ts перенес из папки backend/application/actions/main/request-handlers/profile/display-user-orders. При этом удалил там config.ts со списком логотипов авиакомпаний(!) (на фронте для этого есть компонент которому не нужны такие списки). Переделал на async/await и использование репозиториев. Убрал все что не нужно во вьюхе. Заказы из монги гоню в json чтобы вывести в PAGE_CONFIG на странице (компонент это подхватывает)

  • backend/application/model/User.ts теперь является алиасом для @/components/user/mongo-user-repository/mongo-user. В дальнейшем папку models вообще нужно удалить - все монго модели перенести в их модули-компоненты, по аналогии с @/components/user. Пока же легаси код использует эти старые модели.

  • backend/application/models/Order.ts удалил старую монго-модель заказа, все места её использования переделал на использование нового кода (см. выше)

  • backend/application/services/instant-registration-mailer.ts реализация InstantRegistrationUserNotifier которая шлет юзеру email с временным паролем

  • backend/application/services/order-repo.ts, backend/application/services/user-repo.ts "фабрики" для репозиториев, предполагается что репозитории в хэндлерах будут использоваться таким образом (например import userRepo from "@/application/services/user-repo.ts") пока не появится возможность использовать DI контейнер.

  • backend/components/customer-contacts.ts структура, использующаяся в заказе

  • backend/components/flight/index.ts вместо интерфейса сделал класс, чтобы всегда были все поля и чтобы были дефолты, так же преобразован FlightLeg (в том же файле)

  • backend/components/legacy-flight/legacy-flight-adapter.spec.ts, backend/components/legacy-flight/legacy-flight-adapter.ts исправлены типы а то билд падал

  • backend/components/order/mongo-order-repository/mongo-order-repository.ts монго реализация OrderRepository (backend/components/order/order-repository.ts)

  • backend/components/order/mongo-order-repository/mongo-order.ts монго модель для mongo-order-repository.ts, но легаси код может использовать её напрямую, с чем, конечно, надо бороться

  • backend/components/order/order.ts новая структура для заказа. Там есть NewOrder который шлется с бэкенда, есть Order который хранится в базе (и содержит, помимо полей NewOrder, статус, айдишник (номер заказа), и дату создания)

  • backend/components/passenger/index.ts новая структура для данных пассажира. В папке старых моделей есть старая, и раньше при создании заказа пассажиры из заказа сохранялись в монгу и затем показывались на странице "пассажиры" профиля. Но помимо отображения на указанной странице они более никак не используются так что предлагаю или придумать как их использовать или выпилить этот функционал

  • backend/components/user/mongo-user-repository/mongo-user-repository.ts монго реализация UserRepository (backend/components/user/user-repository.ts)

  • backend/components/user/user.ts вынес из старой модели, сделал классом (по аналогии с остальными компонентами). Названия старые - так себе, но пока не буду трогать - работает же. Но их в дальнейшем надо привести в порядок.

  • backend/index.ts убрал префиксы из импорта роутов - они теперь в урл генераторах. Не очень хорошо, но выигрыш от внедрения урл генераторов больше.

  • backend/tsconfig.json убрал из тайпингов mysql, тк теперь используется mysql2, и жаль что типов для него нет

  • backend/use-cases/order/create-order.ts интерактор (ну допустим дирижер - хорошая аналогия) создания заказа. Читай рецепт создания заказа - содержит высокоуровневые бизнес правила в отрыве от инфраструктуры. Имеет параметры на входе (newOrder) и результат на выходе CreateOrderInteractorResult. По логике работы - он использует другой интерактор - instantRegistrationInteractor ток при этом еще и заказ сохраняет. Т е получается при создании заказа происходит мгновенная регистрация полльзоватея и сохранение заказа.

  • backend/use-cases/user/instant-register/instant-register.ts интерактор "мгновенной регистрации". Создает юзера из CustomerContacts с временным паролем, отправляет юзеру оповещение со сгенерированным паролем.

  • добавил в backend/views/base.twig блоки stylesheets и javascripts. До javascripts в скриптах "сверху" добавил "инициализацию" PAGE_CONFIG (window.PAGE_CONFIG = {}). Для возможности бэкенду класть "конфиг" для фронта на страницу, чтобы запрос не делать. Убрал метрику в отдельный файл - counters.twig

  • backend/views/general/order.twig вместо отрисовки страницы создания заказа твигом был создан вуе компонент create-order

  • backend/views/personal/personal-orders.twig то же самое для страницы "мои заказы" в профиле, компонент order-list. На этой странице в PAGE_CONFIG кладется json orders из контроллера

  • frontend/dummy.spec.ts удалил, есть настоящие тесты

  • frontend/features/create-order - вуе для страницы "создание заказа". Прицип работы: ищем билеты, жмем купить - попадаем на эту страницу. Из локал стораджа (через репозиторий) достается т.н. PreOrder (там выбраный перелет и структура с количество пассажиров). В локал сторадж PreOrder попадает на странице результатов поиска при нажатии на "купить". На странцие заполняются формы с валидацией и заполнный заказ отсылается на бэкенд.

  • frontend/features/create-order/init-legacy-search-form-fields.ts без этого легаси кода некоторые поля формы поиска не заполняются из локал стораджа. Надо удалить при рефакторинге формы поиска.

  • frontend/features/create-order/order-list.vue перенес в frontend/shared/order-list.vue, т к теперь он в еще и на странице "мои заказы" используется

  • frontend/features/create-order/countries-with-iso-codes.ts используется для селектора стран, пока так.

  • frontend/features/create-order/passport-data.ts удалил кусок не нужного более шаблона, который использовался чтобы выводить форму для заполнения данных пассажиров

  • frontend/features/create-order/craete-order-repository.ts умеет слать новый заказ на бэкенд (чтобы сохранить), при этом, так как при создании заказа происходит "мгновенная регистрация" новый пользователь атоматически авторизовывается в ответе saveOrder отдается токен авторизации, кторый кладется в локал сторадж. Этот токен надо слать с каждым запросом при обращении к роутам за авторизацией.

  • frontend/features/create-order/payment.vue компонент с ценой, кнопкой купить и галками. Тут странная проблема с вуелидейтом. Валидация чекбоксов стала работать только с кастомным валидатором required - const required = val => !!val;

  • frontend/features/create-order/index.ts выбросил старый код, оставил только регистрацию вуе компонента

  • frontend/features/index.ts - добавил создание и провайды всех необходимых сервисов для новых компонентов + импорты этих компонентов

  • frontend/features/order-list вуе для страницы "мои заказы". Заказы беруться из пэйдж конфига.

  • frontend/features/order-list/order-list-repository.ts достает заказы из пейдж конфига

  • frontend/features/order-list/order/component.ts тут есть кнопка оплатить, по которой модалка оплаты всплывает с уже заполненой инфой. Так вот эта модалка работает через бутстрап, не стал переделывать - пусть пока так поработает.

  • frontend/features/search-form/index.ts удалил не нужный более код, при нажатии на кнопку "купить" добавил использование preOrderRepo чтобы передать выбранный рейс на страницу "создать заказ" (через локал сторадж). Т к вьюха в результатах поиска работает со старым форматом заказа - добавил legacyFlightAdapter чтобы преобразовать к новому формату. Т е в локал сторадж заказ в новом формате кладется. + причесал некторые строки-шаблоны, кто то же должен это делать

  • frontend/features/template/main.js - удалил импорт shared/components/order-card/order-card и сам этот файл, это все теперь вуе делает

  • frontend/shared/components/element-ui добавил компоненты element-ui чтобы использовать их везде

  • frontend/shared/components/form-field добавил обертку для полей формы, для автоматического отображения ошибок валидации

  • frontend/shared/directives/input-mask добавил директиву для масок ввода и frontend/shared/input-filters и некторые шаблоны для неё. внимание - есть frontend/shared/directives/input-mask/fix-android-hack.ts - это штука которая фиксит поведение масок на мобильных устройствах

  • frontend/shared/model/passenger-numbers.ts структура для передачи количества пассажиров

  • frontend/shared/services/auth-token-repository.ts репозиторий для работы с токеном авторизации, который хранится в локал сторадже

  • frontend/shared/services/backend-router.ts просто обертка для window.location.href, но лучше window напрямую в компонентах не трогать

  • frontend/shared/services/dialog.ts обертка для sweetAlert

  • frontend/shared/services/hardcode-translator.ts транслятор в котором все переводы хардкодом

  • frontend/shared/services/pre-order-repository.ts репозиторйи для раоботы с PreOrder (см выше)

  • frontend/shared/utils добавил форматтер числа (чтобы разряды отделялись), форматтер дат, frontend/shared/utils/is-valid-property-path.ts это для frontend/shared/components/form-field (возможно стоит выпилить его оттуда)

  • frontend/shared/validation добавил некторые валидаторы для вуелидейта

  • frontend/vuelidate.d.ts тайпигнги для вуелидейта, пакета до сих пор нет

  • frontend/webpack.config.js удалил слово entry из генерируемых файлов - нет в нем смысла. поправил стек для postcss-loader (без этой правки не работал), добавил лоадер для шрифтов

  • package.json закрепил версии пакетов где не закреплены были

  • пересобрал дист

Motivation and Context

How Has This Been Tested?

локально

протестировать весь процесс работы с заказом, от поиска/создания, до оплаты

все должно работать

Screenshots (if appropriate):

Types of changes

  • Bug fix (non-breaking change which fixes an issue)
  • New feature (non-breaking change which adds functionality)
  • Breaking change (fix or feature that would cause existing functionality to change)
  • Refactoring (non-breaking change in existing functionality)

Impacted Areas in Application

весь бэкенд/фронтенд связанный с заказами

  • еще по мелочи )

Checklist:

  • My code follows the code style of this project.
  • I have added tests to cover my changes.

Deploy Notes

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment