> ## Documentation Index
> Fetch the complete documentation index at: https://docs.quinnsambal.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Assistant

<style>
  {`
    [class*="max-w-none"][class*="table"] {
      display: block !important;
      overflow-x: auto !important;
      max-width: 100% !important;
      width: 100% !important;
      flex-grow: 0 !important;
    }
    [class*="max-w-none"][class*="table"] > table {
      width: 100% !important;
      max-width: 100% !important;
      table-layout: fixed !important;
    }
    .mermaid {
      max-width: 100% !important;
      overflow-x: auto !important;
    }
    article svg[role="img"] {
      max-width: 100% !important;
      height: auto !important;
    }
    article img, .prose img {
      max-width: 100% !important;
      height: auto !important;
    }
    img[src*="LOGO"], img[src*="logo"] {
      max-width: 120px !important;
      max-height: 40px !important;
      width: auto !important;
      height: auto !important;
      object-fit: contain !important;
    }
    `}
</style>

***

title: "AI Assistant"
description: "Chat AI 3-panel dengan dual engine (Grounded + Fast + ReAct Agent), 25 tool registry, long-term memory, artifact preview, dan voice input."
---------------------------------------------------------------------------------------------------------------------------------------------------------

# AI Assistant

<img src="https://mintcdn.com/quinnofspicy/ny1xnfpEa_OBdv6T/docs/mintlify/screenshots/ai/ai-assistant-chat.png?fit=max&auto=format&n=ny1xnfpEa_OBdv6T&q=85&s=bce8848d46b9471499b4a0c939cde2cd" alt="AI Assistant" width="1920" height="1080" data-path="docs/mintlify/screenshots/ai/ai-assistant-chat.png" />

AI Assistant adalah pusat interaksi kecerdasan buatan SNISHOP ERP. Bukan sekadar chatbot — ini adalah antarmuka multi-engine yang mampu menjawab pertanyaan berbasis data real-time, menjalankan tool lintas modul, menghasilkan artifact (chart, tabel Excel, dokumen Word), dan mengingat preferensi user dalam jangka panjang.

## Arsitektur 3-Panel

```mermaid theme={null}
graph LR
    subgraph LEFT["Panel Kiri — 288px"]
        A1[Daftar Percakapan]
        A2[Search + Filter]
        A3[Pin/Unpin]
        A4[Export .txt]
        A5[Buat Percakapan Baru]
    end
    
    subgraph CENTER["Panel Tengah — Chat"]
        B1[Message Bubbles]
        B2[Model Selector]
        B3[File Upload 100MB]
        B4[Voice Input id-ID]
        B5[Suggested Prompts ×6]
        B6[Tool Links ×6]
    end
    
    subgraph RIGHT["Panel Kanan — 50% width"]
        C1[Artifact Preview]
        C2[Chart Render]
        C3[Excel Preview]
        C4[Word Preview]
        C5[Navigation Actions]
    end
    
    LEFT --> CENTER
    CENTER --> RIGHT
```

## Pipeline Chat — 3 Engine

AI Assistant menggunakan pipeline 3-tier yang dieksekusi secara berurutan:

```mermaid theme={null}
flowchart TD
    A[User Input] --> B{Deteksi Agent<br/>Creation?}
    B --> |Ya| C[create_ai_agent tool]
    B --> |Tidak| D{detectDataIntents}
    
    D --> |Data intent<br/>terdeteksi| E[groundedChat]
    D --> |Tidak ada| F[fastChat]
    
    E --> E1[runGroundedQueries<br/>— parallel]
    E1 --> E2[InvokeLLM +<br/>Structured Answer Schema]
    E2 --> E3[structuredToMarkdown]
    E3 --> G[Render Response]
    
    F --> F1[InvokeLLM<br/>+ 8 message history]
    F1 --> G
    
    C --> C1[Backend function<br/>createAIAgentFromChat]
    C1 --> G
    
    G --> H{Generative UI<br/>Code Blocks?}
    H --> |chart| I[Recharts: Bar/Line/Pie]
    H --> |excel| J[AIExcelExportPreview<br/>CSV + BOM]
    H --> |word| K[AIWordExportPreview<br/>HTML .doc]
    H --> |action_link| L[AICrossMenuNav<br/>Navigasi ERP]
    H --> |Tidak ada| M[ReactMarkdown]
```

### Engine 1: Grounded Chat (457 baris)

Menjawab pertanyaan berbasis data real-time dari database:

| Intent | Query |
| - | - |
| `sales_summary` | Total penjualan, rata-rata, trend |
| `top_products` | Produk terlaris dengan jumlah |
| `inventory_summary` | Ringkasan stok per lokasi |
| `finance_overview` | Income, expense, profit periode |
| `hpp_analysis` | Analisis HPP dan margin |
| `production_summary` | Ringkasan produksi |

**Mekanisme:**

1. `detectDataIntents(text)` — scan keyword, max 3 intent
2. `runGroundedQueries(intents, {companyId, period, locationId})` — parallel query
3. `loadCompanyFacts(companyId)` — fakta statis perusahaan
4. `answerFromFacts(question, facts)` — konteks tambahan
5. `InvokeLLM` dengan `STRUCTURED_ANSWER_SCHEMA`:
   * `ringkasan_eksekutif`, `angka_kunci`, `tabel`, `visualisasi`
   * `analisis`, `rekomendasi`, `navigasi`, `aksi_cepat`

### Engine 2: Fast Chat (156 baris)

Respons cepat untuk pertanyaan umum:

| Parameter | Nilai |
| - | - |
| Model default | `hermes-3-llama-3` |
| Model alternatif | `claude-3-5-sonnet`, `gpt-4o`, `gemini-1-5-pro` |
| Chat history | 8 pesan terakhir |
| Max content length | 2.000 karakter per pesan |
| Internet search | Force `gemini_3_flash` |

### Engine 3: Agent Engine — ReAct Loop (436 baris)

Agen otonom dengan kemampuan tool-calling:

```mermaid theme={null}
sequenceDiagram
    participant AE as Agent Engine
    participant LLM as InvokeLLM
    participant TE as Tool Executor
    participant TR as Tool Registry
    participant MEM as AIMemory

    AE->>AE: buildContext() + loadSOUL()
    AE->>AE: loadMemories(userId)
    
    loop Max 10 Iterasi
        AE->>LLM: JSON Schema: thought, action
        LLM-->>AE: Parse response
        
        alt action = tool_call
            AE->>TE: executeTool(tool_name, params)
            TE->>TR: Lookup tool
            TR-->>TE: Tool implementation
            TE-->>AE: {success, data}
            AE->>AE: onProgress('tool_result')
        else action = save_memory
            AE->>MEM: saveMemory(userId, data)
            MEM-->>AE: Saved
            AE->>AE: onProgress('memory_saved')
        else action = final_answer
            AE-->>AE: Return answer
        end
    end
    
    alt Max iterations reached
        AE->>AE: onProgress('max_iterations')
        AE-->>AE: Return partial answer
    end
```

**13 Prinsip Agent:**

1. Selalu berpikir sebelum bertindak
2. Gunakan tool yang tepat untuk tugas
3. Simpan preferensi user sebagai memori
4. Berikan jawaban final yang lengkap
5. Recovery dari error secara mandiri

## Komponen Utama

### ChatWindow (978 baris)

Komponen inti yang menangani seluruh alur percakapan:

| Fitur | Detail |
| - | - |
| Model Picker | Dropdown 4 model dengan indikator tier |
| File Upload | Max 100MB, upload via Cloudinary |
| Voice Input | SpeechRecognition `id-ID`, auto-send setelah 2 detik hening |
| Credit Tracking | 3/chat, 10/agent run — sync via BroadcastChannel |
| Progress Stream | ThinkingSteps: thinking → tool\_call → tool\_result → complete |

### MessageBubble (561 baris)

Render pesan dengan fitur generatif:

| Code Block | Render |
| - | - |
| ` ```chart ` | Recharts: BarChart, LineChart, PieChart |
| ` ```excel ` | AIExcelExportPreview — CSV UTF-8 BOM |
| ` ```word ` | AIWordExportPreview — HTML .doc |
| ` ```action_link ` | AICrossMenuNav — tombol navigasi ERP |

**Aksi per pesan:**

* Copy ke clipboard
* Simpan ke Notes
* Regenerate respons
* Edit & kirim ulang
* Thumbs up/down (feedback untuk adaptive learning)

### ArtifactPreviewPanel (265 baris)

Panel kanan bergaya Claude untuk preview artifact:

* Render chart interaktif
* Preview dokumen Excel/Word
* Tombol aksi navigasi

### SOUL Personality Engine (115 baris)

```mermaid theme={null}
graph TD
    A[User Settings] --> B[buildSoulPrompt]
    B --> C[agent_name: TODOIT]
    B --> D[communication_style]
    B --> E[proactive_level]
    B --> F[greeting_message]
    C --> G[System Prompt]
    D --> G
    E --> G
    F --> G
    G --> H[Agent Engine]
```

Default personality: empatik, proaktif, menggunakan emoji, berbahasa Indonesia.

## Suggested Prompts & Tool Links

### 6 Suggested Prompts

| Prompt | Fungsi |
| - | - |
| Analisis Penjualan | Ringkasan penjualan + trend |
| Buat Laporan | Generate laporan keuangan |
| Bantu Coding | Bantuan teknis development |
| Desain Konten | Generate konten marketing |
| Riset Pasar | Analisis pasar + kompetitor |
| Otomasi | Setup automasi bisnis |

### 6 Tool Links

Shortcut navigasi ke modul ERP langsung dari chat.

## Natural Language Commands

`assistantCommands.js` (128 baris) menangani perintah langsung:

| Perintah | Fungsi | RBAC |
| - | - | - |
| `jalankan agent` | Jalankan agen AI | Semua user |
| `riwayat AI` | Lihat riwayat agen | Semua user |
| `tambah stok` | Tambah stok produk | `ai_can_add_product` |
| `buat catatan` | Buat catatan baru | Semua user |
| `buat tugas` | Buat tugas baru | Semua user |
| `jadwalkan meeting` | Buat jadwal meeting | Owner/Admin |
| `buat BOM` | Buat Bill of Materials | Owner/Admin |
| `buat agent` | Buat agen AI baru | Owner/Admin |

Semua perintah dicatat di `AuditLog`.

## Export & Backup

### Export Percakapan

File `.txt` dengan format:

```
=== Percakapan: [Judul] ===
Tanggal: [DD/MM/YYYY]

[User]: Pesan user
[AI]: Respons AI

---
```

### Pencarian

Mencari di:

* Judul percakapan
* Isi pesan (user + AI)
* Grouping hasil berdasarkan tanggal

## Integrasi dengan Data Real-Time

AI Assistant terhubung langsung ke database melalui Base44:

| Data Source | Entity |
| - | - |
| Produk & Stok | `CompanyProduct`, `CompanyInventory` |
| Penjualan | `CompanyPOSTransaction` |
| Pelanggan | `Customer` |
| Keuangan | `FinancialRecord`, `GLJournalEntry` |
| Karyawan | `CompanyMember` |
| Kehadiran | `AttendanceRecord` |
| Manufaktur | `ProductionOrder` |

## Batasan

| Batasan | Detail |
| - | - |
| Tidak bisa transaksi langsung | Create/update/delete memerlukan konfirmasi |
| Tidak akses data sensitif | Password, token, API key tidak pernah diakses |
| Kuota bulanan | Terbatas sesuai plan (300-9.000) |
| File upload | Max 100MB per file |
| Chat history | 8 pesan terakhir dalam konteks |
| Memory | Max 50 item per user |

## Tips Penggunaan

* Gunakan bahasa natural — tidak perlu keyword khusus
* Bisa bertanya dalam Bahasa Indonesia atau English
* Sertakan konteks (tanggal, lokasi, produk) untuk jawaban lebih akurat
* Gunakan voice input untuk kecepatan — auto-send setelah 2 detik hening
* Manfaatkan artifact preview untuk melihat chart dan dokumen langsung
* Pin percakapan penting untuk akses cepat

***

**Related Documentation**:

* [AI Agents](/docs/ai/agents)
* [AI Agent Detail](/docs/ai/ai-agent-detail)
* [Agent Dashboard](/docs/ai/agent-dashboard)
* [AI Agent History](/docs/ai/ai-agent-history)
* [AI Overview](/docs/ai/overview)

***

## Entity Relationship Diagram

```mermaid theme={null}
erDiagram
    AIAgent {
        string agent_key PK "Kunci unik agent (slug)"
        string company_id FK "ID perusahaan pemilik"
        string created_by "Email pembuat agent"
        string name "Nama AI Agent"
        string tagline "Deskripsi singkat satu baris"
        string description "Penjelasan lengkap (max 2000)"
        enum category "business|content|writing|social|other"
        string icon "Icon lucide-react"
        string color "Warna hex default #4F46E5"
        string system_prompt "Instruksi LLM (max 4000)"
        array input_fields "Field input dinamis"
        string model "Model LLM default"
        boolean use_internet "Gunakan konteks internet"
        enum status "active|paused|inactive"
        string source_template_key FK "Template asal (nullable)"
        number run_count "Total eksekusi"
        number total_cost_amount "Total biaya Rupiah"
        number total_cost_credit "Total kredit terpakai"
        datetime created_date "Waktu dibuat"
        datetime updated_date "Waktu diperbarui"
    }

    AIAgentRun {
        string user_id "ID user eksekutor"
        string user_email "Email user"
        string company_id FK "ID perusahaan aktif"
        string company_name "Nama perusahaan saat run"
        string agent_key FK "Kunci agent"
        string agent_name "Nama agent saat run"
        string model_used "Model AI yang dipakai"
        string model_name "Nama tampilan model"
        object input_data "Input yang diberikan user"
        string output "Hasil AI (max 100000)"
        number cost_amount "Biaya Rupiah"
        number cost_credit "Kredit terpakai"
        enum payment_method "balance|credit|free"
        enum status "success|failed"
    }

    AIAgentModel {
        string model_key PK "Kunci model InvokeLLM"
        string name "Nama tampilan model"
        string description "Penjelasan kualitas (max 500)"
        number price_multiplier "Pengali biaya"
        enum tier "standard|advanced|premium"
        boolean supports_internet "Dukungan internet"
        boolean is_active "Status aktif"
        number order "Urutan tampil"
    }

    AIAgentSettings {
        string setting_key PK "Kunci pengaturan (global)"
        string description "Catatan pengaturan (max 1000)"
        number credit_to_rupiah_rate "Nilai 1 kredit dlm Rupiah"
        number base_price_per_run "Harga dasar per run"
        boolean allow_credit_payment "Izinkan bayar kredit"
        boolean allow_balance_payment "Izinkan bayar saldo"
    }

    AILearningData {
        string scope_key PK "Kunci scope pembelajaran"
        string user_id FK "ID user (scope personal)"
        string company_id FK "ID perusahaan (scope business)"
        object keyword_map "Peta keyword hasil pembelajaran"
        array corrections "Log koreksi user"
        number positive_count "Jumlah konfirmasi benar"
        number correction_count "Jumlah koreksi"
        datetime last_updated "Terakhir diperbarui"
    }

    AIAgentSchedule {
        string agent_id FK "Referensi agent_key"
        string company_id FK "ID perusahaan"
        enum trigger_type "Jenis trigger"
        object trigger_config "Konfigurasi trigger"
        boolean is_active "Status aktif"
        datetime last_triggered_at "Terakhir fired"
        number trigger_count "Total kali fired"
        enum notification_channel "Channel notifikasi"
        string created_by "Email pembuat"
        datetime created_date "Waktu dibuat"
    }

    AIAgent ||--o{ AIAgentRun : "agent_key"
    AIAgent ||--o{ AIAgentSchedule : "agent_id"
    AIAgentModel }o--|| AIAgentSettings : "pricing config"
    AIAgent }o--o| AIAgent : "source_template_key (self-ref)"
    AILearningData }o--|| AIAgent : "scope pembelajaran"
```

## Tabel Schema Lengkap

### AIAgent — Agen AI Assistant

Entitas agen AI yang digunakan oleh Assistant. Setiap agen memiliki scope per-company dan bisa dibuat dari chat langsung melalui perintah `buat agent` atau dari Agent Hub.

| Field | Tipe | Required | Default | Deskripsi |
| - | - | - | - | - |
| `agent_key` | string | **Ya** | — | Kunci unik agent (auto-generated slug dari nama) |
| `company_id` | string | **Ya** | — | ID perusahaan pemilik (scope company-level) |
| `created_by` | string | **Ya** | — | Email user yang membuat agent |
| `name` | string | **Ya** | — | Nama AI Agent |
| `system_prompt` | string | **Ya** | — | Instruksi sistem utama untuk LLM (max 4.000 karakter) |
| `tagline` | string | Tidak | — | Deskripsi singkat satu baris |
| `description` | string | Tidak | — | Penjelasan lengkap fungsi agent (max 2.000 karakter) |
| `category` | enum | Tidak | `other` | Kategori: `business`, `content`, `writing`, `social`, `other` |
| `icon` | string | Tidak | `Sparkles` | Nama icon lucide-react |
| `color` | string | Tidak | `#4F46E5` | Warna hex untuk tampilan card |
| `input_fields` | array\[object] | Tidak | — | Field input dinamis: `{key, label, type, placeholder, required}` |
| `model` | string | Tidak | `automatic` | Model LLM default |
| `use_internet` | boolean | Tidak | `false` | Gunakan konteks internet saat eksekusi |
| `status` | enum | Tidak | `active` | `active` = jalan otomatis, `paused` = tidak otomatis tapi bisa manual, `inactive` = nonaktif |
| `source_template_key` | string | Tidak | `null` | Link ke AIAgentTemplate asal jika dibuat dari template (nullable) |
| `run_count` | number | Tidak | `0` | Total eksekusi agent |
| `total_cost_amount` | number | Tidak | `0` | Total biaya Rupiah semua run |
| `total_cost_credit` | number | Tidak | `0` | Total kredit yang dipakai semua run |
| `created_date` | datetime | Tidak | — | Waktu agent dibuat |
| `updated_date` | datetime | Tidak | — | Waktu agent terakhir diperbarui |

### AIAgentRun — Riwayat Eksekusi Chat & Agent

Setiap kali Assistant menjalankan agen atau chat diproses melalui pipeline, satu record `AIAgentRun` dibuat untuk audit trail dan billing.

| Field | Tipe | Required | Default | Deskripsi |
| - | - | - | - | - |
| `user_id` | string | **Ya** | — | ID user yang menjalankan |
| `agent_key` | string | **Ya** | — | Kunci agen yang dijalankan |
| `user_email` | string | Tidak | — | Email user eksekutor |
| `company_id` | string | Tidak | — | ID perusahaan aktif (null untuk personal) |
| `company_name` | string | Tidak | — | Nama perusahaan saat agent dijalankan |
| `agent_name` | string | Tidak | — | Nama agen saat run (snapshot) |
| `model_used` | string | Tidak | — | Model AI yang dipakai pada run ini |
| `model_name` | string | Tidak | — | Nama tampilan model |
| `input_data` | object | Tidak | — | Input yang diberikan user |
| `output` | string | Tidak | — | Hasil dari AI Agent (max 100.000 karakter) |
| `cost_amount` | number | Tidak | `0` | Biaya Rupiah yang dipotong |
| `cost_credit` | number | Tidak | `0` | Kredit yang dipotong |
| `payment_method` | enum | Tidak | `balance` | Metode bayar: `balance`, `credit`, `free` |
| `status` | enum | Tidak | `success` | Status eksekusi: `success`, `failed` |

### AIAgentModel — Katalog Model LLM Assistant

Daftar model AI yang tersedia untuk dipilih user di Model Picker pada ChatWindow. Setiap model memiliki multiplier harga dan tier kualitas.

| Field | Tipe | Required | Default | Deskripsi |
| - | - | - | - | - |
| `model_key` | string | **Ya** | — | Kunci model untuk InvokeLLM (contoh: `automatic`, `gpt_5_mini`, `claude_sonnet_4_6`) |
| `name` | string | **Ya** | — | Nama tampilan model (contoh: `Standar (Cepat & Hemat)`) |
| `description` | string | Tidak | — | Penjelasan singkat kualitas/kecepatan (max 500 karakter) |
| `price_multiplier` | number | Tidak | `1` | Pengali biaya — biaya akhir = harga dasar × multiplier |
| `tier` | enum | Tidak | `standard` | Tingkatan kualitas: `standard`, `advanced`, `premium` |
| `supports_internet` | boolean | Tidak | `false` | Model mendukung konteks internet |
| `is_active` | boolean | Tidak | `true` | Status aktif model |
| `order` | number | Tidak | `0` | Urutan tampil di dropdown Model Picker |

### AIAgentSettings — Pengaturan Global Billing Assistant

Konfigurasi global untuk sistem billing dan pembayaran AI. Hanya ada satu record dengan `setting_key = 'global'`. Mengatur konversi kredit dan metode pembayaran yang diizinkan.

| Field | Tipe | Required | Default | Deskripsi |
| - | - | - | - | - |
| `setting_key` | string | **Ya** | `global` | Kunci pengaturan (selalu `global` untuk pengaturan utama) |
| `description` | string | Tidak | — | Catatan pengaturan (max 1.000 karakter) |
| `credit_to_rupiah_rate` | number | Tidak | `10` | Nilai 1 kredit dalam Rupiah (1 kredit = Rp10) |
| `base_price_per_run` | number | Tidak | `1000` | Harga dasar default per run (Rupiah) bila agent tidak set harga sendiri |
| `allow_credit_payment` | boolean | Tidak | `true` | Izinkan user membayar dengan kredit |
| `allow_balance_payment` | boolean | Tidak | `true` | Izinkan user membayar dengan saldo Rupiah |

### AILearningData — Data Pembelajaran Adaptif

Entitas yang menyimpan hasil pembelajaran AI dari feedback user (thumbs up/down) dan koreksi. Digunakan oleh Agent Engine untuk meningkatkan akurasi respons seiring waktu. Scope bisa personal (per user) atau business (per perusahaan).

| Field | Tipe | Required | Default | Deskripsi |
| - | - | - | - | - |
| `scope_key` | string | **Ya** | — | Kunci scope: `ai_learn_personal_<userId>` atau `ai_learn_business_<companyId>` |
| `user_id` | string | Tidak | — | ID user pemilik scope (untuk scope personal) |
| `company_id` | string | Tidak | — | ID perusahaan (untuk scope business) |
| `keyword_map` | object | Tidak | — | Peta keyword → `{category, confidence, type}` hasil pembelajaran |
| `corrections` | array\[object] | Tidak | — | Log koreksi user: `{input_text, original_category, correct_category, type, timestamp, record_id}` |
| `positive_count` | number | Tidak | `0` | Jumlah konfirmasi "benar" dari user |
| `correction_count` | number | Tidak | `0` | Jumlah koreksi dari user |
| `last_updated` | datetime | Tidak | — | Terakhir diperbarui |

### AIAgentSchedule — Jadwal & Trigger Otomatis

Konfigurasi eksekusi otomatis agen berdasarkan jadwal (cron) atau event bisnis. Agent yang dijadwalkan akan dijalankan oleh `runDueAgentSchedules` dan hasilnya dikirim melalui channel notifikasi yang dikonfigurasi.

| Field | Tipe | Required | Default | Deskripsi |
| - | - | - | - | - |
| `agent_id` | string | **Ya** | — | Referensi ke AIAgent (agent\_key) |
| `company_id` | string | **Ya** | — | ID perusahaan |
| `trigger_type` | enum | **Ya** | — | Jenis trigger: `schedule_daily`, `schedule_weekly`, `schedule_monthly`, `event_low_stock`, `event_invoice_overdue`, `event_new_transaction`, `event_task_due`, `event_custom` |
| `created_by` | string | **Ya** | — | Email user yang membuat schedule |
| `trigger_config` | object | Tidak | — | Konfigurasi trigger — Schedule: `{hour, minute, day_of_week?, day_of_month?}` / Event: `{threshold?, product_category?, days_before?}` |
| `is_active` | boolean | Tidak | `true` | Apakah schedule/trigger aktif |
| `last_triggered_at` | datetime | Tidak | — | Waktu terakhir trigger fired |
| `trigger_count` | number | Tidak | `0` | Berapa kali trigger sudah fired |
| `notification_channel` | enum | Tidak | `in_app` | Channel notifikasi: `in_app`, `whatsapp`, `email`, `all` |
| `created_date` | datetime | Tidak | — | Waktu schedule dibuat |

## State Machine — Assistant Conversation Lifecycle

````mermaid theme={null}
stateDiagram-v2
    [*] --> idle: Assistant siap menerima input

    idle --> detecting: User mengirim pesan
    detecting --> grounded: detectDataIntents menemukan intent data
    detecting --> fast: Tidak ada data intent terdeteksi
    detecting --> agent_creation: Perintah "buat agent" terdeteksi

    grounded --> querying: runGroundedQueries (parallel)
    querying --> llm_processing: InvokeLLM + Structured Answer Schema
    llm_processing --> rendering: structuredToMarkdown

    fast --> llm_fast: InvokeLLM + 8 message history
    llm_fast --> rendering

    agent_creation --> backend_create: createAIAgentFromChat
    backend_create --> rendering

    rendering --> artifact_check: Deteksi code block generatif

    artifact_check --> render_chart: ```chart ditemukan
    artifact_check --> render_excel: ```excel ditemukan
    artifact_check --> render_word: ```word ditemukan
    artifact_check --> render_action: ```action_link ditemukan
    artifact_check --> render_markdown: Tidak ada code block generatif

    render_chart --> feedback: User melihat respons
    render_excel --> feedback
    render_word --> feedback
    render_action --> feedback
    render_markdown --> feedback

    feedback --> idle: User mengirim pesan baru
    feedback --> idle: User memberi thumbs up/down
    feedback --> learning: Feedback disimpan ke AILearningData
    learning --> idle

    note right of grounded
        Engine grounded mengambil data real-time
        dari database perusahaan
    end note

    note right of fast
        Engine fast menggunakan 8 pesan
        terakhir sebagai konteks
    end note

    note right of agent_creation
        Membuat agen AI baru langsung
        dari percakapan chat
    end note
````

## Sequence Diagram — Assistant Interaction

### Interaksi Chat Grounded (Data Real-Time)

```mermaid theme={null}
sequenceDiagram
    participant User as User
    participant CW as ChatWindow
    participant PI as Pipeline Chat
    participant DI as detectDataIntents
    participant RQ as runGroundedQueries
    participant DB as Database
    participant LLM as InvokeLLM
    participant MB as MessageBubble

    User->>CW: Ketik pertanyaan (misal: "ringkasan penjualan bulan ini")
    CW->>PI: Kirim pesan ke pipeline
    PI->>DI: detectDataIntents(text)
    DI->>DI: Scan keyword: "penjualan", "bulan ini"
    DI-->>PI: [sales_summary]

    PI->>RQ: runGroundedQueries([sales_summary], {companyId, period})
    RQ->>DB: Query CompanyPOSTransaction
    DB-->>RQ: Data transaksi
    RQ->>DB: Query loadCompanyFacts(companyId)
    DB-->>RQ: Fakta perusahaan
    RQ-->>PI: Grounded data

    PI->>LLM: InvokeLLM + STRUCTURED_ANSWER_SCHEMA
    Note over LLM: ringkasan_eksekutif, angka_kunci,<br/>tabel, visualisasi, analisis,<br/>rekomendasi, navigasi, aksi_cepat
    LLM-->>PI: Structured response

    PI->>MB: structuredToMarkdown + Render
    MB-->>User: Tampilkan respons dengan chart/tabel
```

### Tool Calling — Agent Engine ReAct Loop

```mermaid theme={null}
sequenceDiagram
    participant User as User
    participant CW as ChatWindow
    participant AE as Agent Engine
    participant LLM as InvokeLLM
    participant TE as Tool Executor
    participant TR as Tool Registry (25 tools)
    participant MEM as AIMemory
    participant DB as Database

    User->>CW: "Analisis stok produk yang hampir habis"
    CW->>AE: buildContext() + loadSOUL()
    AE->>MEM: loadMemories(userId)
    MEM-->>AE: Preferensi user

    loop Max 10 Iterasi ReAct
        AE->>LLM: JSON Schema: {thought, action}
        LLM-->>AE: {thought: "Perlu cek stok", action: "get_inventory"}

        AE->>TE: executeTool("get_inventory", {threshold: "low"})
        TE->>TR: Lookup tool "get_inventory"
        TR-->>TE: Tool implementation
        TE->>DB: Query CompanyInventory
        DB-->>TE: Data stok
        TE-->>AE: {success: true, data: [...]}
        AE->>AE: onProgress('tool_result')

        AE->>LLM: JSON Schema: {thought, action}
        LLM-->>AE: {thought: "Cukup data", action: "final_answer"}
    end

    AE-->>CW: Final answer + artifact
    CW->>MEM: saveMemory(userId, preferensi)
    CW-->>User: Tampilkan hasil analisis
```

### Adaptive Learning dari Feedback User

```mermaid theme={null}
sequenceDiagram
    participant User as User
    participant MB as MessageBubble
    participant AL as AILearningData
    participant AE as Agent Engine

    User->>MB: Klik thumbs up (respons benar)
    MB->>AL: Update positive_count += 1
    AL->>AL: Perkuat keyword_map confidence

    User->>MB: Klik thumbs down (respons salah)
    MB->>AL: Prompt koreksi kategori
    User->>MB: Pilih kategori yang benar
    MB->>AL: Push corrections[] + correction_count += 1
    AL->>AL: Update keyword_map dengan koreksi

    Note over AE,AL: Pada percakapan berikutnya,<br/>Agent Engine memuat learning data<br/>untuk meningkatkan akurasi
```

## Enum Tables

### agent\_category — Kategori Agen AI

| Nilai Enum | Label | Deskripsi |
| - | - | - |
| `business` | Bisnis | Analisis bisnis, laporan keuangan, KPI, strategi |
| `content` | Konten | Generate konten produk, deskripsi, katalog |
| `writing` | Penulisan | Copywriting, editing, proofreading, blog |
| `social` | Media Sosial | Konten sosial media, hashtag, caption |
| `other` | Lainnya | Kegunaan umum, custom purpose |

### agent\_status — Status Agen AI

| Nilai Enum | Label | Deskripsi |
| - | - | - |
| `active` | Aktif | Agent berjalan otomatis dan bisa dijalankan manual |
| `paused` | Dijeda | Tidak berjalan otomatis (scheduled off), tapi masih bisa dijalankan manual |
| `inactive` | Nonaktif | Agent nonaktif sepenuhnya, tidak bisa dijalankan |

### model\_tier — Tingkatan Model LLM

| Nilai Enum | Label | Multiplier | Best For |
| - | - | - | - |
| `standard` | Standar | ×1.0 | Tugas sederhana, jawaban cepat, chat ringan |
| `advanced` | Lanjutan | ×1.5 | Analisis, rekomendasi, konten panjang |
| `premium` | Premium | ×3.0 | Complex reasoning, multi-step task, internet search |

### payment\_method — Metode Pembayaran Run

| Nilai Enum | Deskripsi |
| - | - |
| `balance` | Dibayar dari saldo Rupiah perusahaan |
| `credit` | Dibayar dari kredit AI |
| `free` | Gratis (tidak ada biaya) |

### trigger\_type — Jenis Trigger Schedule

| Nilai Enum | Kategori | Deskripsi |
| - | - | - |
| `schedule_daily` | Jadwal | Setiap hari pada waktu yang ditentukan |
| `schedule_weekly` | Jadwal | Setiap minggu pada hari dan waktu tertentu |
| `schedule_monthly` | Jadwal | Setiap bulan pada tanggal dan waktu tertentu |
| `event_low_stock` | Event | Dipicu saat stok produk di bawah threshold |
| `event_invoice_overdue` | Event | Dipicu saat invoice melewati jatuh tempo |
| `event_new_transaction` | Event | Dipicu saat ada transaksi baru masuk |
| `event_task_due` | Event | Dipicu saat tugas mendekati deadline |
| `event_custom` | Event | Trigger kustom yang dikonfigurasi user |

### notification\_channel — Channel Notifikasi

| Nilai Enum | Deskripsi |
| - | - |
| `in_app` | Notifikasi dalam aplikasi |
| `whatsapp` | Kirim via WhatsApp |
| `email` | Kirim via email |
| `all` | Semua channel aktif |

### data\_intent — Intent Data untuk Grounded Chat

| Nilai Intent | Deskripsi | Query Target |
| - | - | - |
| `sales_summary` | Ringkasan penjualan | Total penjualan, rata-rata, trend |
| `top_products` | Produk terlaris | Produk dengan jumlah penjualan tertinggi |
| `inventory_summary` | Ringkasan stok | Stok per lokasi gudang |
| `finance_overview` | Ringkasan keuangan | Income, expense, profit periode |
| `hpp_analysis` | Analisis HPP | Harga pokok penjualan dan margin |
| `production_summary` | Ringkasan produksi | Output produksi dan status |

### learning\_scope — Scope Pembelajaran AI

| Pola Scope Key | Deskripsi |
| - | - |
| `ai_learn_personal_<userId>` | Pembelajaran personal per user — menyimpan preferensi dan koreksi individual |
| `ai_learn_business_<companyId>` | Pembelajaran bisnis per perusahaan — menyimpan pola dan koreksi kolektif |

## RBAC — Hak Akses AI Assistant

| Role | Chat dengan AI | Pilih Model | Jalankan Agent | Buat Agent dari Chat | Lihat Riwayat Chat | Kelola Schedule | Kelola Settings & Model |
| - | - | - | - | - | - | - | - |
| **Super Admin** | Ya | Ya | Ya | Ya | Ya (semua company) | Ya | Ya |
| **Admin Perusahaan** | Ya | Ya | Ya | Ya | Ya (per company) | Ya | Tidak |
| **Manajer** | Ya | Ya | Ya | Ya | Ya (per company) | Ya | Tidak |
| **Staff** | Ya | Ya | Ya | Tidak | Ya (milik sendiri) | Tidak | Tidak |
| **Viewer** | Ya | Ya (read-only) | Tidak | Tidak | Ya (milik sendiri) | Tidak | Tidak |

### Hak Akses Perintah Natural Language

| Perintah | Super Admin | Admin | Manajer | Staff | Viewer |
| - | - | - | - | - | - |
| `jalankan agent` | Ya | Ya | Ya | Ya | Tidak |
| `riwayat AI` | Ya | Ya | Ya | Ya | Ya |
| `tambah stok` | Ya | Ya | Ya | Ya (`ai_can_add_product`) | Tidak |
| `buat catatan` | Ya | Ya | Ya | Ya | Tidak |
| `buat tugas` | Ya | Ya | Ya | Ya | Tidak |
| `jadwalkan meeting` | Ya | Ya | Ya | Tidak | Tidak |
| `buat BOM` | Ya | Ya | Tidak | Tidak | Tidak |
| `buat agent` | Ya | Ya | Tidak | Tidak | Tidak |

### RLS Policy Ringkasan

| Entitas | Create | Read | Update | Delete |
| - | - | - | - | - |
| `AIAgent` | Admin, Manajer | Member company | Admin, Manajer (owner) | Admin (owner) |
| `AIAgentRun` | System (auto) | Member (milik sendiri + admin) | — | — |
| `AIAgentModel` | Admin sistem | Publik (semua role) | Admin sistem | Admin sistem |
| `AIAgentSettings` | Admin sistem | Admin | Admin sistem | — |
| `AILearningData` | System (auto) | Member (milik sendiri + admin) | System (auto) | — |
| `AIAgentSchedule` | Admin, Manajer | Member company | Admin, Manajer | Admin |


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.