fix(deploy): configure distinct quick and reasoning agents
This commit is contained in:
@@ -67,13 +67,17 @@ sudo dobotai-dingtalk-configure
|
||||
|
||||
配置器要求填写阿里云RDS连接串、WeKnora和钉钉凭证;密钥不回显,环境文件原子写入且权限0600。
|
||||
|
||||
`DOBOTAI_TENANT_KEY`不是WeKnora Agent租户键。它是DobotAI内部数据隔离键,首次安装时自动生成并固定保存;配置器不会要求填写或改动它。WeKnora侧只需要在`DOBOTAI_AGENT_BINDINGS`填写实际的Agent ID。
|
||||
`DOBOTAI_TENANT_KEY`不是WeKnora Agent租户键。它是DobotAI内部数据隔离键,首次安装时自动生成并固定保存;配置器不会要求填写或改动它。WeKnora侧只需要填写实际的两个Agent ID。
|
||||
|
||||
配置器会要求两个不同的WeKnora Agent ID,并自动生成`DOBOTAI_AGENT_BINDINGS={"dingtalk:*":"快速问答Agent ID"}`。`DOBOTAI_INGRESS_TOKEN`是保护本机`POST /v1/qa`内部接口的Bearer Token,不用于钉钉或WeKnora;同样由安装器自动生成。
|
||||
|
||||
| 配置 | 示例 | 作用 |
|
||||
| --- | --- | --- |
|
||||
| `DATABASE_URL` | `postgres://USER:***@rds-endpoint:5432/dobotai?sslmode=require` | DobotAI专用阿里云RDS PostgreSQL |
|
||||
| `WEKNORA_BASE_URL` | `http://127.0.0.1:8080` | 宿主机既有WeKnora |
|
||||
| `WEKNORA_API_KEY` | `<你的WeKnora API Key>` | DobotAI专用Key |
|
||||
| `DOBOTAI_QUICK_AGENT_ID` | `<快速问答Agent ID>` | 默认快速问答实际调用的Agent |
|
||||
| `DOBOTAI_REASONING_AGENT_ID` | `<智能推理Agent ID>` | `/think`和持续智能推理实际调用的Agent |
|
||||
| `DINGTALK_CLIENT_ID` | `dingxxxxxxxx` | 钉钉AppKey |
|
||||
| `DINGTALK_CLIENT_SECRET` | `<你的钉钉 AppSecret>` | 钉钉AppSecret |
|
||||
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
#!/usr/bin/env python3
|
||||
import argparse
|
||||
import getpass
|
||||
import json
|
||||
import os
|
||||
from pathlib import Path
|
||||
import subprocess
|
||||
@@ -10,9 +11,8 @@ FIELDS = (
|
||||
("DATABASE_URL", "阿里云RDS PostgreSQL连接串", "已有DobotAI专用阿里云RDS数据库;脚本只检查表,空库才初始化。", "postgres://USER:***@rds-endpoint:5432/dobotai?sslmode=require", True),
|
||||
("WEKNORA_BASE_URL", "WeKnora 地址", "应用容器通过宿主机网络访问既有WeKnora。", "http://127.0.0.1:8080", False),
|
||||
("WEKNORA_API_KEY", "WeKnora API Key", "DobotAI专用WeKnora API Key。", "<你的WeKnora API Key>", True),
|
||||
("DOBOTAI_INGRESS_TOKEN", "DobotAI Ingress Token", "调用/v1/qa的独立令牌。", "<随机长字符串>", True),
|
||||
|
||||
("DOBOTAI_AGENT_BINDINGS", "DobotAI Agent Bindings JSON", "钉钉会话到WeKnora Agent映射。", '{"dingtalk:*":"你的Agent ID"}', False),
|
||||
("DOBOTAI_QUICK_AGENT_ID", "快速问答Agent ID", "默认问答实际调用的WeKnora Agent。", "<快速问答Agent ID>", False),
|
||||
("DOBOTAI_REASONING_AGENT_ID", "智能推理Agent ID", "/think和持续智能推理实际调用的WeKnora Agent。", "<智能推理Agent ID>", False),
|
||||
("DINGTALK_CLIENT_ID", "钉钉 Client ID", "钉钉应用Client ID/AppKey。", "dingxxxxxxxx", False),
|
||||
("DINGTALK_CLIENT_SECRET", "钉钉 Client Secret", "钉钉应用Client Secret/AppSecret。", "<你的钉钉 AppSecret>", True),
|
||||
)
|
||||
@@ -47,6 +47,9 @@ def main():
|
||||
if entered: values[key]=entered
|
||||
missing=[label for key,label,*_ in FIELDS if not values.get(key,"").strip()]
|
||||
if missing: raise SystemExit("以下必填项未配置:"+"、".join(missing))
|
||||
if values["DOBOTAI_QUICK_AGENT_ID"] == values["DOBOTAI_REASONING_AGENT_ID"]:
|
||||
raise SystemExit("快速问答Agent ID与智能推理Agent ID必须不同。")
|
||||
values["DOBOTAI_AGENT_BINDINGS"] = json.dumps({"dingtalk:*": values["DOBOTAI_QUICK_AGENT_ID"]}, separators=(",", ":"))
|
||||
write_env(path,lines,values)
|
||||
subprocess.run([args.schema_script], check=True)
|
||||
os.execv(args.start_script,[args.start_script])
|
||||
|
||||
@@ -26,21 +26,21 @@ install -m 0644 "$source_root"/db/migrations/*.up.sql "$container_dir/migrations
|
||||
|
||||
if [[ ! -f "$app_env" ]]; then
|
||||
umask 077
|
||||
tenant_suffix="$(python3 -c 'import secrets; print(secrets.token_hex(12))')"
|
||||
read -r tenant_suffix ingress_token < <(python3 -c 'import secrets; print(secrets.token_hex(12), secrets.token_urlsafe(32))')
|
||||
cat > "$app_env" <<'EOF'
|
||||
DOBOTAI_LISTEN_ADDR=127.0.0.1:8090
|
||||
DATABASE_URL=
|
||||
WEKNORA_BASE_URL=http://127.0.0.1:8080
|
||||
WEKNORA_API_KEY=
|
||||
DOBOTAI_INGRESS_TOKEN=
|
||||
DOBOTAI_ADMIN_TOKEN=
|
||||
DOBOTAI_AGENT_BINDINGS=
|
||||
DOBOTAI_QUICK_AGENT_ID=builtin-quick-answer
|
||||
DOBOTAI_REASONING_AGENT_ID=builtin-smart-reasoning
|
||||
DOBOTAI_QUICK_AGENT_ID=
|
||||
DOBOTAI_REASONING_AGENT_ID=
|
||||
DINGTALK_CLIENT_ID=
|
||||
DINGTALK_CLIENT_SECRET=
|
||||
EOF
|
||||
printf 'DOBOTAI_TENANT_KEY=dobotai-%s\n' "$tenant_suffix" >> "$app_env"
|
||||
printf 'DOBOTAI_INGRESS_TOKEN=%s\n' "$ingress_token" >> "$app_env"
|
||||
chmod 0600 "$app_env"
|
||||
fi
|
||||
umask 077
|
||||
|
||||
@@ -64,19 +64,19 @@ func TestRDSCredentialConfiguratorPromptsForExternalDatabase(t *testing.T) {
|
||||
t.Fatal(err)
|
||||
}
|
||||
source := string(data)
|
||||
for _, required := range []string{"DATABASE_URL", "阿里云RDS", "getpass.getpass", "os.replace", "0o600"} {
|
||||
for _, required := range []string{"DATABASE_URL", "阿里云RDS", "快速问答Agent ID", "智能推理Agent ID", "getpass.getpass", "os.replace", "0o600"} {
|
||||
if !strings.Contains(source, required) {
|
||||
t.Errorf("RDS configurator missing %q", required)
|
||||
}
|
||||
}
|
||||
if strings.Contains(source, "DobotAI租户键") {
|
||||
t.Fatal("operator must not be prompted for the internal DobotAI tenant key")
|
||||
if strings.Contains(source, "DobotAI租户键") || strings.Contains(source, "Agent Bindings JSON") || strings.Contains(source, "DobotAI Ingress Token") {
|
||||
t.Fatal("operator must only be prompted for real RDS, WeKnora and DingTalk configuration")
|
||||
}
|
||||
installer, err := os.ReadFile("../deploy/dobotai-dingtalk/install-docker.sh")
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if !strings.Contains(string(installer), "secrets.token_hex") || !strings.Contains(string(installer), "DOBOTAI_TENANT_KEY=dobotai-") {
|
||||
t.Fatal("installer must generate and persist the internal DobotAI tenant key")
|
||||
if !strings.Contains(string(installer), "secrets.token_hex") || !strings.Contains(string(installer), "secrets.token_urlsafe") || !strings.Contains(string(installer), "DOBOTAI_TENANT_KEY=dobotai-") {
|
||||
t.Fatal("installer must generate and persist internal tenant and ingress tokens")
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user