ERP Chatbot Dashboard
**IRIS** — *Intec Responsive Information System* — is INTEC Engineering's internal software family. It is a manufacturing ERP (`intec-erp-v2`) that owns the database and all business logic, paired with a natural-language chatbot backend (`intec-erp-chatbot`, internally called "IRIS") that reads the same database and answers questions in English or Bahasa Malaysia using a hybrid regex + local LLM (Ollama `qwen3:30b`) intent engine. Three near-identical client apps — web, Android mobile, and Windows desktop — talk to the chatbot over HTTP so shop-floor and office workers can query work orders, inventory, invoices, BOMs, production, and more conversationally. The ERP is the senior project and the sole schema owner; the chatbot and its clients depend on it, never the other way around.
Audience: a developer who just joined the team and needs to understand the whole family in 10 minutes. This page synthesizes the per-project .cursor/guide/ docs; for any fact beyond what is here, trust those guides — they are the authoritative source this overview synthesizes.
Key invariants: the ERP is the sole schema owner (never migrate from the chatbot); the chatbot never duplicates ERP business logic — it reuses the same Eloquent models via the symlink; the chatbot inherits ERP's model boot logic, global scopes, and observers; the ERP does not call the chatbot — if the chatbot is down, the ERP keeps running.
| From | To | Mechanism | Detail |
|---|---|---|---|
| Web / Mobile / Desktop | Chatbot API | HTTP POST/GET | All three clients call POST /api/v1/chatbot/chat (and /conversation, /config, /health, /version/check, /improve/*) at http://chatbot.inteceng.com.my:8001 (local dev http://localhost:8001). Each client sends client: 'web' | 'mobile' | 'desktop' in the body for query-log filtering. |
| Chatbot API | ERP | Shared MySQL + symlinked models (NOT HTTP) | intec-erp-chatbot/app/Models is a symlink to intec-erp-v2/app/Models. Both projects point .env at the same intec_erp database. The chatbot is read-only for business data and writes only to chatbot_query_logs. Never run migrations from the chatbot. |
| Chatbot API | Ollama | HTTP (local) | OllamaService calls http://localhost:11434 for intent detection fallback and general answers. Model qwen3:30b. |
| ERP | Mobile APK | HTTP download + QR | MobileTerminalReleaseController renders a QR code encoding the APK download URL; operators scan it to install/upgrade. The APK also lives in the chatbot public/downloads/ and is enforced by VersionController. |
| All clients | ERP /api/login | Login flow | Clients POST credentials to {chatbot-host}/api/login (host root, with /api/v1/chatbot stripped). The chatbot's AuthController validates against the shared users table and returns a Sanctum bearer token. Gap: no client currently sends the token on subsequent chat calls, and chatbot routes don't enforce auth. |
| Client identity | Query log | client field in chat body | One of web, mobile, desktop. Written to ChatbotQueryLog so logs can be filtered per client. Treat as required for production clients. |
| UAC context | Chatbot | uac object in chat body (optional) | { user_id, staff_id, department, role }. Used by the self-improvement prompt and LLM classification; not currently enforced as a hard authorization layer on handlers. |
| APK distribution | Chatbot public/downloads/ | Filename convention | Filename convention erp-ai-chatbot-v{VERSION}.apk. VersionController::LATEST_APK names the current APK; MIN_VERSIONS enforces the floor. Bump both together on release. |
| CORS for Tauri | config/cors.php (chatbot) | Allowed origins | The web origin (http://localhost:3001 + production) and the Tauri origin (tauri://localhost or http://tauri.localhost) must be in allowed_origins, with allowed_paths covering /api/*. Without the Tauri origin, desktop chat requests are silently blocked by WebView CORS. (The Rust http_get/http_post bridge bypasses CORS in Tauri mode, but the browser fallback path still needs it.) |
| Collaborative-query + polling | Chatbot /improve/* | POST + poll | POST /improve/collaborative-query returns a task_id when building is needed; clients poll GET /improve/status/{taskId} until COMPLETE. Currently blocked: improve.php references ChatbotImproveController, which does not exist — the REST surface 500s. The self-improvement loop itself works (triggered directly from ChatbotService::processQuery()), but clients cannot poll a taskId. |
| If you want to change... | Edit project | File(s) to touch |
|---|---|---|
| Add or change a chatbot intent | intec-erp-chatbot | config/chatbot_intents.php (LLM catalog), config/intent_patterns.php (regex), app/Services/ChatbotServices/Core/IntentDetectionService.php (isErpDataQuery()), then the matching DataHandlers/* + Formatters/*. See INTENT_SYSTEM_GUIDE.md. |
| Change ERP business logic / a model | intec-erp-v2 | app/Models/, app/Repositories/, app/Services/. Prefer the repository or a service over the controller. The chatbot sees model changes instantly via the symlink. |
| Change ERP schema (migration) | intec-erp-v2 | database/migrations/ + app/Models/. Run php artisan migrate here only. |
| Add a column to chatbot_query_logs | intec-erp-v2 | Migration here (ERP owns the schema); the chatbot writes through the symlinked ChatbotQueryLog model. |
| Change the chatbot API endpoints | intec-erp-chatbot | routes/api/chatbot/*.php (canonical; do not edit the dead routes/api/chatbotAPI.php) + app/Http/Controllers/Api/Chatbot/. |
| Change the LLM / Ollama integration | intec-erp-chatbot | app/Services/OllamaService.php, app/Services/LlmIntentDetectionService.php, config/chatbot.php (ollama, intent_detection). |
| Change the chat UI (web) | erp-ai-chatbot-web | src/components/Chatbot.js, ChatMessage.js, ChatInput.js, Sidebar.js. |
| Change the chat UI (mobile) | erp-ai-chatbot-mobile | src/screens/ChatScreen.js, src/components/ChatMessage.js. |
| Change the chat UI (desktop) | erp-ai-chatbot-desktop | src/components/* (survives) — but fix the build first (see below). |
| Fix the desktop build | erp-ai-chatbot-desktop | Follow BUILD_REGRESSION_AND_RECOVERY_GUIDE.md: restore src-tauri/{Cargo.toml,build.rs,src/main.rs,tauri.conf.json} + ForceUpdate.js/.css + updateService.js + package.json from c0f2e6b, then apply Phase 4 fixes (http_delete, /version/check path, PLATFORM=desktop, backend windows min version). |
| Add a mobile feature | erp-ai-chatbot-mobile | src/screens/, src/components/, then bump version in package.json + app.json + src/config/version.js, build APK, copy to intec-erp-chatbot/public/downloads/, bump VersionController::LATEST_APK. See BUILD_DEPLOYMENT_GUIDE.md. |
| Change auth (login/token) | All clients + chatbot | Clients: src/services/chatbotService.js (add Authorization: Bearer interceptor). Chatbot: enforce auth on /api/v1/chatbot/* and derive uac from the session. See CLIENT_INTEGRATION_GUIDE.md §8. |
| Change shop-floor terminals | intec-erp-v2 | routes/api/terminals/* + app/Http/Controllers/Api/ terminal controllers. See TERMINAL_API_GUIDE.md. |
| Change e-invoice / MyInvois | intec-erp-v2 | app/Services/ e-invoice services + Klsheng\Myinvois. See EINVOICE_SYSTEM_DOCUMENTATION.md. |
| Change CORS (for Tauri or web) | intec-erp-chatbot | config/cors.php (allowed_origins, allowed_paths). |
| Change the mobile minimum version / force-update | intec-erp-chatbot | app/Http/Controllers/Api/Chatbot/VersionController.php (MIN_VERSIONS, LATEST_APK). |
| Priority | Issue | One-line detail | Read for full detail |
|---|---|---|---|
| P1 | Desktop build restoration | erp-ai-chatbot-desktop is not buildable from source (commit 4f81934 deleted the Tauri infra). Restore from c0f2e6b + apply 3 latent-bug fixes + port collaborative-query flow. | erp-ai-chatbot-desktop/.cursor/guide/BUILD_REGRESSION_AND_RECOVERY_GUIDE.md |
| P2 | Cross-client parity | All three clients fail to send the auth token; web has no version check; desktop has no force update; UAC key mismatch on web. | intec-erp-chatbot/.cursor/guide/CLIENT_INTEGRATION_GUIDE.md §8; erp-ai-chatbot-web/.cursor/guide/WEB_CLIENT_SYSTEM_DOCUMENTATION.md |
| P3 | Chatbot backend cleanup | Orphaned progress_query intent; duplicate keys in chatbot_intents.php (9) and intent_patterns.php (2); dead chatbotAPI.php router; missing ChatbotImproveController; new_feature_* stubs out of sync; DeliveryOrder model drift risk. | intec-erp-chatbot/.cursor/guide/CHATBOT_SYSTEM_DOCUMENTATION.md §8; INTENT_SYSTEM_GUIDE.md §5; ERP_INTEGRATION_GUIDE.md §5 |
| P4 | DeliveryOrder decision | Confirm whether DeliveryOrder exists in intec-erp-v2/app/Models and whether the chatbot delivery domain should keep depending on it (ERP models DOs as Invoice + DeliveryEvidence by design). | intec-erp-v2/.cursor/guide/DOMAIN_MODEL_GUIDE.md §9; intec-erp-chatbot/.cursor/guide/ERP_INTEGRATION_GUIDE.md §5.2 |
| P5 | Docs & cleanup | ~50 root-level test_*.php scripts in ERP; stale CODEBASE_STUDY.md; TEMPORARY test_bom_wo.php route; .bak files; align chatbot README's 'Laravel 10.x' claim with composer.json (^8.75). | intec-erp-v2/.cursor/guide/CHATBOT_EXTRACTION_STATUS.md §5; intec-erp-chatbot/.cursor/guide/ERP_INTEGRATION_GUIDE.md §6 |
Cross-cutting note: the auth-token-not-sent gap (P2) is the single most impactful security item — any future change that enforces auth on /api/v1/chatbot/* will break all three clients at once. Fix the clients first (send the token), then enforce on the backend.