1 changed files with 198 additions and 0 deletions
@ -0,0 +1,198 @@ |
|||||||
|
# Arsitektur Super Apps — GIS Portal (`my.gisportal.id`) |
||||||
|
|
||||||
|
> Dokumen ini adalah referensi cepat untuk AI agent / developer baru. |
||||||
|
> Update terakhir: Juni 2026 |
||||||
|
|
||||||
|
--- |
||||||
|
|
||||||
|
## Diagram Arsitektur |
||||||
|
|
||||||
|
```mermaid |
||||||
|
graph TB |
||||||
|
subgraph CLIENT["Client (Browser / PWA)"] |
||||||
|
FE["my.gisportal.id<br/>Next.js 16 + React 19<br/>TailwindCSS + shadcn/ui<br/>Zustand + React Query<br/>@ducanh2912/next-pwa"] |
||||||
|
end |
||||||
|
|
||||||
|
subgraph PROXY["Reverse Proxy (10.100.1.24)"] |
||||||
|
NGINX["Nginx<br/>(SSL termination, routing)"] |
||||||
|
end |
||||||
|
|
||||||
|
subgraph BACKEND["Backend Services (Docker @ 10.100.1.24)"] |
||||||
|
CONSOLE["geonet-console<br/>Laravel 11<br/>console.gisportal.id<br/>Port: 8091→80<br/>Auth, LDAP, Permission,<br/>User Profile, Avatar"] |
||||||
|
COLLECTOR["geonet-collector<br/>FastAPI + SQLAlchemy<br/>collector.gisportal.id<br/>agent.gisportal.id<br/>Port: 18000<br/>Asset Mgmt, GeoNet Agent"] |
||||||
|
end |
||||||
|
|
||||||
|
subgraph STORAGE["Storage"] |
||||||
|
PGCONSOLE[("PostgreSQL<br/>geonet-console DB")] |
||||||
|
PGCOLLECTOR[("PostgreSQL<br/>collector DB")] |
||||||
|
OSS["QNAP QuObjects OSS<br/>S3-compatible<br/>file.gisportal.id<br/>Bucket: super-apps<br/>Avatar, file upload"] |
||||||
|
end |
||||||
|
|
||||||
|
subgraph LDAP["Identity (10.100.1.40)"] |
||||||
|
AD["Windows Server AD<br/>LDAP / Active Directory<br/>User, Group, Auth"] |
||||||
|
end |
||||||
|
|
||||||
|
FE -->|HTTPS| NGINX |
||||||
|
NGINX -->|":8091"| CONSOLE |
||||||
|
NGINX -->|":18000"| COLLECTOR |
||||||
|
CONSOLE -->|LDAP bind| AD |
||||||
|
CONSOLE --- PGCONSOLE |
||||||
|
CONSOLE -->|S3 API| OSS |
||||||
|
COLLECTOR --- PGCOLLECTOR |
||||||
|
|
||||||
|
FE -.->|"API /api/v1/*"| CONSOLE |
||||||
|
FE -.->|"API /api/v1/assets/*"| COLLECTOR |
||||||
|
FE -.->|"Static file read"| OSS |
||||||
|
``` |
||||||
|
|
||||||
|
--- |
||||||
|
|
||||||
|
## Komponen FE yang Sudah Ada |
||||||
|
|
||||||
|
```mermaid |
||||||
|
graph LR |
||||||
|
subgraph PAGES["Pages (src/app/(app))"] |
||||||
|
P1["/dashboard"] |
||||||
|
P2["/profile"] |
||||||
|
P3["/asset-management"] |
||||||
|
P4["/admin/permissions"] |
||||||
|
P5["/(app)/layout → AuthGuard"] |
||||||
|
end |
||||||
|
|
||||||
|
subgraph COMPONENTS["Key Components"] |
||||||
|
C1["ldap-users-panel.tsx<br/>(Admin: User LDAP mgmt)"] |
||||||
|
C2["asset-detail-dialog.tsx<br/>(Asset detail + edit)"] |
||||||
|
C3["asset-detail-sheet.tsx<br/>(Asset quick view)"] |
||||||
|
C4["device-card.tsx<br/>(Profile: device info)"] |
||||||
|
C5["sidebar.tsx + bottom-nav.tsx<br/>(filtered by permission)"] |
||||||
|
end |
||||||
|
|
||||||
|
subgraph LIBS["Libs (src/lib)"] |
||||||
|
L1["api-client.ts<br/>(geonet-console API)"] |
||||||
|
L2["collector-client.ts<br/>(geonet-collector API)"] |
||||||
|
L3["ldap-client.ts<br/>(LDAP user/group ops)"] |
||||||
|
L4["permissions.ts<br/>(usePermission hooks)"] |
||||||
|
L5["auth.ts<br/>(AuthUser interface)"] |
||||||
|
L6["constants.ts<br/>(API URLs, tokens)"] |
||||||
|
end |
||||||
|
``` |
||||||
|
|
||||||
|
--- |
||||||
|
|
||||||
|
## Alur Auth & Permission |
||||||
|
|
||||||
|
```mermaid |
||||||
|
sequenceDiagram |
||||||
|
participant Browser |
||||||
|
participant NextJS as my.gisportal.id |
||||||
|
participant Console as geonet-console |
||||||
|
participant AD as Active Directory |
||||||
|
|
||||||
|
Browser->>NextJS: POST /api/login {username, password} |
||||||
|
NextJS->>Console: POST /api/v1/auth/login |
||||||
|
Console->>AD: LDAP bind (verify credentials) |
||||||
|
AD-->>Console: OK + user groups |
||||||
|
Console-->>NextJS: {token, user, groups[], permissions[]} |
||||||
|
NextJS-->>Browser: Set cookie + redirect /dashboard |
||||||
|
|
||||||
|
Browser->>NextJS: GET /dashboard |
||||||
|
NextJS->>Console: GET /api/v1/me (Bearer token) |
||||||
|
Console-->>NextJS: {username, display_name, groups[], permissions[]} |
||||||
|
NextJS-->>Browser: Render (sidebar/nav filtered by permissions) |
||||||
|
``` |
||||||
|
|
||||||
|
--- |
||||||
|
|
||||||
|
## Permission System |
||||||
|
|
||||||
|
| Permission Key | Fungsi | |
||||||
|
|---|---| |
||||||
|
| `profile.view` / `profile.edit` | Halaman profile | |
||||||
|
| `dashboard.view` | Halaman dashboard | |
||||||
|
| `asset_mgmt.view` / `asset_mgmt.manage` | Asset Management | |
||||||
|
| `cmdb.view` / `cmdb.manage` / `cmdb.assign_owner` | CMDB | |
||||||
|
| `geonet_agent.view` | GeoNet Agent | |
||||||
|
| `monitoring.view` | Monitoring | |
||||||
|
| `ticketing.view` / `ticketing.create` / `ticketing.manage` | Ticketing | |
||||||
|
| `mail.view` | Mail | |
||||||
|
| `admin.users` / `admin.groups` / `admin.permissions` | Admin panel | |
||||||
|
|
||||||
|
Default group mapping (seeder): |
||||||
|
- **Domain Admins** → semua 17 permissions |
||||||
|
- **IT-Admin** → 13 permissions |
||||||
|
- **IT-Staff** → 11 permissions |
||||||
|
- **Management** → 9 permissions |
||||||
|
- **Staff/HR** → 6 permissions |
||||||
|
|
||||||
|
--- |
||||||
|
|
||||||
|
## Environment Variables Penting |
||||||
|
|
||||||
|
### Frontend (`my-portal` / Next.js) |
||||||
|
```env |
||||||
|
NEXT_PUBLIC_API_URL=https://console.gisportal.id |
||||||
|
NEXT_PUBLIC_COLLECTOR_URL=https://collector.gisportal.id |
||||||
|
NEXT_PUBLIC_COLLECTOR_TOKEN=<token> |
||||||
|
``` |
||||||
|
|
||||||
|
### Backend `geonet-console` (Laravel, `/opt/stacks/geonet-console`) |
||||||
|
```env |
||||||
|
LDAP_HOST=10.100.1.40 |
||||||
|
LDAP_PORT=389 |
||||||
|
LDAP_BASE_DN=DC=geonet,DC=co,DC=id |
||||||
|
OSS_ENDPOINT=http://10.100.1.10:8010 |
||||||
|
OSS_BUCKET=super-apps |
||||||
|
OSS_ACCESS_KEY_ID=super-apps:0Jq7KbF31eJzd4k3LSXN |
||||||
|
``` |
||||||
|
|
||||||
|
### Backend `geonet-collector` (FastAPI, `/opt/stacks/geonetagent-collector`) |
||||||
|
```env |
||||||
|
# Source: /opt/stacks/geonetagent-collector/collector-src/ |
||||||
|
# Docker build context: ./collector-src |
||||||
|
``` |
||||||
|
|
||||||
|
--- |
||||||
|
|
||||||
|
## Lokasi Server & Deploy |
||||||
|
|
||||||
|
| Komponen | Server | Path | Deploy Command | |
||||||
|
|---|---|---|---| |
||||||
|
| FE Next.js | 10.100.1.24 | `/opt/stacks/my-portal/` | `docker compose build && up -d` | |
||||||
|
| geonet-console | 10.100.1.24 | `/opt/stacks/geonet-console/` | `docker compose up -d` | |
||||||
|
| geonet-collector | 10.100.1.24 | `/opt/stacks/geonetagent-collector/` | `docker compose build && up -d` | |
||||||
|
| Nginx config | 10.100.1.24 | `/etc/nginx/conf.d/` | `nginx -s reload` | |
||||||
|
|
||||||
|
SSH akses: `ssh -m hmac-sha1 root@10.100.1.24 -p 22` |
||||||
|
|
||||||
|
--- |
||||||
|
|
||||||
|
## Schema Key — Collector API |
||||||
|
|
||||||
|
### `CollectorAsset` (list item) |
||||||
|
```ts |
||||||
|
{ id, hostname, display_name, asset_type, status, manufacturer, model, |
||||||
|
serial_number, owner_ldap_username, owner_display_name, owner_email, |
||||||
|
last_seen_at, snapshot_count, primary_physical_mac } |
||||||
|
``` |
||||||
|
|
||||||
|
### `CollectorSnapshotSummary` (flat — root level, BUKAN nested .system) |
||||||
|
```ts |
||||||
|
{ os_name, os_version, os_build, cpu_model, ram_gb, gpu_model, |
||||||
|
last_boot_at, agent_version, |
||||||
|
system?: { form_factor, chassis_label, ... }, |
||||||
|
cpu?: { model, cores, logical_processors, max_clock_mhz }, |
||||||
|
disks?: [...], network?: [...], memory_summary?: {...} } |
||||||
|
``` |
||||||
|
|
||||||
|
--- |
||||||
|
|
||||||
|
## Microservice Yang Direncanakan (Belum Dibangun) |
||||||
|
|
||||||
|
| Service | Domain (rencana) | Status | |
||||||
|
|---|---|---| |
||||||
|
| Mailcow | `mail.gisportal.id` | 🔴 Belum | |
||||||
|
| Zammad (ticketing) | `zammad.gisportal.id` | 🔴 Belum | |
||||||
|
| geonet-content (posting) | `content.gisportal.id` | 🔴 Belum | |
||||||
|
| geonet-push (push notif VAPID) | `push.gisportal.id` | 🔴 Belum | |
||||||
|
|
||||||
|
Lihat `backlog.md` untuk detail tugas dan prioritas pengerjaan. |
||||||
Loading…
Reference in new issue