# Maria — punte WhatsApp + RAG (LXC 171), acum serviciu în git Sursa: `romfastsql/proxmox/lxc171-claude-agent/maria-whatsapp-bridge/` (repo `ROMFASTSQL`, commit „Add Maria WhatsApp+RAG bridge as a service (LXC 171)"). A pornit ca prototip nefinalizat în `/tmp/maria-bridge/` (fără git, fără serviciu systemd — vezi istoricul acestei conversații). A fost mutat integral în git, ca proiect sibling lui `discord-bridge/`, cu servicii `systemctl --user` proprii și dashboard de control. Nu trebuie confundat cu: - **Maria pe Flowise** (`vfp_roaauto/COMUN/utile/chatbot/`) — chatbot web, memorie Buffer Window (`k=5`) în Flowise. - **Echo / `echo-whatsapp-bridge.service`** (LXC 110 moltbot) — bridge WhatsApp Baileys separat, al lui Echo Core (Claude Opus 4.5). - **Punte Discord -> Claude Code** (`discord-bridge/`, același container) — alt scop (comandă Claude Code de pe Discord), vezi [`discord-bridge-context.md`](discord-bridge-context.md). ## Arhitectură ``` WhatsApp (self-chat implicit) -> whatsapp/index.js (Baileys, port 8099) -> rag/consumer.py (polling, RAG STATELESS — fara chat_history) -> rag/store.py (depozit .txt/.md in ~/.maria-bridge/documents/) -> rag/indexer.py (chunking + embeddings Ollama -> rag_index.json) -> rag/sync.py (rclone pull din Google Drive + reindexare conditionata) dashboard/api.py (stdlib, port 18792) — control total din browser ``` ## Servicii `systemctl --user` (pe LXC 171, sub `~/.config/systemd/user/`) | Unitate | Rol | |---|---| | `maria-whatsapp.service` | Puntea Baileys (Node), port 8099 | | `maria-rag.service` | Consumer RAG (Python venv), răspunde la mesaje | | `maria-sync.service` + `maria-sync.timer` | Sincronizare Drive + reindexare, la 10 min | Instalare: `ops/install.sh` (idempotent, mirror al `discord-bridge/ops/install.sh` — creează `~/.maria-bridge/`, venv, `npm install`, symlink-uri unit, `systemctl --user enable`). Bridge-ul **nu pornește automat** — cere scanarea unui cod QR (pas manual, o singură dată); vezi `README.md` din proiect. ## Control — dashboard COMUN cu puntea Discord (nu unul separat) **Decizie ulterioară** (la cererea explicită a utilizatorului): Maria NU are dashboard propriu. Controlul se face din **dashboard-ul punții Discord** (`discord-bridge/dashboard/`, `https://claude-agent.tailf7372d.ts.net/claude`), secțiunea „Maria — WhatsApp + RAG", adăugată direct în `dashboard/api.py` și `index.html` ale acelui proiect. Rutele Maria (`/api/maria/*`) rulează în ACELAȘI proces Python ca puntea Discord, dar comunică cu Maria doar prin subprocess (`systemctl`, scripturi din `rag/`) și HTTP către bridge — fără import de module Python din `maria-whatsapp-bridge`, ca să nu coliseze cu `discord-bridge/config.py` (ambele s-ar numi `config`). Ce oferă secțiunea Maria din acel panou: - start/stop/restart pentru `maria-whatsapp` și `maria-rag` (unități fixe, aceeași protecție ca la Discord — niciun nume de unit nu vine din request) - stare conexiune WhatsApp + cod QR de asociere (când nu e conectat) - listă documente din depozit, adăugare/ștergere text, reindexare manuală - buton „sincronizează din Drive acum" (`rag/sync.py`, apelat și de timer) - loguri (tail) pentru `whatsapp.log`/`rag.log` Autentificare: aceeași sesiune/cookie ca restul dashboard-ului Discord (`DASHBOARD_TOKEN` din `~/.claude-discord/env`) — un singur login pentru ambele punți. ## Depozit de documente + Google Drive Documentele (`.txt`/`.md`) stau în `~/.maria-bridge/documents/` pe container. Se pot administra manual din dashboard, sau sincroniza automat cu dosarul Google Drive de pe Windows (`D:\GoogleDrive\romfast\document_store`) prin **rclone cu un cont de serviciu Google** (nu OAuth interactiv — containerul e headless). Pași de configurare completi în README-ul proiectului (`maria-whatsapp-bridge/README.md`, secțiunea „Sincronizare cu Google Drive"). `DRIVE_REMOTE` gol în env = sincronizare dezactivată, doar upload manual. ## Context conversațional — neschimbat față de prototip `rag/consumer.py` tot NU ține memorie între mesaje — fiecare întrebare e o interogare RAG independentă (system prompt + top-K chunk-uri din index + întrebare). Nu există nimic de "golit"; comparativ: - Maria/Flowise: fereastră fixă de 5 schimburi; - Discord bridge: context nelimitat (autocompact), golit doar cu `/new`; - Maria WhatsApp+RAG: zero memorie, fiecare mesaj e independent. ## Embeddings — Ollama local pe LXC 171 Inițial `OLLAMA_URL=http://127.0.0.1:11434` din `env` era un placeholder nefuncțional (niciun Ollama instalat nicăieri, nici local nici pe alt LXC — verificat explicit, nu există server Ollama documentat în infrastructură). **Rezolvat 2026-08-31**: instalat Ollama direct pe acest container (`curl -fsSL https://ollama.com/install.sh | sh`, plus `zstd` ca dependință), pornit ca `ollama.service` (systemd la nivel de sistem, nu `--user`), și tras modelul `nomic-embed-text` (`ollama pull nomic-embed-text`, ~274 MB, rulează CPU-only, fără GPU pe container). Cu asta `rag/indexer.py` și `rag/consumer.py` au un backend de embeddings funcțional local, fără nicio dependință externă de rețea. ## Sincronizare Google Drive — status real `rclone` a fost instalat pe container (`apt-get install rclone`), dar `DRIVE_REMOTE` rămâne **negol configurat**: pasul care lipsește e crearea unui cont de serviciu Google (GCP Console → IAM → Service Accounts) și partajarea folderului `document_store` cu adresa lui de email — acțiuni care cer acces la consola Google Cloud a utilizatorului, deci nu pot fi automatizate din container. Vezi README, secțiunea „Sincronizare cu Google Drive", pentru pașii exacți rămași. **Testare imediată a indexării** (fără să aștepte configurarea rclone): s-au adus manual 6 documente reale din folderul Drive `document_store` (`romfast_info.md`, `erori_generale_knowledge.md`, `bilant_knowledge.md`, `import_knowledge.md`, `roafacturare_manual.md`, `spv_semnatura_knowledge.md`) folosind uneltele MCP Google Drive disponibile agentului (cont `mmarius28@gmail.com`, folder id `1C4e75zgH1_7ZK-_oBP5ZZBvUPh3iEo1O`), scrise direct în `~/.maria-bridge/documents/` și indexate cu `rag/indexer.py` — **25 de chunk-uri, index de ~400 KB, reconstruit cu succes** folosind Ollama-ul local de mai sus. Asta confirmă că pipeline-ul store → indexer → embeddings funcționează capăt-la-capăt; rămâne doar conectarea automată la Drive prin `rclone` (pasul manual al utilizatorului, de mai sus). ## Stare la momentul scrierii (actualizat 2026-08-31) `maria-whatsapp`, `maria-rag` și `maria-sync.timer` sunt `active (running)`/ `enabled`. Dashboard-ul propriu (`maria-dashboard.service`) a fost **oprit, dezactivat și eliminat din cod** — controlul e acum consolidat în dashboard-ul punții Discord (secțiunea „Maria — WhatsApp + RAG", verificată funcțională prin `curl` direct pe `/api/maria/status`). Bridge-ul a generat cod QR și așteaptă scanarea din telefon (`connected: false` până atunci). Rămâne de făcut manual: - **scanarea codului QR** din dashboard (cardul „Conectare WhatsApp") — pas fizic, nu poate fi automatizat; - **contul de serviciu Google + `DRIVE_REMOTE`** — vezi secțiunea de mai sus; fără el, sincronizarea automată din Drive rămâne inactivă (dar upload-ul manual de documente + reindexare funcționează deja, testat); - **file picker în dashboard** — cerut explicit de utilizator: secțiunea „Adaugă document" din panoul Maria permite azi doar scrierea manuală de text într-un textarea; de înlocuit/completat cu un input de tip fișier care acceptă selecția mai multor fișiere deodată (upload multipart, nu JSON), pentru administrare mai rapidă a depozitului. **Neimplementat încă.** Bug reparat în timpul instalării inițiale (înainte de consolidare): `install.sh` lega unitatea dashboard-ului propriu la o cale greșită — devenit irelevant odată cu eliminarea acelui dashboard.