feat: implement MC domain filter proxy, API, dashboard
- proxy: asyncio TCP proxy with handshake parser, domain whitelist, transparent backend tunneling, SQLite logging, mtime hot reload - api: FastAPI routes for config/domains/logs/status + restart trigger - frontend: React + Vite NPM-style dashboard (dashboard/domains/logs/settings) - nginx: reverse proxy for /api -> api:8000 and / -> frontend:3000 - docker-compose: full stack with shared data volume - replace spec mc-domain-filter.md with README.md
This commit is contained in:
36
frontend/src/api.js
Normal file
36
frontend/src/api.js
Normal file
@@ -0,0 +1,36 @@
|
||||
const base = '/api'
|
||||
|
||||
async function req(path, opts = {}) {
|
||||
const res = await fetch(base + path, {
|
||||
headers: { 'Content-Type': 'application/json' },
|
||||
...opts,
|
||||
})
|
||||
if (!res.ok) {
|
||||
const text = await res.text().catch(() => '')
|
||||
throw new Error(`${res.status}: ${text || res.statusText}`)
|
||||
}
|
||||
if (res.status === 204) return null
|
||||
return res.json()
|
||||
}
|
||||
|
||||
export const api = {
|
||||
status: () => req('/status'),
|
||||
config: () => req('/config'),
|
||||
putConfig: (cfg) => req('/config', { method: 'PUT', body: JSON.stringify(cfg) }),
|
||||
domains: () => req('/domains'),
|
||||
addDomain: (d) => req('/domains', { method: 'POST', body: JSON.stringify(d) }),
|
||||
deleteDomain: (name) =>
|
||||
req(`/domains/${encodeURIComponent(name)}`, { method: 'DELETE' }),
|
||||
patchDomain: (name, body) =>
|
||||
req(`/domains/${encodeURIComponent(name)}`, {
|
||||
method: 'PATCH',
|
||||
body: JSON.stringify(body),
|
||||
}),
|
||||
logs: (params = {}) => {
|
||||
const q = new URLSearchParams(
|
||||
Object.fromEntries(Object.entries(params).filter(([, v]) => v !== '' && v != null))
|
||||
).toString()
|
||||
return req('/logs' + (q ? `?${q}` : ''))
|
||||
},
|
||||
restart: () => req('/proxy/restart', { method: 'POST' }),
|
||||
}
|
||||
Reference in New Issue
Block a user