kontenhumas-be/docs/MENU_MODULE_QUICK_START.md

9.6 KiB

Quick Start Guide - Menu Module Access System

🚀 Langkah-langkah Setup

1. Jalankan Migration

# Connect ke PostgreSQL dan jalankan migration
psql -U your_username -d your_database -f docs/migrations/004_add_menu_module_access_system.sql

2. Setup Data Master

a. Buat Modules untuk Artikel

INSERT INTO master_modules (name, description, path_url, action_type, status_id, is_active) VALUES
('Lihat Artikel', 'Melihat daftar dan detail artikel', '/api/articles', 'view', 1, true),
('Buat Artikel', 'Membuat artikel baru', '/api/articles', 'create', 1, true),
('Edit Artikel', 'Mengedit artikel yang ada', '/api/articles/:id', 'edit', 1, true),
('Hapus Artikel', 'Menghapus artikel', '/api/articles/:id', 'delete', 1, true),
('Approve Artikel', 'Menyetujui artikel', '/api/articles/:id/approve', 'approve', 1, true);
-- Dapatkan ID modules yang baru dibuat untuk step selanjutnya

b. Buat Menu Artikel

INSERT INTO master_menus (name, description, module_id, icon, "group", position, status_id, is_active) 
VALUES ('Artikel', 'Manajemen Artikel', 1, 'article-icon', 'Konten', 1, 1, true);
-- Dapatkan menu_id untuk step selanjutnya (misal: menu_id = 10)

c. Hubungkan Menu dengan Modules

-- Asumsikan menu_id = 10, dan module_ids = 1,2,3,4,5
INSERT INTO menu_modules (menu_id, module_id, position, is_active) VALUES
(10, 1, 1, true),  -- Lihat
(10, 2, 2, true),  -- Buat
(10, 3, 3, true),  -- Edit
(10, 4, 4, true),  -- Hapus
(10, 5, 5, true);  -- Approve

d. Berikan Akses ke User Levels

-- Admin Pusat (user_level_id = 1) - Full Access
INSERT INTO user_level_module_accesses (user_level_id, module_id, can_access, is_active) VALUES
(1, 1, true, true),  -- Lihat
(1, 2, true, true),  -- Buat
(1, 3, true, true),  -- Edit
(1, 4, true, true),  -- Hapus
(1, 5, true, true);  -- Approve

-- Editor (user_level_id = 2) - Lihat, Buat, Edit saja
INSERT INTO user_level_module_accesses (user_level_id, module_id, can_access, is_active) VALUES
(2, 1, true, true),  -- Lihat
(2, 2, true, true),  -- Buat
(2, 3, true, true);  -- Edit

-- Viewer (user_level_id = 3) - Lihat saja
INSERT INTO user_level_module_accesses (user_level_id, module_id, can_access, is_active) VALUES
(3, 1, true, true);  -- Lihat

3. Implementasi di Code

a. Tambahkan Routes dengan Middleware

Buat file baru atau update: app/router/article.routes.go

package router

import (
    "netidhub-saas-be/app/database"
    "netidhub-saas-be/app/middleware"
    "netidhub-saas-be/app/module/articles/controller"
    
    "github.com/gofiber/fiber/v2"
)

func SetupArticleRoutes(app *fiber.App, db *database.Database, ctrl controller.ArticleController) {
    // Initialize middlewares
    authMw := middleware.NewUserMiddleware(db)
    moduleAccessMw := middleware.NewModuleAccessMiddleware(db)
    
    // Article routes group
    articles := app.Group("/api/articles")
    
    // GET /api/articles - View (module_id = 1)
    articles.Get("/", 
        authMw.ValidateToken(),
        moduleAccessMw.CheckModuleAccess(uint(1)),
        ctrl.GetAll,
    )
    
    // GET /api/articles/:id - View detail (module_id = 1)
    articles.Get("/:id", 
        authMw.ValidateToken(),
        moduleAccessMw.CheckModuleAccess(uint(1)),
        ctrl.GetOne,
    )
    
    // POST /api/articles - Create (module_id = 2)
    articles.Post("/", 
        authMw.ValidateToken(),
        moduleAccessMw.CheckModuleAccess(uint(2)),
        ctrl.Create,
    )
    
    // PUT /api/articles/:id - Edit (module_id = 3)
    articles.Put("/:id", 
        authMw.ValidateToken(),
        moduleAccessMw.CheckModuleAccess(uint(3)),
        ctrl.Update,
    )
    
    // DELETE /api/articles/:id - Delete (module_id = 4)
    articles.Delete("/:id", 
        authMw.ValidateToken(),
        moduleAccessMw.CheckModuleAccess(uint(4)),
        ctrl.Delete,
    )
    
    // POST /api/articles/:id/approve - Approve (module_id = 5)
    articles.Post("/:id/approve", 
        authMw.ValidateToken(),
        moduleAccessMw.CheckModuleAccess(uint(5)),
        ctrl.Approve,
    )
}

b. Register Routes di Main Router

Update app/router/api.go:

// Import article routes
import (
    articleController "netidhub-saas-be/app/module/articles/controller"
)

// Di dalam fungsi RegisterRoutes
func RegisterRoutes(app *fiber.App, db *database.Database) {
    // ... existing routes ...
    
    // Article routes with module access control
    articleCtrl := articleController.NewArticleController(articleService)
    SetupArticleRoutes(app, db, articleCtrl)
}

4. Testing

Test 1: User dengan Full Access (Admin)

# Login sebagai admin (user_level_id = 1)
curl -X POST http://localhost:3000/api/auth/login \
  -H "Content-Type: application/json" \
  -d '{
    "username": "admin",
    "password": "password"
  }'

# Copy token dari response
TOKEN="your_admin_token_here"

# Test akses semua endpoint - Semua harus berhasil
curl -H "Authorization: Bearer $TOKEN" http://localhost:3000/api/articles
curl -X POST -H "Authorization: Bearer $TOKEN" http://localhost:3000/api/articles -d '{"title":"Test"}'
curl -X PUT -H "Authorization: Bearer $TOKEN" http://localhost:3000/api/articles/1 -d '{"title":"Updated"}'
curl -X DELETE -H "Authorization: Bearer $TOKEN" http://localhost:3000/api/articles/1
curl -X POST -H "Authorization: Bearer $TOKEN" http://localhost:3000/api/articles/1/approve

Test 2: User dengan Limited Access (Editor)

# Login sebagai editor (user_level_id = 2)
curl -X POST http://localhost:3000/api/auth/login \
  -H "Content-Type: application/json" \
  -d '{
    "username": "editor",
    "password": "password"
  }'

TOKEN="your_editor_token_here"

# Test akses - View, Create, Edit harus berhasil
curl -H "Authorization: Bearer $TOKEN" http://localhost:3000/api/articles  # ✓ Berhasil
curl -X POST -H "Authorization: Bearer $TOKEN" http://localhost:3000/api/articles -d '{"title":"Test"}' # ✓ Berhasil
curl -X PUT -H "Authorization: Bearer $TOKEN" http://localhost:3000/api/articles/1 -d '{"title":"Updated"}' # ✓ Berhasil

# Test akses - Delete dan Approve harus ditolak
curl -X DELETE -H "Authorization: Bearer $TOKEN" http://localhost:3000/api/articles/1  # ✗ 403 Forbidden
curl -X POST -H "Authorization: Bearer $TOKEN" http://localhost:3000/api/articles/1/approve  # ✗ 403 Forbidden

Test 3: Check Access via API

# Check apakah user level 2 bisa akses module 4 (Delete)
curl -X POST http://localhost:3000/api/user-level-module-accesses/check-access \
  -H "Authorization: Bearer $TOKEN" \
  -H "Content-Type: application/json" \
  -d '{
    "user_level_id": 2,
    "module_id": 4
  }'

# Expected response:
# {
#   "success": true,
#   "messages": ["Access check completed"],
#   "data": {
#     "has_access": false
#   }
# }

5. Manage Access via API

Berikan Akses Baru

# Berikan akses Delete ke Editor (user_level_id = 2, module_id = 4)
curl -X POST http://localhost:3000/api/user-level-module-accesses \
  -H "Authorization: Bearer $ADMIN_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{
    "user_level_id": 2,
    "module_id": 4,
    "can_access": true
  }'

Berikan Akses Multiple Modules Sekaligus

# Berikan akses ke banyak modul sekaligus (batch)
curl -X POST http://localhost:3000/api/user-level-module-accesses/batch \
  -H "Authorization: Bearer $ADMIN_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{
    "user_level_id": 4,
    "module_ids": [1, 2, 3],
    "can_access": true
  }'

Lihat Akses User Level

# Lihat semua akses untuk user_level_id = 2
curl -H "Authorization: Bearer $ADMIN_TOKEN" \
  "http://localhost:3000/api/user-level-module-accesses/user-level/2"

Cabut Akses

# Update akses menjadi false (cabut akses)
curl -X PUT http://localhost:3000/api/user-level-module-accesses/123 \
  -H "Authorization: Bearer $ADMIN_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{
    "can_access": false
  }'

📋 Checklist Implementation

  • Migration script sudah dijalankan
  • Tabel menu_modules dan user_level_module_accesses sudah ada
  • Modules sudah dibuat di master_modules
  • Menu sudah dibuat di master_menus
  • Menu-Module sudah dihubungkan di menu_modules
  • User Level Access sudah dikonfigurasi di user_level_module_accesses
  • Middleware ModuleAccessMiddleware sudah diterapkan di routes
  • Testing berhasil untuk berbagai user level
  • Dokumentasi internal sudah diupdate

🎯 Tips & Best Practices

  1. Konsisten dengan Action Type: Gunakan standar view, create, edit, delete, approve, export
  2. Batch Operations: Gunakan endpoint batch untuk setup awal atau bulk changes
  3. Soft Delete: Gunakan is_active=false daripada hard delete
  4. Audit Log: Log setiap perubahan access control untuk audit trail
  5. Default Deny: Jika tidak ada record = tidak ada akses (secure by default)

Troubleshooting

Error: "User tidak valid"

  • Pastikan middleware auth (ValidateToken()) dipanggil sebelum CheckModuleAccess()
  • Pastikan user sudah login dan token valid

Error: "Module tidak ditemukan"

  • Cek module_id yang digunakan di middleware
  • Pastikan module exists dan is_active = true

Error: "Anda tidak memiliki akses ke modul ini"

  • Cek user_level_module_accesses untuk user level tersebut
  • Pastikan can_access = true dan is_active = true

User Level tidak sesuai

  • Cek user_roles.user_level_id untuk user tersebut
  • Pastikan relasi users -> user_roles -> user_levels sudah benar

📚 Selanjutnya

Baca dokumentasi lengkap di: MENU_MODULE_ACCESS_SYSTEM.md