Migration progress
This is the page to check coverage on: for every Shukah API the app calls in the user and points areas, is there a Locate route that replaces it, and does that route answer on dev today?
Click a Shukah route to see it set against the Locate route on the Shukah vs Locate page. Click Details for the full endpoint page.
Switching the app? Start with the Switch checklist: every change the app must make, in one place.
Status legend
| Mark | Meaning |
|---|---|
| ✅ Replaced | A Locate route exists for this Shukah API. The app can switch to it, after the differences on its page are handled. |
| ❌ Not replaced | No Locate route exists yet. The app keeps calling Shukah for this API. |
| ➖ Not migrating | The API stays on Shukah on purpose. No API has this status today. |
| 🚩 flag | The Locate route exists, but a switch decides whether it is used: a server flag, or an app setting (for enableMerchantService the server route is on, and the app's setting decides whether the app calls it). The note says where the switch lives. |
The Verdict column says what switching the app to the Locate route takes:
| Verdict | Meaning |
|---|---|
| Drop-in | Only the base URL and path change. |
| Adapt | The app must change code: at least one difference is breaking. |
| Blocked | The route exists but the app cannot use it yet (a flag is off or the token is refused). The note gives the reason. |
In the TL;DR box on each endpoint page, 🔴 breaking means today's app breaks or shows wrong data unless its code changes, and 🟡 to watch means the route differs but today's app still works, or only an edge case is affected.
The Dev check column is one request to the Locate route on dev, sent without a token, on the date
shown. It shows whether the route is deployed and answers, not whether it works for a signed-in
client. ✅ answers means the route is there and answered; the HTTP status follows in brackets, for
example (401) when it wants a token. ❌ not on dev means a 404. ⚠️ no answer means the request
failed.
Auth
12 of 14 replaced · 2 not replaced · 0 not migrating
| Shukah API | Locate API | Service | Status | Verdict | Dev check | Page | Note |
|---|---|---|---|---|---|---|---|
GET /maeda/api/reset-otp | GET /api/v1/clients/reset-otp | auth-service | ✅ Replaced | Drop-in | ✅ answers (400) · 2026-10-01 | Details | One route serves sign-in and registration, as on Shukah; on Locate an unknown phone gets 400 "Last Name cannot be blank." (the cue for the app to open registration; from code, while the current Shukah text is not documented) and receive_offers is not read. |
GET /maeda/api/verify-otp | GET /api/v1/clients/verify-otp | auth-service | ✅ Replaced | Adapt | ✅ answers (400) · 2026-10-01 | Details | Returns access_token and a data profile, where the token is a Locate JWT (the Shukah success body has the same shape, captured 2026-10-02), and fcm_token and platform are ignored. |
GET /maeda/api/verify-token | GET /api/v1/clients/verify-token | auth-service | ✅ Replaced | Adapt | ✅ answers (401) · 2026-10-01 | Details | |
GET /maeda/client | GET /api/v1/clients | auth-service | ✅ Replaced | Adapt | ✅ answers (401) · 2026-10-01 | Details | |
GET /maeda/address-book | GET /api/v1/clients/address-book | auth-service | ✅ Replaced | Adapt | ✅ answers (401) · 2026-10-01 | Details | Locate returns is_default as a boolean and id as a 24-hex string, where Shukah returns 0 or 1 and an integer id (lat and lng are numbers on both); the app default check accepts the boolean, but anything that treats the id as a number must change. |
GET /maeda/address-book/:id | GET /api/v1/clients/address-book/:id | auth-service | ✅ Replaced | Adapt | ✅ answers (401) · 2026-10-01 | Details | |
POST /maeda/address-book | POST /api/v1/clients/address-book | auth-service | ✅ Replaced | Adapt | ✅ answers (401) · 2026-10-01 | Details | |
PUT /maeda/address-book/:id | PUT /api/v1/clients/address-book/:id | auth-service | ✅ Replaced | Adapt | ✅ answers (401) · 2026-10-01 | Details | Flat Shukah-style body; the id may be a 24-hex id or a numeric Shukah id. |
DELETE /maeda/address-book/:id | DELETE /api/v1/clients/address-book/:id | auth-service | ✅ Replaced | Adapt | ✅ answers (401) · 2026-10-01 | Details | |
PUT /maeda/client/:client_id | PUT /api/v1/clients/:client_id | auth-service | ✅ Replaced | Adapt | ✅ answers (401) · 2026-10-01 | Details | |
PUT /maeda/client/:client_id | PUT /api/v1/clients/setting | auth-service | ✅ Replaced | Adapt | ✅ answers (401) · 2026-10-01 | Details | |
POST /maeda/client/add-device-id | POST /api/v1/clients/add-device-id | auth-service | ✅ Replaced | Drop-in | ✅ answers (200) · 2026-10-01 | Details | |
GET /maeda/client/status | — | — | ❌ Not replaced | — | — | — | No Locate route. The app snapshot declares this route but no code calls it, yet the production traffic sheet of 2026-10-02 shows 768 calls in 3 days; dev Shukah answers 404 "The route maeda/client/status could not be found." |
GET /maeda/client/delete | — | — | ❌ Not replaced | — | — | — | No Locate route deletes an account, so the app keeps calling this Shukah route, which needs a token Shukah accepts. The app deletes its stored token on a 401 here, so a JWT-only app is signed out by it. |
Points
11 of 16 replaced · 5 not replaced · 0 not migrating
| Shukah API | Locate API | Service | Status | Verdict | Dev check | Page | Note |
|---|---|---|---|---|---|---|---|
GET /maeda/client/points | GET /api/v2/client/points | order-v2 → point-service | ✅ Replaced | Drop-in | ✅ answers (401) · 2026-10-01 | Details | |
GET /maeda/point-rate | GET /api/v2/client/system_configs/point_rates | order-v2 | ✅ Replaced 🚩 enableMerchantService | Drop-in | ✅ answers (200) · 2026-10-01 | Details | |
GET /maeda/giftcard-code/use | POST /api/v2/client/gift-card-code | order-v2 | ✅ Replaced 🚩 enableMerchantService | Drop-in | ✅ answers (401) · 2026-10-01 | Details | Locate takes POST with {code} instead of GET ?code= and checks codes against the gift-card codes Locate holds itself (it is not known whether Shukah-issued codes exist there); the app already calls it in Merchant mode. 0 calls in the production traffic sheet of 2026-10-02 (3 days). |
GET /maeda/client/point-history | GET /api/v2/client/point-history | order-v2 → point-service | ✅ Replaced | Adapt | ✅ answers (401) · 2026-10-01 | Details | |
GET /maeda/point-offer | GET /api/v2/client/point-offers | order-v2 → point-service | ✅ Replaced | Drop-in | ✅ answers (401) · 2026-10-01 | Details | The ?id= filter is ignored: the call still returns the whole list. |
GET /maeda/point-occasion | GET /api/v2/client/point-occasions | order-v2 → point-service | ✅ Replaced | Drop-in | ✅ answers (401) · 2026-10-01 | Details | |
POST /maeda/point-order | POST /api/v2/client/point-orders | order-v2 → point-service | ✅ Replaced 🚩 POINT_ORDER_POINT_ENABLED | Adapt | ✅ answers (401) · 2026-10-01 | Details | Accepts only payment_type point or checkout (not payfort or hyperpay) and returns a different order shape (correlation_id, money_amount, and so on). |
POST /maeda/point-order/get-description | POST /api/v2/client/point-orders/description | order-v2 → point-service | ✅ Replaced | Drop-in | ✅ answers (401) · 2026-10-01 | Details | |
POST /maeda/order/checkout-payment-standalone | POST /api/v2/client/point-orders/:correlation_id/pay/card | order-v2 → point-service | ✅ Replaced 🚩 POINT_ORDER_CARD_ENABLED | Adapt | ✅ answers (401) · 2026-10-01 | Details | For point orders only: same body (id, cvv), but the order is named in the path by correlation_id, not point_order_id. |
POST /maeda/order/checkout-payment-flow | POST /api/v2/client/point-orders/:correlation_id/pay/session | order-v2 → point-service | ✅ Replaced 🚩 POINT_ORDER_CARD_ENABLED | Adapt | ✅ answers (401) · 2026-10-01 | Details | For point orders only: same body (rememberMe); point_order_id and payment_type are ignored and the order is named by correlation_id in the path. |
GET /maeda/points-faq | GET /api/v2/client/points-faq | order-v2 → point-service | ✅ Replaced | Drop-in | ✅ answers (401) · 2026-10-01 | Details | The five FAQ entries are identical to Shukah on dev, but Locate needs a token where Shukah answered without one. |
GET /maeda/point-order | — | — | ❌ Not replaced | — | — | — | No Locate route lists the sent gifts of a user, so the Sent gifts tab keeps calling Shukah. |
POST /maeda/order/checkout-payment | — | — | ❌ Not replaced | — | — | — | For point orders, Locate offers only a saved-card route and a session route, so the route that pays with a Checkout.com card token has no replacement. 0 calls in the production traffic sheet of 2026-10-02 (3 days). |
POST /maeda/order/checkout-payment-stcpay | — | — | ❌ Not replaced | — | — | — | By design (D24), Locate is meant to handle STC Pay inside the pay-session route, not the separate order-v2 STC Pay endpoint; not yet proven on a device. |
POST /maeda/order/payfort-token | — | — | ❌ Not replaced | — | — | — | PayFort is deferred by design for Locate point orders, so the PayFort path keeps calling Shukah. 0 calls in the production traffic sheet of 2026-10-02 (3 days). |
POST /maeda/order/payfort-stc-pay-checkout | — | — | ❌ Not replaced | — | — | — | PayFort is deferred by design for Locate point orders, so this STC Pay path keeps calling Shukah. 0 calls in the production traffic sheet of 2026-10-02 (3 days). |
New endpoints (no Shukah equivalent)
These Locate routes have no Shukah API behind them, so they are not rows in the tables above. They are new capabilities the app can use.
GET /api/v1/users: the profile of the client a token belongs to.POST /api/v1/clients/exchange-token: trade a Shukah token for a Locate token, or the other way round.GET /api/v2/client/point-offers/:id: one point offer.GET /api/v2/client/point-orders/:correlation_id: read a point order back, for example after a timeout.
Where this list comes from
The list is the Shukah calls found in a snapshot of the mobile app (mobile/locate-client, branch
development) dated 2026-02-26, checked against the Locate service docs and code read on
2026-10-01. Two later sources were added on 2026-10-02:
- The production traffic sheet ("api used last 3 days", received 2026-10-02): the Shukah routes
production served in 3 days, with call counts. It added
client/status(768 calls) and showed that four rows had no calls at all (see below). Its "Implemented in Laravel" column tracks Shukah's own port to Laravel at the same URLs, not the move to Locate. - App 2.31.5 captures (dev, 2026-10-02): the request bodies app 2.31.5 sent to the
checkout-payment-flowandcheckout-payment-stcpayroutes.
The snapshot is still the only source for the app's code. Anything the app added after 2026-02-26 and that the two sources above do not show is missing from this page.
No calls in 3 days. The traffic sheet shows 0 calls for giftcard-code/use,
order/checkout-payment, order/payfort-token and order/payfort-stc-pay-checkout. They keep
their rows, because the app's code still has the calls; each row's note says so.
Mobile team: please confirm this list against today's app. Tell us about any Shukah call in the user or points areas that is missing here, and any row that the app no longer calls.
Left out on purpose, because they are not user or points migration:
GET /maeda/api/settings, which Locate serves as order-v2GET /api/v2/client/settings. It is general app configuration and the app calls it in Merchant mode only. It has no row and no dev check.- Catalog and restaurants:
merchant,item,category,cuisine,service,advert,popular-search,bannerandapi/restaurant-config, with their sub-routes. - Orders, checkout and group orders:
order,order/history,order/checkout, themake-payment-*andconfirm-order-changeroutes,api/get-distance, thegroup-orderroutes,order/add-push-tokenandclient/apns/token. - Order changes:
order/calculate-delivery-fee,order/change-to-deliveryandorder/change-to-pickup. - Restaurant orders on the four
order/checkout-payment*routes. The rows above cover their point-order use only. - Saved cards:
order/payment-card(get and delete). The point service's docs name Locate routes for these on order-v2. - Notifications:
notificationandnotification/status. No Locate route for them was found. - General FAQ and terms:
faq. Terms is a page onlocate.sa, not an API call. - Declared in the app but never called:
client/create-food-truck-user,api/point-orderandapi/point-offer. A ShukahGET point-order/{id}is in the app's code too, but no screen uses it, so it has no row. (client/statuswas in this list until 2026-10-02. The traffic sheet shows 768 calls in 3 days, so it now has a row.) - Server-to-server: routes that backend services call, not the app. Call counts are from the
traffic sheet (3 days).
client/add-point(30,049 calls) andclient/reduce-point(2,434). order-v2 still credits points through Shukahadd-pointwhile itsusePointServiceflag is off (see Points wallet).GET client/{id}(21 calls): the client's profile.talon-one-servicecalls it with an API key, not a client token. Dev Shukah answers a client's own token with401.POST billing-info/create(14 calls) andPUT billing-info/{id}(38 calls): store billing data, not user data.locate-merchant-v2-api's merchant sync sends store billing changes to Shukah withPOST billing-infoandPUT billing-info/{Shukah merchant id}. Which caller uses the/createpath: Not documented yet.
How status is decided
- ✅ Replaced means the Locate route is implemented on the service's
developbranch. Whether it is deployed to production is a separate question that the Dev check and the flag notes speak to. - ❌ Not replaced means no Locate route for the API was found on
develop. This is decided from the code. - 🚩 flag means the route is implemented but switched off by a flag. The status stays Replaced and the flag shows what has to be on.
- Dev check is a single request without a token to the Locate route on dev. It was made on 2026-10-01. A date older than a change to the route means the check is stale.
How to update this page
The tables are not written by hand. Each row is one entry in
sites/internal/src/components/migration/registry.ts, and the same entry feeds the
Shukah vs Locate tables and the "Replaces" box on every endpoint page.
To change a row, edit that one entry (its status, flag, dev check or note), then run:
npm run test:internal && npm run build:internal
The tests check the registry's rules and the build checks every link. Do not run the build while a dev server is running in the same checkout; see the repository README. To add a Shukah API, add an
entry and its section on the comparison page, and point page at an endpoint block that exists.
Translations
Vietnamese: translated 2026-10-02 from the English pages of that date.
Arabic: translated 2026-10-02 from the English pages of that date — needs review by a native Arabic speaker before it is shared.