Backup automatico script del 2026-08-23 12:04

This commit is contained in:
daniele committed 2026-08-23 12:04:16 +02:00
1 parent 11823447a2
commit 795a15a7b6
66 files changed
+8546

No files matched your search

@@ -0,0 +1,91 @@
# Integrazione app homelab — P5/P6/P7
Tool live e RAG su **Loogle Casa**, **Home Assistant**, **Irrigazione** e **Turni**.
---
## P5 — Casa + Home Assistant
| Tool | Scope | Sorgente |
|------|-------|----------|
| `get_home_dashboard` | home:read | Loogle Casa |
| `get_home_weather` | home:read | Loogle Casa |
| `get_network_overview` | home:read | Loogle Casa |
| `get_network_failover_status` | home:read | Loogle Casa |
| `get_ha_entity` | home:read | Home Assistant |
| `list_ha_entities` | home:read | Home Assistant |
| `search_ha_entities` | home:read | Home Assistant |
### Variabili `.env`
```bash
LOOGLE_CASA_URL=https://casa.loogle.it
LOOGLE_CASA_API_URL=http://192.168.128.81:5602 # opzionale, LAN
LOOGLE_CASA_PASSWORD_DANIELE=... # daniele MCP → admin Casa
HA_URL=https://ha.loogle.it
HA_API_URL=http://192.168.128.81:8123
HA_TOKEN=<long-lived token HA>
```
**Mapping utenti MCP → app:**
- `daniele` → Casa `admin`, Irrigazione `admin`, Turni `daniely`
---
## P6 — Irrigazione + Turni
| Tool | Scope | Sorgente |
|------|-------|----------|
| `get_irrigation_status` | irrigation:read | irri.loogle.it |
| `get_irrigation_zones` | irrigation:read | irri.loogle.it |
| `get_irrigation_history` | irrigation:read | irri.loogle.it |
| `get_turni_status` | — (pubblico) | turni.loogle.it |
| `get_my_shifts` | turni:read | turni.loogle.it |
| `list_turni_doctors` | turni:read | turni.loogle.it |
```bash
IRRIGAZIONE_URL=https://irri.loogle.it
IRRIGAZIONE_API_URL=http://192.168.128.81:5601
IRRIGAZIONE_PASSWORD_DANIELE=...
TURNI_URL=https://turni.loogle.it
TURNI_PASSWORD_DANIELE=... # utente Turni: daniely
# oppure TURNI_JWT_DANIELE=...
```
---
## P7 — RAG storico app
Il worker `loogle-mcp-indexer` indicizza periodicamente:
- snapshot stato/zone Irrigazione
- storico irrigazioni ed eventi
- lavori manutenzione giardino
- turni e anagrafica medici Turni
| Collection Qdrant | Contenuto |
|-------------------|-----------|
| `apps_shared_family` | Irrigazione + Turni (famiglia) |
| Tool | Scope | Funzione |
|------|-------|----------|
| `search_apps_knowledge` | knowledge:read | RAG solo app |
| `search_knowledge` | knowledge:read | Include anche app |
| `list_apps_indexed` | knowledge:read | Stato indicizzazione |
| `reindex_apps` | admin | Forza sync |
```bash
APPS_INDEX_ENABLED=yes
APPS_INDEX_USER=daniele
```
---
## Test
```bash
docker exec loogle-mcp python3 /srv/scripts/test_p5_home.py
docker exec loogle-mcp python3 /srv/scripts/test_p6_apps.py
docker exec loogle-mcp python3 /srv/scripts/test_p7_apps_rag.py
```
+297
View File
@@ -0,0 +1,297 @@
# Loogle MCP Hub — Architettura e parametri
Documento di riferimento per la piattaforma MCP domestica LOOGLE.IT.
Ultimo aggiornamento: 2026-08-22
---
## Scopo
**Loogle MCP Hub** espone agli assistenti AI (Claude, ChatGPT, Gemini, Cursor) due capacità principali:
1. **Archivio contesto** — memoria persistente per progetti e task, isolata per utente
2. **Knowledge base RAG** — ricerca semantica su documenti Paperless e sui contesti salvati
Tutti i dati restano in LAN/NAS; laccesso esterno avviene solo via HTTPS + OAuth.
---
## Architettura logica
```
┌─────────────────────────────────────────────────────────────┐
│ Client AI (ChatGPT / Claude / Gemini / Cursor) │
└───────────────────────────┬─────────────────────────────────┘
│ HTTPS + OAuth Bearer
┌─────────────────────────────────────────────────────────────┐
│ NPM VIP 192.168.128.85 → mcp.loogle.it:443 │
└───────────────────────────┬─────────────────────────────────┘
┌─────────────────────────────────────────────────────────────┐
│ Pi-1 :8700 loogle-mcp (FastAPI) │
│ ├── /mcp JSON-RPC MCP │
│ ├── /oauth/* OAuth 2.1 PKCE │
│ └── /dashboard UI famiglia │
│ Pi-1 :8700 loogle-mcp-indexer (worker Paperless→vector) │
└───────┬─────────────────────────────┬───────────────────────┘
│ │
▼ ▼
┌───────────────┐ ┌─────────────────────┐
│ SQLite │ │ Vector store │
│ /data/*.db │ │ Qdrant DS920 :6333 │
│ utenti OAuth │ │ o fallback SQLite │
└───────────────┘ └─────────────────────┘
┌─────────────────────────────────────────────────────────────┐
│ NFS /mnt/ha-apps/mcp/context/{utente}/projects/... │
└─────────────────────────────────────────────────────────────┘
┌─────────────────────────────────────────────────────────────┐
│ Paperless docs.loogle.it (sorgente documenti + OCR) │
└─────────────────────────────────────────────────────────────┘
```
---
## Componenti e percorsi
| Componente | Host | Porta | Percorso / container |
|------------|------|-------|----------------------|
| MCP Gateway | Pi-1 | 8700 | `loogle-mcp` |
| Indexer | Pi-1 | — | `loogle-mcp-indexer` |
| Qdrant (primario) | DS920 | 6333 | opzionale, compose extrema |
| Vector fallback | Pi-1 | — | `/data/vector_fallback.db` |
| Context NFS | NAS | — | `/mnt/ha-apps/mcp/context/` |
| DB SQLite | Pi-1 | — | `/home/daniely/docker/loogle-mcp/data/loogle_mcp.db` |
| Compose locale | Pi-1 | — | `/home/daniely/docker/loogle-mcp/` |
| Compose failover | Pi-1/Pi-2 | — | `/home/daniely/rete/compose/failover/loogle-mcp-compose.yml` |
| Runbook | — | — | `/home/daniely/rete/ha/RUNBOOK-mcp.md` |
---
## URL e endpoint
| Servizio | URL |
|----------|-----|
| MCP (client AI) | `https://mcp.loogle.it/mcp` |
| Dashboard web | `https://mcp.loogle.it/dashboard` |
| Health | `https://mcp.loogle.it/health` |
| OAuth authorize | `https://mcp.loogle.it/oauth/authorize` |
| OAuth token | `https://mcp.loogle.it/oauth/token` |
| Metadata OAuth | `https://mcp.loogle.it/.well-known/oauth-authorization-server` |
| Metadata risorsa MCP | `https://mcp.loogle.it/.well-known/oauth-protected-resource` |
---
## DNS
| Record | Tipo | Valore | Dove configurato |
|--------|------|--------|------------------|
| `mcp.loogle.it` | A | `192.168.128.85` (VIP NPM) | Pi-hole `/etc/pihole/pihole.toml` → hosts |
| Risoluzione LAN | — | Pi-hole → Unbound → split-horizon | Come `docs.loogle.it`, `pass.loogle.it` |
**Script setup:** `/home/daniely/rete/scripts/setup-mcp-dns-npm.sh`
**Verifica:**
```bash
dig +short mcp.loogle.it @127.0.0.1 # → 192.168.128.85
curl -sf https://mcp.loogle.it/health
```
---
## NPM (reverse proxy)
| Parametro | Valore |
|-----------|--------|
| Proxy host ID | 30 |
| Dominio | `mcp.loogle.it` |
| Upstream normale | `192.168.128.80:8700` |
| Certificato TLS | `npm-65` (Let's Encrypt) |
| Failover route | `rete/ha/npm-routes.conf` riga `30\|mcp.loogle.it\|8700\|...` |
| Websocket | ON |
| Force SSL | ON |
**Failover:** `npm-failover-route.sh` aggiorna upstream su Pi-2 / DS920 in base allo scenario HA.
---
## Variabili d'ambiente (`.env`)
File: `/home/daniely/docker/loogle-mcp/.env`
| Variabile | Descrizione | Esempio |
|-----------|-------------|---------|
| `MCP_BASE_URL` | URL pubblico (issuer JWT) | `https://mcp.loogle.it` |
| `MCP_JWT_SECRET` | Segreto firma token OAuth | *(stringa lunga casuale)* |
| `MCP_OAUTH_CLIENT_ID` | Client OAuth pre-registrato | `loogle-mcp-public` |
| `PAPERLESS_URL` | API documenti | `https://docs.loogle.it` |
| `PAPERLESS_API_TOKEN` | Token API admin (fallback) | vedi [PAPERLESS-TOKEN.md](PAPERLESS-TOKEN.md) |
| `PAPERLESS_API_TOKEN_{USER}` | Token API per utente | `DANIELE`, `LUCIA`, `DAVIDE`, `LUCA` |
| `QDRANT_URL` | Vector DB remoto | `http://192.168.128.100:6333` |
| `OLLAMA_URL` | Embedding locale | `http://192.168.128.100:11434` |
| `OLLAMA_EMBED_MODEL` | Modello embedding | `nomic-embed-text` |
| `OPENAI_API_KEY` | Fallback embedding cloud | *(opzionale)* |
| `INDEXER_INTERVAL_MINUTES` | Intervallo sync Paperless | `30` |
| `THERMAL_TEMP_HARD_C` | Pausa embedding se CPU DS920 ≥ °C | `70` |
| `THERMAL_TEMP_SOFT_C` | Rallenta embedding sopra °C | `58` |
| `THERMAL_CPU_TARGET_PCT` | Cap load1 (nproc × %) | `40` |
| `OLLAMA_NUM_THREAD` | Thread CPU per richiesta embed | `1` |
| `OLLAMA_EMBED_DELAY_S` | Pausa tra embed (duty-cycle lento) | `10` |
| `DS920_THERMAL_URL` | Probe temp/load DS920 | `http://192.168.128.100:9191/thermal` |
---
## Utenti e isolamento
| Persona | Username | Ruolo | Password iniziale |
|---------|----------|-------|-------------------|
| Daniele | `daniele` | admin | `daniele` *(cambiarla)* |
| Lucia | `lucia` | user | `lucia` |
| Davide | `davide` | user | `davide` |
| Luca | `luca` | user | `luca` |
- Ogni utente vede **solo** i propri progetti in `/mnt/ha-apps/mcp/context/{username}/`
- I token OAuth JWT contengono `sub` = username; ogni tool filtra per utente
- Ladmin può `reindex_document`, vedere audit completo, revocare refresh token
**Scope OAuth:** `context:read`, `context:write`, `knowledge:read`, `knowledge:write`, `gitea:read`, `gitea:write`, `home:read`, `irrigation:read`, `turni:read`, `admin` (solo daniele)
---
## Tool MCP esposti
| Tool | Scope minimo | Funzione |
|------|--------------|----------|
| `ping` | — | Test connettività |
| `whoami` | — | Utente e scope attivi |
| `list_projects` | context:read | Elenco progetti |
| `create_project` | context:write | Nuovo progetto |
| `get_project_context` | context:read | Legge memoria progetto |
| `save_context` | context:write | Salva/appende memoria |
| `archive_project` | context:write | Archivia progetto |
| `search_context` | context:read | Ricerca semantica contesti |
| `search_knowledge` | knowledge:read | RAG Paperless + contesti + Gitea + app |
| `search_gitea_knowledge` | knowledge:read | RAG solo Gitea |
| `search_apps_knowledge` | knowledge:read | RAG Irrigazione + Turni |
| `list_apps_indexed` | knowledge:read | Stato indicizzazione app |
| `reindex_apps` | admin | Re-sync RAG app |
| `get_document` | knowledge:read | Testo documento Paperless |
| `list_recent_documents` | knowledge:read | Ultimi doc indicizzati |
| `reindex_document` | admin | Re-indicizza documento |
| `get_home_dashboard` | home:read | Dashboard Loogle Casa |
| `get_home_weather` | home:read | Meteo casa |
| `get_network_overview` | home:read | Panoramica rete LAN |
| `get_network_failover_status` | home:read | Stato failover cluster |
| `get_ha_entity` | home:read | Entità Home Assistant |
| `list_ha_entities` | home:read | Elenco entità HA |
| `search_ha_entities` | home:read | Cerca entità HA |
| `get_irrigation_status` | irrigation:read | Stato irrigazione |
| `get_irrigation_zones` | irrigation:read | Zone irrigazione |
| `get_irrigation_history` | irrigation:read | Storico irrigazioni |
| `get_turni_status` | — | Stato servizio Turni |
| `get_my_shifts` | turni:read | Turni utente corrente |
| `list_turni_doctors` | turni:read | Medici Turni-Live |
Vedi anche tool Gitea in `docs/GITEA-TOKEN.md` e app homelab in `docs/APPS-INTEGRATION.md`.
---
## Storage contesto (per progetto)
```
/mnt/ha-apps/mcp/context/{username}/projects/{project-id}/
meta.json # titolo, tag, date, stato, gitea_repo (opz.)
context.md # memoria persistente
sessions/ # snapshot conversazioni
artifacts/ # file generati dagli agenti
```
---
## Vector store / RAG
| Collection Qdrant | Contenuto |
|-------------------|-----------|
| `kb_shared_family` | Documenti famiglia (tag non personali) |
| `kb_personal_{user}` | Documenti personali |
| `ctx_{user}` | Embedding dei contesti agente |
| `gitea_shared_family` | File testo da repo Gitea non privati |
| `gitea_personal_{user}` | File testo da repo Gitea privati dell'owner |
| `apps_shared_family` | Export Irrigazione + Turni (P7) |
**Nota Pi 5:** Qdrant locale su ARM (page size 16K) non è supportato. Default: Qdrant su DS920 o fallback SQLite in `/data/vector_fallback.db`.
**Pipeline indexer:** ogni 30 min:
1. Paperless → chunk → embedding (Ollama DS920) → upsert `kb_*`
2. Gitea (repo configurati in `GITEA_INDEX_REPOS_*`) → file `.md`/`.py`/`.sh` → chunk → upsert `gitea_*`
3. Irrigazione + Turni → snapshot/storico → upsert `apps_shared_family` (vedi `docs/APPS-INTEGRATION.md`)
---
## Sicurezza
- TLS terminato su NPM (Let's Encrypt)
- OAuth 2.1 Authorization Code + PKCE
- JWT access token 1h + refresh token 30 giorni (revocabili)
- Audit log: `{timestamp, user, tool, resource_id}` in SQLite
- CrowdSec attivo su NPM
- Nessun accesso cross-user ai dati
---
## Operazioni comuni
```bash
# Stato servizi
cd /home/daniely/docker/loogle-mcp && docker compose ps
# Log
docker logs -f loogle-mcp
docker logs -f loogle-mcp-indexer
# Redeploy
./scripts/deploy.sh
# DNS + NPM (se reinstall)
sudo /home/daniely/rete/scripts/setup-mcp-dns-npm.sh
# Failover route
/home/daniely/rete/scripts/npm-failover-route.sh normal
# Backup dati MCP
/home/daniely/rete/infra-monitor/mcp-restic-backup.sh
```
---
## Failover (tier-b)
| Scenario | Comportamento |
|----------|---------------|
| Pi-1 down, Pi-2 up | Stack MCP su Pi-2, NPM upstream → `.81:8700` |
| Extrema DS920 | NPM3 + upstream DS920 |
| Monitoraggio | Probe `mcp_ok` in `failover-status.sh` |
---
## Da completare (post-install)
1. **`PAPERLESS_API_TOKEN_*`** in `.env` — vedi [PAPERLESS-TOKEN.md](PAPERLESS-TOKEN.md)
2. **Ollama su DS920** con `nomic-embed-text` per embedding locali
3. **Qdrant su DS920** (opzionale): `rete/compose/extrema-ds920/loogle-mcp-compose.yml`
4. **Cambio password** per tutti gli utenti dal dashboard
5. **`MCP_JWT_SECRET`** — impostare valore robusto in produzione
---
## Riferimenti
- [Guida utenti famiglia](docs/GUIDA-UTENTI.md)
- [Onboarding tecnico client AI](docs/ONBOARDING.md)
- [Runbook operativo](/home/daniely/rete/ha/RUNBOOK-mcp.md)
- [README progetto](README.md)
+209
View File
@@ -0,0 +1,209 @@
# Token Gitea per Loogle MCP
## Cosa usare: Personal Access Token (PAT)
Gitea espone l'API REST su `https://git.loogle.it/api/v1/` con header:
```
Authorization: token <token>
```
Ogni utente Gitea ha i propri repository e permessi. L'hub MCP usa un token **per utente famiglia**, come Paperless.
---
## Dove generarlo
Per ogni utente che deve usare i tool Gitea da Claude/Cursor (daniele, lucia, …):
1. Accedi a https://git.loogle.it con quell'account
2. **Impostazioni****Applicazioni****Genera nuovo token**
3. Nome suggerito: `loogle-mcp`
4. Scope minimi:
- `read:repository` — list_repos, get_file, search_code, list_issues, get_issue, RAG
- `write:repository`**P4:** create_or_update_file
- `write:user`**P4:** create_gitea_repo (`POST /user/repos`)
- `write:issue` — create_issue
- `read:user` — consigliato per `/user/repos`
5. Copia il token (mostrato una sola volta) in `.env`
### Alternativa CLI (admin, sul nodo con Gitea attivo)
```bash
docker exec -u git gitea gitea admin user generate-access-token \
--username daniele \
--token-name loogle-mcp \
--scopes 'read:repository,write:repository,write:issue,write:user,read:user'
```
---
## Configurazione in Loogle MCP
Modifica `/home/daniely/docker/loogle-mcp/.env`:
```env
GITEA_URL=https://git.loogle.it
GITEA_API_TOKEN_DANIELE=
GITEA_API_TOKEN_LUCIA=
GITEA_API_TOKEN_DAVIDE=
GITEA_API_TOKEN_LUCA=
```
| Utente MCP | Variabile `.env` | Account Gitea |
|------------|------------------|---------------|
| Daniele | `GITEA_API_TOKEN_DANIELE` | daniele |
| Lucia | `GITEA_API_TOKEN_LUCIA` | lucia |
| Davide | `GITEA_API_TOKEN_DAVIDE` | davide |
| Luca | `GITEA_API_TOKEN_LUCA` | luca |
### URL API interno (opzionale)
Se `https://git.loogle.it` non è raggiungibile dal container MCP (rete LAN, failover), imposta un URL diretto:
```env
GITEA_API_URL=http://192.168.128.81:3002
```
I link nei risultati restano su `GITEA_URL` pubblico.
### Fallback admin
```env
GITEA_API_TOKEN=<token-admin>
```
Tutti gli utenti MCP useranno lo stesso token (sconsigliato salvo test).
---
## Tool MCP Gitea
| Tool | Scope | Descrizione |
|------|-------|-------------|
| `list_repos` | gitea:read | Repository accessibili |
| `get_file` | gitea:read | Legge file o elenca directory |
| `search_code` | gitea:read | Cerca nel codice (API `/search/code` o fallback tree) |
| `list_issues` | gitea:read | Issue aperte/chiuse |
| `get_issue` | gitea:read | Dettaglio issue |
| `create_issue` | gitea:write | Crea issue |
| `create_gitea_repo` | gitea:write | Crea repo sotto l'utente MCP corrente |
| `create_or_update_file` | gitea:write | Commit singolo di un file (create/update via Contents API) |
Dopo modifica `.env`:
```bash
cd /home/daniely/docker/loogle-mcp && docker compose up -d --build
```
---
## Verifica
```bash
/home/daniely/docker/loogle-mcp/scripts/test_gitea_integration.py
```
Oppure da MCP (con token OAuth): tool `list_repos` e `get_file` su `daniele/rete`.
---
## Collegamento progetto ↔ repository (P2)
Ogni progetto MCP può referenziare un repo Gitea in `meta.json`:
```json
"gitea_repo": "daniele/rete"
```
### Tool
| Tool | Azione |
|------|--------|
| `create_project` | Parametri opzionali `gitea_repo`, `seed_from_gitea` |
| `link_project_repo` | Collega, cambia repo o scollega (`gitea_repo` vuoto) |
| `get_project_context` | Aggiunge blocco `gitea` con README, `docs/` e issue aperte |
### Seed README
Con `seed_from_gitea: true` il README del repo viene importato in `context.md` (una sola volta, marker `<!-- seed:gitea ... -->`).
### Verifica P2
```bash
/home/daniely/docker/loogle-mcp/scripts/test_project_gitea_p2.py
```
---
## RAG su repository Gitea (P3)
Il worker `loogle-mcp-indexer` indicizza periodicamente file testo dai repo Gitea (`.md`, `.py`, `.sh`, …) in collection Qdrant dedicate:
| Collection | Contenuto |
|------------|-----------|
| `gitea_shared_family` | Repo non privati |
| `gitea_personal_{user}` | Repo privati dell'owner |
### Config `.env`
```env
GITEA_INDEX_ENABLED=yes
GITEA_INDEX_REPOS_DANIELE=daniele/rete,daniele/loogle-scripts
GITEA_INDEX_MAX_FILES_PER_REPO=150
GITEA_INDEX_MAX_FILE_BYTES=120000
```
Se `GITEA_INDEX_REPOS_{USER}` è vuoto → tutti i repo accessibili via API.
### Tool MCP
| Tool | Descrizione |
|------|-------------|
| `search_gitea_knowledge` | Ricerca semantica solo su Gitea |
| `search_knowledge` | Include Paperless + contesti + Gitea |
| `list_gitea_indexed_files` | Stato indicizzazione |
| `reindex_gitea_repo` | Forza re-index di un repo |
### Verifica P3
```bash
docker exec loogle-mcp python3 /srv/scripts/test_gitea_rag_p3.py
```
---
## Scrittura su Gitea (P4)
L'AI può creare repository e committare singoli file via API Gitea (senza git push locale).
| Tool | Scope | Azione |
|------|-------|--------|
| `create_gitea_repo` | gitea:write | Crea repo sotto l'utente MCP autenticato |
| `create_or_update_file` | gitea:write | Crea o aggiorna un file (Contents API + commit) |
Regole:
- Scrittura consentita solo su repo di cui l'utente è **owner** (salvo admin MCP).
- Dopo scrittura, opzionalmente re-indicizza il file nel RAG (`reindex: true` default).
- Token Gitea: `write:user` (create repo) + `write:repository` (file).
### Workspace davide e luca
| Utente | Repo Gitea | Progetto MCP |
|--------|------------|--------------|
| davide | `davide/progetti` | Progetti Davide |
| luca | `luca/progetti` | Progetti Luca |
Setup iniziale:
```bash
docker exec loogle-mcp python3 /srv/scripts/setup_gitea_p4_repos.py
```
### Verifica P4
```bash
docker exec loogle-mcp python3 /srv/scripts/test_gitea_p4.py
```
+190
View File
@@ -0,0 +1,190 @@
# Guida amministratore — Daniele
Guida operativa per gestire e usare Loogle MCP Hub.
---
## Accesso rapido
| Cosa | URL / comando |
|------|----------------|
| Dashboard admin | https://mcp.loogle.it/dashboard (login `daniele`) |
| Health | `curl -sf https://mcp.loogle.it/health` |
| Log gateway | `docker logs -f loogle-mcp` |
| Log indexer | `docker logs -f loogle-mcp-indexer` |
| Compose | `cd /home/daniely/docker/loogle-mcp` |
---
## Configurazione iniziale (checklist)
- [x] Stack Docker avviato (`docker compose up -d`)
- [x] DNS Pi-hole: `mcp.loogle.it``192.168.128.85`
- [x] NPM proxy host 30 + TLS Let's Encrypt
- [ ] Token Paperless in `.env` — vedi [PAPERLESS-TOKEN.md](PAPERLESS-TOKEN.md) (Profilo utente, non «Applicazione social»)
- [ ] `MCP_JWT_SECRET` robusto in `.env`
- [ ] Ollama su DS920 con `ollama pull nomic-embed-text`
- [ ] Qdrant su DS920 (opzionale, vedi compose extrema)
- [ ] Password cambiate per tutta la famiglia
- [ ] Ogni familiare ha collegato almeno un client AI
**Script utili:**
```bash
sudo /home/daniely/rete/scripts/setup-mcp-dns-npm.sh # DNS + NPM
./scripts/deploy.sh # rebuild + restart
/home/daniely/rete/scripts/npm-failover-route.sh normal # upstream failover
```
---
## Come usare tu (Daniele)
### Dashboard
1. https://mcp.loogle.it/dashboard — login `daniele`
2. Vedi progetti, audit log completo, revoca refresh token (sezione admin)
### Con Cursor / Claude / ChatGPT
Stesso URL MCP: `https://mcp.loogle.it/mcp`
**Cursor** — aggiungi in `.cursor/mcp.json` del progetto:
```json
{
"mcpServers": {
"loogle-mcp": {
"url": "https://mcp.loogle.it/mcp"
}
}
}
```
### Workflow consigliato per un task
1. **create_project** — es. «Homelab MCP», tag `rete`, `2026`
2. Lavori con lAI (Cursor, Claude, ecc.)
3. **save_context** — a fine sessione salvi decisioni e stato
4. **search_knowledge** — recuperi doc da Paperless quando serve
5. **search_context** — ritrovi discussioni passate semanticamente
### Tool solo admin
- `reindex_document` — forza re-indicizzazione di un doc Paperless
- Revoca token refresh da dashboard
- Audit log di tutti gli utenti via `/api/audit`
---
## Gestione utenti
Gli utenti sono in SQLite (`loogle_mcp.db`). Password hash PBKDF2.
| Utente | Admin | Reset password |
|--------|-------|----------------|
| daniele | sì | dashboard o diretto DB |
| lucia, davide, luca | no | dashboard (self-service) |
Password iniziale = username. `must_change_password` è attivo al primo login consigliato.
Per aggiungere utenti in futuro: estendi `FAMILY_USERS` in `app/auth.py` e redeploy.
---
## Paperless → knowledge base
Vedi guida completa: [PAPERLESS-TOKEN.md](PAPERLESS-TOKEN.md)
**Non usare** i token «Applicazione social» dell'admin Django (schermata nell'immagine): servono al login OAuth web di Paperless, non all'API REST MCP.
**Usa** i token API utente: docs.loogle.it → menu utente → **Profilo** → pulsante freccia circolare accanto a «Token API».
Configura in `.env` (un token per ogni account Paperless della famiglia):
```bash
PAPERLESS_API_TOKEN_DANIELE=<token account Daniele>
PAPERLESS_API_TOKEN_LUCIA=<token account Lucia>
PAPERLESS_API_TOKEN_DAVIDE=<token account Davide>
PAPERLESS_API_TOKEN_LUCA=<token account Luca>
```
Ogni familiare genera il proprio token da docs.loogle.it → **Profilo** → Token API. Se un utente non ha ancora account Paperless, lascia la riga vuota finché non lo crei.
Alternativa: solo `PAPERLESS_API_TOKEN=` con token admin (Daniele superuser) — tutti gli utenti MCP condividono lo stesso scope.
Riavvia indexer:
```bash
cd /home/daniely/docker/loogle-mcp && docker compose restart loogle-mcp loogle-mcp-indexer
```
**Visibilità documenti (tag Paperless):**
- Tag `personal` / `privato` → solo collection personale del owner
- Senza tag personali → `kb_shared_family` (tutti in famiglia)
---
## Embedding e Qdrant
| Componente | Dove | Note |
|----------|------|------|
| Ollama | DS920 `:11434` | `OLLAMA_EMBED_MODEL=nomic-embed-text` |
| Qdrant | DS920 `:6333` | Non gira su Pi5 (limitazione ARM) |
| Fallback | `/data/vector_fallback.db` | Automatico se Qdrant non raggiungibile |
Deploy Qdrant su DS920:
```bash
# sul DS920, path mirror extrema
docker compose -f /volume1/extrema/compose/extrema-ds920/loogle-mcp-compose.yml up -d qdrant
```
---
## DNS e NPM — cosa è stato configurato
**Pi-hole** (`/etc/pihole/pihole.toml`):
```
"192.168.128.85 mcp.loogle.it"
```
**NPM** proxy host ID 30:
- Dominio: `mcp.loogle.it`
- Backend: `192.168.128.80:8700`
- Cert: `npm-65`
**Failover** (`npm-routes.conf`):
```
30|mcp.loogle.it|8700|pi1|pi1|local|ds920
```
Se reinstalli NPM da zero, riesegui:
```bash
sudo /home/daniely/rete/scripts/setup-mcp-dns-npm.sh
/home/daniely/sync-npm-full.sh # sync Pi2 + DS920
```
---
## Monitoraggio e backup
- **Failover status:** probe `mcp_ok` / `mcp_be` in `failover-status.sh`
- **Runbook incidenti:** `/home/daniely/rete/ha/RUNBOOK-mcp.md`
- **Backup restic:** `/home/daniely/rete/infra-monitor/mcp-restic-backup.sh`
---
## Onboarding famiglia
Invia a ciascuno:
- [Guida utenti](GUIDA-UTENTI.md) — istruzioni semplici per ChatGPT/Claude/Gemini
- URL dashboard per cambio password
- Username personale (non condividere password)
Progetto demo già creato per ogni utente (es. `progetti-personali` per Lucia).
---
## Documentazione tecnica
- [Architettura e parametri](ARCHITETTURA.md)
- [Onboarding client AI (dettaglio)](ONBOARDING.md)
- [Runbook HA](/home/daniely/rete/ha/RUNBOOK-mcp.md)
@@ -0,0 +1,237 @@
# Paperless — Guida per la famiglia LOOGLE
**Archivio documenti di casa:** https://docs.loogle.it
Questa guida spiega **perché** usiamo Paperless, **come** configurarlo e **come** installare lapp sul telefono.
---
## Perché usiamo Paperless
Paperless è l**archivio digitale di casa**: bollette, contratti, manuali, referti, ricevute, documenti scolastici, ecc.
| Prima (cartaceo) | Con Paperless |
|------------------|---------------|
| Documenti sparsi in cassetti e cartelle | Tutto in un unico archivio searchable |
| Difficile trovare «la bolletta luce del 2024» | Cerca per parola, tag, mittente, data |
| Fotocopie e PDF persi nel telefono | PDF centralizzati, backup su NAS di casa |
| Solo chi ha il foglio fisico | Chi ha laccount può consultare (con permessi) |
**Vantaggi per noi:**
- **Resta in casa** — i file sono sui nostri dispositivi (Pi + NAS), non su Google Drive o iCloud di terzi
- **OCR in italiano** — Paperless legge il testo nei PDF e nelle scansioni, così puoi cercare anche dentro il documento
- **Integrazione** — lassistente AI (MCP) può cercare documenti già archiviati quando chiedi «trova la bolletta gas»
- **Accesso da telefono** — consulta e carica documenti ovunque (in rete casa o via VPN)
---
## Cos’è, in pratica
Paperless-ngx è un sito web dove:
1. **Carichi** un PDF o una foto (upload, email, cartella sul telefono)
2. **Paperless** fa OCR, propone titolo, data, tag
3. **Tu** confermi o correggi (opzionale)
4. **Archivi** — il documento resta indicizzato e ricercabile
**Indirizzo:** https://docs.loogle.it
Funziona da browser (PC, tablet, telefono) o da app dedicata.
---
## Account famiglia
| Nome | Username | Password iniziale |
|------|----------|-------------------|
| Daniele | `daniele` | *(chiedi a Daniele)* |
| Lucia | `lucia` | `lucia` |
| Davide | `davide` | `davide` |
| Luca | `luca` | `luca` |
**Al primo accesso cambia la password** (vedi sotto).
Ogni persona vede i **propri** documenti e quelli **condivisi in famiglia** (secondo i permessi impostati).
---
## Primo accesso e configurazione (browser)
### 1. Accedi al sito
1. Apri **https://docs.loogle.it** (da casa o in VPN — vedi sotto)
2. Inserisci **username** e **password**
3. Se è la prima volta, Paperless può chiederti di completare il profilo
### 2. Cambia la password
1. Clicca sul **nome utente** in alto a destra
2. Vai su **Profilo** / **Impostazioni**
3. Sezione **Password** → inserisci la vecchia e la nuova
4. Salva
### 3. Conosci linterfaccia
| Area | A cosa serve |
|------|----------------|
| **Dashboard** | Panoramica, documenti recenti |
| **Documenti** | Elenco e ricerca di tutti i PDF |
| **Inbox** (se attiva) | Documenti appena caricati da revisionare |
| **Tag / Tipi / Corrispondenti** | Organizzazione (es. tag `bollette`, `salute`) |
### 4. Caricare un documento
**Da computer:**
1. **Documenti****Carica** (o trascina il PDF nella finestra)
2. Attendi lOCR (qualche secondo)
3. Controlla titolo, data, tag → **Salva**
**Da telefono (browser):**
- Stesso procedimento dal browser mobile su docs.loogle.it
**Suggerimento:** usa tag semplici e coerenti, es. `bollette`, `casa`, `auto`, `salute`, `scuola`.
### 5. Cercare un documento
- Barra **Cerca** in alto: parole chiave (es. «enel», «bolletta», «assicurazione»)
- Filtri per **tag**, **tipo documento**, **data**
- Paperless cerca anche **dentro** il testo del PDF (OCR)
### 6. Scaricare o condividere
- Apri un documento → icona **Download** o **Condividi**
- Puoi inviare il PDF via email/WhatsApp dal telefono
---
## Accesso da fuori casa (VPN)
`docs.loogle.it` è raggiungibile **in rete di casa** (WiFi domestico o dati se sei a casa).
**Se sei fuori** (ufficio, viaggio): connettiti prima alla **VPN di casa**:
- Indirizzo: **https://vpn.loogle.it**
- Credenziali WireGuard: chiedi a Daniele (file `.conf` o QR code)
Dopo la VPN, apri normalmente https://docs.loogle.it o lapp Paperless.
---
## App sul telefono
Paperless **non ha unapp ufficiale** del team Paperless-ngx, ma esistono app **compatibili** che si collegano al nostro server.
### Consigliate
| App | Android | iPhone/iPad |
|-----|---------|-------------|
| **Paperless Mobile** | [Google Play](https://play.google.com/store/apps/details?id=de.astubenbord.paperless_mobile) | Cerca «Paperless Mobile» su App Store |
| **Paperless Go** | [Google Play](https://play.google.com/store/apps/details?id=com.github.iweinzierl.paperlessgo) / F-Droid | [App Store](https://apps.apple.com/app/paperless-go/id6738696198) |
Per la famiglia consigliamo **Paperless Mobile** (molto usata, italiano supportato) oppure **Paperless Go** (interfaccia moderna, scansione documenti).
---
## Installazione app — passo passo
### Android (Paperless Mobile)
1. Apri **Google Play Store**
2. Cerca **«Paperless Mobile»** (sviluppatore: Andrei Stübenbord)
3. **Installa**
4. Apri lapp → **Aggiungi account** / **Connect**
5. **URL server:** `https://docs.loogle.it`
6. **Username** e **password** (le tue credenziali Paperless)
7. Accetta eventuale avviso certificato (connessione sicura LOOGLE)
8. Fatto — vedi lelenco documenti
### iPhone / iPad (Paperless Mobile o Paperless Go)
1. Apri **App Store**
2. Cerca **«Paperless Mobile»** o **«Paperless Go»**
3. **Scarica** e apri
4. Inserisci:
- **Server URL:** `https://docs.loogle.it`
- **Username** / **Password**
5. Opzionale: attiva **Face ID / Touch ID** per proteggere lapp
6. Fatto
### Scansione con il telefono (Paperless Go)
1. Nellapp → **Scansiona** / icona fotocamera
2. Inquadra il documento (bolletta, lettera)
3. Ritaglia e conferma
4. Scegli tag / tipo se richiesto → **Carica**
5. Il PDF compare in Paperless dopo pochi secondi
---
## Configurazione consigliata nellapp
| Impostazione | Consiglio |
|--------------|-----------|
| **Tema scuro** | Più comodo di sera |
| **Biometria** | Face ID / impronta per aprire lapp |
| **Notifiche** | Opzionali (nuovi documenti in inbox) |
| **Account multipli** | Un account per persona (non condividere la stessa login) |
---
## Buone abitudini
1. **Carica subito** bollette e documenti importanti (non lasciare pile di carta)
2. **Usa tag** — pochi ma chiari (`luce`, `gas`, `banca`, `medico`)
3. **Controlla linbox** — correggi titolo/data se Paperless sbaglia
4. **Non eliminare** loriginale cartaceo finché non sei sicuro che il PDF sia ok
5. **Cambia password** se pensi che qualcuno labbia vista
---
## Collegamento con lassistente AI (MCP)
Se usi ChatGPT, Claude o Cursor collegati a **Loogle MCP** (`https://mcp.loogle.it`):
- Puoi chiedere: *«Cerca in Paperless la bolletta luce dellultimo trimestre»*
- LAI cerca solo nei documenti **che il tuo account può vedere**
- Per funzionare, i documenti devono **già essere** in Paperless
La guida MCP è separata: `GUIDA-UTENTI.pdf` nella stessa cartella.
---
## Problemi comuni
| Problema | Cosa fare |
|----------|-----------|
| «Sito non raggiungibile» | Sei in rete casa? Se no, attiva **VPN** (vpn.loogle.it) |
| Login fallisce | Controlla username/password; prova da browser prima |
| App «connessione fallita» | URL esatto: `https://docs.loogle.it` (con **https**) |
| Certificato / SSL | Accetta il certificato LOOGLE; data/ora telefono corretta |
| Non vedo un documento | Potrebbe essere personale di un altro utente; chiedi a Daniele |
| OCR illeggibile | Scansiona con buona luce; PDF meglio di foto storta |
---
## Contatti
**Daniele** — account, permessi, VPN, problemi tecnici.
---
## Scheda rapida
```
Sito: https://docs.loogle.it
VPN fuori: https://vpn.loogle.it
App Android: Paperless Mobile (Play Store)
App iPhone: Paperless Mobile o Paperless Go (App Store)
Server URL: https://docs.loogle.it
Login: il tuo username (lucia / davide / luca)
Primo passo: cambia password → installa app → carica una bolletta di prova
```
---
*Loogle — documenti di famiglia, a casa nostra.*
+289
View File
@@ -0,0 +1,289 @@
# Guida utenti — Loogle MCP Hub
Questa guida è per **Lucia, Davide e Luca** (e chiunque usi gli assistenti AI collegati a casa).
---
## Cos’è
Loogle MCP è la **memoria di casa** per i tuoi assistenti AI. Permette a ChatGPT, Claude o Gemini di:
- **Ricordare** i tuoi progetti (es. ristrutturazione, studio, hobby)
- **Cercare** documenti che abbiamo già archiviato in Paperless (bollette, manuali, PDF)
- **Salvare** note e riassunti che lAI produce durante un lavoro, così non devi ripetere tutto ogni volta
I tuoi dati restano **solo sui nostri dispositivi** a casa, non nel cloud dellAI.
---
## Le tue credenziali
| Nome | Username | Password iniziale |
|------|----------|-------------------|
| Lucia | `lucia` | `lucia` |
| Davide | `davide` | `davide` |
| Luca | `luca` | `luca` |
**Al primo accesso cambia la password:**
1. Apri https://mcp.loogle.it/dashboard
2. Accedi con username e password
3. Sezione **Cambia password** → inserisci la nuova password (minimo 6 caratteri)
Ogni persona vede **solo i propri progetti**. Non puoi vedere (né lAI) i progetti degli altri familiari.
---
## Collegare ChatGPT
Richiede account **Plus, Pro, Business o Edu**.
1. Apri ChatGPT → **Impostazioni**
2. Attiva **Developer Mode** (se non già attivo)
3. Vai a **Connectors****Add MCP Connector**
4. Inserisci lURL del server:
```
https://mcp.loogle.it/mcp
```
5. Clicca **Connect** — si apre una pagina di login Loogle
6. Accedi con **il tuo** username e password (es. `lucia` / la tua nuova password)
7. Autorizza laccesso
Nelle conversazioni, abilita i tool del connector **Loogle MCP** quando vuoi usare memoria o documenti.
### Esempi di richieste a ChatGPT
- *«Usa list_projects per vedere i miei progetti»*
- *«Leggi il contesto del progetto X e riassumilo»*
- *«Cerca nei documenti di casa informazioni sulla caldaia»*
- *«Salva in save_context questo riepilogo del lavoro fatto oggi»*
---
## Collegare Claude (App / Desktop)
1. Apri Claude → **Settings** → **Connectors**
2. **Add remote MCP server**
3. URL:
```
https://mcp.loogle.it/mcp
```
4. Al primo utilizzo: login con le **tue** credenziali Loogle MCP
5. Autorizza
Claude potrà usare gli stessi tool (progetti, ricerca documenti, salvataggio contesto).
---
## Collegare Cursor IDE
1. Crea o modifica `~/.cursor/mcp.json` (globale) oppure `.cursor/mcp.json` nel progetto:
```json
{
"mcpServers": {
"loogle-mcp": {
"url": "https://mcp.loogle.it/mcp",
"auth": {
"CLIENT_ID": "cursor",
"scopes": [
"context:read", "context:write",
"knowledge:read", "knowledge:write",
"gitea:read", "gitea:write",
"home:read", "irrigation:read", "turni:read"
]
}
}
}
}
```
2. **Riavvia Cursor completamente** (esci dallapp, non solo chiudi la finestra)
3. **Cursor Settings** → **Tools & MCP** → **Connect** su `loogle-mcp` (**una sola volta**, attendi 1015 s)
4. Si apre il browser su **Loogle MCP — Login** → accedi con le **tue** credenziali MCP
5. In chat, chiedi all'AI di usare i tool (`list_projects`, `search_knowledge`, …)
### Cursor: «Unauthorized» nei log
| Log Cursor | Significato |
|------------|-------------|
| `MCP OAuth redirect` + `Unauthorized` | **Normale prima del login** — clicca **Connect** e completa il browser |
| `Redirect URI non consentito` | Errore server (già risolto) — riprova **Reconnect** |
| `credentials cleared` | Hai cliccato Connect/Disconnect in loop — riavvia Cursor e riprova una volta |
**Password:** se hai cambiato quella iniziale, usa quella attuale (es. admin `daniele` non usa più `daniele`/`daniele`). Verifica su https://mcp.loogle.it/dashboard
**Se il browser non si apre:** prova la config con `"CLIENT_ID": "cursor"` sopra, oppure apri manualmente https://mcp.loogle.it/dashboard per testare le credenziali.
---
## Collegare Gemini
**Gemini CLI** (da terminale / PC):
1. Apri il file di configurazione MCP di Gemini (es. `~/.gemini/settings.json`)
2. Aggiungi:
```json
{
"mcpServers": {
"loogle-mcp": {
"url": "https://mcp.loogle.it/mcp"
}
}
}
```
3. Al primo avvio completa il login OAuth nel browser con le tue credenziali
Lapp Gemini mobile potrebbe non supportare ancora MCP remoto; in quel caso usa ChatGPT o Claude.
---
## Dashboard web
Indirizzo: **https://mcp.loogle.it/dashboard**
Da qui puoi:
- Vedere lelenco dei **tuoi progetti**
- **Cambiare password**
- Consultare le **ultime azioni** che lAI ha fatto (audit log)
---
## Come usarlo nel quotidiano
### 1. Crea un progetto per ogni tema importante
Chiedi allAI:
> «Crea un progetto chiamato "Rinnovo bagno" con tag casa, 2026»
(Usa il tool `create_project` — lAI lo farà automaticamente se il connector è attivo.)
### 2. Lavora e fai salvare la memoria
A fine sessione:
> «Salva in save_context un riepilogo di quello che abbiamo deciso oggi, nel progetto rinnovo-bagno»
La prossima volta lAI potrà rileggere tutto con `get_project_context`.
### 3. Cerca documenti di casa
> «Cerca in search_knowledge la bolletta luce dellultimo trimestre»
> «Trova nel archivio documenti il manuale della caldaia»
(I documenti devono essere già in Paperless su docs.loogle.it.)
### 4. Cerca tra i tuoi appunti passati
> «search_context: cosa avevamo deciso sul parquet?»
### 5. Codice e runbook su Gitea
> «list_repos: quali repository ho su git.loogle.it?»
> «get_file su daniele/rete ha/RUNBOOK-failover.md»
> «search_code tier-b nel repo daniele/rete»
### 6. Progetto MCP collegato al codice
> «create_project "Infra Rete" con gitea_repo daniele/rete e seed_from_gitea true»
> «link_project_repo sul progetto homelab-loogle → daniele/rete»
> «get_project_context sul progetto attivo» — include README e elenco file in `docs/` dal repo collegato
> «search_gitea_knowledge: come funziona il failover tier-b?»
> «reindex_gitea_repo daniele/rete» — forza aggiornamento indicizzazione
### 7. Ricerca semantica su runbook Git (RAG)
> «search_gitea_knowledge failover su daniele/rete»
> «search_knowledge keepalived VIP» — cerca anche in Paperless e Gitea indicizzati
L'indexer in background indicizza `.md`, script e config dai repo collegati (vedi `docs/GITEA-TOKEN.md` sezione P3).
### 8. Casa, rete e Home Assistant (P5)
> «get_home_weather: che tempo fa a casa?»
> «get_network_overview: qualcosa è offline in rete?»
> «get_network_failover_status: com'è lo scenario failover?»
> «get_ha_entity switch.pompa_pozzo» — stato entità Home Assistant (solo lettura)
> «search_ha_entities caldaia»
### 9. Irrigazione e turni (P6)
> «get_irrigation_status: programma irrigazione oggi»
> «get_irrigation_zones: quali zone sono attive?»
> «get_my_shifts: i miei turni di lavoro questo mese»
> «list_turni_doctors» — elenco medici in Turni-Live
### 10. Ricerca storica app (P7)
> «search_apps_knowledge irrigazione prato ieri»
> «search_knowledge valvola pozzo» — include anche Irrigazione/Turni indicizzati
Dettagli tecnici e configurazione: `docs/APPS-INTEGRATION.md`.
---
## Cosa può e non può fare
| Può | Non può |
|-----|---------|
| Leggere i **tuoi** progetti | Vedere progetti di altri familiari |
| Cercare documenti **famiglia** e **personali** (secondo tag Paperless) | Modificare Paperless o cancellare PDF |
| Aggiungere testo alla **tua** memoria progetto | Accedere senza login OAuth |
| Cercare semanticamente (capisce il significato, non solo parole esatte) | Funzionare senza internet verso casa* |
| Leggere codice e issue da **Gitea** (repo a cui hai accesso) | Push/commit git via MCP (usa git normalmente) |
| Meteo/rete da **Loogle Casa**, sensori **Home Assistant** (lettura) | Controllare luci/valvole via MCP (solo lettura HA) |
| Stato **irrigazione** e **turni** (se configurati per te) | Modificare programmi irrigazione o turni via MCP |
\*Da fuori casa serve VPN WireGuard (`vpn.loogle.it`) o connessione alla rete di casa.
---
## Problemi comuni
| Problema | Cosa fare |
|----------|-----------|
| Login fallisce | Verifica username/password; reset da dashboard |
| ChatGPT non trova il server | URL esatto: `https://mcp.loogle.it/mcp` (con https) |
| «Knowledge vuota» | I documenti Paperless potrebbero non essere ancora indicizzati — chiedi a Daniele |
| Token scaduto | Riconnetti il connector OAuth (disconnect + connect) |
| Cursor «Unauthorized» | Clicca **Connect** una volta; login browser; usa config con `"CLIENT_ID": "cursor"` |
| Sito non raggiungibile | Sei in VPN/rete casa? Prova https://mcp.loogle.it/health |
---
## Contatti
Per problemi tecnici (token Paperless, servizio down, nuovo progetto di gruppo): **Daniele**.
Per la password dimenticata: chiedi a Daniele (admin) o usa il dashboard se ricordi quella vecchia.
---
## Scheda rapida
```
URL MCP: https://mcp.loogle.it/mcp
Dashboard: https://mcp.loogle.it/dashboard
Login: il tuo username (lucia / davide / luca)
Primo passo: cambia password → collega ChatGPT o Claude → crea un progetto
```
+157
View File
@@ -0,0 +1,157 @@
# Onboarding client AI — Loogle MCP Hub
Endpoint MCP: `https://mcp.loogle.it/mcp`
OAuth: al primo collegamento compare la pagina login Loogle. Usa le credenziali famiglia.
Password iniziale = username (es. `lucia` / `lucia`). Cambiala da https://mcp.loogle.it/dashboard
---
## Daniele (admin)
- Username: `daniele`
- Tool admin: `reindex_document`, audit completo, revoca token refresh
## Lucia
- Username: `lucia`
- Progetti isolati in `/mnt/ha-apps/mcp/context/lucia/`
## Davide
- Username: `davide`
## Luca
- Username: `luca`
---
## ChatGPT (Plus/Pro/Business)
1. Abilita **Developer Mode** nelle impostazioni ChatGPT
2. Settings → Connectors → **Add MCP Connector**
3. URL server: `https://mcp.loogle.it/mcp`
4. Completa OAuth con le tue credenziali
5. Abilita i tool desiderati nella conversazione
Redirect URI supportati (pre-registrati):
- `https://chatgpt.com/connector_platform_oauth_redirect`
- `https://chat.openai.com/connector_platform_oauth_redirect`
## Claude App / Claude Desktop
1. Settings → Connectors → **Add remote MCP server**
2. URL: `https://mcp.loogle.it/mcp`
3. Autenticazione OAuth al primo uso
Redirect URI: `https://claude.ai/api/mcp/auth_callback`
## Cursor IDE
Cursor supporta MCP remoto con **OAuth automatico** (Streamable HTTP).
### Configurazione
**Globale** (tutti i progetti): `~/.cursor/mcp.json`
**Solo questo repo**: `.cursor/mcp.json` (già presente nel progetto loogle-mcp)
```json
{
"mcpServers": {
"loogle-mcp": {
"url": "https://mcp.loogle.it/mcp"
}
}
}
```
### Collegamento
1. Apri **Cursor Settings****Tools & MCP**
2. Trova **loogle-mcp** → clic **Connect**
3. Si apre il browser → login con le **tue** credenziali Loogle (`daniele`, `lucia`, …)
4. Autorizza → Cursor torna con i tool attivi
Redirect OAuth Cursor (già registrati sul server):
- `https://www.cursor.com/agents/mcp/oauth/callback` (web / Agents)
- `http://localhost:8787/callback` (desktop app)
### Uso in chat
Chiedi all'agente di usare i tool MCP, ad esempio:
> «Usa whoami e list_projects per vedere i miei progetti Loogle»
Se il server risulta disconnesso: **Reconnect** da Tools & MCP.
---
## Gemini CLI
Aggiungi in `~/.gemini/settings.json` (o equivalente):
```json
{
"mcpServers": {
"loogle": {
"url": "https://mcp.loogle.it/mcp",
"transport": "http"
}
}
}
```
Al primo avvio completa il flow OAuth nel browser.
## Cursor IDE
File `.cursor/mcp.json` nel progetto:
```json
{
"mcpServers": {
"loogle-mcp": {
"url": "https://mcp.loogle.it/mcp"
}
}
}
```
---
## Tool disponibili
| Tool | Descrizione |
|------|-------------|
| `ping` | Test connettività |
| `whoami` | Utente e scope |
| `list_projects` | Progetti utente |
| `create_project` | Nuovo archivio contesto |
| `get_project_context` | Legge memoria progetto |
| `save_context` | Salva/appende memoria |
| `search_context` | Ricerca semantica contesti |
| `search_knowledge` | RAG su Paperless + contesti + Gitea indicizzati |
| `search_gitea_knowledge` | RAG solo su file Gitea (runbook, markdown) |
| `list_gitea_indexed_files` | File Gitea nel vector store |
| `reindex_gitea_repo` | Re-indicizza un repo (admin/owner) |
| `get_document` | Testo documento Paperless |
| `list_recent_documents` | Ultimi doc indicizzati |
| `reindex_document` | Solo admin |
| `list_repos` | Repository Gitea accessibili |
| `get_file` | Legge file da repo Gitea |
| `search_code` | Cerca nel codice sorgente |
| `list_issues` / `get_issue` | Issue su repo Gitea |
| `create_issue` | Crea issue (scope gitea:write) |
| `link_project_repo` | Collega/scollega repo Gitea a un progetto |
## Esempio prompt agente
> "Usa list_projects per vedere i miei progetti, poi get_project_context sul progetto attivo e search_knowledge per trovare documenti rilevanti su [argomento]."
## Troubleshooting
- **401 su MCP**: token scaduto — riconnetti il connector OAuth
- **Knowledge vuota**: verifica token Paperless e Ollama su DS920
- **Dashboard**: https://mcp.loogle.it/dashboard
+108
View File
@@ -0,0 +1,108 @@
# Token Paperless per Loogle MCP
## Cosa NON usare: token «Applicazione social»
Nell'admin Django di Paperless (`/admin/socialaccount/socialtoken/`) compare il form **«Aggiungi token dell'applicazione social»** con campi Token, Token segreto, Scade il.
Questi token servono a **django-allauth** per il login OAuth web (Google, Microsoft, ecc.) su Paperless. **Non** sono token dell'API REST di Paperless e **non** vanno usati per Loogle MCP.
Non devi configurare nulla in quella schermata per il nostro hub MCP.
---
## Cosa usare: token API utente
Paperless espone un'API REST autenticata con header:
```
Authorization: Token <token>
```
Ogni utente Paperless ha il proprio token, legato ai permessi di quell'account (documenti visibili, tag, ecc.).
### Dove generarlo
Per **ogni** familiare con account Paperless (daniele, lucia, davide, luca):
1. Accedi a https://docs.loogle.it con quell'account
2. Menu utente (in alto a destra) → **Profilo** / **Il mio profilo**
3. Sezione **Token API** → pulsante freccia circolare (rigenera token)
4. Copia il token nella riga corrispondente di `.env`
Alternativa admin: Django admin → **Token** (app `authtoken`), associato all'utente.
---
## Configurazione in Loogle MCP
Modifica `/home/daniely/docker/loogle-mcp/.env`:
### Opzione consigliata — token per utente (4 familiari)
```env
PAPERLESS_URL=https://docs.loogle.it
PAPERLESS_API_TOKEN_DANIELE=
PAPERLESS_API_TOKEN_LUCIA=
PAPERLESS_API_TOKEN_DAVIDE=
PAPERLESS_API_TOKEN_LUCA=
```
| Utente MCP | Variabile `.env` | Account Paperless |
|------------|------------------|-------------------|
| Daniele | `PAPERLESS_API_TOKEN_DANIELE` | utente admin / superuser |
| Lucia | `PAPERLESS_API_TOKEN_LUCIA` | utente Lucia |
| Davide | `PAPERLESS_API_TOKEN_DAVIDE` | utente Davide |
| Luca | `PAPERLESS_API_TOKEN_LUCA` | utente Luca |
Righe vuote = utente saltato dall'indexer finché non inserisci il token.
### Opzione alternativa — un solo token admin
Se preferisci un unico account Paperless (es. Daniele superuser):
```env
PAPERLESS_API_TOKEN=<token-daniele>
```
Tutti gli utenti MCP useranno quel token in fallback.
### Opzione C — mappa JSON
```env
PAPERLESS_API_TOKENS={"daniele":"...","lucia":"...","davide":"...","luca":"..."}
```
---
## Comportamento nel sistema
| Componente | Comportamento |
|------------|---------------|
| **Indexer** | Usa tutti i token configurati, unisce l'elenco documenti (deduplica per ID) |
| **`search_knowledge`** | Cerca su tutto ciò che è stato indicizzato |
| **`get_document`** | Usa il token dell'utente MCP loggato; se manca, fallback su `PAPERLESS_API_TOKEN` o token Daniele |
Con token separati, ogni familiare può scaricare via MCP solo i documenti visibili al proprio account Paperless.
---
## Applicare le modifiche
```bash
cd /home/daniely/docker/loogle-mcp
# modifica .env con i token reali
docker compose restart loogle-mcp loogle-mcp-indexer
docker logs loogle-mcp-indexer --tail 30
```
Log atteso: indicizzazione da `daniele`, `lucia`, `davide`, `luca` (solo utenti con token impostato).
---
## Checklist onboarding Paperless
- [ ] Account Paperless creato per daniele, lucia, davide, luca (se non esistono)
- [ ] Token API generato per ciascuno (Profilo → Token API)
- [ ] Quattro righe compilate in `.env`
- [ ] `docker compose restart loogle-mcp loogle-mcp-indexer`
- [ ] Log indexer senza errori 401
Binary file not shown.
Binary file not shown.