feat: runtime config via DB — ganti VITE_URL_API_DESA_PLUS dengan proxy

- Tambah model AppConfig (key-value) ke schema + migration
- Tambah GET/PUT /api/admin/config (DEVELOPER only)
- Tambah proxy /api/proxy/desa-plus/* yang baca URL dari DB
- Hapus VITE_URL_API_DESA_PLUS dari frontend, ganti semua URL desa-plus ke relative proxy path
- Aktifkan Settings tab di /dev dengan UI untuk set URL_API_DESA_PLUS

URL desa-plus kini bisa diubah via /dev → Settings tanpa rebuild image.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
2026-04-29 15:47:21 +08:00
parent b63117694b
commit ccc43e0c96
6 changed files with 197 additions and 31 deletions

View File

@@ -1,30 +1,30 @@
export const API_BASE_URL = import.meta.env.VITE_URL_API_DESA_PLUS
const DESA_PLUS_PROXY = '/api/proxy/desa-plus'
export const API_URLS = {
getVillages: (page: number, search: string) =>
`${API_BASE_URL}/api/monitoring/get-villages?page=${page}&search=${encodeURIComponent(search)}`,
infoVillages: (id: string) =>
`${API_BASE_URL}/api/monitoring/info-villages?id=${id}`,
gridVillages: (id: string) =>
`${API_BASE_URL}/api/monitoring/grid-villages?id=${id}`,
graphLogVillages: (id: string, time: string) =>
`${API_BASE_URL}/api/monitoring/graph-log-villages?id=${id}&time=${time}`,
getUsers: (page: number, search: string) =>
`${API_BASE_URL}/api/monitoring/user?page=${page}&search=${encodeURIComponent(search)}`,
getLogsAllVillages: (page: number, search: string) =>
`${API_BASE_URL}/api/monitoring/log-all-villages?page=${page}&search=${encodeURIComponent(search)}`,
getGridOverview: () => `${API_BASE_URL}/api/monitoring/grid-overview`,
getDailyActivity: () => `${API_BASE_URL}/api/monitoring/daily-activity`,
getComparisonActivity: () => `${API_BASE_URL}/api/monitoring/comparison-activity`,
postVersionUpdate: () => `${API_BASE_URL}/api/monitoring/version-update`,
createVillages: () => `${API_BASE_URL}/api/monitoring/create-villages`,
createUser: () => `${API_BASE_URL}/api/monitoring/create-user`,
listRole: () => `${API_BASE_URL}/api/monitoring/list-userrole-villages`,
listGroup: (id: string) => `${API_BASE_URL}/api/monitoring/list-group-villages?id=${id}`,
listPosition: (id: string) => `${API_BASE_URL}/api/monitoring/list-position-villages?id=${id}`,
editUser: () => `${API_BASE_URL}/api/monitoring/edit-user`,
updateStatusVillages: () => `${API_BASE_URL}/api/monitoring/update-status-villages`,
editVillages: () => `${API_BASE_URL}/api/monitoring/edit-villages`,
getVillages: (page: number, search: string) =>
`${DESA_PLUS_PROXY}/api/monitoring/get-villages?page=${page}&search=${encodeURIComponent(search)}`,
infoVillages: (id: string) =>
`${DESA_PLUS_PROXY}/api/monitoring/info-villages?id=${id}`,
gridVillages: (id: string) =>
`${DESA_PLUS_PROXY}/api/monitoring/grid-villages?id=${id}`,
graphLogVillages: (id: string, time: string) =>
`${DESA_PLUS_PROXY}/api/monitoring/graph-log-villages?id=${id}&time=${time}`,
getUsers: (page: number, search: string) =>
`${DESA_PLUS_PROXY}/api/monitoring/user?page=${page}&search=${encodeURIComponent(search)}`,
getLogsAllVillages: (page: number, search: string) =>
`${DESA_PLUS_PROXY}/api/monitoring/log-all-villages?page=${page}&search=${encodeURIComponent(search)}`,
getGridOverview: () => `${DESA_PLUS_PROXY}/api/monitoring/grid-overview`,
getDailyActivity: () => `${DESA_PLUS_PROXY}/api/monitoring/daily-activity`,
getComparisonActivity: () => `${DESA_PLUS_PROXY}/api/monitoring/comparison-activity`,
postVersionUpdate: () => `${DESA_PLUS_PROXY}/api/monitoring/version-update`,
createVillages: () => `${DESA_PLUS_PROXY}/api/monitoring/create-villages`,
createUser: () => `${DESA_PLUS_PROXY}/api/monitoring/create-user`,
listRole: () => `${DESA_PLUS_PROXY}/api/monitoring/list-userrole-villages`,
listGroup: (id: string) => `${DESA_PLUS_PROXY}/api/monitoring/list-group-villages?id=${id}`,
listPosition: (id: string) => `${DESA_PLUS_PROXY}/api/monitoring/list-position-villages?id=${id}`,
editUser: () => `${DESA_PLUS_PROXY}/api/monitoring/edit-user`,
updateStatusVillages: () => `${DESA_PLUS_PROXY}/api/monitoring/update-status-villages`,
editVillages: () => `${DESA_PLUS_PROXY}/api/monitoring/edit-villages`,
getGlobalLogs: (page: number, search: string, type: string, userId: string, dateFrom?: string, dateTo?: string) => {
const params = new URLSearchParams({ page: String(page), search, type, userId })
if (dateFrom) params.set('dateFrom', dateFrom)