You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Интеграционный test suite для Web API (api.php → /api/v1), который гоняет headless Nuxt customer journey на уровне HTTP-контракта: Router + middleware + controllers + envelope. Не domain facades и не source-scan.
Сейчас в репозитории много unit/smoke и несколько Level-2 сервисов. Почти нет тестов, которые проходят storefront flow так же, как Nuxt.
Проблема, которую решает
Регрессии в TokenMiddleware, Response::normalizeResponse/getData(), CORS, cart→order bind и submit ломают Nuxt, а CI остаётся зелёным: тесты проверяют SQLite-facade или static helpers, не wire-контракт.
Нужен один suite «headless journey», который падает, если изменился JSON/HTTP публичного API.
Текущее покрытие (проверено по journey)
Легенда: HTTP = Router::dispatch / Web API envelope. Domain = facade/service без Web boundary. Static = helpers / source-scan / DTO.
то же + AuthManagerLifecycleTest (token rotate, SQLite/MySQL)
Domain + HTTP* stubs
9
Set address
нет Web: order/address/set, customer/addresses*
—
10
Select delivery
нет Web set delivery_id; pairing — DeliveryPaymentAvailabilityTest source-scan
Static
11
Select payment
нет Web set payment_id
—
12
Calculate costs GET /order/cost*
OrderCostEngineTest, manager recalculator — не Web OrderController
Domain
13
Create/draft order
cart draft via facade; ProgrammaticOrderServiceTest = sessionless, не storefront
Domain
14
Submit POST /order/submit
OrderFinalizeServiceTest domain finalize — не Web submit + redirect
Domain
15
Retrieve order GET /customer/orders*
CustomerOrderServiceDtoTest DTO/params — не HTTP
Static
* CustomerAuthEndpointsTest делает Router::loadRoutes(web.php) + dispatch, но runProcessor заглушен. Это mapping auth routes/status codes, не полный login+DB+cart transfer.
В web.php пока нет public delivery/list, payment/list, category API (#563–#569). Journey ставит delivery_id/payment_id из fixture IDs (как Fenom form), с пометкой «discovery later».
Затронутые места
tests/Integration/WebApi/* (новые)
composer.json scripts / scripts/ci-php.sh / CI workflow
Переиспользовать stubs: WebApiModxStub, CustomerAuthPdoStore, OrderProductSqliteStore где возможно
Не дублировать mgr ACL tests
Альтернативные варианты
Только расширять facade tests. Не ловит Web controller / getData() / middleware.
Browser e2e (Playwright). Дорого. Не заменяет API contract suite.
Описание функции
Интеграционный test suite для Web API (
api.php→/api/v1), который гоняет headless Nuxt customer journey на уровне HTTP-контракта: Router + middleware + controllers + envelope. Не domain facades и не source-scan.Сейчас в репозитории много unit/smoke и несколько Level-2 сервисов. Почти нет тестов, которые проходят storefront flow так же, как Nuxt.
Проблема, которую решает
Регрессии в TokenMiddleware,
Response::normalizeResponse/getData(), CORS, cart→order bind и submit ломают Nuxt, а CI остаётся зелёным: тесты проверяют SQLite-facade или static helpers, не wire-контракт.Нужен один suite «headless journey», который падает, если изменился JSON/HTTP публичного API.
Текущее покрытие (проверено по journey)
Легенда: HTTP =
Router::dispatch/ Web API envelope. Domain = facade/service без Web boundary. Static = helpers / source-scan / DTO.GET /product/listProductCatalogServiceTest— limit/offset/sort helpersGET /product/get/{id}POST /cart/addCartFacadeDraftStoreTest→Cartfacade + SQLite productsPOST /cart/changePOST /cart/change-optionCartCustomerFacadeStructureTest; runtime test нетGET /cart/getcart/statusне контракт-тестится (#570)POST /customer/registerCustomerAuthEndpointsTest/ Routes / ProcessorsDtoPOST /customer/loginAuthManagerLifecycleTest(token rotate, SQLite/MySQL)order/address/set,customer/addresses*delivery_id; pairing —DeliveryPaymentAvailabilityTestsource-scanpayment_idGET /order/cost*OrderCostEngineTest, manager recalculator — не Web OrderControllerProgrammaticOrderServiceTest= sessionless, не storefrontPOST /order/submitOrderFinalizeServiceTestdomain finalize — не Web submit + redirectGET /customer/orders*CustomerOrderServiceDtoTestDTO/params — не HTTP*
CustomerAuthEndpointsTestделаетRouter::loadRoutes(web.php)+dispatch, ноrunProcessorзаглушен. Это mapping auth routes/status codes, не полный login+DB+cart transfer.Что ещё есть (не journey)
CorsConfigNormalizeTest— pure config ([Bug] CORS: дефолт allowed_origins=* вместе с allow_credentials=true #335), не HTTP preflight.ResponseFromProcessorTest,RateLimitMiddlewareTest— изолированные куски.composer test:smoke→ standalonetests/*Test.php; PHPUnit →tests/Unit+tests/Integration.Сквозного headless HTTP journey нет. Domain coverage cart/order/auth кусками есть. Для Nuxt gate этого мало.
Предлагаемое решение
Архитектура suite
Фазы:
CustomerAuthEndpointsTest—Router+web.php+ stubbed services/DI для cart/order/product, assert HTTP status + envelope keys. Быстро в CI.AuthManagerMysqlLifecycleTest/ cart SQLite — draft rows, published product, delivery/payment members.api.phpчерез built-in server — nightly, не блокер merge.Минимум для закрытия issue: Phase A+B на PHPUnit (
composer testилиcomposer test:web-api).Auth handling
GET /customer/token/getили TokenMiddleware auto-mint → сохранить token.Authorization: Bearerи отдельно cookiems3_token.customer_id > 0.Database fixtures (Phase B)
msDeliveryMember.Полный MODX manager bootstrap не обязателен, если xPDO/SQLite harness уже принят в Integration/.
CORS
CorsConfigNormalizeTest).OPTIONSчерез Router/middleware → 200 + headers при allowlisted origin. Кейс empty origins /*+credentials ([Bug] CORS: дефолт allowed_origins=* вместе с allow_credentials=true #335).Happy path (assert envelope)
Где endpoint существует:
successв body — см. [Feature] Web API: единый контракт ошибок и HTTP-статусов для TypeScript/Nuxt #572getData()).success/datashape.status.total_*после add/change ([Feature] Web API: нормализовать контракт ответа корзины (cart/get) для headless #570).cart_cost/delivery_cost/payment_cost/costпосле set delivery/payment.data.redirectили payment redirect key.Error cases (минимум)
ms3_err_token_*)Чего suite не должен ждать
В
web.phpпока нет publicdelivery/list,payment/list, category API (#563–#569). Journey ставитdelivery_id/payment_idиз fixture IDs (как Fenom form), с пометкой «discovery later».Затронутые места
tests/Integration/WebApi/*(новые)composer.jsonscripts /scripts/ci-php.sh/ CI workflowWebApiModxStub,CustomerAuthPdoStore,OrderProductSqliteStoreгде возможноАльтернативные варианты
getData()/ middleware.Примеры использования
Nuxt-команда перед релизом витрины: зелёный journey = контракт
/api/v1не сломан.Обратная совместимость
@group mysql/ skip без DSN (как существующие Mysql integration).Критерии приёмки
success/data(не только domain arrays).composer ci:phpили отдельный required job; skip policy для MySQL задокументирован.Дополнительный контекст
CustomerAuthEndpointsTest.php.Integration/Cart/CartFacadeDraftStoreTest.php(нет change-option).OrderFinalizeServiceTest≠POST /order/submit.