TL;DR (EN→ZH)
Start from the reasoning core, then align facts and outcomes with consent, audit, and guardrails. → 先抓「中間的論證核心」(治理與理由資料化),再回頭校對事實(頭)與結果(尾),以同意、稽核、風險欄位收斂到可落地的產品與決策。
一句話:先把「道理」變資料,再讓資料校正事實與結果。
我們用二組三軸,把倫理/法規/風險向量化(0~1)以便決策透明:
autonomy(自主):是否尊重受照者意願與能力(同意、代理授權範圍)。wellbeing(福祉):照護介入是否提升生活品質/安全/醫療遵從。dignity(尊嚴):資訊與介入是否避免污名/過度監控/不當暴露。liquidity(流動性):分享/動用是否影響短中期現金流需求。risk(風險):產品與操作之市場/信用/操作風險。fairness(公平):分配/收費/資訊不對稱風險。這六個軸都不是「最後答案」,而是補中間的「理由向量」,其值由規則/問卷/模型推導。
可直接在 PostgreSQL 或 ORM(如 Prisma/SQLAlchemy)使用;命名遵循 Web-Modern 通用習慣。
sql
-- 高齡者主檔
CREATE TABLE elder_profile (
elder_id UUID PRIMARY KEY,
name_hash TEXT NOT NULL, -- 去識別(雜湊/假名)
birth_year SMALLINT,
contact_encrypted TEXT, -- 加密
risk_tags TEXT[], -- ex: ["frailty","cognitive_mild"]
created_at TIMESTAMP DEFAULT now()
);
-- 授權/同意紀錄(多版本)
CREATE TABLE consent_record (
consent_id UUID PRIMARY KEY,
elder_id UUID REFERENCES elder_profile(elder_id),
purpose TEXT, -- ex: "care_coordination","asset_sharing_advice"
scope_json JSONB, -- 權限細節:欄位/用途/保存期
granter_role TEXT, -- elder/self; legal_guardian; PoA
method TEXT, -- wet-sign; esign; verbal+recording
valid_from TIMESTAMP,
valid_to TIMESTAMP,
revoke_at TIMESTAMP,
evidence_link TEXT, -- 影像/文件憑證
version INTEGER DEFAULT 1,
created_at TIMESTAMP DEFAULT now()
);
-- 關係人(子女、代理人、理專)
CREATE TABLE stakeholder (
stakeholder_id UUID PRIMARY KEY,
elder_id UUID REFERENCES elder_profile(elder_id),
role TEXT, -- child; caregiver; advisor; social_worker
contact_encrypted TEXT,
trust_score NUMERIC(3,2) DEFAULT 0.50
);
2.2 長照資料(事件/介入/風險)
CREATE TABLE care_event (
event_id UUID PRIMARY KEY,
elder_id UUID REFERENCES elder_profile(elder_id),
event_type TEXT, -- fall, med, nutrition, rehab, social
payload_json JSONB, -- 可擴充(ex:跌倒情境、藥囑變更)
autonomy NUMERIC(3,2),
wellbeing NUMERIC(3,2),
dignity NUMERIC(3,2),
created_at TIMESTAMP DEFAULT now()
);
2.3 金融摘要(僅等級化,不存明細金額以降敏)
CREATE TABLE finance_snapshot (
snap_id UUID PRIMARY KEY,
elder_id UUID REFERENCES elder_profile(elder_id),
date_on DATE,
asset_mix_json JSONB, -- ex: {"cash":0.35,"bond":0.45,"equity":0.20}
liquidity NUMERIC(3,2),
risk NUMERIC(3,2),
fairness NUMERIC(3,2),
advisor_note TEXT,
created_at TIMESTAMP DEFAULT now()
);
2.4 中間論證(Reasoning-as-Data)與守護欄位(Guardrails)
-- 可複用規則/測試(與 Odoo 範式一樣可 JSON 化)
CREATE TABLE rule_catalog (
rule_id UUID PRIMARY KEY,
name TEXT, -- ex: "best_interest_elder","poa_scope_check"
category TEXT, -- ethics/legal/finance/care
elements JSONB, -- 要件
exceptions JSONB, -- 例外
weight NUMERIC(3,2) -- 對總評分影響
);
-- 推理層:一次決策場景的理由快照
CREATE TABLE reasoning_layer (
reason_id UUID PRIMARY KEY,
elder_id UUID REFERENCES elder_profile(elder_id),
context TEXT, -- ex: "weekly_review","portfolio_adjustment"
care_axes JSONB, -- {"autonomy":0.6,"wellbeing":0.8,"dignity":0.9}
fin_axes JSONB, -- {"liquidity":0.7,"risk":0.4,"fairness":0.8}
rules_applied JSONB, -- [{"rule_id":"...","pass":true},...]
std_of_review TEXT, -- proportionality/strict/...
summary TEXT, -- 人可讀摘要(LLM/人工)
created_at TIMESTAMP DEFAULT now()
);
-- 守護檢核:反事實/洩漏/域轉移/幻覺
CREATE TABLE guardrail_check (
check_id UUID PRIMARY KEY,
elder_id UUID REFERENCES elder_profile(elder_id),
reason_id UUID REFERENCES reasoning_layer(reason_id),
type TEXT, -- counterfactual/leakage/domain/hallucination
payload JSONB, -- 測試設定
score NUMERIC(4,3),
passed BOOLEAN,
evidence_link TEXT,
created_at TIMESTAMP DEFAULT now()
);
-- 稽核軌跡
CREATE TABLE audit_log (
audit_id UUID PRIMARY KEY,
actor TEXT, -- 系統/人員
action TEXT, -- view/update/export/share
resource TEXT, -- 表名/資源
resource_id UUID,
reason TEXT, -- 查閱目的
at TIMESTAMP DEFAULT now()
);
關鍵:結果(是否同意分享/資產動用)不直接當特徵;我們以 reasoning_layer 的軸與規則作為「中間層」來支撐解釋與決策。
前端:Next.js + React(App Router),以Server Actions存取安全 API;Component 控制遮蔽顯示與分權視圖。
後端:Node/Express(或 Next API routes)+ Postgres(PG/Prisma)。
向量/LLM:可用本地或 API(論證摘要、規則對映),所有輸出必附來源或稽核碼。
事件匯流:使用 Webhooks / Kafka(選配)記錄「照護事件與金融快照」流入 reasoning-layer。
3.1 API 範例:建立一次「中間層推理」並觸發守護檢核
// /api/reasoning/create.ts (Next.js App Route)
import { z } from "zod";
import { db } from "@/server/db";
const Schema = z.object({
elderId: z.string().uuid(),
context: z.string(),
careAxes: z.object({ autonomy: z.number(), wellbeing: z.number(), dignity: z.number() }),
finAxes: z.object({ liquidity: z.number(), risk: z.number(), fairness: z.number() }),
rulesApplied: z.array(z.object({ ruleId: z.string().uuid(), pass: z.boolean() })),
summary: z.string().min(10)
});
export async function POST(req: Request) {
const body = Schema.parse(await req.json());
// 1) 寫入 reasoning_layer
const reason = await db.reasoning_layer.create({
data: {
elder_id: body.elderId,
context: body.context,
care_axes: body.careAxes,
fin_axes: body.finAxes,
rules_applied: body.rulesApplied,
std_of_review: "proportionality",
summary: body.summary
}
});
// 2) 觸發一組守護檢核(反事實、洩漏)
await db.guardrail_check.createMany({
data: [
{
elder_id: body.elderId,
reason_id: reason.reason_id,
type: "counterfactual",
payload: { autonomy_flip: 0.2 },
score: 0.0, passed: false
},
{
elder_id: body.elderId,
reason_id: reason.reason_id,
type: "leakage",
payload: { mask_outcome_terms: true },
score: 0.0, passed: false
}
]
});
// 3) 稽核
await db.audit_log.create({
data: { actor: "system", action: "create", resource: "reasoning_layer", resource_id: reason.reason_id, reason: "weekly_review" }
});
return new Response(JSON.stringify({ ok: true, reasonId: reason.reason_id }), { status: 201 });
}
3.2 前端元件:理由檢視器(先理由後結果)
// components/ReasoningInspector.tsx
import React from "react";
export function ReasoningInspector({
careAxes, finAxes, rules, summary
}:{
careAxes:{autonomy:number;wellbeing:number;dignity:number};
finAxes:{liquidity:number;risk:number;fairness:number};
rules:{name:string;pass:boolean}[];
summary:string;
}) {
return (
中間層理由(Reasoning-as-Data)
Care Axes
Autonomy: {careAxes.autonomy.toFixed(2)}
Wellbeing: {careAxes.wellbeing.toFixed(2)}
Dignity: {careAxes.dignity.toFixed(2)}
Finance Axes
Liquidity: {finAxes.liquidity.toFixed(2)}
Risk: {finAxes.risk.toFixed(2)}
Fairness: {finAxes.fairness.toFixed(2)}
Applied Rules
{rules.map((r, i)=>({r.name} — {r.pass ? "PASS" : "FAIL"}))}
{summary}
{/* 結果區在別的卡片顯示,避免「先看尾巴」 */}
);
}
3.3 守護檢核(單元測試思路)
// tests/guardrails.spec.ts
import { expect } from "vitest";
import { simulateCounterfactual, scanLeakage } from "../src/guardrails";
test("反事實:降低 autonomy,應提升護理告知/家屬參與需求", () => {
const before = { autonomy:0.8, wellbeing:0.7, dignity:0.9 };
const after = simulateCounterfactual(before, { autonomy_flip:0.2 });
expect(after.autonomy).toBeLessThan(before.autonomy);
expect(after).toHaveProperty("needs_more_consent", true);
});
test("洩漏掃描:facts_clean 不可包含結果詞彙", async () => {
const hitTerms = await scanLeakage("...facts_clean text...");
expect(hitTerms.length).toBe(0);
});
題目蒸餾(Input):把需求寫成可量化 KPI 與邊界(資料可近性/法規)。
資料契約(Data Contract):欄位字典/敏感等級/遮蔽規則/來源頻率。
中間層工程(Reasoning):六軸量化+規則 JSON 化+審查強度。
監箱保單(Guardrails/Eval):反事實/洩漏/域轉移/幻覺檢核報告。
講故事(Output):先理由後結果;呈現同理×原理×制度的三段式敘事。
卡 A:理由卡(Reasoning Card)
─ 顯示六軸、規則通過情形、審查強度、摘要與引用。
卡 B:結果卡(Decision/Sharing Card)
─ 僅在理由卡「通過守護檢核」時解鎖;顯示是否分享/動用、金額級距、通知對象。
設計原則:先中間層,後結果層;每次點擊結果卡都在 audit_log 留痕。
System:
You are a compliance co-pilot. Summarize reasoning without using outcome terms.
Mask any verdict-like expressions.
User (inputs):
Assistant (task):
合規先行:consent_record 覆蓋率、有效期間、撤回率。
洩漏零容忍:guardrail_check(type=leakage).passed 比率=100%。
反事實理性:改變 autonomy/liquidity 後,決策合理變動的比例。
域轉移韌性:不同月份/場域/族群下的穩定度(score 波動 < 閾值)。
可追溯性:每次查看/導出均有 audit_log 理由與證據鏈。
[ ] PII 分級欄位完成(加密/遮蔽/最小必要)。
[ ] 結果詞彙黑名單(facts_clean 過濾 + 單測)。
[ ] PoA/監護/同意版本控管與到期提醒。
[ ] 模型與規則版本號寫入 reasoning_layer。
[ ] LLM 輸出必附來源 key(不可生造引用)。
[ ] 「不分享」預設行為(privacy by default)。
W1:資料契約 + 同意樣板 + 去識別/遮蔽管線。
W2:六軸量化表(問項與權重)+ 規則庫最小集。
W3:Reasoning API + 守護檢核(反事實/洩漏)。
W4:理由卡/結果卡 + 稽核面板 + 操作手冊。
W5:實場 A/B 測 + 場域遷移測 + 匯報。
法律的厲害,在於抽出可遷移的「中間理由」;
產品的可靠,在於用欄位把理由存下來,用守護把風險擋在外面;
長照與高齡金融最在意人:我們用同理×原理×制度三段式,
讓每一次分享與照護,都能說得清、追得回、改得動。
Final line:先抓中間(理由),再對齊頭尾(事實/結果),其餘交給管線與守護。