From 230962b1d0c7e8b0b335609998790e859507f7ee Mon Sep 17 00:00:00 2001 From: Sathira Sri Sathara Date: Thu, 3 Sep 2026 13:02:24 +0530 Subject: [PATCH] Add current backend status documentation --- Documentation/CURRENT_BACKEND_STATUS.md | 362 ++++++++++++++++++++++++ 1 file changed, 362 insertions(+) create mode 100644 Documentation/CURRENT_BACKEND_STATUS.md diff --git a/Documentation/CURRENT_BACKEND_STATUS.md b/Documentation/CURRENT_BACKEND_STATUS.md new file mode 100644 index 0000000..e819f55 --- /dev/null +++ b/Documentation/CURRENT_BACKEND_STATUS.md @@ -0,0 +1,362 @@ +# ZUMRI Current Backend Status + +Audit date: 2026-09-03 +Scope: repository source, configuration, lockfile, existing documentation, safe syntax/test/dependency checks. No database, Redis, S3, email, or other external service was mutated. + +## 1. Executive Summary + +This repository is an early modular-monolith foundation, not yet an e-commerce backend. It contains working-shaped user registration/email verification, OTP login, basic profiles, RBAC tables/controllers, notifications, activity logging, S3 upload plumbing, document generation, Redis/BullMQ workers, and one cron. Important pieces are incomplete or broken in integration. The estimated completion against the 25-module ZUMRI target is **about 12%**. + +No original development-plan day is fully complete. Day 1 is approximately 55%: Express, Sequelize/MySQL, Redis/BullMQ, a Dockerfile, and a health route exist, but Swagger, robust health checks, Node 22 alignment, production bootstrap/error handling, Compose/Nginx, migrations, and tests do not. Day 2 is approximately 38%; Day 3 approximately 18%; notification/job/file/document/audit foundations from later days were built early. + +The code still carries prior-project terminology (`Oceanic Titan`, `oceanic-db`, Oceanic demo URL) and role names that conflict with the actual user ENUM. Future work should preserve usable primitives, but first complete and secure foundation/authentication. + +Status terms: **COMPLETE** = end-to-end implementation is credible from source; **PARTIAL** = meaningful code exists but requirements/integration are incomplete; **STUB** = structure only; **MISSING** = no implementation; **BROKEN** = known source/integration defect. + +## 2. Current Architecture + +- `server.js` loads `.env`, imports `app.js`, and listens on `0.0.0.0:${PORT|3070}`. +- `app.js` authenticates Sequelize and calls unrestricted `sequelize.sync()` in an unawaited startup IIFE, then starts cron jobs. The HTTP listener starts independently, so requests can arrive before database readiness, and DB failure does not stop the process. +- Middleware order is cookie parser, CORS, JSON parser, Morgan, `/health`, `/api`, static documentation, then Bull Board. There is no URL-encoded parser, request ID, Helmet, compression, rate limiting, global 404 handler, or global error handler. +- API base path is `/api` (not versioned). Routes delegate mostly directly to Sequelize-backed controllers; there is only a permission service and activity service. +- Redis connections are created at module import. One shared client is used by queues/workers, while password reset and S3 utilities create additional clients. +- Workers are a separate `npm run worker` process. The server does not start them. Activity, log, and document consumers exist. +- Cron runs in every API process after DB sync; there is no distributed lock, so multi-instance deployments duplicate scheduling. +- Sequelize models are registered centrally and their `associate` functions are invoked. No migrations are present. +- Environment keys exist locally; `.env` is ignored/untracked. `.env.sample` is tracked. No actual secret values are reproduced here. + +### Bootstrap and operational findings + +| Concern | Status | Evidence / impact | +|---|---|---| +| Express start and base path | Partial | `server.js`, `app.js`; `/api` and `/health` | +| JSON / cookies / CORS / logging | Partial | JSON, cookies, single-origin credentialed CORS, Morgan `dev`; no body-size configuration or URL-encoded parser | +| Security middleware | Missing | No Helmet or API rate limiter | +| 404/global errors | Missing | Errors depend on individual controllers; unmatched routes use Express defaults | +| Database readiness | Broken | Listener is not gated on authenticate/sync; failure is logged only | +| Redis readiness | Partial | Event logging exists; health endpoint never checks Redis | +| BullMQ/workers | Partial | Separate process required and undocumented operationally; retries only on document jobs | +| Cron initialization | Partial | Starts after DB sync, once per server process, with no leader lock | +| Health check | Broken | Sends response before asynchronous DB authentication completes and hardcodes mail/Redis as OK | +| Graceful shutdown | Missing | No SIGTERM/SIGINT cleanup for server, Sequelize, Redis, workers, or cron | +| Process errors | Missing | No `unhandledRejection`/`uncaughtException` policy | + +## 3. Existing Infrastructure + +| Component | Status | Files | Notes | +|---|---|---|---| +| Express API | Partial | `server.js`, `app.js`, `app/routes/*` | Express 5; no versioning/global errors/security middleware | +| MySQL/Sequelize | Partial | `app/config/db.config.js`, `app/models/index.js` | Pool configured; runtime `sync()`, no migrations | +| Redis | Partial | `redis.config.js`, `redisClient.js` | Functional client pattern; excessive clients, no shutdown/readiness | +| BullMQ | Partial | `app/queues/*`, `app/workers/*` | Three queues and matching consumers; only document jobs have attempts/backoff/retention | +| Bull Board | Broken/unsafe | `bullBoard.config.js`, `app.js` | Only activity queue shown; `/admin/queues` has no authentication | +| Cron | Partial | `cron/*` | Transactional notification deletion; no distributed lock or retention-age policy | +| Email | Partial | `mail.config.js`, `mail.util.js`, templates | SMTP/template sender exists; verifies on import, sends inline, no queue/retry/escaping | +| S3 storage | Broken | `s3.config.js`, `s3Upload.utill.js` | S3 client is entirely commented out, so `s3.send` fails | +| Uploads | Broken | upload middleware/controller/model | MIME/size checks exist; account guard is incompatible; no magic-byte validation/cleanup/ownership | +| Documents | Partial/broken | document controller, logic, templates, queue/worker | PDF/Excel framework is substantive; S3 breaks completion; access is overly broad and role guards mismatch | +| Notifications | Partial | notification models/controller/cron | In-app records only; no assignment API/service, email/FCM/preferences/delivery tracking | +| Activity/audit | Partial | activity service/model/queue/worker/controller | Async append-only-shaped records; no actor/IP/change metadata, integrity/retention, or broad coverage | +| Logging | Partial | console utility/log queue/worker | Local daily files; may receive sensitive payloads; no rotation/structured sink | +| API docs | Partial | `Documentation/*`, docs routes | Handwritten Markdown/HTML, not Swagger/OpenAPI; docs auth is forgeable | +| Tests | Missing | package script only | Jest finds zero tests; Supertest is not installed | +| Docker | Partial | `Dockerfile` | Uses Node 20 instead of target Node 22; API image only; no healthcheck/non-root user | +| Nginx/Compose/CI/CD | Missing | none | No reverse proxy, service orchestration, or pipeline files | +| Payments/FCM/OpenAI | Missing | none | No dependencies, config, models, or consumers | + +Queue behavior: `document-generation` has 3 exponential attempts (2s base), completed retention, and retained failures. `activity-queue` and `logQueue` have consumers but no explicit retry/backoff/retention/dead-letter policy and are not idempotent. Re-delivery can duplicate activity rows or log lines. Queue event listeners attached to `Queue` are not a reliable substitute for `QueueEvents` for all lifecycle events. Worker failures are logged only. Document status is not reconciled on job failure/success. + +## 4. Existing Database Models + +All models use timestamps and none uses `paranoid`. Aside from the unique flags noted below, explicit indexes are absent. + +| Model / table | Key and important fields | Purpose | Important relations | Status | +|---|---|---|---|---| +| User / `users` | PK string `id`; names, unique email, password, accountType ENUM, accountStatus ENUM, emailVerifiedAt | Identity/account | hasOne Profile; hasMany UserPermission | Partial; no role FK/`roleID` despite service/controller use, no sessions/tokenVersion/social IDs | +| Profile / `profiles` | PK `profile_id`; unique `user_id`; theme, notificationsEnabled, image IDs, DOB, phone | Basic preferences/profile | belongsTo User | Partial; no gender/language/address; image IDs lack FKs | +| UserActivity / `UserActivity` | integer PK; user/name/description/type/module/date/time | Activity trail | None | Partial; user FK absent, redundant time fields, no indexes | +| Upload / `uploads` | integer PK; S3 path/type/size/name/use/uploaded_by | Media metadata | None | Partial; uploader/user and ownership FKs absent | +| Permission / `permission` | PK `permission_id`; name/page/module/action | Permission definition | hasMany role/user grants | Partial | +| Role / `roles` | PK `role_id`; name/description | Named role | hasMany role grants | Partial; User has no role association | +| RolePermission / `rolePermission` | PK `rp_id`; role_id, permission_id | Role grant | belongsTo Role/Permission | Partial; no composite unique constraint | +| UserPermission / `userPermission` | integer PK; user_id, permission_id | Direct additive grant | belongsTo User/Permission | Partial; no composite unique; cannot deny/expire grants | +| Document / `Document` | PK `doc_id`; reference_no, doc_type, JSON data, status | Saved business documents | None | Partial; status/type unconstrained, no creator/owner/FKs/indexes | +| DocumentType / `DocumentType` | integer PK; nullable name, JSON description | Document registry metadata | None | Partial; name is neither required nor unique | +| ReferenceNumber / `referenceNumbers` | PK string; unique sequence_key, integer counter, last value | Atomic sequence generation | None | Reusable; transaction/row locking implemented by utility | +| Notification / `notification` | PK string; headline/body, USER/ANNOUNCEMENT ENUM, active/date | In-app notification content | hasMany UserNotification as `users` | Partial | +| UserNotification / `user_notification` | integer PK; user_id, notification_id, isRead | Per-user notification state | belongsTo User; belongsTo Notification | Partial; constraints disabled, no composite unique/index; include alias is inconsistent (controller asks `notification`, association defines no alias) | + +Association registration does execute. However, User's `roleID` is not a declared attribute or FK, notifications deliberately disable FK constraints, activities/uploads/documents have no user association, and join-table uniqueness is not enforced. `sequelize.sync()` masks the absence of schema migrations and makes production schema evolution unsafe. + +## 5. Existing API Endpoints + +All paths below are derived from actual mounting. “Self-or-admin” is not implemented anywhere; parameterized user endpoints generally trust the requested ID after coarse account-type checks. + +| Method | Endpoint | Auth | Permission / guard | Status | Notes | +|---|---|---|---|---|---| +| GET | `/health` | No | None | Broken | Returns before DB check; Redis/mail are hardcoded OK | +| GET | `/api/auth/me` | Yes | None | Partial | Returns token payload plus effective permissions | +| POST | `/api/auth/req-otp` | No | None | Partial/unsafe | Password + in-memory OTP; logs OTP; enumeration; no attempts/rate limit/status check | +| POST | `/api/auth/login` | No | None | Partial/unsafe | OTP to one-day access cookie; no refresh/session/rotation/status check | +| POST | `/api/auth/logout` | No | None | Partial | Clears cookie only; bearer tokens remain valid | +| POST | `/api/user` | No | None | Partial/bug | Registration + profile + verification; activity uses undefined `req.user` after commit | +| POST | `/api/user/verify-email` | No | None | Partial | Redis one-use hashed token; no resend endpoint | +| GET | `/api/user` | Yes | accountType `admin` | Partial | Paginated list | +| GET | `/api/user/:id` | Yes | listed legacy types | Broken/IDOR | Most listed types cannot exist; no ownership enforcement | +| PATCH | `/api/user/:id` | Yes | listed legacy types | Broken/privilege escalation | Mass updates accountType/undeclared role fields; no ownership/field validation; early returns leak transaction | +| DELETE | `/api/user/:id` | Yes | `admin` | Partial | Hard delete; related profile handling depends on DB state; early return leaks transaction | +| GET | `/api/activity` | Yes | `admin` | Partial | Full audit list, no pagination | +| GET | `/api/activity/user/:userId` | Yes | `admin` | Partial | No paging/index | +| POST | `/api/upload` | Yes | `admin` or nonexistent `staff` | Broken | S3 client undefined; DB requires `use_for`; upload not transactional | +| GET | `/api/upload/signed-url/:id` | Yes | `admin` or nonexistent `staff` | Broken | S3 undefined; catch sends no response; no ownership check | +| GET | `/api/document/types` | Yes | admin or nonexistent legacy types | Partial | Effectively admin-only under current ENUM | +| POST | `/api/document/saved` | Yes | same | Partial | Body filter on a read operation; no owner/pagination; Sequelize `exclude` placed incorrectly | +| POST | `/api/document/generate` | Yes | same | Broken | Queues correctly, but worker S3 upload fails; validation shallow | +| POST | `/api/document/draft` | Yes | same | Partial | Saves arbitrary JSON; no ownership/validation | +| GET | `/api/document/reference-number/:documentType` | Yes | same | Partial | Consumes sequence on GET | +| GET | `/api/document/job/:jobId/status` | Yes | same | Partial/IDOR | Exposes stacktrace and any job by ID | +| GET | `/api/document/download/:uuid` | Yes | same | Broken/unsafe | S3 undefined; deletes shared object after response; no ownership | +| DELETE | `/api/document/job/:jobId` | Yes | same | Partial/IDOR | Any allowed user can remove any removable job | +| GET | `/api/document/:docId` | Yes | same | Partial/IDOR | Arbitrary document access | +| POST | `/api/docs/login` | No | Static credentials | Unsafe | Sets unsigned boolean cookie; no expiry/rate limiting | +| POST | `/api/docs/logout` | No | None | Partial | Clears cookie | +| GET | `/api/docs/markdown-files` | docs cookie | `docsAuth === "true"` | Unsafe | Cookie can be forged by client | +| GET | `/api/docs/view/:file` | docs cookie | same | Partial | Extension/path checks; auth is weak | +| POST | `/api/profile/req-reset-password` | No | None | Partial/unsafe logging | Enumeration-resistant response; raw reset token is logged | +| POST | `/api/profile/reset-password` | No | None | Partial | Hashed one-use Redis token; new password is not policy-validated | +| POST | `/api/profile/change-password` | Yes | legacy account types | Broken/partial | Effectively admin-only; no new-password validation/session revocation | +| GET | `/api/profile/avatar/:userId` | Yes | legacy account types | Broken | S3 undefined, missing upload null check, wrong `profile.userId` property, IDOR | +| GET | `/api/profile/background/:userId` | Yes | legacy account types | Broken | Same issues | +| POST | `/api/notification` | Yes | admin or nonexistent `management` | Partial | Creates content only; no user assignment | +| GET | `/api/notification/announcements` | Yes | legacy account types | Partial | Effectively admin-only | +| GET | `/api/notification/user/:userId` | Yes | legacy account types | Broken/IDOR | Include alias mismatch likely throws; no ownership | +| PATCH | `/api/notification/user/:userId/notification/:notificationId/read` | Yes | legacy account types | Broken/IDOR | No ownership; effectively admin-only | +| ALL | `/admin/queues/*` | No | None | Unsafe | Bull Board exposed; only activity queue registered | +| GET | `/Documentation/*` | No | Blocks `.md` only | Partial | Static HTML documentation is public | + +### Defined but unreachable permission routes + +`app/routes/permission.routes.js` defines 18 endpoints under the intended permission router (permission CRUD/bulk; role CRUD and grants; user grants CRUD/bulk), but `app/routes/index.js` imports `permissionRoutes` and never calls `router.use(...)`. Therefore none has an actual URL and all are **BROKEN/unreachable**. If mounted as `/permission`, their paths would be `/`, `/bulk`, `/:permissionId`, `/roles`, `/roles/:roleId`, `/roles/:roleId/permissions`, `/roles/permissions/bulk`, `/users/:userId/permissions`, `/users/permissions`, `/users/permissions/bulk`, and `/users/permissions/:upId` with the methods declared in that file. Read endpoints require authentication; mutations require accountType exactly `admin`. Controllers are substantial CRUD logic, but integration, uniqueness, cache invalidation, validation, and transactions are inconsistent. + +## 6. Development Plan Status + +| Module | Completion | Status | Evidence | Remaining Work | +|---|---:|---|---|---| +| 01 Authentication & Authorization | 38% | Partial | Password hashing, register/verify, OTP access JWT, middleware, RBAC structures | Refresh/session lifecycle, OAuth/Apple, durable OTP/limits, status enforcement, role linkage, mount/fix RBAC | +| 02 Customer Profile & Address Management | 22% | Foundation | User/Profile with phone, DOB, images/preferences | Self-service ownership, addresses/default, gender/language, deactivation, robust image flow | +| 03 Product Catalogue Management | 0% | Missing | No models/routes | Full catalogue/category/variant/review/SEO model and APIs | +| 04 Multi-Language Content | 0% | Missing | No content translation system | Locale strategy and translated content | +| 05 Inventory Management | 0% | Missing | No inventory entities | Stock, reservations, warehouses, adjustments | +| 06 Cart & Wishlist | 0% | Missing | None | Entire module | +| 07 Promotions, Coupons & Banners | 0% | Missing | None | Entire module | +| 08 Checkout | 0% | Missing | None | Pricing/shipping/tax/transaction orchestration | +| 09 Order Management | 0% | Missing | Document names are not commerce orders | Full order state machine and returns | +| 10 Payment Management | 0% | Missing | No provider code/dependencies | PayHere/Stripe, webhooks, idempotency, refunds | +| 11 Delivery & Rider Management | 2% | Foundation only | `rider` account ENUM; document templates named delivery/dispatch | Rider profiles, assignments, tracking, zones/rates | +| 12 Loyalty, Reward Points & Membership | 0% | Missing | None | Ledger, tiers, generic earn rules, rewards/vouchers | +| 13 Wholesale / Business Accounts | 2% | Foundation only | `business_customer` ENUM only | Approval/profile/pricing/MOQ/tiers/credit/settlements/invoices/analytics | +| 14 Notification System | 28% | Partial | Notification/user join models, CRUD/read endpoints, cleanup cron, mail utility | Fix aliases/ownership; assignment and preferences; FCM/email jobs/templates/status | +| 15 Support Ticket System | 0% | Missing | None | Tickets, messages, SLA/escalation/help center | +| 16 AI Customer Support Chatbot | 0% | Missing | No OpenAI integration | Conversations, tools, safety, human escalation | +| 17 Product Recommendations | 0% | Missing | None | Events and recommendation service | +| 18 Admin Dashboard & Analytics | 1% | Foundation | Admin user type and raw activity endpoint | Metrics, aggregation, secured dashboard APIs | +| 19 File & Media Management | 25% | Broken foundation | Multer, Upload model, S3/presigned utilities | Restore/configure client, ownership, object validation/lifecycle, media transformations | +| 20 Audit Logging & System Configuration | 22% | Partial | Async activity records/log queue | Full audit schema/coverage, immutability, config models, secure structured logging | +| 21 Background Jobs & Queues | 35% | Partial | Redis, 3 queues/consumers, worker entry, document retry | Idempotency, policies for every queue, monitoring auth, graceful shutdown, scheduler topology | +| 22 Security | 15% | Weak foundation | bcrypt, JWT verification, HttpOnly cookie, basic MIME limits | Findings in §10; headers, throttles, validation, authorization, secrets/token discipline | +| 23 Testing & Quality Assurance | 2% | Missing | Jest dependency/script only | Tests, Supertest, fixtures, lint/type/static checks, CI | +| 24 API Documentation | 18% | Partial | Handwritten endpoint Markdown/HTML | OpenAPI/Swagger, synchronization, schemas/security/error contracts | +| 25 Deployment & Infrastructure | 18% | Partial | Dockerfile | Node 22, Compose, Nginx, healthcheck, non-root, migrations, CI/CD, observability | + +## 7. Original 15-Day Plan Status + +| Day | Intended Scope | Completion | Notes | +|---|---|---:|---| +| 1 | Foundation | 55% | Express/Sequelize/MySQL/Redis/BullMQ/Docker present; health broken; Swagger/Compose/migrations/production lifecycle missing | +| 2 | Authentication | 38% | Basic verified registration and OTP access JWT; core session/OAuth/security requirements incomplete | +| 3 | Customer + business accounts | 18% | Basic user/profile and enum only; no addresses/business domain | +| 4 | Products/categories/variants | 0% | Missing | +| 5 | Inventory/admin products | 0% | Missing | +| 6 | Cart/wishlist | 0% | Missing | +| 7 | Promotions/checkout | 0% | Missing | +| 8 | Orders | 0% | Missing | +| 9 | Payments | 0% | Missing | +| 10 | Delivery/rider | 2% | Rider enum and unrelated document templates only | +| 11 | Loyalty | 0% | Missing | +| 12 | Notifications/support | 16% | Partial in-app notification foundation; support absent | +| 13 | AI/recommendations | 0% | Missing | +| 14 | Analytics/security | 8% | Raw activities and scattered security controls only | +| 15 | QA/production | 5% | Dockerfile only; no tests/CI/Nginx/production hardening | + +**Last genuinely complete day: none.** Development reached partway through Day 1 and Day 2, with selected infrastructure from Days 12, 14, and 15 implemented early. + +## 8. Demo Website Requirement Gaps + +| Feature | Present on Demo | Present Backend | Original Plan | Action Needed | +|---|---|---|---|---| +| Email/password login | Yes | Partial (password then email OTP) | Auth | Clarify desired login flow; secure OTP/session lifecycle | +| Remember me | Yes | No | Auth | Add session-specific lifetime safely | +| Forgot/reset password | Yes | Partial | Auth | Stop token logging, validate password, revoke sessions | +| Google sign-in | Yes | No | Auth | Add provider verification/linking | +| Apple sign-in | Yes | No | Potential added requirement | Add to auth scope explicitly | +| Account overview/recent orders/counts | Yes | No | Customer/orders | Aggregate dashboard endpoint after domain models | +| Points/vouchers/membership/progress | Yes | No | Loyalty | Ledger, tier/rule/reward architecture | +| Default address/profile/addresses | Yes | Profile partial; addresses absent | Customer | Ownership-safe profile and address CRUD/default constraint | +| Wishlist/order history/sign out | Yes | Sign-out cookie only; rest absent | Cart/orders/auth | Implement modules and true session revocation | +| Silver/Gold/Platinum tiers/benefits | Yes | No | Loyalty | Configurable tiers; do not hardcode demo examples | +| Point transaction history | Yes | No | Loyalty | Immutable ledger | +| Purchases/reviews/referrals/birthdays earning | Yes | No | Loyalty/reviews | Generic earn-source rules with idempotency | +| Reward redemption/vouchers/shipping rewards | Yes | No | Loyalty/promotions | Reward definitions, redemption transaction, vouchers | +| Business approval/Partner ID/tier | Yes | Account enum only | Wholesale | Business profile and approval workflow | +| Monthly/history/discount/top buyers/orders | Yes | No | Wholesale/analytics | Wholesale aggregates and reporting | +| Credit limit/available/utilization | Yes | No | Wholesale | Credit account/ledger and authorization rules | +| Settlement terms/dates/invoices | Yes | No | Wholesale/payment | Terms, statements, invoice/payment lifecycle | +| Wholesale catalogue/MOQ/pricing tiers/bulk | Yes | No | Wholesale/catalogue | Customer-segment pricing and volume tiers | +| Featured inventory/reorder | Yes | No | Inventory/wholesale | Stock and reorder workflows | +| Shipping thresholds/methods/zones/fees | Yes | No | Checkout/delivery | Configurable rate engine | +| International shipping/duties display | Yes | No | Delivery/checkout | Destination rules and duty estimate representation | +| Order tracking | Yes | No | Orders/delivery | Shipment event timeline | +| 30-day return/eligibility/reason/status | Yes | No | Orders (gap detail) | Configurable returns/RMA state machine | +| Pickup/refund/exchange | Yes | No | Delivery/payment/orders | Integrate RMA, courier, payment refund, exchange order | +| Help center/FAQs/sizing/payment help | Yes | No | Support/content | CMS/help content APIs | +| Email support/tickets | Yes | No | Support | Ticket/conversation/SLA module | +| AI Style Assistant/human escalation | Yes | No | AI/support | AI conversation with ticket/advisor handoff | +| Newsletter consent lifecycle | Yes | No | Demo gap | Dedicated subscriber consent/status/source/language model; not profile notification preference | +| New/featured/sale products | Yes | No | Catalogue/promotions | Merchandising fields/rules | +| Category/editorial collections | Yes | No | Catalogue/content | Collections and ordered merchandising | +| Related products | Yes | No | Recommendations/catalogue | Explicit and computed relations | +| Reviews/verified purchase reviews | Yes | No | Catalogue/recommendations | Review moderation and verified-order link | +| Size guides | Yes | No | Catalogue/content | Structured, category/product-linked guides | +| Product SEO | Yes | No | Catalogue | Slugs/meta/canonical data | +| Banners | Yes | No | Promotions | Placement, locale, schedule, targeting | +| Multiple languages | Yes | No | Multi-language | Localized product/content model | + +Current order/delivery architecture cannot support shipping or returns: no commerce Order, OrderItem, Shipment, Address, Return, Refund, or state-transition entities exist. The similarly named generated documents are generic JSON documents and should not be treated as domain substitutes. + +## 9. Technical Debt + +### CRITICAL + +- Restore a valid S3 client before any upload/document endpoint can work. +- Align authorization vocabulary and enforce ownership; current legacy guards, IDORs, and accountType mutation enable denial of access or privilege escalation. +- Remove raw OTP/reset-token and decoded-auth logging; rotate any credentials if operational logs captured them. +- Replace production `sequelize.sync()` with migrations and gate server readiness on required services. +- Implement a real access/refresh session model with rotation, revocation, account-status enforcement, and secure logout. + +### HIGH + +- Mount and repair permission routes; add User-role linkage and grant uniqueness/cache invalidation. +- Add validation schemas and centralized error handling; prevent arbitrary field updates. +- Protect Bull Board and documentation sessions. +- Fix notification association alias and user ownership checks. +- Add rate limits for login, OTP, verification, reset, docs login, and general API traffic. +- Add tests for auth/authorization, transactions, uploads/jobs, and failure paths. +- Fix transaction leaks on early returns in user update/delete. + +### MEDIUM + +- Standardize response/error formats and status codes; stop returning internal error messages/stack traces. +- Consolidate Redis connections and add lifecycle/readiness handling. +- Make jobs idempotent and add retry/backoff/retention/dead-letter/alert policies. +- Move email to a job and add retry/delivery tracking and safe template escaping. +- Add pagination/indexes to activity, notification, document, and user queries. +- Remove legacy Oceanic naming and reconcile API versioning. + +### LOW + +- Correct mojibake in source/log messages, inconsistent singular/plural table names, and `*.utill.js` spelling. +- Remove unused imports/constants and dead/commented code. +- Split giant permission controller and move business logic into services after behavior is tested. + +## 10. Security Findings + +- No tracked `.env` was detected. `.env.sample` is tracked. Potential secret-bearing configuration exists in local `.env`; values were not inspected/reproduced. If this file has ever been shared or committed elsewhere, rotate credentials. +- JWT falls back to a public placeholder secret if configuration is missing. There is no issuer/audience/session ID/tokenVersion or refresh-token revocation. +- Login OTP uses `Math.random`, process memory, and no attempt/rate limit; it fails across instances/restarts and is logged in plaintext. +- Password reset token is logged in plaintext. Reset/change paths do not validate the new password policy or revoke existing access tokens. +- Login does not reject pending, suspended, or deactivated accounts. +- User update allows coarse-authorized callers to target arbitrary IDs and set `accountType`, a privilege-escalation and IDOR risk. Many profile/notification/document endpoints have the same ownership defect. +- Bull Board is public. Docs protection is an unsigned client cookie equal to `true`; credentials are brute-forceable without rate limiting. +- CORS is a single credentialed origin and cookie flags are reasonable for cross-site production, but CSRF protection/origin validation is absent for cookie-authenticated mutations. +- Multer limits size and declared MIME, but image wildcard acceptance lacks content sniffing, image decompression safeguards, antivirus scanning, extension normalization policy, and object lifecycle cleanup. +- S3 `PutObject` sets no ACL (good default if bucket blocks public access), but actual bucket policy/encryption cannot be verified. Signed URLs are cached; authorization is checked only before URL issuance and ownership is not checked. +- Controllers expose `error.message`; job status exposes stack traces. Production Sequelize logging is inverted to `true`, which can leak query data. +- Request validation is handwritten and sparse; mass assignment exists in user update. Sequelize query values are generally parameterized, so no direct raw-SQL injection was found. +- Foreign-key constraints are disabled for notification joins; missing uniqueness and transactions create races/duplicates in grants and notifications. +- No Helmet, API rate limiting, CSRF strategy, audit integrity, session revocation, or centralized security error policy exists. + +## 11. Broken / Suspicious Implementations + +- `app/config/s3.config.js`: the entire client/export is commented; every S3 caller receives `{}`. +- `app/routes/index.js`: imports `permissionRoutes` but never mounts it. +- `app/utils/documentJob.util.js`: requires nonexistent `../queues/pdf.queue`; currently appears orphaned. +- `app/services/permission.service.js#getEffectivePermissions`: queries `user.roleID`, which is not a User model attribute; role grants cannot reliably apply. +- `app/routes/{user,profile,document,notification}.routes.js`: guards use `management`, `team_head`, `user`, or `staff`, none of which is in the User ENUM. Valid `manager`, `customer`, `business_customer`, `rider`, `support_agent`, and `superadmin` are largely excluded. +- `user.controller#createNewUser`: calls `logActivity({user: req.user})` on a public route, causing a post-commit exception after the account has been created; client may receive 500 and retry. +- `user.controller#updateUser`: accepts accountType and undeclared role/department fields; does not update email despite destructuring it; opens transaction before lookups and does not roll back early 404 responses. +- `user.controller#deleteUser`: early 404 does not roll back; hard delete may conflict with Profile because cascade is unspecified. +- `profile.controller#getProfileAvatar/getProfileBackgroundImage`: assumes upload exists, uses wrong `profile.userId` response property, lacks ownership, and reaches broken S3. +- `upload.controller#getFileUrl`: empty catch block can leave requests hanging. +- `notification.controller#getUserNotifications`: requests association alias `notification`, but `belongsTo` defines no alias; likely Sequelize eager-loading error. +- `notification.controller`: USER notifications are created but never assigned to users through an endpoint/service. +- `app.js#/health`: asynchronous DB result races with response; reports `N/A`/hardcoded OK rather than real readiness. +- `app.js` bootstrap: server listens before DB boot finishes; DB errors are swallowed; each instance starts cron. +- `app/middleware/permission.middleware.js`: unused `hasPermission`; admin bypass only recognizes `admin`, not `superadmin`; wildcard logic differs between helper and actual check. +- `docsSession.middleware.js`: trusts an unsigned, client-set boolean cookie. +- `document.controller#getSavedDocuments`: `exclude` is not nested under `attributes`, so JSON data may still be fetched; filter is in POST body despite message saying query parameter. +- `document.controller#downloadDocument`: destructive read deletes the object after delivery and lacks job/user ownership. +- `app/logic/documents/registry.js`: catches module load failure but still registers undefined functions, deferring failure to runtime. +- `consoleLog.utill.js` and auth/reset utilities: log pipelines may persist secrets and full error objects. +- Production DB logging is enabled while non-production logging is disabled, likely inverted. + +Orphaned or unused-looking code includes `documentJob.util.js`, `notification.utill.js` (empty), `logic/documents/engine/pdf.engine.js` (generation uses `pdfGenerator.js`), several Excel/id/vendor/calendar/basis utilities not referenced by mounted features, `Assets` in upload controller (unregistered), imported `PERMISSIONS`/`checkPermission` in routes where checks are absent/commented, and unused dependencies likely including `pdfmake` and `nodeman`. `nodemon` is incorrectly a production dependency. Static analysis cannot prove every dynamic/template use; confirm before removal. + +## 12. Reusable Existing Components + +- Sequelize model registry/association convention can be extended after migrations replace runtime sync. +- User/Profile registration transaction, bcrypt utility, hashed one-use email verification token, and hashed password-reset-token concepts are sound foundations once error/logging/session issues are fixed. +- Cookie-or-Bearer authentication middleware structure is reusable after it loads current user/session/status and applies token claims. +- Permission, role, role-grant, and user-grant models/controllers/service are worth repairing rather than rebuilding; add role linkage, constraints, mounting, validation, and cache invalidation. +- Shared Redis factory/client and permission/user cache helpers can be consolidated and retained. +- Activity queue/service/worker is a useful async audit foundation; extend its schema and coverage. +- BullMQ worker entry pattern and document queue retry/backoff settings are reusable; standardize them across queues. +- Upload metadata model, Multer memory-storage limits, S3 key generation, and presigned URL caching are reusable after the S3 client and authorization/content validation are fixed. +- Document registry, PDF/Excel generators, templates, queue/worker, Document/DocumentType models, and atomic reference-number generator are substantive reusable subsystems. They are auxiliary business-document infrastructure, not order/payment replacements. +- Notification/UserNotification models, read-state concept, announcement query, and transactional cleanup cron can be repaired and extended for channel delivery. +- Email transport/template system and existing verification/reset/welcome templates can be moved behind an email queue. + +## 13. Recommended Next Development Phase + +Continue with a **Foundation, security, and authentication completion phase** before starting catalogue work. + +First make startup deterministic and production-safe: Node 22 alignment, validated environment configuration, migrations, real readiness/liveness checks, global 404/errors, Helmet/rate limits, protected operations dashboards, graceful shutdown, and a test harness. Then complete identity: Redis-backed cryptographic OTP with limits, account-status checks, access/refresh sessions with rotation/revocation, secure logout/reset, validation, ownership rules, and a repaired/mounted role-permission system. Repair S3 only as part of restoring already-promised profile/media/document behavior. + +After that baseline passes integration tests, finish customer/business profile and address primitives, reusing User/Profile, auth middleware, Redis, permission service, upload system, activity logger, email templates, queues, and reference-number utility. Only then begin catalogue/product models. + +## 14. Recommended Updated Roadmap + +1. **Phase 0 — Stabilize foundation:** Node 22, env validation, migrations, startup/readiness, global errors/security middleware, graceful shutdown, protected Bull Board, baseline Jest/Supertest and CI. +2. **Phase 1 — Complete identity and authorization:** OTP/session/refresh rotation, status checks, logout/revocation, password recovery hardening, OAuth Google/Apple, ownership rules, repaired roles/permissions. +3. **Phase 2 — Repair existing cross-cutting services:** S3/media, email jobs, notification aliases/assignment, queue reliability/idempotency, audit schema, document ownership and job lifecycle. +4. **Phase 3 — Customer and business foundations:** Profile completion, addresses/defaults, preferences/deactivation, business approval/partner identity/credit and settlement primitives. +5. **Phase 4 — Catalogue/content:** Categories, products, variants, media, localized content, SEO, size guides, collections, reviews. +6. **Phase 5 — Inventory and merchandising:** Warehouses/stock/reservations, wholesale pricing/MOQ/volume tiers, banners/promotions/coupons. +7. **Phase 6 — Shopping and checkout:** Cart, wishlist, pricing, shipping zones/rates/duties, checkout transactions. +8. **Phase 7 — Orders/payments:** Order state machine, PayHere/Stripe webhook idempotency, invoices, refunds, returns/exchanges. +9. **Phase 8 — Delivery/rider:** Assignments, tracking events, pickup/return logistics. +10. **Phase 9 — Loyalty and wholesale completion:** Generic earn ledger, tiers, rewards/vouchers/referrals; credit utilization/settlements/analytics. +11. **Phase 10 — Support/AI/recommendations:** Help content, tickets/SLA, advisor escalation, AI assistant, recommendation events/services. +12. **Phase 11 — Analytics and production QA:** Dashboards, security testing, load/integration/e2e tests, observability, Nginx/Compose/deployment/runbooks. + +## 15. Do Not Rebuild List + +Preserve and extend these concepts/files after adding tests: centralized Sequelize registration; User/Profile base tables; bcrypt helper; Redis connection/cache helpers; email verification/password-reset token hashing; auth middleware extraction of cookie/Bearer tokens; RBAC model/controller foundation; activity queue/service/worker; document registry/generators/templates/queue/worker; reference-number sequencing; Upload metadata/Multer limits/S3 utility interface; Notification/UserNotification read-state model; cleanup cron transaction; mail templates/transport interface; Docker Chromium setup for Puppeteer. + +## Verification and Dependency Audit + +- `node --check` passed for every repository JavaScript file. +- `npm test -- --runInBand` failed because Jest found **0 tests**. +- `npm ls --depth=0` completed without reporting missing installed top-level packages. +- `npm audit --omit=dev` reported **28 production dependency vulnerabilities**: 19 high, 8 moderate, 1 low, 0 critical. Dependency upgrades were intentionally not performed. +- Broken local import scan found active-looking `documentJob.util.js -> ../queues/pdf.queue`; the commented future `email.worker` reference is not an active defect. +- Targeted dependency observations: Supertest, Swagger/OpenAPI tooling, Helmet, rate limiting, FCM, payment SDKs, and OpenAI SDK are missing. `nodemon` should be dev-only; `nodeman` and `pdfmake` appear unused. Confirm with runtime coverage before removal.