feat(ai): provider OpenAI-compatible + DeepSeek, AI Telegram, self-healing dengan toggle (port upstream)
- telegramAiService/adminAiTools: dukung openai, deepseek, groq, openrouter, custom (base URL + key + model) - selfHealingService: billing vs isolir, konsistensi secret PPPoE, sesi RADIUS stale, IP ACS kosong - mikrotikService: getActivePppoeUsers, isolateCustomerPppoe, unisolateCustomerPppoe (upstream memanggil fungsi yang tidak ada) - cron 30 menit hanya jalan bila ai_self_healing_enabled=true (default off) + scan brute force MikroTik tiap 2 menit - Pengaturan: kartu AI & Self-Healing (provider, key/model, toggle, tombol Diagnosa/Perbaiki) - bot Telegram: pesan non-command dari admin dijawab AI
This commit is contained in:
@@ -2128,6 +2128,44 @@ async function getBackup(routerId = null) {
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// ─── KOMPATIBILITAS AI / SELF-HEALING ───────────────────────────────────────
|
||||
async function getActivePppoeUsers() {
|
||||
const map = await getActivePppoeSessionsMap();
|
||||
const out = [];
|
||||
map.forEach((v, user) => out.push({
|
||||
user,
|
||||
address: v.ip || '',
|
||||
uptime: v.uptime || '',
|
||||
callerId: v.callerId || '',
|
||||
routerId: v.routerId ?? null,
|
||||
routerName: v.routerName || ''
|
||||
}));
|
||||
return out;
|
||||
}
|
||||
|
||||
async function isolateCustomerPppoe(routerId, username, opts = {}) {
|
||||
const profile = String(opts.pppoeProfile || 'ISOLIR');
|
||||
await setPppoeProfile(username, profile, routerId ?? null);
|
||||
await kickPppoeUser(username, routerId ?? null).catch(() => {});
|
||||
return true;
|
||||
}
|
||||
|
||||
async function unisolateCustomerPppoe(routerId, username) {
|
||||
const name = String(username || '').trim();
|
||||
if (!name) return false;
|
||||
const row = db.prepare(`
|
||||
SELECT p.name as package_name
|
||||
FROM customers c
|
||||
LEFT JOIN packages p ON c.package_id = p.id
|
||||
WHERE c.pppoe_username = ? COLLATE NOCASE
|
||||
LIMIT 1
|
||||
`).get(name);
|
||||
const profile = row && row.package_name ? row.package_name : 'default';
|
||||
await setPppoeProfile(name, profile, routerId ?? null);
|
||||
return true;
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
checkConnection,
|
||||
getConnection,
|
||||
@@ -2149,6 +2187,9 @@ module.exports = {
|
||||
getHotspotProfiles,
|
||||
getPppoeActive,
|
||||
getActivePppoeSessionsMap,
|
||||
getActivePppoeUsers,
|
||||
isolateCustomerPppoe,
|
||||
unisolateCustomerPppoe,
|
||||
getAllActiveSessionsMap,
|
||||
getHotspotActive,
|
||||
getIpPools,
|
||||
|
||||
Reference in New Issue
Block a user