# WorkPulse — Logout, sesi & kontrak BE (Gin)

Dokumen ini melengkapi `docs/BE_WORKPULSE_GIN_REALTIME.md` untuk perilaku **logout** dan sesi agar selaras dengan frontend setelah perbaikan alur auth di Nuxt.

---

## 1. Masalah yang sudah diperbaiki di FE (bukan bug BE)

Gejala: setelah klik **Logout**, layar menempel pada teks **"Redirecting to login..."** dan form login baru muncul setelah **refresh manual**.

**Penyebab teknis (FE):**

1. State `isAuthenticated` sempat tidak selaras dengan URL `/login` dalam satu frame navigasi (race `signOut` + `navigateTo`).
2. Cabang layout `v-else` ("Redirecting...") aktif bila `!isLoginRoute && !authenticated` — jika Vue Router sesaat tidak menganggap path sebagai `/login` (hydration / transisi), layar bisa **macet** meski bilah alamat sudah `/login`.
3. Solusi final: **`middleware/auth.global.ts`** memaksa redirect di klien sebelum render bermasalah, dan layout hanya dua mode: **authenticated → shell** atau **else → `<slot />` penuh** (tanpa placeholder "Redirecting...").

**Perbaikan FE (folder `FE`):**

- `middleware/auth.global.ts` — guard klien: anonim → `/login`, sudah login di `/login` → `/`.
- `layouts/default.vue` — dua cabang saja (shell vs slot penuh); tidak ada lagi teks "Redirecting to login...".
- `composables/useAuth.ts` — `logout()` memanggil `POST {api}/api/v1/auth/logout` dengan **timeout 8s + abort**, lalu selalu bersihkan state lokal + `navigateTo('/login')` (tidak menggantung pada BE).
- `composables/useWorkpulseRealtime.ts` — WebSocket `wss://…` + path `workpulseWsPath` saat `isAuthenticated` (putus saat logout).
- `nuxt.config.ts` — `runtimeConfig.public.workpulseApiBase` / `workpulseWsPath` (override lewat env `NUXT_PUBLIC_*`).

### 1.1 CORS & cookie (BE wajib selaras)

- Origin FE: `https://work.rycroftapparel.com` (dan dev) harus diizinkan di Gin (`Access-Control-Allow-Origin`, methods, headers `Authorization`).
- Jika `credentials: 'include'` dari FE: `Access-Control-Allow-Credentials: true` dan origin **bukan** `*`.
- Cookie cross-subdomain: set `WORKPULSE_COOKIE_DOMAIN` sesuai kebijakan (mis. `.rycroftapparel.com`).

Backend **tidak** menjadi penyebab layar "Redirecting to login..." macet; itu murni alur layout/rute FE. Panggilan `POST /api/v1/auth/logout` di FE bersifat **best-effort** (timeout); kegagalan jaringan tidak memblokir logout lokal.

---

### 2.1 Logout berbasis cookie (disarankan)

| Method | Path | Perilaku |
|--------|------|----------|
| `POST` | `/api/v1/auth/logout` | Body kosong atau `{ "everywhere": false }`. Hapus / blacklist **refresh token** di DB; **Set-Cookie** untuk `access_token` / `refresh_token` **Max-Age=0** (path & domain sama seperti saat login). |

Response `204 No Content` atau `200` dengan `{ "ok": true }`.

### 2.2 Logout berbasis Bearer saja

Jika hanya header `Authorization: Bearer <access>`:

- `POST /api/v1/auth/logout` — invalidasi refresh token di server; klien **wajib** membuang access token dari memori / `localStorage` (FE sudah lewat `logout()`).

### 2.3 WebSocket / realtime

Setelah logout berhasil:

- Tutup koneksi WS dari sisi klien (FE).
- Server: saat refresh token di-revoke, **broadcast** atau **disconnect** sesi socket yang terikat `user_id` tersebut (channel `user:{id}`).

---

## 3. Urutan panggilan FE → BE (nanti)

1. (Opsional) `POST /api/v1/auth/logout` dengan `credentials: 'include'` jika pakai cookie.
2. Panggil `logout()` di composable (clear `localStorage` flag demo + navigasi).
3. Jika BE mengembalikan error jaringan, FE tetap boleh memanggil `logout()` lokal agar pengguna tidak terkunci di shell.

---

## 4. HTTPS dan cookie

Jika nanti cookie `Secure` dipakai, origin FE harus **HTTPS** (`https://work.rycroftapparel.com`). API `https://apiwork.rycroftapparel.com` harus mengatur:

- `SameSite=None; Secure` hanya jika cross-site cookie memang diperlukan; untuk subdomain sama parent (`*.rycroftapparel.com`) konsultasikan opsi `SameSite=Lax` + domain cookie `.rycroftapparel.com` dengan tim infra.

---

## 5. Referensi file terkait (FE)

| File | Peran |
|------|--------|
| `composables/useAuth.ts` | `logout()`, `useState`, sinkron `localStorage` |
| `plugins/auth-init.client.ts` | Hydrasi auth sebelum layout |
| `layouts/default.vue` | Guard rute + UI shell vs login |
| `components/layout/AppSidebar.vue` | Tombol Logout |
| `components/layout/AppTopbar.vue` | Menu Logout |

---

*Dokumen: `docs/BE_WORKPULSE_LOGOUT_SESSION.md`*
