外观
知识与制度库
虹元里的"知识"有两种。一种是知识对象:智悟沉淀下来的误报案例、交接班汇总、核对单、周报月报、复盘报告,一条一行,带版本与密级。另一种是制度库:企业自己的制度文件、HSE 操作规程、人工确认过的案例,切成条款块,供企业问答检索和核对出处。
两种都只在虹元存放与治理。怎么用是智悟的事:虹元不调大模型成文,也不做问答决策。它保证三件事:检索结果里没有越权、失效、被替代的内容;核对出处时逐条说清能不能引用;每次问答都留得下来。
知识对象
| 接口 | 作用 |
|---|---|
POST /api/uancore/objects/knowledge | 沉淀一条。同一个 src_system 加 src_pk 只落一条,重复沉淀回既有那条 |
GET /api/uancore/objects/knowledge | 列表,可筛选、可翻页 |
GET /api/uancore/objects/knowledge/{core_id}?tenant_code= | 取一条 |
POST /api/uancore/objects/knowledge/{core_id}/revise | 人工修订报告里留给人写的段 |
凭据同任务接口:管理密钥或登录会话。客户租户的门户会话只能动自己租户的知识。
每条知识的字段:coreId、tenantCode、srcSystem、srcPk、title、kind、sourceRef、securityLevel、version、validUntil、body、createdAt。sourceRef 只收 JSON 对象,写明这条知识从哪来,比如 {"type":"event","id":124161}。
列表怎么筛
| 参数 | 说明 |
|---|---|
tenant_code | 租户。运营侧不给就是全部租户 |
kind | 类型,精确匹配 |
exclude_kind | 逗号分隔,这几类不要 |
src_system、src_pk | 来源,精确匹配 |
ref_key、ref_value | 按 sourceRef 的顶层键找,两个一起给。ref_key=id&ref_value=124161 找得到上面那条 |
since、until | 落库时间窗,左闭右开。必须带时区,写 Z 或 +08:00 |
fields | 只认 meta,不回正文。列表页用,一条误报案例的正文就有几 KB |
limit、offset | 每页默认 100,最多 1000;offset 最大 10000 |
排序按落库时间倒序,同一时刻再按 core_id 倒序,翻页稳定。
since、until 只写日期、或不带时区的时刻,一律回 400。虹元不替调用方猜时区:租户不在同一个时区,按北京时间猜,海外现场的窗口会整段错开,而且不报错。
翻页途中有新知识落库,后面每页会整体往后挪。要翻得稳,从第一页起每页带同一个 until。
没有按 body 里任意键筛选的口。要按出处找,沉淀时把出处写进 sourceRef。
取一条
tenant_code 必须给,只在这个租户里找。缺租户回 400;客户会话指明别家回 403;不存在、已删、不归这个租户,一律 404。
人工修订
复盘报告的原因、责任、整改措施这几段要人补。智悟出报告时把这些段标成 "editable": "human",人在工作台补完交修订:
json
{"tenant_code": "<租户码>",
"sections": {"cause": "阀门密封老化", "measures": "月检加密封项"},
"by": "<经办人>", "note": "复盘会补", "expected_version": 1}几条规矩:
- 只许改标了
human的段。有一段不合规就整次拒绝,一段都不改。每段最多 8000 字。 - 改成功版本加 1,改到的段记修订人与修订时刻。改前改后整行进审计。
- 文字和原来一样的段不算改。一段都没变回
changed: false,不升版本。 expected_version可选,填打开页面时看到的版本。库里已经不是这一版,回 409,一个字都不改。两个人同时补文字,后交的那个会被拦下,重新打开再改。
回包带改后的整条知识与改到的段名。
制度库
制度库分三路做:
| 谁 | 做什么 |
|---|---|
| 虹元 | 文件台账、原件存储、切块落库、检索、出处核验、问答留痕、密级授权 |
| 智悟的入库程序 | 解析与切块、HSE 制度同步、案例同步、补向量 |
| 智悟工作台 | 制度库页、企业问答页、问答的硬规则 |
页面在智悟工作台,见智悟智能体 · 企业问答。虹元控制台没有制度库页面。
文件与状态
每份文件在台账里一行:标题、文号、版本、生效日、失效日、密级、来源、原件指纹。同一租户同一来源键只登记一次。
text
已上传 --入库程序取走--> 解析中 --交切块--> 待核对 --人点生效--> 已生效 --新版生效--> 已替代
+--作废(必填原因)--> 已作废
HSE 制度同步、案例同步交切块后直接生效
解析中超过 30 分钟没交切块,下次重新发状态码依次是 uploaded、parsing、review、effective、superseded、withdrawn。
同一份制度任何时候只有一版生效。新版登记时用 supersedes 指向旧版,新版生效时旧版在同一个事务里置为已替代。两份新版指向同一份旧版,后生效的那份回 409。
只有已生效、生效日已到、失效日没过的块能进检索结果,能通过核验。
| 接口 | 作用 |
|---|---|
POST /api/uancore/kb/docs | 登记一份文件 |
POST /api/uancore/kb/docs/{doc_id}/file | 上传原件,单个 25MB 以内,大小与 sha256 要和登记的一致 |
GET /api/uancore/kb/docs | 列表,可按状态、来源、来源键前缀筛 |
GET /api/uancore/kb/docs/{doc_id} | 详情,带切块与整套切块的指纹 |
GET /api/uancore/kb/docs/{doc_id}/file | 取原件。取出的字节和登记的 sha256 对不上就报错,不交出去 |
GET /api/uancore/kb/docs/pending | 入库程序取活 |
POST /api/uancore/kb/docs/{doc_id}/chunks | 交切块,整份替换 |
POST /api/uancore/kb/docs/{doc_id}/state | 生效、作废、置为已替代 |
原件存储
原件存 S3 兼容的对象存储,没配就存本地目录(缺省 /opt/uancore/kbdocs)。存储键由虹元按 kb/<租户>/<文件号>/<sha256> 拼,不接受外部传入。原件存本地目录时,备份脚本另打一个原件包。
取原件可以要短时下载地址(presign=1,5 分钟有效)。只有配了对外地址 UANCORE_DOC_S3_PUBLIC_ENDPOINT 才签;没配回 400,改走字节流。
切块
一份最多 5000 块,每块 2 万字以内。每块记条款路径、页码、原文与原文指纹。检索词由虹元自己切:中文按二字一组,英文数字整体成词,条款号整体再出一个词,第12条 和 第十二条 互相能命中。
交切块可带 parse_note 解析备注,比如"第 3、5 页是扫描件,没进库"。备注接在文件的状态说明后面,审核人在待核对时看得到;超过 1000 字截断。
审核人点生效时带回详情里的切块指纹(expect_chunks_sha256)。审核期间切块被重交过,指纹对不上,回 409,生效的永远是审核人看过的那一版。
检索
POST /api/uancore/kb/search体:tenant_code、subject(提问人)、query,可选 query_embedding、embed_model、top_k(缺省 6,最多 20)、src_systems、auto_embed。
- 硬过滤先在库里做。 租户、已生效、在有效期内、密级不高于提问人的最高密级、来源系统。越权的块进不了候选。
- 召回。 关键字取前 200 块;有问句向量时,再按余弦相似度取前 50 块,两边合并。
- 打分。 关键字分是问句检索词在块里的加权覆盖率,0 到 1。有向量时
score = 0.35 × 关键字分 + 0.65 × 向量分,没有向量时只用关键字分。 - 排序。 按总分,再按关键字分,再按文件与序号。同样的输入永远同样的输出。
回包带 index_version(kb1/lex 或 kb1/hybrid/<向量模型>),两种模式的分不能放在一起比,智悟按它分别定门限。
问句向量从哪来:调用方给了就用调用方的。没给的,虹元配了嵌入服务(UANCORE_EMBED_URL)就自己把问句算成向量。代算不成照旧只用关键字出结果,不报错,原因写在 vec_note:
vec_note | 含义 |
|---|---|
| 空 | 混合检索 |
no_query_embedding | 调用方没给向量,并且带了 auto_embed: false |
embed_not_configured | 虹元没配嵌入服务 |
embed_unavailable | 配了,这次没算成(连不上、超时之类) |
embed_model_mismatch | 调用方指定的向量模型和嵌入服务不一致 |
no_embedded_chunks | 库里还没有补过向量的块 |
dim_mismatch | 库里向量的维度和问句对不上,要重补向量 |
回包里的出错说明不带嵌入服务的地址。GET /api/uancore/version 的 kbQueryEmbed 看虹元有没有开代算。
出处核验
POST /api/uancore/kb/chunks/verify一次 1 到 50 个块编号,按顺序逐条回能不能引用:
| 原因 | 什么情况 |
|---|---|
| 空 | 能引用 |
not_found | 不存在、不在这个租户,或超出提问人的密级。三种情况说法一样,不透露"有但你看不了" |
hash_mismatch | 原文和入库时的指纹对不上 |
superseded、withdrawn | 已被替代、已作废 |
not_effective | 还没生效 |
expired、not_yet_effective | 失效日已过、生效日未到 |
问答留痕
| 接口 | 作用 |
|---|---|
POST /api/uancore/kb/qa_log | 记一次问答:提问人、问题、回答、引了哪些块、拒答原因、口径版本与索引版本、耗时。答了、拒了都记 |
GET /api/uancore/kb/qa_log | 查留痕,客户会话只看得到自己的 |
POST /api/uancore/kb/qa_log/{qa_id}/feedback | 提问人本人标"有用"或"不对" |
问答留痕是"模型说过什么"的凭据,只有服务通道与控制台能写,客户会话直连写不了。留痕可能含个人信息,放在租户自己的库里。保留期按租户配(scope=qa_log,必须写天数),每小时清一次;没有默认天数,不配不删。
密级授权
密级从低到高四档:public 公开、internal 内部、confidential 秘密、secret 机密。文件登记时定密级,缺省内部。
账号的最高密级用 POST /api/uancore/kb/clearance 授予,变更进审计;没有授过的账号按内部算。读文件(列表、详情、原件)必须说清按谁的密级:带提问人头 x-uancore-subject,或者服务通道、控制台显式带 all_levels=1。后者每次都记进查询审计。
谁能动什么:
| 来路 | 能动的租户 | 能做的事 |
|---|---|---|
| 服务通道 | 全部 | 全部 |
| 控制台会话(沅虹运营视图) | 只有运营租户与评测租户 | 全部 |
| 客户租户的门户会话 | 只有自己 | 只读:列表、详情、原件、检索、核验、看自己的留痕、给自己的问答反馈 |
登记、上传、交切块、改状态、补向量、授密级、写留痕都算管理动作,客户会话直连做不了。企业的制度库管理员经智悟工作台做,名单在智悟那边判。
定向删除
制度库的四张表(文件、切块、密级、问答留痕)都在租户库里,随定向删除一起删。删完表再按 kb/<租户>/ 前缀删原件,删了几个写在回包和删除明细里。存储配置不全或连不上,预演就报错,整次不删。
规划中
- 扫描件识别:通道留好了,当前版本整份扫描件不收。
- 大规模向量索引:现在每次检索在进程里算余弦,单租户几千块没问题,上万块之后换库内向量索引。
- 原件直传对象存储:现在原件上传、下载经智悟中转。