Send patient context once per session, not on every turn
This commit is contained in:
@@ -156,6 +156,15 @@ export function ChatPanel({
|
|||||||
// Fetched once; `getPatientProfile()` itself returns null on a 401, so an
|
// Fetched once; `getPatientProfile()` itself returns null on a 401, so an
|
||||||
// anonymous visitor never even attempts an authenticated call more than once.
|
// anonymous visitor never even attempts an authenticated call more than once.
|
||||||
const patientProfileRef = useRef<PatientProfile | null>(null);
|
const patientProfileRef = useRef<PatientProfile | null>(null);
|
||||||
|
// Which sessionId has already had the patient-context clause sent. Prepending
|
||||||
|
// on every single turn (the original design) adds "Bệnh nhân X tuổi, Y kg."
|
||||||
|
// noise to queries that have nothing to do with dosing/patient-specific
|
||||||
|
// context — measured live: it pushed a plain ADR-listing question
|
||||||
|
// (unrelated to age/weight) from a correct answerable answer into
|
||||||
|
// evidence_insufficient. `rag/understanding.py`'s multi-turn merge already
|
||||||
|
// carries a stated fact forward, so sending it once per conversation is
|
||||||
|
// enough — this only resets when `sessionId` itself changes.
|
||||||
|
const patientContextSentForSessionRef = useRef<string | null>(null);
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
getPatientProfile()
|
getPatientProfile()
|
||||||
@@ -202,16 +211,22 @@ export function ChatPanel({
|
|||||||
}, 1000);
|
}, 1000);
|
||||||
|
|
||||||
try {
|
try {
|
||||||
|
patientContextSentForSessionRef.current = sessionId;
|
||||||
const res = await fetch("/api/chat", {
|
const res = await fetch("/api/chat", {
|
||||||
method: "POST",
|
method: "POST",
|
||||||
headers: { "Content-Type": "application/json" },
|
headers: { "Content-Type": "application/json" },
|
||||||
body: JSON.stringify({
|
body: JSON.stringify({
|
||||||
// Prepends saved patient context (age/weight/renal/hepatic/allergy)
|
// Prepends saved patient context on the first turn of this session
|
||||||
// to what's actually sent, never to what's shown in the chat
|
// only — never to what's shown in the chat bubble above. The LLM
|
||||||
// bubble above — the LLM understanding step already extracts these
|
// understanding step extracts these fields from free text and
|
||||||
// fields from free text every turn (see rag/understanding.py), so
|
// carries them across the conversation (rag/understanding.py), so
|
||||||
// this reuses that exact path instead of adding a second one.
|
// repeating them on every later turn only adds noise to queries
|
||||||
content: withPatientContext(userText, patientProfileRef.current),
|
// that aren't patient-specific (measured: it broke a plain ADR
|
||||||
|
// lookup). See patientContextSentForSessionRef above.
|
||||||
|
content:
|
||||||
|
patientContextSentForSessionRef.current === sessionId
|
||||||
|
? userText
|
||||||
|
: withPatientContext(userText, patientProfileRef.current),
|
||||||
conversationId: sessionId,
|
conversationId: sessionId,
|
||||||
responseMode,
|
responseMode,
|
||||||
}),
|
}),
|
||||||
|
|||||||
Reference in New Issue
Block a user