Files
hedena_gold/docs/REPLICATION-CHECKLIST.md
T
s.esmaeiliandCursor afb068c643 feat: paginate customer orders and polish the dashboard hero
Add paged orders API and infinite scroll, short order numbers, and align the guest invite card with the logged-in hero shell.

Co-authored-by: Cursor <cursoragent@cursor.com>
2026-10-17 13:11:42 +03:30

21 KiB
Raw Blame History

چک‌لیست تکرار ایرادها (کاری — قدم‌به‌قدم)

منبع جزئیات: parity/CHANGELOG.md، parity/ISSUES.md، parity/DECISIONS.md.

این سند برای همین ریپو (gold-bank / تهران تاج) است تا ایرادها را verify کنیم یا باقی‌مانده‌ها را ببندیم — و در عین حال قالب تکرار برای پروژهٔ مشابه.

قبل از هر تغییر UI سمت اپ: از مالک (Honar) بپرس. منطق/رفتار بدون سوال؛ ظاهر نه. اپ مبنا برای منطق: هر دو apps/user-app و apps/user-app-v2 (مگر خلافش گفته شود).


دامنهٔ تکرار (قوانین سخت)

موضوع تکرار؟ قانون
ایرادهای امنیتی / پولی / دامنه / UX کارکردی بله منطق یکسان
فونت IRANSans (اپ + ادمین) بله همان فونت و wiring
لوگو / فاویکون / آیکن برند / wordmark خیر برند تهران تاج دست‌نخورده — BRANDING.md
کاروسل / hero / ShowcaseSlider خیر اصلاً دست نزن (حتی در verify)
فیچر اپ مثل PWA install، pull-refresh، incomplete-profile banner بله فقط منطق/رفتار؛ UI با زبان طراحی خودِ اپ
دیزاین / layout ادمین بله ادمین قابل‌رفرنس از همین ریپو (بدون تعویض لوگو)

نحوهٔ کار

نماد وضعیت معنا
انجام‌شده — verify در parity به‌عنوان FIXED ثبت شده؛ فقط smoke/خواندن کد، بازپیاده‌سازی نکن
باقی‌مانده هنوز باید پیاده یا اصلاح شود
منتظر تصمیم منتظر ruling مالک
عمداً خارج یخ‌زده یا deferred — دست نزن

چک‌باکس‌ها:

  • [x] = بسته / verify پاس شده در همین دور کار
  • [ ] = هنوز باز یا verify نشده

ترتیب پیشنهادی: ۱ امنیت → ۲ پول/سفارش → ۳ مشتری → ۴ UX اپ (منطق) → ۵ کاتالوگ/SMS → ۶ فیچر اپ → ۷ ادمین → ۸ حسابداری.


یخ‌زده (عمداً خارج — دست نزن)

موضوع قانون
کاروسل / hero اسپرینگ / ShowcaseSlider هیچ پورت دیزاین Hedena؛ هیچ بازنویسی layout
لوگو / فاویکون / brand-* / wordmark فقط طبق BRANDING.md؛ از Hedena کپی نکن
  • تأیید کلامی: کاروسل و برند در این دور کار دست نخورده‌اند

۱) امنیت و احراز هویت (اولویت بحرانی)

ID ایراد مسیر تقریبی فیکس وضعیت انجام
SEC-09 روت‌های ledger با @Public() قابل نوشتن API accounting.controller.ts حذف @Public سطح کلاس؛ rid روی هر روت: wallet.list, wallet.charge, document.create, document.list.confirm انجام‌شده — verify [ ]
SEC-10 PATCH orders/:id/status عمومی + actorAdminUserId جعلی API orders.controller.ts فقط ادمین؛ rid order.list.sts.submit انجام‌شده — verify [ ]
SEC-08 GET /customers کل دفتر مشتری را لو می‌داد API customers (حذف)؛ اپ Login / api/client حذف روت‌های با customerId؛ /customer/me* از JWT انجام‌شده — verify [ ]
SEC-03 / D6 OTP تأیید نمی‌شد API customer-auth/ + CustomerOtp؛ اپ Login bcrypt، انقضا ۲ دقیقه، ۵ تلاش، یک‌بارمصرف، throttle انجام‌شده — verify [ ]
T1 سشن مشتری جدا نبود customer-auth/، JWT_CUSTOMER_SECRET، typ: 'customer' JWT جدا از ادمین؛ خواندن مجدد DB در هر درخواست انجام‌شده — verify [ ]
SEC-02 POST /orders عمومی با customerId از body orders.controller/service، DTO، Cart @CustomerAuth()؛ customerId فقط از توکن انجام‌شده — verify [ ]
SEC-02b GET /orders/:id IDOR همان ماژول getOwnedById → 404 نه 403؛ ادمین مسیر جدا انجام‌شده — verify [ ]
SEC-11 OTP در SmsMessage.body plaintext customer-auth.service deliver() فقط خط audit سانسورشده انجام‌شده — verify [ ]
SEC-04 JWT ضعیف پیش‌فرض + CORS باز boot API / CORS production بدون JWT_SECRET بالا نیاید؛ CORS_ORIGINS انجام‌شده — verify [ ]
SEC-05 seed دمو (پسورد = موبایل) در production prisma/seed.ts، bootstrap.ts دمو فقط با SEED_DEMO_DATA=true انجام‌شده — verify [ ]
SEC-07 setRoles رشتهٔ دلخواه admin-users / roles فقط ALL_RIDS (+ والدین درخت) انجام‌شده — verify [ ]
DEPLOY-02 env خالی "" در Docker JWT را می‌شکست common/env.ts (envOr) blank = unset انجام‌شده — verify [ ]
DEPLOY-01 compose بدون JWT/SMS/OTP docker-compose.yml forward همهٔ envهای auth/SMS انجام‌شده — verify [ ]
REL-01 master OTP در production customer-auth، boot checks OTP_MASTER_CODE؛ در prod ممنوع مگر فلگ تست انجام‌شده — verify [ ]
REL-03 JWT_CUSTOMER_SECRET fallback به secret ادمین customer JWT helper secret جدا؛ enforce در production انجام‌شده — verify [ ]

Smoke پیشنهادی: apps/api/scripts/auth-smoke.sh (در صورت در دسترس بودن سرور محلی).


۲) پول، قیمت، سفارش

ID ایراد مسیر تقریبی فیکس وضعیت انجام
MON-08 کلاینت می‌توانست wage/discount/rial بگذارد orders.service، pricing/wage-formula، wage-quote قیمت فقط سرور؛ نادیده کلاینت؛ لاگ mismatch انجام‌شده — verify [ ]
ACC-03 / MON-04 بدهی دوبار با ورود مجدد به DELIVERED_TO_AGENT LedgerService.syncOrderDebt sync به هدف؛ فقط delta؛ rollback/cancel درست انجام‌شده — verify [ ]
MON-05 canPlaceOrders اعمال نمی‌شد مسیر create سفارش اپ → 403؛ ادمین می‌تواند برای مشتری ثبت کند انجام‌شده — verify [ ]
MON-01 سقف موجودی در سبد نبود (v2) cartStore، CartItem/SingleProduct capQty/maxQty + disable + toast انجام‌شده — verify [ ]
ORD-01 ویرایش وضعیت سفارش retail خراب admin order/List.vue body از tempRow.id مثل Omde/Tamin انجام‌شده — verify [ ]
کانال سفارش اپ سفارش اپ به‌اشتباه RETAIL orders.service، DTO، migration، admin-orders پیش‌فرض/ذخیره WHOLESALE برای مسیر اپ + migrate ردیف‌های قبلی انجام شد 2026-10-17 — placedBy=customer ⇒ WHOLESALE؛ migration 20261017120000_app_orders_wholesale_channel [x]

۳) مشتری / اشخاص / نام / درصد

ID ایراد مسیر تقریبی فیکس وضعیت انجام
CUST-01 fname: fullName, lname: '' نام‌ها را یکی می‌کرد migration firstName/lastName؛ فرم‌ها ستون‌های واقعی؛ حذف split(' ') انجام‌شده — verify (schema دارد) [ ]
CUST-02 percent از کمیسیون نماینده makingChargeOffsetPercent؛ CRUD مشتری ستون خود مشتری؛ پیش‌فرض ۳؛ required در create انجام‌شده — verify [ ]
D17 / CUST-03 فرم کارشناس فروش ناقص SalesExpertProfile؛ ReagentCustomer.vue پروفایل جدا؛ autofill شهر→کمیسیون انجام‌شده — verify (فرم ncode/city/gram دارد) [ ]
PERS-02 شهر flat به‌جای درخت استان City.parentId، CityTreeSelect درخت استان؛ ارث‌بری درصد از ancestor انجام‌شده — verify [ ]
PERS-03 تاریخ تولد نبود Customer.birthDate، DateInput فیلد جلالی create/update انجام‌شده — verify [ ]
D19 موبایل نرمال نمی‌شد / SMS خوش‌آمد admin-customers / admin-users faToEn قبل uniqueness؛ welcome SMS fire-and-forget انجام‌شده — verify [ ]

۴) لاگین اپ / act-as / ناوبری / تازگی داده

فقط رفتار را port/verify کن؛ ظاهر Login/Dialog/Nav را از زبان طراحی خودِ اپ بگیر — کپی پیکسلی Hedena نکن. قبل از تغییر UI از Honar بپرس.

ID ایراد مسیر تقریبی فیکس وضعیت انجام
AUTH-01 شماره ثبت‌نشده → موفقیت جعلی → OTP requestOtp، Login 404 + پیام فارسی انجام‌شده — verify [ ]
AUTH-02 شکست SMS → موفقیت جعلی deliver 503 + «SMS در دسترس نیست» انجام‌شده — verify [ ]
AUTH-03 مشکل حساب کارشناس مثل «ثبت‌نشده» resolveExpertTradingAccount پیام‌های 403 جدا انجام‌شده — verify [ ]
APP-03 صفحات شخصی مهمان silent redirect router/index.ts toast «ابتدا وارد شوید» + نگه داشتن ?redirect= انجام‌شده — verify [ ]
EXP-01…03 «ورود به حساب مشتری» برای کارشناس نبود JWT strategy، X-Act-As-Customer، session، ActingAsBar act-as با هدر (نه توکن minted)؛ پاک کردن cache/cart؛ نوار دائمی انجام‌شده — verify [ ]
NAV-01…04 back همیشه route ثابت؛ login/401 تاریخچه مرده PageBar، navStore، Login، main.ts back تاریخچه‌دار؛ replace بعد login/401 انجام‌شده — verify [ ]
READ-01…03 keep-alive صفحه را دوباره fetch نمی‌کرد Orders/Transactions/Home/Dashboard، queryCache refresh روی onMounted+onActivated انجام‌شده — verify [ ]

۵) کاتالوگ / علاقه‌مندی / SMS / آپلود

ID ایراد مسیر تقریبی فیکس وضعیت انجام
STUB-03 کل کاتالوگ یکجا؛ pagination فقط کلاینت catalog API + اپ‌ها page/filter/sort سرور؛ ?ids=، /:id، /facets مرحله ۴ انجام شد 2026-10-17 — Search/Newest/Home/Collection روی هر دو اپ؛ UI همان زبان طراحی [x]
FAV-01 علاقه‌مندی فقط memory API customer/me/favorites*، favoritesStore load/toggle سمت سرور انجام‌شده — verify [ ]
SMS-03 بدون SMS ثبت سفارش orders.service notify + ORDER_ADMIN_MOBILES SMS بعد commit به ادمین/مشتری/کارشناس انجام‌شده — verify [ ]
STUB-05 موبایل ادمین hardcode env PROFILE_ADMIN_MOBILES، ORDER_ADMIN_MOBILES انجام‌شده — verify [ ]
UPL-01 اپ نمی‌توانست مدرک آپلود کند POST customer/me/documents آپلود برای complete-profile انجام‌شده — verify [ ]
D22–D24 complete-profile / گزارش بدون IDOR customer modules whitelist write؛ گزارش scoped انجام‌شده — verify [ ]

۶) فیچرهای اپ (منطق بله — دیزاین خیر)

تم چه چیزی port شود چه چیزی port نشود وضعیت انجام
فونت IRANSans فایل‌های فونت + fonts.less / wiring در اپ و ادمین — ادمین wired (farsi.less)؛ اپ‌ها را verify کن [ ]
PWA install prompt beforeinstallprompt، prompt قابل dismiss، logic ظاهر مودال Hedena باقی‌مانده — usePwaInstall / InstallPromptModal در ریپو نیست؛ UI بعد از تأیید Honar [ ]
Pull-to-refresh / incomplete-profile / gate login رفتار و شرط‌ها layout/illustration/رنگ Hedena pull-refresh و complete-profile موجود — verify رفتار [ ]
کاروسل / ShowcaseSlider / hero — اصلاً تکرار نکن عمداً خارج —
لوگو / فاویکون / brand assets — اصلاً تکرار نکن عمداً خارج —

رفرنس منطق PWA (اگر از پروژهٔ مرجع بیاید — فقط رفتار، نه UI): composable usePwaInstall + مودال dismiss/defer؛ markup را با کامپوننت‌های خود اپ بازنویسی کن.


۷) ادمین / پرمیشن / UX (دیزاین قابل‌رفرنس)

ID / تم ایراد مسیر تقریبی فیکس وضعیت انجام
PERM-01 ridهای یتیم dashboard migration merge → dashboard.view merge/حذف ridهای قدیمی انجام‌شده — verify [ ]
PERM-02 ridهای enforced ولی غایب از درخت permissionConst.ts افزودن newsletters، persons.list.sellers.view منتظر تصمیم [ ]
D30 ویژگی‌های retail/بانک/شعبه فقط super-admin super-admin.ts، منو/گارد gate با موبایل ثابت؛ hide + 403 انجام‌شده — verify (در صورت پیاده) [ ]
super-admin rids سوپرادمین همه rid نداشت super-admin.ts، permissionConst ALL_RIDS؛ اسلایدر زیر ثابت‌ها انجام‌شده — verify [ ]
Order UX وضعیت سفارش UX ضعیف Listها / مودال وضعیت drawer راست + confirm خروج — دیزاین از ادمین همین ریپو باقی‌مانده / verify — فایل‌های OrderStatusModal.vue / OrderViewModal.vue در این ریپو پیدا نشد؛ List.vue فعلی را بسنج [ ]
Icon migration وابستگی @ant-design/icons-vue Icon محلی + icons.json آیکون محلی باقی‌مانده — ادمین هنوز از @ant-design/icons-vue زیاد استفاده می‌کند [ ]
Dashboard unify / فرم محصول و مشتری chrome ناهماهنگ Dashboard.vue، AddProduct، AddCustomer unify بصری (بدون تعویض لوگو) بخشی انجام‌شده — PROTECTED dashboard chrome؛ verify [ ]
فونت ادمین خوانایی farsi.less / IRANSans همان فونت؛ لوگو را عوض نکن انجام‌شده — verify [ ]
PROMO-TAK-01 type_customer / ridهای .tak promotions ثبت و/یا gate API باقی‌مانده (logged) [ ]
CINY-01 ciny_ids در update نادیده admin-products update هم trays را ذخیره کند باقی‌مانده (logged) [ ]
ANLY-01 analytics dwell-time — — عمداً خارج — deferred، اولویت پایین —

۸) حسابداری یکپارچه

ID ایراد فیکس وضعیت انجام
ACC-06 TLS خودامضا / hostname fail cert pin؛ هرگز verify را خاموش نکن انجام‌شده — verify [ ]
ACC-07 «متصل است ولی sync نمی‌شود» رد provider ناقص؛ inactiveReason؛ گروه‌های انتخاب‌شده الزامی انجام‌شده — verify [ ]
ACC-08/09 sync کند / بدون on-demand poll سریع + دکمه sync + وضعیت زنده انجام‌شده — verify [ ]

جزئیات: ACCOUNTING-INTEGRATION-PLAN.md.


صف باقی‌ماندهٔ واقعی (اولویت اجرا بعد از verify امنیت)

  1. کانال WHOLESALE ✅
  2. STUB-03 مرحله ۴ ✅ (منتظر چک UI تو)
  3. PWA install — فقط منطق؛ UI بعد از سؤال از Honar
  4. PERM-02 — بعد از ruling
  5. Icon محلی ادمین / Order drawer UX — در صورت نیاز
  6. PROMO-TAK-01، CINY-01

پرامپت آماده برای Cursor پروژهٔ دوم

کپی کن و در چت پروژهٔ مشابه بگذار:

این پروژه شبیه hedena_gold / gold-banking-monorepo است و همان ایرادها را دارد.
همان فیکس‌ها را با منطق یکسان پیاده کن. اولویت با امنیت و پول است.

قوانین دامنه (سخت):
- فونت IRANSans را برای اپ و ادمین بیاور (فایل + wiring).
- لوگو / فاویکون / آیکن برند / wordmark را عوض نکن و از Hedena کپی نکن.
- کاروسل / hero اسپرینگ / showcase دیزاین‌شدهٔ Hedena را اصلاً تکرار نکن.
- فیچرهای اپ مثل PWA install، pull-refresh، incomplete-profile banner: فقط منطق/رفتار را port کن؛ UI را با زبان طراحی و کامپوننت‌های خودِ این اپ بساز — از مودال/رنگ/illustration هدنا کپی نکن.
- پنل ادمین یکی است: برای دیزاین drawer سفارش، Icon محلی، dashboard unify، فرم‌ها می‌توانی مستقیم از ادمین مرجع رفرنس بگیری (باز هم بدون تعویض لوگو).
- قبل از هر تغییر UI سمت اپ از مالک بپرس.

A) امنیت
- روت‌های ledger و تغییر وضعیت سفارش را از Public دربیاور؛ فقط ادمین با rid مناسب
- GET لیست مشتری برای login را حذف کن؛ سشن مشتری با JWT جدا (JWT_CUSTOMER_SECRET، typ=customer)
- OTP واقعی: bcrypt، انقضا ۲ دقیقه، ۵ تلاش، یک‌بارمصرف، throttle؛ OTP را در SMS audit plaintext ذخیره نکن
- POST /orders پشت CustomerAuth؛ customerId فقط از توکن؛ GET order با مالکیت → 404 نه 403
- production بدون JWT_SECRET بالا نیاید؛ CORS از CORS_ORIGINS؛ seed دمو فقط با SEED_DEMO_DATA
- env خالی "" را unset بگیر (envOr)؛ JWT مشتری fallback به secret ادمین نداشته باشد
- OTP_MASTER_CODE در production ممنوع مگر فلگ تست

B) پول/سفارش
- wage/discount/rial را از کلاینت نپذیر؛ فرمول سرور + لاگ mismatch
- sync بدهی سفارش idempotent با delta (نه پست دوباره)
- canPlaceOrders در اپ 403 کند؛ ادمین بتواند برای مشتری ثبت کند
- سقف موجودی در سبد (capQty/maxQty)
- سفارش‌های اپ را WHOLESALE ذخیره کن نه RETAIL (اگر دامنه B2B است)

C) مشتری
- firstName/lastName جدا؛ percent خود مشتری (makingChargeOffsetPercent) نه کمیسیون نماینده
- پروفایل کارشناس فروش کامل؛ درخت شهر استان؛ تاریخ تولد؛ faToEn روی موبایل

D) اپ (منطق بله — دیزاین از خودِ این پروژه)
- requestOtp: 404 ثبت‌نشده، 503 SMS fail، 403 پیام جدا برای کارشناس
- toast ورود برای صفحات شخصی + redirect=
- act-as کارشناس با هدر X-Act-As-Customer (نه mint توکن)
- back تاریخچه‌دار؛ بعد login/401 از replace استفاده کن
- صفحات keep-alive را روی activate دوباره fetch کن
- PWA install: beforeinstallprompt + dismiss/defer؛ UI با کامپوننت‌های خود اپ
- IRANSans را وصل کن؛ لوگو و کاروسل را دست نزن

E) کاتالوگ/SMS
- pagination/فیلتر سرور برای محصولات؛ favorites سمت سرور
- SMS ثبت سفارش بعد commit؛ شماره‌ها از env نه hardcode
- آپلود مدرک مشتری برای complete-profile

F) ادمین (دیزاین قابل‌رفرنس)
- ridهای یتیم dashboard را merge کن
- ویژگی‌های خطرناک فقط super-admin؛ سوپرادمین ALL_RIDS
- Order status UX به صورت drawer راست + confirm logout — layout از ادمین مرجع
- Icon محلی به‌جای @ant-design/icons-vue اگر همان وابستگی را دارید
- IRANSans در ادمین؛ لوگو را عوض نکن

برای هر آیتم: اول محل معادل در این ریپو را پیدا کن، بعد فیکس را با تست/smoke کوتاه اعمال کن.
جزئیات کامل: در ریپوی مرجع فایل docs/REPLICATION-CHECKLIST.md

منبع برای جزئیات بیشتر