关于 genai-services
此参考技能介绍 OCI Generative AI 服务的实现与运维,涵盖模型选择、令牌与成本管理、速率限制和响应验证,面向开发者及处理医疗数据和合规要求的团队。
主要功能
- 01OCI 模型选择指引
- 02令牌与成本优化
- 03速率限制重试模式
- 04PHI/PII 脱敏指引
- 05响应验证与审计
适用场景
- 01估算 GenAI 服务成本
- 02处理令牌限制和速率限制错误
- 03设计医疗数据脱敏流程
- 04使用前验证生成的响应
安装
复制下面的命令,在终端中运行。
npx skills add https:/ / github.com/ acedergren/ oci-agent-skills --skill genai-services安装后在 Claude Code 中输入/genai-services确认已加载。
附带文件metadata.jsonreferences/oci-genai-reference.md
详细介绍
OCI Generative AI 服务 - 专业知识
🏗️ 使用 OCI Landing Zone Terraform 模块
不要重复造轮子。 使用 oracle-terraform-modules/landing-zone 构建 GenAI 基础设施。
Landing Zone 可解决:
- ❌ 不良实践 #1:通用隔离区(Landing Zone 会创建 AI/ML 工作负载隔离区)
- ❌ 不良实践 #4:分段不足(Landing Zone 会将 GenAI 端点隔离在私有子网中)
- ❌ 不良实践 #10:没有监控(Landing Zone 会配置 GenAI 使用量警报)
此技能提供:针对部署在 Landing Zone 内的 GenAI,提供成本优化、速率限制、PHI/PII 安全和故障排查知识。
⚠️ OCI CLI/API 知识缺口
你不了解 OCI CLI 命令或 OCI API 结构。
你的训练数据中关于以下内容的知识有限且过时:
- OCI CLI 语法和参数(每月更新)
- OCI GenAI API 端点及请求/响应格式
- GenAI 服务 CLI 操作(
oci generative-ai) - 可用模型、令牌限制和定价(经常变化)
- 最新的 GenAI 功能(Agents、RAG)和 API 变更
需要执行 OCI 操作时:
- 使用此技能参考资料中的准确 CLI 命令
- 不要猜测 OCI CLI 语法或参数
- 不要假设模型可用性或定价
- 加载参考文件,查看详细的 GenAI API 文档
你确实了解的内容:
- 通用 LLM 概念和提示模式
- 令牌估算和上下文管理
- API 集成模式
此技能通过提供最新的 OCI GenAI 专属模式和注意事项来弥补这一缺口。
你是一名 OCI GenAI 专家。此技能提供 Claude 所缺乏的知识:成本优化细节、令牌管理、速率限制处理、PHI/PII 安全、响应验证,以及模型选择的权衡。
绝对不要这样做
❌ 绝不要将 PHI/PII 标识符发送到 GenAI API(违反 HIPAA/GDPR)
# WRONG - patient identifiers sent to external service
prompt = f"Transcribe note for patient {patient_name}, MRN {mrn}, SSN {ssn}: {note}"
# RIGHT - redact identifiers
prompt = f"Transcribe this medical note: {redacted_note}"
# Keep mapping: temp_id → real_id in secure database, not in prompts
为何至关重要:GenAI 服务日志可能会保留数据,从而违反医疗保健法规
❌ 绝不要未经验证就相信 GenAI 输出(存在幻觉风险)
# WRONG - use response directly in critical systems
diagnosis = genai_response.text
db.execute("UPDATE patients SET diagnosis = ?", diagnosis)
# RIGHT - validate structure and flag for human review
response = genai_response.text
if validate_medical_format(response):
db.execute("UPDATE patients SET ai_suggested_diagnosis = ?, status = 'PENDING_REVIEW'", response)
幻觉率:事实类查询为 5-15%,医疗/法律领域更高
❌ 绝不要忽略令牌限制
- command-r-plus:128k 上下文窗口(输入 + 输出)
- command-r:4k 上下文(便宜得多,但有限制)
- 超出限制:请求会被静默截断,或以 400 错误失败
❌ 绝不要在未处理速率限制的情况下调用 GenAI
# WRONG - no retry logic, fails on rate limit
response = genai_client.chat(request)
# RIGHT - exponential backoff
def call_with_retry(func, max_retries=5):
for attempt in range(max_retries):
try:
return func()
except oci.exceptions.ServiceError as e:
if e.status == 429 and attempt < max_retries - 1:
wait = (2 ** attempt) + random.uniform(0, 1)
logger.warning(f"Rate limited, retry in {wait:.2f}s")
time.sleep(wait)
else:
raise
❌ 绝不要未经同意就缓存响应(数据隐私)
- 缓存可以节省成本,但可能违反隐私政策
- 缓存医疗/个人数据前,须获得用户明确同意
- 仅缓存匿名化数据
❌ 绝不要将 GenAI 用于确定性任务
- 错误:“从 OCR 文本中提取发票总额”(应使用正则表达式/结构化解析)
- 错误:“验证电子邮件格式”(应使用验证库)
- 正确:“总结患者病史”“生成报告叙述”(创造性任务)
模型选择:成本与性能
| 模型 | 上下文 | 成本(每 1M 个令牌) | 最适合 | 避免用于 |
|---|---|---|---|---|
| command-r-plus | 128k | ~$15 输入,$75 输出 | 复杂推理、长文档 | 简单任务(成本高) |
| command-r | 4k | ~$1.50 输入,$7.50 输出 | 聊天、短提示词、高调用量 | 长文档、RAG |
| embed-english-v3 | 不适用 | 每 1M 个约 ~$0.10 | 语义搜索、聚类 | 文本生成 |
| llama-2-70b | 4k | ~$2 输入,$10 输出 | 开放权重、经济高效 | 生产环境(支持有限) |
成本优化策略:
- 优先使用嵌入进行搜索(成本比生成低 1000 倍)
- 缓存重复查询的响应(需征得同意)
- 简单任务使用 command-r,仅在需要时使用 command-r-plus
- 智能截断输入(仅保留相关上下文)
成本计算示例
场景:医疗转录服务
- 平均病历:输入 500 个 token,输出 300 个 token = 共 800 个 token
- 每天 1000 份病历 = 每天 80 万个 token = 每月 2400 万个 token
未优化:
Model: command-r-plus
Input: 12M × ($15/1M) = $180/month
Output: 12M × ($75/1M) = $900/month
Total: $1,080/month
优化后(缓存命中率为 30%,简单病历使用 command-r):
70% unique notes = 16.8M tokens
60% simple (command-r): 10M × $1.50 input + $7.50 output = $90
40% complex (command-r-plus): 6.72M × $15 input + $75 output = $605
Total: $695/month (36% savings)
Token 管理
各模型的 Token 限制
| 模型 | 最大上下文 | 最大输出 | 备注 |
|---|---|---|---|
| command-r-plus | 128k(输入+输出) | 不定 | 每个 token 约 4 个字符(粗略估算) |
| command-r | 4k | 2k | 适用于聊天 |
| embed-english-v3 | 512 | 不适用 | 仅用于嵌入 |
截断策略
def truncate_for_model(text: str, model: str = "command-r-plus", max_output: int = 2000):
"""Truncate input to fit token budget"""
# Rough estimate: 1 token ≈ 4 characters
if model == "command-r-plus":
max_input_tokens = 128000 - max_output
elif model == "command-r":
max_input_tokens = 4000 - max_output
else:
max_input_tokens = 2000
max_chars = max_input_tokens * 4
if len(text) <= max_chars:
return text
# Keep most recent content (chronological data like logs, notes)
logger.warning(f"Input exceeds {max_input_tokens} tokens, truncating")
return "...[earlier content truncated]...\n" + text[-max_chars:]
提示词优化
效率低(浪费 token):
Please carefully analyze the following medical record and provide a comprehensive
summary including all diagnoses, medications, allergies, and treatment plans. Be
thorough and include all relevant details from the patient's history...
[5000 word medical record]
优化后(减少 40% 的 token):
Summarize: diagnoses, meds, allergies, treatment plan.
[5000 word medical record]
节省的 token:每个提示词约节省 50 个 token × 每天 1000 次请求 = 每天节省 5 万个 token = 每天 $2.25(每月 $68)
速率限制
OCI GenAI 服务限制(每个区间):
| 模型 | 每分钟请求数 | 每天请求数 | 每次请求的 Token 数 |
|---|---|---|---|
| command-r-plus | 20 | 1000 | 128k |
| command-r | 60 | 3000 | 4k |
| Embeddings | 100 | 10000 | 512 |
错误处理
import time
import random
from oci.exceptions import ServiceError
def generate_with_backoff(genai_client, request, max_retries=5):
"""Call GenAI with exponential backoff on rate limits"""
for attempt in range(max_retries):
try:
response = genai_client.chat(request)
return response.data.chat_response.text
except ServiceError as e:
if e.status == 429: # Rate limit
if attempt < max_retries - 1:
# Exponential backoff: 1s, 2s, 4s, 8s, 16s
wait = (2 ** attempt) + random.uniform(0, 1)
logger.warning(f"Rate limited (429), retry {attempt+1}/{max_retries} in {wait:.1f}s")
time.sleep(wait)
else:
logger.error(f"Rate limit exceeded after {max_retries} retries")
raise
elif e.status == 400: # Bad request (often token limit)
logger.error(f"Bad request (400): {e.message}")
if "token" in e.message.lower():
logger.error("Token limit exceeded - truncate input")
raise
else:
logger.error(f"GenAI error ({e.status}): {e.message}")
raise
响应验证(医疗保健领域至关重要)
def validate_medical_response(response: str) -> tuple[bool, list[str]]:
"""Validate GenAI medical response for safety"""
issues = []
# Check 1: Response not empty
if not response or len(response.strip()) < 10:
issues.append("Response too short or empty")
# Check 2: No obvious hallucination markers
hallucination_markers = [
"I don't have access",
"I cannot",
"As an AI",
"[INSERT",
"TODO",
]
for marker in hallucination_markers:
if marker.lower() in response.lower():
issues.append(f"Potential hallucination marker: {marker}")
# Check 3: Expected structure present (customize per use case)
required_sections = ["Chief Complaint", "Assessment", "Plan"]
missing_sections = [s for s in required_sections if s.lower() not in response.lower()]
if missing_sections:
issues.append(f"Missing sections: {missing_sections}")
# Check 4: No PII leak (if input was redacted)
pii_patterns = [
r'\b\d{3}-\d{2}-\d{4}\b', # SSN
r'\b[A-Z]{2}\d{6,8}\b', # MRN patterns
]
for pattern in pii_patterns:
if re.search(pattern, response):
issues.append(f"Potential PII in response: {pattern}")
is_valid = len(issues) == 0
return is_valid, issues
# Usage
response_text = genai_response.data.chat_response.text
is_valid, issues = validate_medical_response(response_text)
if is_valid:
store_for_review(response_text)
else:
logger.warning(f"Invalid response: {issues}")
flag_for_manual_review(response_text, issues)
医疗保健领域的特定注意事项
HIPAA 合规性
最低要求:
- ✅ 与 Oracle 签订业务伙伴协议(BAA)
- ✅ 发送至 GenAI 前对 PHI 进行脱敏
- ✅ 记录所有 GenAI API 调用的审计日志
- ✅ 传输中和静态数据均加密
- ✅ 访问控制(哪些人可以调用 GenAI)
- ✅ 数据保留政策(提示词/响应的保留时长)
切勿默认认为 GenAI 符合 HIPAA 要求——请向 Oracle 核实 BAA 的覆盖范围
去标识化策略
def redact_phi(text: str) -> tuple[str, dict]:
"""Remove PHI from text, return redacted text + mapping"""
mapping = {}
redacted = text
# Patient names (use NER or pattern matching)
names = extract_names(text) # Your NER function
for i, name in enumerate(names):
placeholder = f"[PATIENT_{i}]"
mapping[placeholder] = name
redacted = redacted.replace(name, placeholder)
# Medical Record Numbers
mrn_pattern = r'\b(MRN|Medical Record):?\s*([A-Z0-9]{6,10})\b'
redacted = re.sub(mrn_pattern, r'\1: [REDACTED]', redacted)
# SSN
ssn_pattern = r'\b\d{3}-\d{2}-\d{4}\b'
redacted = re.sub(ssn_pattern, '[SSN_REDACTED]', redacted)
# Dates (optional - some use cases need dates)
# date_pattern = r'\b\d{1,2}/\d{1,2}/\d{4}\b'
# redacted = re.sub(date_pattern, '[DATE]', redacted)
return redacted, mapping
# Usage
redacted_note, phi_mapping = redact_phi(patient_note)
genai_response = genai_client.chat(prompt=f"Summarize: {redacted_note}")
# Store phi_mapping securely, use to re-identify if needed
渐进式加载参考资料
OCI Generative AI 参考资料(Oracle 官方文档)
在以下情况下加载 oci-genai-reference.md:
- 需要全面了解 GenAI API 文档
- 了解所有可用模型及其功能
- 使用 OCI 实现 RAG(检索增强生成)
- 需要 Oracle 关于 GenAI Agent 的官方指导
- 了解微调和自定义模型部署
以下情况无需加载:
- 快速了解 API 用法示例(此技能中已涵盖)
- 模型选择指导(见上方决策树)
- 成本计算(见上方公式)
何时使用此技能
- GenAI API 实现:模型选择、成本估算、SDK 用法
- 错误排查:速率限制(429)、Token 限制(400)、身份验证
- 成本优化:缓存策略、降级模型、提示词优化
- 医疗保健/合规:PHI 处理、HIPAA 要求、审计日志
- 响应验证:幻觉检测、结构检查
- 生产环境:速率限制处理、错误恢复、监控