AI System Architecture

Asisten AI Situs: Batas Kemampuan dan Solusi Teknis

Asisten AI situs saat ini adalah tanya-jawab otomatis berbasis aturan (basis pengetahuan bawaan, tanpa akses rekam medis dan tanpa LLM eksternal); berikut rencana solusi teknis untuk menjelaskan pendekatan desain dan implementasi referensi.

Status saat ini:"Asisten AI" di pojok kanan bawah situs adalahTanya jawab otomatis berbasis aturan, jawaban berasal dari entri basis pengetahuan preset situs ini, tidak terhubung ke rekam medis pribadi, dan bukan nasihat medis; untuk bantuan manusia gunakan "Konsultasi Gratis" atau WhatsApp, koordinator medis akan menghubungi Anda dalam 24 jam. Berikut adalahSolusi teknis yang direncanakan, belum semuanya diluncurkan, hanya untuk menggambarkan pendekatan desain dan implementasi teknik.
Ringkasan Arsitektur

Arsitektur sistem keseluruhan

Klien
Antarmuka percakapan · Web component / mobile · multibahasa · aksesibilitas
▼
Integrasi
API gateway · HTTPS/WSS · autentikasi · rate limiting
▼
Layanan
Layanan pemrosesan pesan · manajemen sesi · routing intent · pagar kepatuhan · penyusunan konteks
▼
Cerdas
Integrasi antarmuka percakapan LLM (rencana) · RAG · Function Calling · output streaming
Modul pembuatan / perbaikan kode (asisten R&D, rencana) · kode intent & FAQ · PR perbaikan otomatis
▼
Data
Basis Pengetahuan KB / pencarian vektor
CRM / sistem tiket
Agen manusia (eskalasi)
Pembagian Modul

Tanggung jawab empat modul inti

M1

Antarmuka percakapan (frontend)

Komponen React/Vue: daftar pesan, input, indikator mengetik, chip cepat, rendering streaming, pengalih bahasa, dan aksesibilitas (aria / keyboard).

M2

Layanan pemrosesan pesan (backend)

Status sesi, routing intent, pagar kepatuhan, penyusunan konteks, pemanggilan API LLM, pemicuan eskalasi, dan audit log.

M3

Integrasi antarmuka percakapan LLM (rencana)

API layanan LLM: System Prompt kepatuhan medis, RAG, Function Calling untuk KB/CRM, balasan streaming SSE.

M4

Agen bantu R&D · generasi / perbaikan kode

Agen bantu R&D yang direncanakan: menghasilkan kode intent dan FAQ baru, memperbaiki bug, menghasilkan PR, digabung setelah review manual.

Aliran data

Rantai pemrosesan satu permintaan percakapan

  1. 1
    Pengguna mengirim

    Frontend mengumpulkan pesan dan sessionId, lalu mengirimnya terenkripsi lewat WSS/HTTPS ke /api/chat.

  2. 2
    Routing intent

    Backend mengenali intent (harga / mata / perjalanan / anggota / darurat) lewat kata kunci dan model klasifikasi, lalu menyusun konteks dan cuplikan basis pengetahuan.

  3. 3
    menghasilkan antarmuka percakapan LLM

    Backend memanggil API LLM (dengan pagar kepatuhan dan RAG), mengembalikan respons streaming SSE; jika memenuhi syarat eskalasi, dialihkan ke agen manusia.

  4. 4
    Rendering frontend

    Frontend merender balasan secara bertahap, mencatat log percakapan dan tingkat kepuasan untuk iterasi dan perbaikan mandiri berikutnya.

Jalur bantu R&D berjalan independen: pengembang mengajukan tiket (intent baru / Bug) → agen menghasilkan atau memperbaiki kode → menghasilkan Pull Request → direview dan digabung ke produksi.

Definisi antarmuka

Antarmuka kunci / kontrak data

POST /api/chat (SSE) request/response contract:

// Request
{
  "sessionId": "sess_8f3a",     // session id
  "message": "How much is a dental implant?",   // user text
  "lang": "en"                  // language
}
// Response (text/event-stream, chunked)
data: {"delta": "The indicative USD range for a single implant is ..."}
data: {"delta": "Final pricing follows the hospital."}
data: [DONE]

Kontrak pemanggilan LLM (backend → layanan model):

POST https://api.openai.com/v1/chat/completions
{
  "model": "gpt-4o-mini",
  "stream": true,
  "messages": [
    {"role":"system","content":"compliance guardrails + KB snippets"},
    {"role":"user","content":"[en] How much is a dental implant?"}
  ]
}

Kontrak tugas agen bantu R&D (backend → agen):

{
  "task": "Tambahkan follow-up FAQ untuk intent harga: apakah sudah termasuk biaya penambahan tulang",
  "file": "src/intents/price.js",
  "failing_test": null,
  "review": "required"            // harus direview manual sebelum merge
}
Kode yang bisa dijalankan

Implementasi fungsi kunci (bisa langsung dijalankan)

Berikut contoh umum, hanya untuk menggambarkan pendekatan integrasi,bukan kode produksi situs ini, dan belum dideploy.

Layanan pemrosesan pesan + integrasi LLM (Node 18+, memerlukan express dan openai):

// server.js
import express from 'express';
import OpenAI from 'openai';
const app = express();
app.use(express.json());
const openai = new OpenAI({ apiKey: process.env.OPENAI_API_KEY });

// Medical compliance guardrails: no diagnosis / prescriptions / efficacy promises
const GUARDRAILS = [
  'You are the AI assistant of a medical travel concierge site; provide objective process and credential information only.',
  'Never diagnose, prescribe, promise outcomes, or rank doctors.',
  'Actual treatment requires an in-person visit with a licensed physician; costs follow hospital pricing.',
  'For emergencies, guide users to local emergency numbers (120 in China / 911 in the US).',
  'When unsure, escalate to a human agent.'
].join(String.fromCharCode(10));

// Intent routing: keyword hit decides the class, otherwise general
const INTENTS = {
  price: /价格|比价|费用|报价|usd|\$/i,
  eye: /眼科|近视|激光|smile|lasik|icl|白内障/i,
  travel: /行程|签证|机票|酒店|陪护/i,
  member: /会员|登录|账号|保险/i,
  emergency: /紧急|急救|意外|危险/i
};
function route(text){ for(const k in INTENTS) if(INTENTS[k].test(text)) return k; return 'general'; }

app.post('/api/chat', async (req, res) => {
  const { sessionId, message, lang = 'zh-CN' } = req.body;
  const intent = route(message);
  const kb = await retrieveKB(intent, message); // vector retrieval placeholder
  const stream = await openai.chat.completions.create({
    model: 'gpt-4o-mini', stream: true,
    messages: [
      { role:'system', content: GUARDRAILS + '\nKB snippets:\n' + kb },
      { role:'user', content: '[' + lang + '] ' + message }
    ]
  });
  res.setHeader('Content-Type','text/event-stream');
  for await (const chunk of stream) {
    const t = (chunk.choices[0] && chunk.choices[0].delta && chunk.choices[0].delta.content) || '';
    if (t) res.write('data: ' + JSON.stringify({ delta: t }) + String.fromCharCode(10) + String.fromCharCode(10));
  }
  res.write('data: [DONE]' + String.fromCharCode(10) + String.fromCharCode(10));
  res.end();
});

async function retrieveKB(intent, q){ return '(Example) public credential and price-range notes for this intent.'; }
app.listen(3000, () => console.log('AI chat service on :3000'));

Pemanggilan streaming frontend (browser):

// chat-client.js
export async function sendChat(sessionId, message, lang, onDelta) {
  const res = await fetch('/api/chat', {
    method:'POST', headers:{'Content-Type':'application/json'},
    body: JSON.stringify({ sessionId, message, lang })
  });
  const reader = res.body.getReader();
  const dec = new TextDecoder();
  while (true) {
    const { done, value } = await reader.read();
    if (done) break;
    for (const line of dec.decode(value).split(String.fromCharCode(10))) {
      if (line.startsWith('data: ')) {
        const payload = line.slice(6);
        if (payload === '[DONE]') return;
        onDelta(JSON.parse(payload).delta);
      }
    }
  }
}

Modul pembuatan / perbaikan kode (asisten R&D, rencana) (Python, memerlukan openai, ganti model saat menghubungkan agen bantu R&D):

# codex_agent.py
import os, openai, sys
client = openai.OpenAI(api_key=os.environ['OPENAI_API_KEY'])

def generate_or_fix(task, file_path=None, failing_test=None):
    ctx = ''
    if file_path and os.path.exists(file_path):
        ctx += '\n# Existing file ' + file_path + '\n' + open(file_path, encoding='utf-8').read()
    if failing_test:
        ctx += '\n# Failing test output\n' + failing_test
    prompt = ('You are the code engineer for the customer-service system. Task: ' + task +
              '\nOutput only a mergeable code diff or the complete file, with a brief explanation.\n' + ctx)
    r = client.chat.completions.create(
        model='gpt-4o',  # replace model when wiring in the actual code model
        messages=[{'role':'system','content':'You are a senior frontend / Node engineer familiar with this customer-service system.'},
                  {'role':'user','content':prompt}])
    return r.choices[0].message.content

if __name__ == '__main__':
    print(generate_or_fix(sys.argv[1], sys.argv[2] if len(sys.argv) > 2 else None))
Catatan kepatuhan: kode contoh adalah demo arsitektur; balasan medis wajib ditambah pagar kepatuhan ketat dan verifikasi manusia; API Key disuntikkan lewat variabel lingkungan, jangan hardcode atau diekspos ke frontend.