Add Spec 034 Nextcloud integration with VM112 Carbonio mail.
Defines hybrid hot/warm storage to expand tenant mail capacity via Nextcloud Hub on proposed VM116.
This commit is contained in:
parent
6c4b063f76
commit
f6cf9f8e1c
8 changed files with 875 additions and 1 deletions
|
|
@ -30,6 +30,7 @@ ligbox-ops-platform/
|
|||
| **123** | 10.10.10.123 | :2523 | FOSSBilling + Odoo + OpenPanel + Console UI | `projects/finance/` |
|
||||
| **104** | 10.10.10.104 | :2504 | Wazuh SIEM | integração Spec 002, 019 |
|
||||
| **114** | 10.10.10.114 | — | Traefik (CT) | `docs/network/TRAEFIK_*` |
|
||||
| **116** | 10.10.10.116 | :2516 | Nextcloud Hub — ampliar storage mail (Spec 034) | `deploy/vm116-nextcloud/` |
|
||||
| **130** | 10.10.10.130 | :2530 | **Spec Hub** Git + Obsidian + Portal | CT130 local |
|
||||
|
||||
---
|
||||
|
|
@ -44,6 +45,7 @@ ligbox-ops-platform/
|
|||
| 022 | carbonio-account-exists-release |
|
||||
| 025 | wizard-onboarding-continuity |
|
||||
| 026 | purge-traefik-validation |
|
||||
| 034 | nextcloud-carbonio-vm112-integration |
|
||||
| 010 | desk-assist-takeover (fases VM112) |
|
||||
|
||||
→ [Ficha VM112](VM112.md)
|
||||
|
|
|
|||
|
|
@ -25,6 +25,7 @@ specs/017-vm112-domain-orchestration/
|
|||
specs/022-carbonio-account-exists-release/
|
||||
specs/025-wizard-onboarding-continuity/
|
||||
specs/026-purge-traefik-validation/
|
||||
specs/034-nextcloud-carbonio-vm112-integration/
|
||||
```
|
||||
|
||||
## Deploy na VM112
|
||||
|
|
@ -37,5 +38,6 @@ git clone https://git.spec.ligbox.com.br/ligbox/ligbox-ops-platform.git
|
|||
## Integração
|
||||
|
||||
- **→ VM122:** webhooks `onboarding.*` · Assist/takeover API
|
||||
- **→ CT114:** Traefik routers mail/onboard
|
||||
- **→ CT114:** Traefik routers mail/onboard · `files.{dom}` (Spec 034)
|
||||
- **→ VM116:** IMAP/SMTP (Nextcloud Mail app) · OCS provisioning (Spec 034)
|
||||
- **← Desk:** purge, DNS revalidate, assist actions
|
||||
|
|
|
|||
32
docs/vms/VM116.md
Normal file
32
docs/vms/VM116.md
Normal file
|
|
@ -0,0 +1,32 @@
|
|||
# VM116 — Nextcloud Hub (Spec 034)
|
||||
|
||||
| Item | Valor |
|
||||
|------|-------|
|
||||
| **IP LAN** | `10.10.10.116` (proposto) |
|
||||
| **SSH WAN** | `95.216.14.146:2516` (reservar pfSense) |
|
||||
| **Hostname** | `cloud.ligbox.com.br` |
|
||||
| **URLs tenant** | `files.{dominio}` |
|
||||
|
||||
## Papel
|
||||
|
||||
- Armazenamento **Files** ampliado para tenants Ligbox Mail (VM112)
|
||||
- App **Mail** opcional → IMAP/SMTP Carbonio VM112
|
||||
- MinIO S3 (fase 2) — volume secundário Carbonio
|
||||
|
||||
## No repo Git (CT130)
|
||||
|
||||
```
|
||||
deploy/vm116-nextcloud/ # (a criar — Fase 0)
|
||||
specs/034-nextcloud-carbonio-vm112-integration/
|
||||
```
|
||||
|
||||
## Integração
|
||||
|
||||
- **← VM112:** Wizard provisiona users OCS após conta Carbonio
|
||||
- **→ VM112:** Mail app IMAP `:993` · SMTP `:587`
|
||||
- **→ CT114:** Traefik `files.{dom}` + `cloud.ligbox.com.br`
|
||||
- **← Desk VM122:** health, status quota, purge users (Spec 017 ext.)
|
||||
|
||||
## Estado
|
||||
|
||||
📋 **Não provisionada** — Spec 034 Fase 0 pendente aprovação Roger.
|
||||
|
|
@ -0,0 +1,173 @@
|
|||
# Contrato — Nextcloud Provisioning + Desk API (Spec 034)
|
||||
|
||||
**Versão:** 0.1 draft
|
||||
**Auth Nextcloud OCS:** Basic (admin app password) ou token de serviço
|
||||
**Auth Desk:** Bearer session (RBAC Spec 027)
|
||||
|
||||
---
|
||||
|
||||
## 1. Nextcloud OCS — utilizador (Wizard VM112)
|
||||
|
||||
### Criar utilizador
|
||||
|
||||
```http
|
||||
POST /ocs/v1.php/cloud/users
|
||||
Authorization: Basic {admin}:{app_password}
|
||||
OCS-APIRequest: true
|
||||
Content-Type: application/x-www-form-urlencoded
|
||||
|
||||
userid=admin%40empresa.com.br&password=***&displayName=Admin+Empresa
|
||||
```
|
||||
|
||||
**Resposta 200:**
|
||||
|
||||
```xml
|
||||
<ocs>
|
||||
<meta><status>ok</status></meta>
|
||||
<data/>
|
||||
</ocs>
|
||||
```
|
||||
|
||||
### Definir quota Files
|
||||
|
||||
```http
|
||||
PUT /ocs/v1.php/cloud/users/{userid}
|
||||
Content-Type: application/x-www-form-urlencoded
|
||||
|
||||
key=quota&value=25GB
|
||||
```
|
||||
|
||||
### Apagar utilizador (purge)
|
||||
|
||||
```http
|
||||
DELETE /ocs/v1.php/cloud/users/{userid}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 2. Wizard VM112 — evento interno
|
||||
|
||||
Após provision OK:
|
||||
|
||||
```json
|
||||
{
|
||||
"event": "onboarding.nextcloud.provisioned",
|
||||
"domain": "empresa.com.br",
|
||||
"email": "admin@empresa.com.br",
|
||||
"nextcloud_userid": "admin@empresa.com.br",
|
||||
"files_url": "https://files.empresa.com.br",
|
||||
"quota_files": "25GB",
|
||||
"carbonio_quota_gb": 5,
|
||||
"session_id": "uuid"
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 3. Desk API — health
|
||||
|
||||
### GET `/api/v1/nextcloud/health`
|
||||
|
||||
**Roles:** `super_admin`, `ops_lead`, `technician`, `noc`
|
||||
|
||||
**Resposta 200:**
|
||||
|
||||
```json
|
||||
{
|
||||
"status": "ok",
|
||||
"vm116": {
|
||||
"reachable": true,
|
||||
"nextcloud_version": "30.0.0",
|
||||
"disk_used_pct": 12,
|
||||
"url": "https://cloud.ligbox.com.br"
|
||||
},
|
||||
"carbonio_vm112": {
|
||||
"reachable": true,
|
||||
"disk_used_pct": 22
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 4. Desk API — status domínio
|
||||
|
||||
### GET `/api/v1/nextcloud/domains/{domain}/status`
|
||||
|
||||
**Roles:** `super_admin`, `ops_lead`, `technician`
|
||||
|
||||
**Resposta 200:**
|
||||
|
||||
```json
|
||||
{
|
||||
"domain": "empresa.com.br",
|
||||
"carbonio": {
|
||||
"accounts": 3,
|
||||
"domain_quota_gb": 30,
|
||||
"domain_used_gb": 8.2,
|
||||
"mail_host": "mail.empresa.com.br"
|
||||
},
|
||||
"nextcloud": {
|
||||
"enabled": true,
|
||||
"users": 3,
|
||||
"files_url": "https://files.empresa.com.br",
|
||||
"total_quota_gb": 75,
|
||||
"total_used_gb": 12.1
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 5. Desk API — provision manual
|
||||
|
||||
### POST `/api/v1/nextcloud/domains/{domain}/users`
|
||||
|
||||
**Roles:** `super_admin`, `ops_lead`
|
||||
|
||||
**Body:**
|
||||
|
||||
```json
|
||||
{
|
||||
"email": "vendas@empresa.com.br",
|
||||
"display_name": "Vendas",
|
||||
"quota_files": "25GB",
|
||||
"sync_password": true,
|
||||
"password": "********"
|
||||
}
|
||||
```
|
||||
|
||||
**Resposta 201:**
|
||||
|
||||
```json
|
||||
{
|
||||
"userid": "vendas@empresa.com.br",
|
||||
"files_url": "https://files.empresa.com.br",
|
||||
"provisioned_at": "2026-06-20T22:00:00Z"
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 6. Erros standard
|
||||
|
||||
| HTTP | code | Descrição |
|
||||
|------|------|-----------|
|
||||
| 404 | `domain_not_found` | Domínio não orquestrado VM112 |
|
||||
| 409 | `user_exists` | User NC ou Carbonio já existe |
|
||||
| 502 | `nextcloud_unreachable` | VM116 down |
|
||||
| 503 | `feature_disabled` | `NEXTCLOUD_INTEGRATION=0` |
|
||||
|
||||
---
|
||||
|
||||
## 7. Variáveis ambiente (Wizard VM112)
|
||||
|
||||
```env
|
||||
NEXTCLOUD_INTEGRATION=0
|
||||
NEXTCLOUD_OCS_URL=https://10.10.10.116
|
||||
NEXTCLOUD_ADMIN_USER=ligbox-provisioner
|
||||
NEXTCLOUD_ADMIN_APP_PASSWORD=***
|
||||
NEXTCLOUD_DEFAULT_QUOTA=25GB
|
||||
NEXTCLOUD_FILES_URL_TEMPLATE=https://files.{domain}
|
||||
CARBONIO_DEFAULT_QUOTA_GB=5
|
||||
```
|
||||
172
specs/034-nextcloud-carbonio-vm112-integration/infrastructure.md
Normal file
172
specs/034-nextcloud-carbonio-vm112-integration/infrastructure.md
Normal file
|
|
@ -0,0 +1,172 @@
|
|||
# Spec 034 — Infraestrutura Nextcloud + VM112
|
||||
|
||||
**Actualizado:** 2026-06-20
|
||||
|
||||
---
|
||||
|
||||
## Topologia proposta
|
||||
|
||||
```
|
||||
Internet (95.216.14.146)
|
||||
│
|
||||
├── pfSense NAT
|
||||
│ ├── :2512 → VM112:22 (mail/wizard)
|
||||
│ ├── :2516 → VM116:22 (nextcloud) ← reservar
|
||||
│ └── :443 → CT114 Traefik
|
||||
│
|
||||
└── CT114 (10.10.10.114)
|
||||
├── mail.{dominio} → VM112:443
|
||||
├── onboard.ligbox.com.br → VM112:8090
|
||||
├── files.{dominio} → VM116:443 ← novo router
|
||||
└── cloud.ligbox.com.br → VM116:443 ← hub Ligbox
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## VM116 — Nextcloud Hub (nova)
|
||||
|
||||
| Parâmetro | Valor proposto |
|
||||
|-----------|----------------|
|
||||
| **VMID** | 116 |
|
||||
| **Nome** | `vm116-nextcloud-ligbox` |
|
||||
| **IP LAN** | `10.10.10.116/24` |
|
||||
| **Gateway** | `10.10.10.1` (pfSense) |
|
||||
| **SSH WAN** | `95.216.14.146:2516` |
|
||||
| **vCPU** | 4 |
|
||||
| **RAM** | 8192 MB |
|
||||
| **Disco** | 500 GB (`local-lvm` ou volume dedicado) |
|
||||
| **SO** | Ubuntu 24.04 LTS |
|
||||
|
||||
### Serviços
|
||||
|
||||
| Serviço | Porta | Notas |
|
||||
|---------|-------|-------|
|
||||
| Nextcloud (Apache/nginx) | 443 | Behind Traefik ou direct SNI |
|
||||
| PostgreSQL | 5432 | localhost only |
|
||||
| Redis | 6379 | localhost — locking/sessions |
|
||||
| MinIO (fase 2) | 9000 | S3 API — localhost + VM112 ACL |
|
||||
|
||||
### Instalação recomendada
|
||||
|
||||
**Opção A — Docker Compose** (preferida para IaC no repo):
|
||||
|
||||
```
|
||||
deploy/vm116-nextcloud/
|
||||
├── docker-compose.yml
|
||||
├── .env.example
|
||||
├── traefik/dynamic-files.yml.snippet
|
||||
└── scripts/
|
||||
├── install.sh
|
||||
├── occ-provision-user.sh
|
||||
└── backup-occ.sh
|
||||
```
|
||||
|
||||
**Opção B — Nextcloud snap** — mais rápido para piloto manual.
|
||||
|
||||
---
|
||||
|
||||
## VM112 — ligação existente (sem alterar mail)
|
||||
|
||||
| Parâmetro | Valor actual |
|
||||
|-----------|--------------|
|
||||
| IP | `10.10.10.112` |
|
||||
| Carbonio LMTP | `:7025` (Desk transport) |
|
||||
| Carbonio IMAP | `:993` |
|
||||
| Carbonio SMTP | `:25` / submission |
|
||||
| Wizard API | `:8090` |
|
||||
|
||||
### Conectividade VM116 → VM112
|
||||
|
||||
| Origem | Destino | Porta | Uso |
|
||||
|--------|---------|-------|-----|
|
||||
| VM116 (Mail app users) | VM112 | 993 | IMAP SSL |
|
||||
| VM116 (Mail app users) | VM112 | 587/465 | SMTP submission |
|
||||
| VM116 (provision script) | VM112 | 8090 | Opcional — estado domínio |
|
||||
| VM112 (wizard worker) | VM116 | 443 | OCS Provisioning API |
|
||||
|
||||
**Firewall pfSense:** permitir LAN `10.10.10.116 → 10.10.10.112:993,587,8090`.
|
||||
|
||||
---
|
||||
|
||||
## CT114 — Traefik / SNI
|
||||
|
||||
### Novo router `files.{domain}`
|
||||
|
||||
Seguir padrão Spec 017 (`mail.{domain}`):
|
||||
|
||||
1. Adicionar `files.{dom}` em `sni_vm112.lst` → **renomear** para `sni_tenant_apps.lst` (mail + files)
|
||||
2. Router Traefik `files-*-Router` → backend `http://10.10.10.116:443`
|
||||
3. Certbot SAN multi-dom ou cert por domínio (mesmo fluxo mail)
|
||||
|
||||
### Router hub
|
||||
|
||||
```yaml
|
||||
# cloud.ligbox.com.br → VM116
|
||||
http:
|
||||
routers:
|
||||
nextcloud-hub:
|
||||
rule: Host(`cloud.ligbox.com.br`)
|
||||
service: nextcloud-vm116
|
||||
tls:
|
||||
certResolver: letsencrypt
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## DNS Cloudflare (por tenant)
|
||||
|
||||
| Registo | Tipo | Valor |
|
||||
|---------|------|-------|
|
||||
| `files.{dominio}` | A | IP público (via Traefik) |
|
||||
| `_carddav._tcp.{dominio}` | SRV | opcional — CalDAV/CardDAV NC |
|
||||
|
||||
**Nota:** MX continua `mail.{dominio}` → Carbonio. Nextcloud **não** recebe mail directo.
|
||||
|
||||
---
|
||||
|
||||
## Storage — fase 2 (Carbonio S3 offload)
|
||||
|
||||
```
|
||||
VM112 Carbonio
|
||||
└── volume secondary (Custom S3)
|
||||
└── MinIO VM116 :9000
|
||||
bucket: carbonio-archive-{tenant}
|
||||
```
|
||||
|
||||
Credenciais S3 em `/opt/zextras/conf/` (VM112) — **nunca** no repo Git.
|
||||
|
||||
---
|
||||
|
||||
## Backup & DR
|
||||
|
||||
| Componente | Método | Frequência |
|
||||
|------------|--------|------------|
|
||||
| VM116 snapshot | Proxmox | diário |
|
||||
| Nextcloud data | `occ files:scan` + rsync/borg | diário |
|
||||
| PostgreSQL NC | `pg_dump` | diário |
|
||||
| MinIO (fase 2) | replica ou snapshot volume | diário |
|
||||
|
||||
**RPO alvo:** 24 h · **RTO alvo:** 4 h (restaurar VM116 + re-ligar Traefik).
|
||||
|
||||
---
|
||||
|
||||
## Monitorização
|
||||
|
||||
| Métrica | Alerta |
|
||||
|---------|--------|
|
||||
| Disco VM116 > 80% | ops_lead email |
|
||||
| Disco VM112 > 85% | crítico — revisar quotas hot |
|
||||
| Nextcloud status.php != 200 | Infra stack health Desk |
|
||||
| IMAP latency VM112 > 2s | investigar carga Mail app |
|
||||
|
||||
---
|
||||
|
||||
## Decisão pendente (Roger)
|
||||
|
||||
| Opção | Prós | Contras |
|
||||
|-------|------|---------|
|
||||
| **VM116 dedicada** (proposto) | Disco isolado, escala independente | Nova VM para gerir |
|
||||
| Nextcloud na VM112 | Menos VMs | Piora problema de disco |
|
||||
| Nextcloud na VM123 | Já tem stack Docker | Mistura finance/hosting com mail |
|
||||
|
||||
**Recomendação Spec 034:** VM116 dedicada.
|
||||
126
specs/034-nextcloud-carbonio-vm112-integration/quickstart.md
Normal file
126
specs/034-nextcloud-carbonio-vm112-integration/quickstart.md
Normal file
|
|
@ -0,0 +1,126 @@
|
|||
# Quickstart — Piloto Nextcloud + Carbonio VM112 (Spec 034)
|
||||
|
||||
**Público:** ops_lead, super_admin
|
||||
**Pré-requisito:** VM116 provisionada · Carbonio VM112 operacional · acesso CT114
|
||||
|
||||
---
|
||||
|
||||
## Regra operacional
|
||||
|
||||
> **Carbonio continua MTA.** Nextcloud **não** altera MX/DKIM.
|
||||
> Piloto começa com **1 domínio de teste** (não `ligbox.com.br` produção até validar).
|
||||
|
||||
---
|
||||
|
||||
## 1. Verificar Carbonio VM112
|
||||
|
||||
```bash
|
||||
ssh root@10.10.10.112 -p 2512 # via Proxmox jump se necessário
|
||||
|
||||
# Conta teste
|
||||
zmprov ga admin@DOMINIO-TESTE.com zimbraMailQuota 2>/dev/null | head -5
|
||||
|
||||
# IMAP local
|
||||
openssl s_client -connect 127.0.0.1:993 -quiet </dev/null 2>&1 | head -3
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 2. Instalar Nextcloud VM116 (piloto)
|
||||
|
||||
```bash
|
||||
ssh root@10.10.10.116
|
||||
|
||||
# Após clone repo + deploy/vm116-nextcloud/
|
||||
cd /opt/ligbox-ops-platform/deploy/vm116-nextcloud
|
||||
cp .env.example .env
|
||||
# Editar: NC_DOMAIN=cloud.ligbox.com.br, ADMIN_PASS=***
|
||||
docker compose up -d
|
||||
|
||||
docker exec -u www-data nextcloud occ status
|
||||
```
|
||||
|
||||
URL piloto: `https://cloud.ligbox.com.br`
|
||||
|
||||
---
|
||||
|
||||
## 3. Criar utilizador Nextcloud (= e-mail Carbonio)
|
||||
|
||||
```bash
|
||||
docker exec -u www-data nextcloud occ user:add \
|
||||
--display-name="Admin Teste" \
|
||||
--password-from-env \
|
||||
admin@DOMINIO-TESTE.com
|
||||
|
||||
docker exec -u www-data nextcloud occ user:setting \
|
||||
admin@DOMINIO-TESTE.com files quota 25GB
|
||||
```
|
||||
|
||||
**Importante:** usar o **mesmo e-mail** que existe no Carbonio.
|
||||
|
||||
---
|
||||
|
||||
## 4. Configurar Mail app (Nextcloud → Carbonio)
|
||||
|
||||
No browser, login Nextcloud como `admin@DOMINIO-TESTE.com`:
|
||||
|
||||
1. Activar app **Mail**
|
||||
2. Nova conta:
|
||||
- E-mail: `admin@DOMINIO-TESTE.com`
|
||||
- IMAP: `mail.DOMINIO-TESTE.com` · port **993** · SSL
|
||||
- SMTP: `mail.DOMINIO-TESTE.com` · port **587** · STARTTLS
|
||||
- Utilizador/senha: credenciais Carbonio
|
||||
|
||||
3. Enviar e-mail teste → verificar recepção no webmail Carbonio.
|
||||
|
||||
---
|
||||
|
||||
## 5. Teste capacidade (Files vs Mail)
|
||||
|
||||
```bash
|
||||
# Upload ficheiro 50 MB no Files — deve funcionar
|
||||
# Verificar quota Carbonio não aumentou:
|
||||
ssh root@10.10.10.112 "zmprov gq admin@DOMINIO-TESTE.com"
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 6. Traefik — files.{dominio} (opcional piloto)
|
||||
|
||||
No CT114, seguir template Spec 017 para `mail.{dom}` substituindo backend por `10.10.10.116:443`.
|
||||
|
||||
Teste:
|
||||
|
||||
```bash
|
||||
curl -sI "https://files.DOMINIO-TESTE.com/status.php" | head -5
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 7. Desk — health (após implementação API)
|
||||
|
||||
```bash
|
||||
curl -s -u root:805353 \
|
||||
"http://10.10.10.122:8180/api/v1/nextcloud/health" | jq .
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Checklist piloto OK
|
||||
|
||||
- [ ] Nextcloud status 200
|
||||
- [ ] User NC criado com e-mail `@dominio`
|
||||
- [ ] Mail app lê Inbox Carbonio
|
||||
- [ ] Envio SMTP funciona
|
||||
- [ ] Upload 50 MB em Files OK
|
||||
- [ ] Quota Carbonio inalterada após upload Files
|
||||
- [ ] ops_lead aprova continuar Fase 1 (wizard)
|
||||
|
||||
---
|
||||
|
||||
## Rollback piloto
|
||||
|
||||
```bash
|
||||
docker exec -u www-data nextcloud occ user:delete admin@DOMINIO-TESTE.com
|
||||
# Remover router Traefik files.{dom} se criado
|
||||
```
|
||||
320
specs/034-nextcloud-carbonio-vm112-integration/spec.md
Normal file
320
specs/034-nextcloud-carbonio-vm112-integration/spec.md
Normal file
|
|
@ -0,0 +1,320 @@
|
|||
# Spec 034 — Nextcloud + E-mail VM112 (ampliar capacidade Carbonio)
|
||||
|
||||
**Criado:** 2026-06-20
|
||||
**Solicitado por:** Roger
|
||||
**Status:** 📋 Draft — aguarda validação arquitectura
|
||||
**Prioridade:** P1 (capacidade mail tenants + produto Ligbox Mail)
|
||||
**Sistema:** VM112 (Carbonio) + **VM116** (Nextcloud — proposto) + CT114 (Traefik) + Desk VM122
|
||||
**Relacionado:** Spec **017** (purge domínio) · **022** (Carbonio release) · **013/019** (migração mail) · **027** (RBAC) · **033** (Infra stack health)
|
||||
|
||||
---
|
||||
|
||||
## Resumo
|
||||
|
||||
Integrar **Nextcloud Hub** ao ecossistema **Ligbox Mail (VM112)** para **ampliar a capacidade efectiva de e-mail e ficheiros** dos tenants Carbonio, sem substituir o motor de mail.
|
||||
|
||||
**Problema:** a VM112 tem disco limitado (~96 GB) e o Carbonio CE guarda mail + blobs localmente. Quotas altas por domínio esgotam o volume rapidamente.
|
||||
|
||||
**Solução proposta:** modelo **híbrido em camadas**:
|
||||
|
||||
| Camada | Produto | Função | Quota típica |
|
||||
|--------|---------|--------|--------------|
|
||||
| **Hot** | Carbonio VM112 | SMTP/IMAP, webmail, calendário, contactos | 5–10 GB / caixa |
|
||||
| **Warm** | Nextcloud Files VM116 | Anexos grandes, documentos, partilha | 50–500 GB / utilizador |
|
||||
| **Cold** (fase 2) | Carbonio → S3 secundário | Arquivo IMAP antigo, blobs offload | Configurável |
|
||||
|
||||
O Carbonio **permanece autoridade** para `@dominio` (MX, DKIM, LMTP). Nextcloud **complementa** capacidade de armazenamento e UX unificada (Mail app + Files).
|
||||
|
||||
---
|
||||
|
||||
## Problema
|
||||
|
||||
### Limitações actuais (VM112)
|
||||
|
||||
| Item | Estado |
|
||||
|------|--------|
|
||||
| Disco VM112 | `/dev/sda1` ~96 GB (~20 GB usados hoje — cresce com tenants) |
|
||||
| Storage Carbonio | Volumes **locais** (Primary + Index) |
|
||||
| Quota domínio/conta | `zmprov` / Domain Admin — sem offload automático |
|
||||
| Integração nativa Nextcloud | **Inexistente** no Carbonio CE (Zextras: sem roadmap oficial) |
|
||||
| ManageSieve (4190) | **Não disponível** — filtros Nextcloud Mail não funcionam nativamente |
|
||||
|
||||
### Impacto operacional
|
||||
|
||||
1. Onboarding cria contas com quota default alta → risco de encher disco.
|
||||
2. Anexos grandes (PST import, ficheiros 25 MB+) pressionam o mesmo volume do mailstore.
|
||||
3. Clientes pedem «mais espaço de e-mail» — hoje só há aumento de quota Carbonio (mesmo disco).
|
||||
4. Purge domínio (Spec 017) remove Carbonio mas **não** limpa workspace Nextcloud (futuro).
|
||||
|
||||
---
|
||||
|
||||
## Decisões de arquitectura (propostas — Roger valida)
|
||||
|
||||
| # | Tema | Decisão proposta |
|
||||
|---|------|------------------|
|
||||
| 1 | Motor de mail | **Carbonio VM112** — inalterado como MTA/MUA principal |
|
||||
| 2 | Armazenamento expandido | **Nextcloud Hub** em VM dedicada com disco ampliado |
|
||||
| 3 | VM alvo Nextcloud | **VM116** `10.10.10.116` (nova) — 4 vCPU, 8 GB RAM, **500 GB+** disco |
|
||||
| 4 | Identidade | Conta Nextcloud = **mesmo e-mail** `@dominio` (provisionamento paralelo ao Carbonio) |
|
||||
| 5 | Autenticação | Fase 1: **senha sincronizada** no wizard · Fase 2: **OIDC/SAML** ou LDAP Carbonio |
|
||||
| 6 | URL tenant | `files.{dominio}` (SNI CT114) · hub Ligbox: `cloud.ligbox.com.br` |
|
||||
| 7 | Mail Nextcloud | App **Mail** → IMAP/SMTP Carbonio (`mail.{dominio}`) — **opcional** na UI |
|
||||
| 8 | Offload Carbonio | Fase 2: volume **S3 secundário** (MinIO na VM116) via Carbonio Storage |
|
||||
| 9 | Orquestração | Wizard VM112 API + Desk VM122 (monitorização, purge, RBAC) |
|
||||
| 10 | Produto comercial | Pacote **Ligbox Mail Plus** = Carbonio base + Nextcloud Files quota |
|
||||
|
||||
---
|
||||
|
||||
## Arquitectura
|
||||
|
||||
```mermaid
|
||||
flowchart TB
|
||||
subgraph Internet
|
||||
Users[Utilizadores / Browser]
|
||||
CF[Cloudflare DNS]
|
||||
end
|
||||
|
||||
subgraph CT114["CT114 Traefik + SNI"]
|
||||
TR[Traefik :443]
|
||||
end
|
||||
|
||||
subgraph VM112["VM112 — Carbonio + Wizard"]
|
||||
WZ[Wizard API :8090]
|
||||
CB[Carbonio CE<br/>SMTP :25 · IMAP :993 · LMTP :7025]
|
||||
DA[Domain Admin]
|
||||
end
|
||||
|
||||
subgraph VM116["VM116 — Nextcloud Hub (proposto)"]
|
||||
NC[Nextcloud :443]
|
||||
NCMAIL[App Mail → IMAP Carbonio]
|
||||
NCFiles[App Files — quota ampliada]
|
||||
S3[MinIO S3 :9000<br/>fase 2]
|
||||
end
|
||||
|
||||
subgraph VM122["VM122 — Desk"]
|
||||
DS[Ops Desk API]
|
||||
end
|
||||
|
||||
Users --> CF
|
||||
CF --> TR
|
||||
TR -->|mail.{dom}| CB
|
||||
TR -->|onboard.ligbox| WZ
|
||||
TR -->|files.{dom}| NC
|
||||
NCMAIL -->|IMAP/SMTP| CB
|
||||
CB -.->|volume secundário fase 2| S3
|
||||
WZ -->|provision user| NC
|
||||
WZ -->|webhooks| DS
|
||||
DS -->|stack health / purge| NC
|
||||
DS -->|proxy status| WZ
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Modelo de capacidade (quotas)
|
||||
|
||||
### Política Ligbox Mail (default proposto)
|
||||
|
||||
| Plano | Quota Carbonio (hot) | Quota Nextcloud Files | Notas |
|
||||
|-------|----------------------|------------------------|-------|
|
||||
| **Starter** | 5 GB | 25 GB | Wizard default |
|
||||
| **Business** | 10 GB | 100 GB | FOSSBilling add-on |
|
||||
| **Enterprise** | 20 GB | 500 GB | Negociado |
|
||||
|
||||
**Regra:** quota Carbonio **sempre ≤** hot tier; crescimento comercial → Nextcloud Files, não aumento cego no mailstore local.
|
||||
|
||||
### Fluxos de offload (UX)
|
||||
|
||||
1. **Anexo grande no webmail Carbonio** — aviso «Guarde em Files» + link `files.{dominio}`.
|
||||
2. **Nextcloud Mail** — utilizador lê mail via IMAP; anexos > N MB → «Guardar no Files» (manual fase 1).
|
||||
3. **Fase 2 — Archive** — job `carbonio powerstore` move mensagens > 90 dias para volume S3; stub no IMAP.
|
||||
|
||||
---
|
||||
|
||||
## Integração VM112 (Wizard + Domain Admin)
|
||||
|
||||
### Provisionamento no onboarding
|
||||
|
||||
Após `POST /api/onboarding/account/create` (Carbonio OK):
|
||||
|
||||
| Passo | Acção |
|
||||
|-------|--------|
|
||||
| NC-1 | Criar utilizador Nextcloud via **OCS Provisioning API** |
|
||||
| NC-2 | Definir quota Files conforme plano |
|
||||
| NC-3 | Pré-configurar conta Mail app (IMAP host, SSL, e-mail) — **opcional** |
|
||||
| NC-4 | Registar `nextcloud_user_id` + `files_url` no estado do domínio |
|
||||
| NC-5 | Webhook Desk `onboarding.nextcloud.provisioned` |
|
||||
|
||||
**Feature flag wizard:** `NEXTCLOUD_INTEGRATION=0|1` (default **0** até piloto).
|
||||
|
||||
### Domain Admin (`/admin`)
|
||||
|
||||
| Funcionalidade | Descrição |
|
||||
|----------------|-----------|
|
||||
| Ver quota Carbonio + Files | Painel unificado |
|
||||
| Link «Abrir Files» | Redirect `files.{dominio}` |
|
||||
| Reset senha | Sincroniza Carbonio + Nextcloud (fase 1) |
|
||||
|
||||
---
|
||||
|
||||
## Integração Desk VM122
|
||||
|
||||
### Módulo Desk (Spec 015)
|
||||
|
||||
| Campo | Valor |
|
||||
|-------|--------|
|
||||
| `id` | `nextcloud-storage` |
|
||||
| `label` | Nextcloud Storage |
|
||||
| `default_enabled` | `false` (piloto) |
|
||||
| `nav_views` | _(vazio — tile em Serviços / Infra)_ |
|
||||
|
||||
### API Desk (novos endpoints)
|
||||
|
||||
| Método | Path | Descrição |
|
||||
|--------|------|-----------|
|
||||
| GET | `/api/v1/nextcloud/domains/{domain}/status` | Quota, users, health |
|
||||
| GET | `/api/v1/nextcloud/domains/{domain}/users` | Lista utilizadores tenant |
|
||||
| POST | `/api/v1/nextcloud/domains/{domain}/users` | Provision manual (ops) |
|
||||
| DELETE | `/api/v1/nextcloud/domains/{domain}/users/{email}` | Remover user |
|
||||
| GET | `/api/v1/nextcloud/health` | Probe VM116 |
|
||||
|
||||
Ver contrato: [contracts/nextcloud-provisioning-api.md](./contracts/nextcloud-provisioning-api.md).
|
||||
|
||||
### Stack health (Spec 033)
|
||||
|
||||
Adicionar probe VM116 em `stack_health.py`:
|
||||
|
||||
| Serviço | URL | VM |
|
||||
|---------|-----|-----|
|
||||
| Nextcloud Hub | `https://cloud.ligbox.com.br/status.php` | 116 |
|
||||
| Nextcloud OCS | `https://10.10.10.116/ocs/v2.php/cloud/capabilities` | 116 |
|
||||
|
||||
### Purge domínio (extensão Spec 017)
|
||||
|
||||
Ordem **após** purge Carbonio:
|
||||
|
||||
1. Listar users Nextcloud com e-mail `@dominio`
|
||||
2. Apagar utilizadores via OCS API
|
||||
3. Apagar grupo tenant (se existir)
|
||||
4. Registar passo na timeline purge
|
||||
|
||||
---
|
||||
|
||||
## Infraestrutura VM116
|
||||
|
||||
Detalhe: [infrastructure.md](./infrastructure.md)
|
||||
|
||||
| Item | Valor proposto |
|
||||
|------|----------------|
|
||||
| VMID | 116 |
|
||||
| IP LAN | `10.10.10.116/24` |
|
||||
| SSH WAN | `95.216.14.146:2516` (reservar no pfSense) |
|
||||
| Hostname | `cloud.ligbox.com.br` |
|
||||
| SO | Ubuntu 24.04 LTS |
|
||||
| Stack | Nextcloud 30+ (snap ou Docker), PostgreSQL, Redis |
|
||||
| TLS | Let's Encrypt via Traefik CT114 |
|
||||
| Backup | Proxmox snapshot + Nextcloud `occ` backup diário |
|
||||
|
||||
---
|
||||
|
||||
## RBAC (Spec 027)
|
||||
|
||||
| Acção | Perfis |
|
||||
|-------|--------|
|
||||
| Ver status Nextcloud (Desk) | `super_admin`, `ops_lead`, `technician` |
|
||||
| Provision manual user | `super_admin`, `ops_lead` |
|
||||
| Alterar quotas tenant | `super_admin`, `ops_lead` |
|
||||
| Purge users Nextcloud | `super_admin`, `ops_lead` (com purge domínio) |
|
||||
| Cliente Domain Admin | Gerente domínio — só o seu tenant |
|
||||
|
||||
Binding software (matriz RBAC):
|
||||
|
||||
```yaml
|
||||
software_group: vm112-nextcloud
|
||||
host: VM116
|
||||
roles:
|
||||
nextcloud_admin: [super_admin, ops_lead]
|
||||
nextcloud_read: [technician, noc]
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Fases de implementação
|
||||
|
||||
### Fase 0 — Piloto infra (sem wizard)
|
||||
|
||||
- [ ] Provisionar VM116 + Nextcloud + TLS
|
||||
- [ ] Conta manual `admin@ligbox.com.br` + teste Mail app → Carbonio VM112
|
||||
- [ ] Documentar quotas e limites IMAP
|
||||
|
||||
### Fase 1 — Provisionamento wizard + Desk read-only
|
||||
|
||||
- [ ] API Nextcloud provisioning no wizard (flag OFF default)
|
||||
- [ ] Endpoints Desk status/health
|
||||
- [ ] Traefik `files.{dom}` template (CT114)
|
||||
- [ ] Stack health card Infra
|
||||
|
||||
### Fase 2 — Purge + quotas comerciais
|
||||
|
||||
- [ ] Purge Nextcloud no fluxo Spec 017
|
||||
- [ ] FOSSBilling add-on «Mail Plus»
|
||||
- [ ] Domain Admin painel unificado quota
|
||||
|
||||
### Fase 3 — Offload S3 Carbonio
|
||||
|
||||
- [ ] MinIO VM116
|
||||
- [ ] Volume secundário Carbonio → S3
|
||||
- [ ] Política retenção / archive IMAP
|
||||
|
||||
---
|
||||
|
||||
## Fora de escopo (v1)
|
||||
|
||||
- Substituir webmail Carbonio por Nextcloud Mail como única UI
|
||||
- ManageSieve / filtros Nextcloud nativos (requer bridge custom — backlog)
|
||||
- Integração nativa Carbonio Files ↔ Nextcloud (inexistente no CE)
|
||||
- Nextcloud Talk / Office (avaliar Spec separada)
|
||||
- Multi-tenant Nextcloud federado (um hub Ligbox basta no piloto)
|
||||
|
||||
---
|
||||
|
||||
## Riscos e mitigações
|
||||
|
||||
| Risco | Mitigação |
|
||||
|-------|-----------|
|
||||
| Duplicar senhas (Carbonio + NC) | Fase 2 OIDC; rotação via Domain Admin |
|
||||
| IMAP Nextcloud Mail sobrecarrega VM112 | Rate limit; quota hot baixa; monitor CPU |
|
||||
| Purge incompleto (dados órfãos NC) | Passo obrigatório Spec 017 + audit |
|
||||
| Disco VM112 enche antes do piloto | Alertas quota 80% + política quota default 5 GB |
|
||||
| S3 MinIO single point | Replicação fase 3; backup S3 |
|
||||
|
||||
---
|
||||
|
||||
## Critérios de aceitação (Fase 1)
|
||||
|
||||
1. VM116 Nextcloud acessível em `https://cloud.ligbox.com.br` com TLS válido.
|
||||
2. Utilizador `admin@ligbox.com.br` lê/envia mail via Nextcloud Mail → Carbonio VM112.
|
||||
3. Wizard com flag ON cria user Nextcloud após conta Carbonio.
|
||||
4. Desk exibe quota Carbonio + Nextcloud no tile domínio (read-only).
|
||||
5. Documentação quickstart validada por ops_lead.
|
||||
|
||||
---
|
||||
|
||||
## Documentos relacionados
|
||||
|
||||
| Documento | Conteúdo |
|
||||
|-----------|----------|
|
||||
| [infrastructure.md](./infrastructure.md) | VM116, rede, Traefik, disco |
|
||||
| [quickstart.md](./quickstart.md) | Piloto manual ops |
|
||||
| [tasks.md](./tasks.md) | Checklist implementação |
|
||||
| [contracts/nextcloud-provisioning-api.md](./contracts/nextcloud-provisioning-api.md) | OCS + Desk API |
|
||||
| `docs/EMAIL_LIGBOX_VM112.md` | Arquitectura mail actual |
|
||||
| `docs/vms/VM112.md` | Ficha VM112 |
|
||||
|
||||
---
|
||||
|
||||
## Referências externas
|
||||
|
||||
- [Carbonio CE Storage](https://docs.zextras.com/carbonio-ce/html/adminpanel/storage.html)
|
||||
- [Carbonio S3 volumes](https://docs.zextras.com/carbonio/html/admincli/storages.html)
|
||||
- [Nextcloud OCS Provisioning API](https://docs.nextcloud.com/server/latest/admin_manual/configuration_user/user_provisioning_api.html)
|
||||
- [Zextras Forum — Nextcloud integration](https://community.zextras.com/forum/carbonio-general-thread/nextcloud-for-carbonio-ce/) — sem integração nativa CE
|
||||
47
specs/034-nextcloud-carbonio-vm112-integration/tasks.md
Normal file
47
specs/034-nextcloud-carbonio-vm112-integration/tasks.md
Normal file
|
|
@ -0,0 +1,47 @@
|
|||
# Spec 034 — Tasks
|
||||
|
||||
**Status:** Draft · **Início:** 2026-06-20
|
||||
|
||||
---
|
||||
|
||||
## Fase 0 — Piloto infra
|
||||
|
||||
- [ ] Roger aprovar VM116 (recursos Proxmox + porta SSH 2516)
|
||||
- [ ] Criar VM116 Ubuntu 24.04 · 500 GB disco
|
||||
- [ ] `deploy/vm116-nextcloud/` — docker-compose + scripts
|
||||
- [ ] TLS `cloud.ligbox.com.br` via Traefik CT114
|
||||
- [ ] Teste Mail app → Carbonio (domínio teste)
|
||||
- [ ] Documentar resultados no quickstart
|
||||
|
||||
## Fase 1 — Wizard + Desk
|
||||
|
||||
- [ ] `NEXTCLOUD_API_URL` + credenciais admin OCS (secrets VM112)
|
||||
- [ ] Serviço wizard `nextcloud_provision.py`
|
||||
- [ ] Hook pós `account/create` (flag `NEXTCLOUD_INTEGRATION`)
|
||||
- [ ] Webhook Desk `onboarding.nextcloud.provisioned`
|
||||
- [ ] API Desk: `/api/v1/nextcloud/health`, `.../domains/{domain}/status`
|
||||
- [ ] Stack health VM116 em `stack_health.py` (Spec 033)
|
||||
- [ ] Traefik template `files.{domain}` (CT114)
|
||||
- [ ] Módulo Desk `nextcloud-storage` (Spec 015)
|
||||
|
||||
## Fase 2 — Operações
|
||||
|
||||
- [ ] Extensão purge Spec 017 — apagar users Nextcloud
|
||||
- [ ] Domain Admin — painel quota unificado
|
||||
- [ ] FOSSBilling produto «Ligbox Mail Plus»
|
||||
- [ ] Alertas disco VM112/VM116
|
||||
|
||||
## Fase 3 — Offload S3
|
||||
|
||||
- [ ] MinIO VM116
|
||||
- [ ] Volume secundário Carbonio → S3
|
||||
- [ ] Política archive + runbook ops
|
||||
|
||||
## Documentação
|
||||
|
||||
- [x] Spec 034 `spec.md`
|
||||
- [x] `infrastructure.md`
|
||||
- [x] `quickstart.md`
|
||||
- [x] `contracts/nextcloud-provisioning-api.md`
|
||||
- [ ] Actualizar `docs/vms/README.md` + `VM112.md`
|
||||
- [ ] Publicar no Spec Hub Portal (Spec 031)
|
||||
Loading…
Reference in a new issue