filipposemilia/secure-insurance-rag-ai
GitHub: filipposemilia/secure-insurance-rag-ai
面向保险文档场景的安全 RAG 概念验证,在 embedding 前进行 PII 掩码并构建多层 guardrail 防御提示词注入等 LLM 安全风险。
Stars: 0 | Forks: 0
# 🛡️ Secure Insurance RAG AI
这是一个关于**保险文档安全 RAG** 的 PoC。检索增强生成(retrieval-augmented generation)只是简单的部分:让此类系统能够在保险公司真正投入使用的,是它周边的配套措施——在个人数据离开安全边界之前进行匿名化处理、防御提示词注入(prompt injection)(包括隐藏在文档中的注入)、对向量进行访问控制,以及可追溯的审计记录(audit trail)。
## 功能展示
| | 能力 | 查看位置 |
| :--- | :--- | :--- |
| 🔒 | **在 embedding 前进行 PII 掩码**:在 vector store 中不存在明文的 CF 或 IBAN。文档之间使用稳定的占位符(`[IBAN_001]`)。 | `secure-rag ingest` |
| 🚫 | **直接提示词注入(Prompt Injection)** 在调用模型前被拦截:耗时 0 ms,消耗 0 token。 | 场景 2 |
| 🧨 | 隐藏在定损报告 HTML 注释中的**间接提示词注入**:该 chunk 被隔离并触发事件告警。 | 场景 3 |
| 👤 | **基于向量的 RBAC**:同一个问题,针对代理人和管理层会返回不同的结果。 | 场景 5 和 6 |
| 📋 | **审计记录(Audit trail)** 采用 JSONL 格式,包含问题哈希(绝不包含明文)、来源、隔离记录及 guard 的判定结果。 | `secure-rag audit` |
| 🔌 | **可互换的 Provider**:支持 OpenAI、Azure OpenAI、本地部署的 Ollama,或使用 `fake` 进行离线运行。 | `.env` |
## 快速开始
```
uv venv --python 3.12
uv pip install -e ".[dev]"
cp .env.example .env # funziona già così: LLM_PROVIDER=fake, nessuna API key richiesta
.venv/bin/secure-rag ingest # anonimizza e indicizza
.venv/bin/secure-rag attack-demo # i sei scenari di sicurezza
.venv/bin/streamlit run app/streamlit_app.py
```
若要使用真实的模型,请在 `.env` 中设置:`LLM_PROVIDER=openai` 和 `OPENAI_API_KEY=…`(或者 `azure` /
`ollama`)。如果更换了 embedding 的 provider,则必须重新执行 `ingest`,因为向量的维度会发生变化。
完整的引导式演示:`bash scripts/demo.sh`。测试:`.venv/bin/pytest -q`(共 32 个测试,全部为离线测试)。
## 架构
```
flowchart LR
A[Documenti] --> B[PII masking]
B --> C[Chunking + metadati
clearance] C --> D[(ChromaDB)] Q[Query utente] --> G1{Input guard} G1 -->|bloccata| X[Rifiuto
0 token] G1 --> R[Retrieval
filtrato per ruolo] D --> R R --> G2{Context guard} G2 -->|payload| QU[Quarantena
+ alert] G2 --> P[Prompt LCEL
contesto delimitato] P --> L[LLM] L --> G3{Output guard} G3 --> ANS[Risposta
con citazioni] G3 -->|PII o allucinazione| X ANS --> AU[(Audit JSONL)] X --> AU QU --> AU ``` 关于四个层级、分步流程以及向企业级架构扩展的节点详细信息:**[docs/ARCHITECTURE.md](docs/ARCHITECTURE.md)**。 ## 安全性:已缓解与未覆盖的风险 | OWASP LLM 风险 | 缓解措施 | 文件 | | :--- | :--- | :--- | | LLM01 — 直接提示词注入(Prompt Injection) | 基于 pattern 的 Input guard,在调用模型前进行拦截 | `security/guardrails.py` | | LLM01 — 间接提示词注入(Prompt Injection) | 扫描检索到的 chunk + 在 prompt 中使用严格的分隔符 | `security/guardrails.py`, `rag.py` | | LLM04 — 拒绝服务(Denial of Service) | 限制查询长度,固定检索的 `k` 值 | `security/guardrails.py` | | LLM06 — 敏感信息泄露(Sensitive Information Disclosure) | embedding 前进行掩码、基于检索的 RBAC、Output guard、不含明文查询的审计 | `security/pii.py`, `vectorstore.py`, `security/audit.py` | | LLM08 — 过度代理(Excessive Agency) | 只读系统:模型不执行任何实际动作 | 架构设计 | | LLM09 — 过度依赖(Overreliance) | 设置 `temperature=0`、强制要求引用、设定拒答规则、进行 groundedness 检查 | `rag.py`, `security/guardrails.py` | 系统局限性已明确声明——基于规则的 guardrail 可通过改写措辞绕过,基于正则表达式的 PII 无法覆盖自由语境下的名称,无真实的身份验证机制,groundedness 仅通过词汇方式衡量:**[docs/SECURITY.md](docs/SECURITY.md)**。 ## 目录结构 ``` src/secure_rag/ ├── config.py impostazioni da .env ├── providers.py factory LLM/embeddings (openai | azure | ollama | fake) ├── ingestion.py load → mask → chunk → metadati di clearance ├── vectorstore.py ChromaDB + filtro RBAC sul retrieval ├── rag.py pipeline con i sette passi di controllo ├── cli.py ingest · ask · attack-demo · audit └── security/ ├── pii.py masking con segnaposto stabili + vault ├── guardrails.py input guard · context guard · output guard └── audit.py audit trail JSONL app/streamlit_app.py UI demo con pannello di sicurezza data/policies/ 4 documenti sintetici, uno deliberatamente compromesso tests/ 32 test, nessuna chiamata di rete ``` ## 文档 - **[docs/ARCHITECTURE.md](docs/ARCHITECTURE.md)** — 四个层级、请求流程、扩展节点 - **[docs/SECURITY.md](docs/SECURITY.md)** — 威胁模型、OWASP Top 10 for LLM 映射、已声明的局限性 - **[docs/DECISIONS.md](docs/DECISIONS.md)** — ADR:为何进行前置掩码、为何将 guard 置于链外、为何采用 800 大小的 chunk - **[ROADMAP.md](ROADMAP.md)** — 待完成事项及工作量评估(Presidio, LangGraph, hybrid search, Qdrant…) ## 技术栈 Python 3.12 · LangChain (LCEL) · ChromaDB · Streamlit · pydantic-settings · pytest · uv
clearance] C --> D[(ChromaDB)] Q[Query utente] --> G1{Input guard} G1 -->|bloccata| X[Rifiuto
0 token] G1 --> R[Retrieval
filtrato per ruolo] D --> R R --> G2{Context guard} G2 -->|payload| QU[Quarantena
+ alert] G2 --> P[Prompt LCEL
contesto delimitato] P --> L[LLM] L --> G3{Output guard} G3 --> ANS[Risposta
con citazioni] G3 -->|PII o allucinazione| X ANS --> AU[(Audit JSONL)] X --> AU QU --> AU ``` 关于四个层级、分步流程以及向企业级架构扩展的节点详细信息:**[docs/ARCHITECTURE.md](docs/ARCHITECTURE.md)**。 ## 安全性:已缓解与未覆盖的风险 | OWASP LLM 风险 | 缓解措施 | 文件 | | :--- | :--- | :--- | | LLM01 — 直接提示词注入(Prompt Injection) | 基于 pattern 的 Input guard,在调用模型前进行拦截 | `security/guardrails.py` | | LLM01 — 间接提示词注入(Prompt Injection) | 扫描检索到的 chunk + 在 prompt 中使用严格的分隔符 | `security/guardrails.py`, `rag.py` | | LLM04 — 拒绝服务(Denial of Service) | 限制查询长度,固定检索的 `k` 值 | `security/guardrails.py` | | LLM06 — 敏感信息泄露(Sensitive Information Disclosure) | embedding 前进行掩码、基于检索的 RBAC、Output guard、不含明文查询的审计 | `security/pii.py`, `vectorstore.py`, `security/audit.py` | | LLM08 — 过度代理(Excessive Agency) | 只读系统:模型不执行任何实际动作 | 架构设计 | | LLM09 — 过度依赖(Overreliance) | 设置 `temperature=0`、强制要求引用、设定拒答规则、进行 groundedness 检查 | `rag.py`, `security/guardrails.py` | 系统局限性已明确声明——基于规则的 guardrail 可通过改写措辞绕过,基于正则表达式的 PII 无法覆盖自由语境下的名称,无真实的身份验证机制,groundedness 仅通过词汇方式衡量:**[docs/SECURITY.md](docs/SECURITY.md)**。 ## 目录结构 ``` src/secure_rag/ ├── config.py impostazioni da .env ├── providers.py factory LLM/embeddings (openai | azure | ollama | fake) ├── ingestion.py load → mask → chunk → metadati di clearance ├── vectorstore.py ChromaDB + filtro RBAC sul retrieval ├── rag.py pipeline con i sette passi di controllo ├── cli.py ingest · ask · attack-demo · audit └── security/ ├── pii.py masking con segnaposto stabili + vault ├── guardrails.py input guard · context guard · output guard └── audit.py audit trail JSONL app/streamlit_app.py UI demo con pannello di sicurezza data/policies/ 4 documenti sintetici, uno deliberatamente compromesso tests/ 32 test, nessuna chiamata di rete ``` ## 文档 - **[docs/ARCHITECTURE.md](docs/ARCHITECTURE.md)** — 四个层级、请求流程、扩展节点 - **[docs/SECURITY.md](docs/SECURITY.md)** — 威胁模型、OWASP Top 10 for LLM 映射、已声明的局限性 - **[docs/DECISIONS.md](docs/DECISIONS.md)** — ADR:为何进行前置掩码、为何将 guard 置于链外、为何采用 800 大小的 chunk - **[ROADMAP.md](ROADMAP.md)** — 待完成事项及工作量评估(Presidio, LangGraph, hybrid search, Qdrant…) ## 技术栈 Python 3.12 · LangChain (LCEL) · ChromaDB · Streamlit · pydantic-settings · pytest · uv
标签:ChromaDB, Kubernetes, LangChain, 人工智能, 安全规则引擎, 提示词注入防护, 数据脱敏, 检索增强生成, 用户模式Hook绕过, 轻量级