إنتقل إلى المحتوى الرئيسي

سجل النقاط

الخلفية​

على Shukah يقرأ التطبيق سجل نقاط العميل كله باستدعاء واحد، GET /maeda/client/point-history: فعلى dev عادت 8,134 صفًا لعميل الاختبار في مصفوفة واحدة (و8,136 في 2026-10-02). ويُرجع GET /api/v2/client/point-history في Locate شكلَي الصفوف نفسيهما، لكنه يعطي صفحة واحدة في كل مرة: 20 صفًا افتراضيًا وبحد أقصى 100. ولا يرسل التطبيق page ولا limit، لذا فبعد التحوّل لن يرى سوى أحدث 20 صفًا. وثلاثة أمور أخرى تستحق العناية: معرّف صف المصروفات سلسلة من 24 حرفًا، وكثير من صفوف الكسب لها description فارغ، وتسرد Locate كل صفوف السجل (ledger)، بما فيها الصفوف المعكوسة (reversals) والصفوف التي لم تحرّك الرصيد.

الميزة​

السجل قائمة بمعاملات نقاط العميل. وفي نسخة التطبيق اللحظية بتاريخ 2026-02-26 تستخدمه شاشتان. وتتشاركان استدعاءً واحدًا، لا يرسل page ولا limit:

أين في التطبيقماذا يفعل
شاشة المحفظة (Wallet)تستدعيه قائمة «آخر المعاملات» عند فتح الشاشة وتعرض أول 3 صفوف من الإجابة.
شاشة سجل المحفظة (Wallet history)تستدعيه القائمة الكاملة عند فتح الشاشة وعند السحب للتحديث، وتعرض الإجابة كلها.

ويعيد التطبيق أيضًا تحميل السجل بعد استرداد كود بطاقة هدية وبعد دفع هدية.

لا يعمل على dev اليوم إلا token من Shukah: فقد حصل JWT من Locate على 401 Invalid or expired token على هذا الـ route في 2026-10-02، مع أن الـ token كليهما عملا على route الرصيد في 2026-10-01 (انظر Which tokens work). يمرّر order-v2 الاستدعاء إلى خدمة النقاط ويُرجع إجابتها دون تغيير.

ترقيم الصفحات (Paging). تبدأ page من 1 وقيمة limit الافتراضية 20، وحدها الأقصى 100. والإجابة مصفوفة مجردة. ليس فيها إجمالي ولا علامة «الصفحة التالية» ولا header للترقيم، لذا على التطبيق مواصلة الطلب إلى أن تعيد صفحة صفوفًا أقل من limit. والصفوف مرتبة بوقت الإنشاء، الأحدث أولًا، والصفوف ذات وقت الإنشاء نفسه لا ترتيب ثابت لها، لذا قد ينتقل صف بين الصفحات.

شكلان للصفوف. تفرّع بحسب points_type. لصف الكسب 7 مفاتيح ولصف المصروفات 14.

ما يمكن أن تحتويه القائمة. لا ترشّح الخدمة شيئًا:

  • صفوف الهدايا. الهدية المدفوعة بالنقاط تكتب صف مصروفات للمرسِل وصف كسب للمستلم. والهدية المدفوعة بالبطاقة تكتب صف الكسب للمستلم عند التقاط الدفعة (capture).
  • صفوف الانتهاء. تسجّل Shukah الانتهاء كصف سالب. وتحتفظ الصفوف المنسوخة من سجل Shukah بهذا الشكل: صف كسب بقيمة total_points سالبة. أما الانتهاءات منذ 2026-09-16 وتلك التي تجريها مهمة Locate نفسها فهي صفوف مصروفات بمبلغ موجب.
  • صفوف العكس (Reversal). يستطيع المسؤول عكس معاملة. ويضيف ذلك صفًا جديدًا من النوع المعاكس بالمبلغ نفسه، ويبقى الأصلي. ولا شيء يميّزه: فهو يبدو كأي صف كسب أو مصروفات آخر، ويبدأ نصه بـ reversal of. ولا ينشئ التطبيق واحدًا أبدًا.
  • الصفوف التي لم تُحتسب. الصف القادم من Shukah الذي حالته غير نشطة، وعكسُ مثل هذا الصف، يُخزَّن بوصفه غير محتسب. فلا يغيّر الرصيد، لكنه يُسرد بـ total_points العادية. وصف المصروفات من هذا النوع ما زال يقول "status": "active".

GET /api/v2/client/point-history​

يستبدل ShukahGET /maeda/client/point-history✅ تم الاستبدال
يحتاج تعديل التطبيق2 breaking · 5 للمراقبة
  • 🔴 تقسّم Locate إلى صفحات من 20 صفًا (الحد الأقصى 100)؛ وأرسلت Shukah كل الـ 8,136؛ ولا يرسل التطبيق ترقيمًا فيتوقف عند 20.
  • 🔴 لا يوجد إجمالي ولا علامة للصفحة التالية؛ كرّر الطلب مع page وlimit (الافتراضي 20 والحد الأقصى 100) حتى صفحة قصيرة.
  • 🟡 صفوف الإنفاق: 14 مفتاحًا، وtotal_points "360.00" (سلسلة نصية)، بلا shukah_id؛ ويقرأ التطبيق 5 مفاتيح ويعرضها.
  • 🟡 8 من 9 صفوف الكسب فيها description "" (وفي Shukah نص)؛ ويعرض التطبيق سطرًا فارغًا تحت التاريخ.
  • 🟡 أحدث صف في Locate هو 2026-09-29 12:45:07 (id 1351722)؛ وفي Shukah هو 2026-10-01 17:00:01 (id 1351767).
  • 🟡 الصفوف ذات date_created نفسه بلا ترتيب ثابت بين الصفحات؛ وkeyExtractor في التطبيق هو date + points.
  • 🟡 يحصل JWT من Locate على 401 على dev؛ أرسل token من Shukah.

الطلب (Request)​

الحقلالموضعالنوعمطلوبالقيودالوصف
AuthorizationheaderstringنعمBearer <token>: token من Shukah على dev اليوم. أما JWT من Locate فيحصل على 401 Invalid or expired token (التُقط على dev، 2026-10-02): انظر Which tokens work.الـ token الخاص بالعميل نفسه. ومنه يُؤخذ معرّف العميل.
pagequeryintegerلاالافتراضي 1. عدد صحيح موجب بعد تحويل النص إلى رقم.الصفحة، تُعدّ من 1.
limitqueryintegerلاالافتراضي 20. عدد صحيح موجب، بحد أقصى 100.عدد الصفوف في الصفحة.
languagequerystringلايُقبل ويُتجاهل. ويضيفه التطبيق إلى كل استدعاء.يُبقى حتى تظل سلسلة query القديمة لـ Shukah تعمل.

تُحوَّل القيم إلى أرقام قبل الفحص، لذا فإن 1e1 تساوي 10 و" 2 " تساوي 2. أما page= أو limit= الفارغة، و0، والقيمة السالبة، و1.5، وabc فتُرفض بـ 400.

الاستجابة (Response)​

200 مع مصفوفة مجردة، الأحدث أولًا. وهي [] عندما تكون الصفحة بعد النهاية.

صف الكسب (قيمة points_type هي earn)، 7 مفاتيح بهذا الترتيب:

الحقلالنوعيقبل nullالصيغة / القيودالوصف
shukah_idintegerنعممعرّف Shukah للصف عندما يوجد. وnull للصفوف التي كتبتها Locate بنفسها.معرّف الصف على جانب Shukah.
total_pointsnumberلارقم JSON. سالب في صفوف الانتهاء القديمة.النقاط المضافة.
date_createdstringلاYYYY-MM-DD HH:mm:ss، بتوقيت ساعة Asia/Riyadh، دون علامة منطقة زمنية.وقت إنشاء الصف.
descriptionstringلا"" عند عدم وجود نص. وكانت 8 من صفوف الكسب التسعة ضمن أول 10 صفوف "" في 2026-10-02، وكان واحد منها manual credit.نص حر للصف.
messagestringلادائمًا "".غير مستخدم.
points_typestringلادائمًا "earn".نوع الصف.
trans_typestringلاadjustment في كل صف ملتقط. وعندما لا يكون للصف نوع، adjustment.نوع معاملة Shukah.
{
"shukah_id": 1351722,
"total_points": 60,
"date_created": "2026-09-29 12:45:07",
"description": "",
"message": "",
"points_type": "earn",
"trans_type": "adjustment"
}

التُقط على dev، 2026-10-01 (العميل 356259، page=1&limit=5): أول الصفوف الخمسة.

صف المصروفات (قيمة points_type هي expenses)، 14 مفتاحًا بهذا الترتيب:

الحقلالنوعيقبل nullالصيغة / القيودالوصف
idstringلامعرّف hex من 24 حرفًا لصف السجل (ledger). وفي Shukah هو رقم.معرّف الصف.
client_idintegerلاالمستدعي.معرّف العميل.
merchant_idintegerلا0 عندما لا يوجد تاجر.التاجر.
order_idintegerلا0 عندما لا يوجد طلب.الطلب.
total_pointsstringلاخانتان عشريتان بالضبط، مثل "360.00". لاحظ أن صف الكسب يرسل رقمًا.النقاط المصروفة.
statusstringلادائمًا "active"، حتى للصف الذي لم يُحتسب.حالة الصف.
date_createdstringلاYYYY-MM-DD HH:mm:ss، بتوقيت Asia/Riyadh.وقت إنشاء الصف.
ip_addressstringلادائمًا "".غير مستخدم.
total_points_amtnumberلاقيمة النقاط بالريال (SAR)، 0.25 ريال لكل نقطة (360 نقطة تعطي 90). و0 عند عدم الضبط.القيمة بالريال.
trans_typestringلاorder في الصف الملتقط. وعندما لا يكون للصف نوع، order.نوع المعاملة.
points_typestringلادائمًا "expenses".نوع الصف.
remarksstringلاالنص نفسه كما في description.نص حر.
external_idnullنعمدائمًا null.غير مستخدم.
descriptionstringلا"" عند عدم وجود نص.نص حر للصف.
{
"id": "6ab5fee68fd829e4e33785f9",
"client_id": 356259,
"merchant_id": 0,
"order_id": 0,
"total_points": "360.00",
"status": "active",
"date_created": "2026-09-25 07:56:06",
"ip_address": "",
"total_points_amt": 90,
"trans_type": "order",
"points_type": "expenses",
"remarks": "You have sent a gift Graduation of 300 points to Test User (*****0000) #100004",
"external_id": null,
"description": "You have sent a gift Graduation of 300 points to Test User (*****0000) #100004"
}

التُقط على dev، 2026-10-01 (العميل 356259، page=1&limit=100): صف المصروفات الوحيد بين أول عشرة صفوف مخزَّنة؛ واستُبدل اسم المستلم وأرقام هاتفه. وهو هدية بـ 300 نقطة كلّفت المرسِل 360 نقطة.

نص الهدية. الصفوف التي تكتبها Locate لهدية تقرأ You have sent a gift … to <name> (*****<last 4 digits>) #<order number> للمرسِل، وYou have received a gift … from … للمستلم. ويتبع النص لغة المالك. وبالنسبة إلى مالك لغته العربية، يأتي النص من قالب في إعدادات النقاط، والقالب الفارغ يترك description فارغًا. وهل القوالب مملوءة على dev أو production: غير موثّق بعد.

الأخطاء​

HTTPBodyمتى
400{"success":false,"error":{"code":"VALIDATION_ERROR","message":"Invalid query","details":{"formErrors":[],"fieldErrors":{"limit":["Number must be less than or equal to 100"]}}}}فشل page أو limit في الفحص. والمثال لـ ?limit=101، من تشغيل محلي لـ schema الخدمة، ولم يُلتقط مباشرة. أما رسائل القيم الأخرى فهي Number must be greater than 0 وExpected integer, received float وExpected number, received nan.
401{"success":false,"error":{"code":"UNAUTHORIZED","message":"Missing or invalid authorization header"}}لا يوجد header باسم Authorization، أو لا يبدأ بـ Bearer . التُقط على dev، 2026-10-01، دون token.
401الشكل نفسه، مع message بالقيمة Invalid or expired token أو auth service unreachable: <error text> أو auth response missing numeric client id.رفضت خدمة المصادقة الـ token، أو تعذّر الوصول إليها (فعطل خدمة المصادقة يبدو كـ token سيئ)، أو أجابت دون معرّف عميل. وقد التُقط Invalid or expired token على dev، 2026-10-02، مع JWT من Locate.
500{"success":false,"error":{"code":"INTERNAL_ERROR","message":"Internal server error"}}أي فشل غير متوقع في خدمة النقاط، مثل خطأ في قاعدة البيانات. وتكون الرسالة AUTH_SERVICE_URL not set عندما تكون الخدمة مضبوطة خطأً. لم يُلتقط.
502{"success":false,"error":{"code":"POINT_SERVICE_UNAVAILABLE","message":"Point service unavailable: <error text>"}}تعذّر على order-v2 الوصول إلى خدمة النقاط. وهذا الـ body صادر عن order-v2، لا عن خدمة النقاط. لم يُلتقط.
504{"success":false,"error":{"code":"POINT_SERVICE_TIMEOUT","message":"Point service did not respond in time; the request outcome is unknown"}}لم تجب خدمة النقاط خلال 10 ثوانٍ. وهذا الـ body صادر عن order-v2. لم يُلتقط.

كل خطأ صادر عن خدمة النقاط له الغلاف (envelope) {"success":false,"error":{"code":"…","message":"…"}}.

جرّبه​

export ORDER_BASE_URL=https://dev.v2.api.order.locate.sa
export SHUKAH_TOKEN='<shukah-token>' # a Locate JWT gets 401 here today; see "Which tokens work" on Points wallet
curl -s "$ORDER_BASE_URL/api/v2/client/point-history?page=1&limit=5" -H "Authorization: Bearer $SHUKAH_TOKEN"

المتوقع: 200 ومصفوفة من خمسة صفوف على الأكثر، الأحدث أولًا. استخدم token من Shukah على dev اليوم: فـ JWT من Locate يحصل على 401 Invalid or expired token (2026-10-02). ومع limit=101 تحصل على 400 المبيّن تحت «الأخطاء».

الفروق عن Shukah​

الجانبShukahLocateالأثر على التطبيق
URLGET $SHUKAH_BASE_URL/maeda/client/point-historyGET $ORDER_BASE_URL/api/v2/client/point-historyغيّر base URL والمسار.
الـ Tokentoken معتم (opaque) من Shukah.token من Shukah فقط على dev اليوم. أما JWT من Locate فيحصل على 401 (التُقط على dev، 2026-10-02).يجب أن يواصل التطبيق إرسال token من Shukah هنا. وللبيئات الأخرى: غير موثّق بعد.
ترقيم الصفحاتالسجل كله في مصفوفة واحدة: 8,134 صفًا للعميل 356259 (التُقط على dev، 2026-10-01، 2.3 ث)، و8,136 في 2026-10-02.20 صفًا افتراضيًا، وبحد أقصى 100 (أعاد limit=100 ما قدره 100 صف على dev). لا إجمالي ولا علامة للصفحة التالية.لا يرسل التطبيق page ولا limit، لذا لن يعرض سوى أحدث 20 صفًا. وعليه أن يواصل الطلب حتى تأتي صفحة أقصر من limit.
id صف المصروفاترقم (تقرير التطابق في يوليو؛ ولا يوجد صف مصروفات في الالتقاط المخزَّن لـ Shukah).سلسلة من 24 حرفًا (التُقط على dev، 2026-10-01).لا شيء للتطبيق اليوم: فنوع السجل لديه لا يحتوي id ولا shukah_id.
مفاتيح صف الكسب7 مفاتيح.المفاتيح السبعة نفسها بالترتيب نفسه (التُقط على dev، 2026-10-01).لا شيء.
description للكسبنص مثل Points gained by buy item Order ID L07678739 في أحدث صفوف Shukah."" في 8 من صفوف الكسب التسعة ضمن أول 10 صفوف، وmanual credit في واحد (التُقط على dev، 2026-10-02). ولا يشترك الجانبان في أي معرّف صف ضمن أحدث الصفوف، فلم تُقارَن الصفوف نفسها.سيعرض التطبيق سطرًا فارغًا للصفوف التي لا نص لها. وهل لنسخ Shukah من تلك الصفوف نص: غير موثّق بعد.
أحدث صف2026-10-01 17:00:01، shukah_id 1351767 (التُقط على dev، 2026-10-02).2026-09-29 12:45:07، shukah_id 1351722: أقل بـ 45 معرّفًا من معرّفات Shukah وأقدم بنحو يومين (استنتاج: النسخة القادمة من Shukah متأخرة).قد تغيب من القائمة معاملة أُجريت في الأيام الأخيرة. وهل التغذية (feed) حديثة على dev: غير موثّق بعد.
مبالغ الكسبقيم total_points هي 2 و2 و2 و2 و10 في أحدث الصفوف (التُقط على dev، 2026-10-02).2 و2 و2 و10 و60 في أحدث الصفوف.لا شيء: المقياس نفسه. وفي 2026-10-01 كانت أحدث صفوف Shukah 0.5 و0.5 و2.5 و0.5 و4، وبدت كأنها بمقياس مختلف.
صفوف الانتهاءصف كسب سالب.صف مصروفات بمبلغ موجب للانتهاءات منذ 2026-09-16. والأقدم صفوف كسب سالبة.إذا كان التطبيق يجمع الصفوف أو يلوّنها بحسب points_type والإشارة، فستبدو الانتهاءات مختلفة.
الصفوف المعكوسة وغير المحتسبةهل تسردها Shukah: غير موثّق بعد.تُسرد كصفوف عادية.قد يعرض التطبيق صفًا لم يحرّك الرصيد قط.
status للمصروفاتموجود (تقرير parity لشهر يوليو 2026)؛ ولم تُلتقط القيم.دائمًا "active".لا شيء.
body الخطأ{"name":"Unauthorized","message":"Your request was made with invalid credentials.","code":0,"status":401,"type":"Illuminate\\Auth\\AuthenticationException"} (التُقط على dev، 2026-10-01، بلا token).غلاف خدمة النقاط الوارد تحت «الأخطاء».يجب تغيير أي شيء يطابق نص الخطأ أو name أو type.

تنبيه​

  • لا يرسل التطبيق page ولا limit، لذا فمقابل Locate لن يعرض سوى أحدث 20 صفًا. ولا إجمالي، فعليه مواصلة الطلب حتى تأتي صفحة أقصر.
  • ترسل صفوف الكسب total_points كرقم، وترسلها صفوف المصروفات كسلسلة بخانتين عشريتين، ويعرّفها التطبيق كرقم.
  • الصفوف التي لم تُحتسب وصفوف العكس من المسؤول تُسرد مثل أي صف آخر.

التفاصيل (للـ backend)​

فُحص dev فقط، عبر order-v2 على https://dev.v2.api.order.locate.sa، والبادئة /api/v2/client. الـ hosts في UAT وproduction: غير موثّق بعد. في هذا القسم تعني OV2: المستودع locate-order-v2-api@d9e4e5f6 وتعني PS: المستودع locate-point-service@2c44ce3. وكيف يعمل الـ proxy وفحص الـ token وغلاف الأخطاء موصوف مرة واحدة، تحت كيف تعمل الاستدعاءات الممرَّرة.

الـ Route والـ proxy​

يذهب GET /api/v2/client/point-history إلى GET /api/client/point-history في خدمة النقاط. ويمرّر order-v2 Authorization والـ query كله (بما فيه language وأي مفتاح آخر)، بحد زمني 10 ثوانٍ (OV2: src/modules/client/point/point.controller.ts:31-45، PS: services/api/src/routes/client.routes.ts:18، PS: services/api/src/handlers/client-point-history.ts:13-19). وتقرأ خدمة النقاط page و limit فقط، وما عداهما يُتجاهل (PS: services/api/src/handlers/client-point-history.ts:7-10,14). وتقول وثيقة الخدمة الشيء نفسه عن language (PS: docs/integrations/2026-07-16-client-facing-point-apis.md:113).

قواعد التحويل (coercion) مصدرها تشغيل محلي لـ schema الخدمة مع zod 3.25.76 (الإصدار الموجود في lockfile): فالقيمة الفارغة تتحول إلى 0 وتفشل، و0x10 تصبح 16، و1.5 وabc تفشلان.

الاستعلام​

point_transactions.find({client_id}).sort({created_at: -1}).skip((page - 1) * limit).limit(limit) (PS: services/api/src/services/client-points.service.ts:35-39). لا يوجد ترشيح بحسب counted، ولا بحسب النوع، ولا بحسب روابط العكس. ومفتاح الترتيب هو created_at وحده، لذا فالصفوف ذات created_at المتطابق لا ترتيب ثابت لها بين الصفحات. والاستجابة هي المصفوفة ولا شيء غيرها (PS: services/api/src/handlers/client-point-history.ts:17-18). وأي شكل يحصل عليه الصف يعتمد على type الخاص به في السجل (PS: services/api/src/services/client-points.mappers.ts:73-91).

صفوف العكس​

العكس (reversal) صف جديد في السجل من type المعاكس بالمقدار نفسه، مع reason بالقيمة reversal of <original correlation_id> وref.source بالقيمة reversal ورابط إلى الأصلي. ولا يُغيَّر الأصلي أبدًا، والسجل للإضافة فقط (append-only) (PS: packages/core/src/points/reverse-point-transaction.ts:50-55,145-148، PS: packages/core/src/db/models/point-transaction.model.ts:55-63). ولا ينشئ واحدًا إلا route للمسؤول: POST /api/admin/wallets/:client_id/transactions/:id/reverse (PS: services/api/src/routes/admin.routes.ts:31). وليس في الـ mapper علامة له. فيرجع trans_type الخاص به إلى adjustment (كسب) أو order (مصروفات) ما لم يكن التسليم الذي يبدأ من Shukah (Shukah-first delivery) قد سجّل نوعًا (PS: packages/core/src/points/reverse-point-transaction.ts:236-241).

الصفوف التي لم تُحتسب​

تُخزَّن صفوف counted: false عندما تكون status الصف القادم من Shukah غير active (PS: packages/core/src/points/sync-shukah-points.ts:104) وعندما يُعكس صف غير محتسب (PS: packages/core/src/points/reverse-point-transaction.ts:54). ولا تحرّك الرصيد وتُتجاهل لتاريخ الانتهاء (PS: packages/core/src/points/apply-point-txn.ts:53,58-59)، لكنها تُسرد بـ total_points الاسمية. وهل يسرد سجل Shukah الصفوف غير النشطة: غير موثّق بعد؛ والسؤال مفتوح منذ يوليو (PS: docs/integrations/2026-07-16-client-facing-point-apis.md:471-474).

صفوف الانتهاء​

تسجّل Shukah الانتهاء كصف سالب في جدول الكسب لديها. وتُخزَّن الصفوف المنسوخة من سجلها ككسب سالب، لذا تعود بشكل الكسب مع total_points سالبة. أما الصفوف المدفوعة مباشرة منذ 2026-09-16 والصفوف الصادرة عن مهمة الانتهاء في Locate فتُخزَّن كمصروفات بمقدار موجب، لذا تعود بشكل المصروفات (PS: packages/core/src/points/sync-shukah-points.ts:97-102، PS: docs/plans/2026-09-16-point-expiration-job.md:53,59، PS: docs/plans/2026-07-30-accept-negative-earn.md:6). ونصها هو Points expired after <days> days of inactivity <YYYY-MM-DD> (PS: packages/core/src/points/expire-points.ts:68-70).

صفوف الهدايا ونصها​

الصفوف التي تكتبها Locate لهدية (طرفا طلب مدفوع بالنقاط، وإضافة طلب مدفوع بالبطاقة) تحمل ref.source بالقيمة point_order ومعرّف تحويل. وليس لها shukah_id ولا trans_type خاص بها، لذا تُظهر صفوف الكسب adjustment وصفوف المصروفات order. ويحصل المالكون الإنجليز على الجملة الإنجليزية. ويحصل المالكون العرب على القالب من إعدادات النقاط، والقالب الفارغ يترك description فارغًا (PS: packages/core/src/points/order-reason.ts:62-87، PS: docs/plans/2026-10-01-app-language-and-arabic-reason.md:21-42). ومن بين 118,029 مستخدمًا حيًّا، لدى 117,965 العربية لغةً لهم (PS: packages/core/src/points/client-lookup.ts:8-9)، لذا فالقالب الفارغ مهم. وهل القوالب مملوءة: غير موثّق بعد.

أوصاف الكسب الفارغة والتواريخ​

تبني Shukah نص صف الكسب عند قراءته، وقد لا يحمله الدفع المباشر إلى Locate، لذا قد يكون لصفوف الكسب التي وصلت بتلك التغذية description: "" (PS: docs/integrations/2026-07-16-client-facing-point-apis.md:486-489، PS: docs/reports/2026-07-17-client-api-parity.md:22). ويُنسَّق date_created من وقت UTC المخزَّن. أما خطأ +3 ساعات الذي وجده تقرير يوليو فمصدره المزامنة الواردة وقد أُصلح هناك (PS: packages/core/src/points/shukah-date.ts:4-13، PS: packages/core/src/points/sync-shukah-points.ts:105). ولا يمكن فحصه على التقاطات اليوم، لأنه لا يشترك أي من صفوف Locate الخمسة في معرّف مع صفوف Shukah المخزَّنة.

التطبيق​

نوع السجل في التطبيق له خمسة مفاتيح: total_points وdate_created وdescription وpoints_type و trans_type. ولا يقرأ id ولا shukah_id، وتستدعي شاشتا القائمة السجل دون أي query (mobile/locate-client@e960c3a: src/entities/points/model/types/pointsHistory.server.ts:6-12، mobile/locate-client@e960c3a: src/entities/points/model/api/dto/points.dto.ts:70-88، mobile/locate-client@e960c3a: src/entities/points/model/api/services/points.service.ts:46-60).

حيث تختلف الوثائق عن الشيفرة (القول للشيفرة)​

  • وجد تقرير التطابق في يوليو أن Locate تقسّم الصفحات بـ 50 وأن Shukah تُرجع كل شيء، وأن Locate تسرد صفوف العكس والصفوف غير المحتسبة. وكلاهما ما زال صحيحًا في 2026-10-01، مع أن الافتراضي في Locate صار 20 وحدها الأقصى 100 (PS: docs/reports/2026-07-17-client-api-parity.md:62).
  • نتيجة تقرير يوليو عن "fractional total_points_amt" كانت مقارنة خاطئة بين صفين مختلفين؛ وتُظهر إعادة الفحص الصف نفسه بالقيمة 171 على الجانبين (PS: docs/reports/2026-07-17-client-api-parity-recheck.md:97-134).
  • 2026-10-02: قالت هذه الصفحة إن token من Shukah وJWT من Locate عملا كلاهما هنا. والـ JWT يحصل الآن على 401، ويستخدم قسم «جرّبه» token من Shukah (PS: services/api/src/services/client-auth.service.ts:22-29؛ انظر Which tokens work).
  • 2026-10-02: قالت هذه الصفحة إن أحدث مبالغ الكسب في Shukah (0.5 و0.5 و2.5 و0.5 و4) بمقياس مختلف عن مقياس Locate. وأحدث صفوف Shukah الآن 2 و2 و2 و2 و10: لا فجوة في المقياس. وأحدث صف فيها هو 2026-10-01 17:00:01 لا 10:40:44، وفيها 8,136 صفًا لا 8,134.
  • 2026-10-02: قالت هذه الصفحة إن أربعة من خمسة صفوف كسب في Locate لها description فارغ. وفي أول 10 صفوف هي 8 من 9.

Sources​

  • locate-order-v2-api@d9e4e5f6: src/modules/client/point/point.controller.ts:31-45
  • locate-point-service@2c44ce3: services/api/src/routes/client.routes.ts:18، services/api/src/handlers/client-point-history.ts:7-19، services/api/src/services/client-points.service.ts:35-39، services/api/src/services/client-points.mappers.ts:10-28,73-91، services/api/src/routes/admin.routes.ts:31، packages/core/src/points/reverse-point-transaction.ts:50-55,145-148,236-241، packages/core/src/db/models/point-transaction.model.ts:55-63، packages/core/src/points/sync-shukah-points.ts:97-105، packages/core/src/points/apply-point-txn.ts:53,58-59، packages/core/src/points/expire-points.ts:68-70, packages/core/src/points/order-reason.ts:62-87، packages/core/src/points/client-lookup.ts:8-9, packages/core/src/points/shukah-date.ts:4-13
  • وثائق locate-point-service@2c44ce3: docs/integrations/2026-07-16-client-facing-point-apis.md:113,471-474,486-489، docs/plans/2026-09-16-point-expiration-job.md:53,59, docs/plans/2026-07-30-accept-negative-earn.md:6، docs/plans/2026-10-01-app-language-and-arabic-reason.md:21-42، docs/reports/2026-07-17-client-api-parity.md:22,62، docs/reports/2026-07-17-client-api-parity-recheck.md:97-134
  • نسخة الجوال اللحظية mobile/locate-client@e960c3a (الفرع development، 2026-02-26؛ شيفرة التطبيق نفسه، وليست من Locate): src/entities/points/model/api/services/points.service.ts:46-60، src/entities/points/model/api/dto/points.dto.ts:70-88، src/entities/points/model/types/pointsHistory.server.ts:6-12، src/features/LastPointsTransactionsList/ui/LastPointsTransactionsList/LastPointsTransactionsList.tsx:34-36، src/entities/points/model/api/rtk/pointsApi.ts:48-68، src/features/PointsHistoryList/ui/PointsHistoryList/PointsHistoryList.tsx:27، platforms/mobile/products/locate/screens/home/mainInner/Wallet/ui/Wallet/Wallet.tsx:81، platforms/mobile/products/locate/screens/home/WalletHistory/ui/WalletHistory/WalletHistory.tsx:25، src/widgets/ApplyPointsPromoCode/model/services/applyPointsPromoCode.ts:27-50، src/widgets/PointGiftsCheckout/model/hooks/usePointGiftsCheckout.ts:221-232
  • التقاطات dev، 2026-10-02 (parity audit): point-history--shukah وpoint-history--locate-st و point-history--locate-jwt
  • التقاطات dev، 2026-10-01: locate-point-history وlocate-point-history-limit-100 و shukah-point-history وprobe-locate-point-history وprobe-shukah-point-history