Autumn
|
d0033724a6
|
Merge pull request #189 from Autumn-27/fix/sse-same-origin
fix(web): SSE 活动流默认同源,修复反代部署连不上 :8787
|
2026-10-03 08:10:35 +08:00 |
|
Autumn-27
|
e2c8a23a98
|
fix(web): SSE 活动流默认同源,修复反代部署连不上 :8787
sseUrl() 原先无条件把 SSE 地址拼成 ${hostname}:8787,连生产静态导出
也带这个硬编码。反代到 443 的部署里页面从 https://域名/ 加载,SSE 却被
指向 https://域名:8787/...,而 8787 未对公网开放,导致活动流连不上、反复重连。
改为用 NODE_ENV 区分:生产默认同源(相对路径),仅 next dev 保留 :8787
以绕过 Next.js /api 反代对 SSE 的缓冲。NEXT_PUBLIC_SSE_BASE 覆盖口保留。
验证:NEXT_EXPORT=1 next build 后生产包里 :8787 分支已被 tree-shake。
补充 README 反向代理部署文档(同源说明 + nginx 关缓冲配置)。
Closes #169
|
2026-10-02 20:10:08 -04:00 |
|
Autumn
|
160fe13c24
|
Merge pull request #187 from Autumn-27/fix/notify-digest-and-mask
fix(notify): 汇总模式退化、目的地留空误判、SMTP 缺 SSRF 守卫
|
2026-10-01 19:00:43 +08:00 |
|
Autumn
|
314105e827
|
Merge pull request #185 from lucksec/feat/vuln-im-push
feat(notify): 漏洞发现支持推送到钉钉/飞书/企业微信等六种渠道
|
2026-10-01 18:58:50 +08:00 |
|
Autumn-27
|
5081d95b99
|
fix(notify): 邮件渠道的 SMTP 拨号补上 SSRF 守卫
emailDial 用的是裸 net.Dialer,没挂 blockInternalDial,Validate 也只检查
host 非空。于是 SMTP 是整套 SSRF 防护里唯一的缺口:host 填 169.254.169.254
或 127.0.0.1 能直接连上,而 smtp.NewClient 握手失败时会把对端返回的那一行
(textproto 的 short response)包进错误、经 last_error 由投递历史接口回显,
正是其它渠道已经关掉的半盲读原语;「连接被拒 vs 超时」的耗时差异还能
用来探测端口。
拨号阶段是最终生效点,也覆盖 DNS 重绑定,与 HTTP 系渠道共用同一道守卫。
RFC1918 私网继续放行,与 isBlockedDialIP 既有的取舍一致——内网自建 SMTP
中继是常见的合法部署。
这个缺口没有测试会发现:本包 TestMain 全局打开了 ARTEX_NOTIFY_ALLOW_LOCAL,
邮件用例无论守卫在不在都会通过。新增的两条用例自己清掉该变量,
并配一条反向用例确认显式放开后本机 SMTP 仍可投递。
|
2026-10-01 06:43:48 -04:00 |
|
Autumn-27
|
77834f0080
|
fix(notify): 目的地字段留空不应被判成地址变更
Telegram 渠道从第二次保存起会永久失败,用户什么都没改也存不上:
新建时 base_url 留空(用官方 API 地址),创建路径直接存下 base_url:""
→ 第一次保存,MergeConfig 把空串当显式清空、delete 掉该键
→ 第二次保存,前端照常提交 base_url:"",而 stored 里已经没这个键
→ sameConfigValue("", nil) 比较 `""` 与 `null`,判为不等 → changed=[base_url]
→ bot_token 是掩码回显值 → 400「目标地址已变更,请同时重新填写凭据字段」
此后每次保存都失败,除非重新粘贴一遍 Bot Token,而错误提示还把人
往「凭据有问题」上引。
根因是 MergeConfig 与 sameConfigValue 对「空」的口径不一致:前者认为
空串就是「该删掉这个键」,后者认为 "" 与键不存在是两个不同的值。
现在比较前先归一化,口径与 MergeConfig 的清空判定对齐。
这是上一轮修「改目标地址、保留凭据」那条凭据外发路径时引入的回归——
守卫本身是对的,只是把一个没变的空字段误判成了地址变更。配套用例覆盖了
两个方向的真实变更(空→自建反代、自建反代→空)仍必须要求重填 Token,
确认防护没有被削弱。
|
2026-10-01 06:43:48 -04:00 |
|
Autumn-27
|
93c1d39df3
|
fix(notify): 汇总模式按消息计量限流,批次大小不再被每轮请求预算掐死
令牌桶的额度此前被同时当成两个量纲用:对实时模式它是「发几条消息」,
对汇总模式却被直接当成「一批装几条漏洞」传给 ClaimDigestBatch。
notifyMaxSendsPerChannelPerTick(=5)是由租约时长倒推的 HTTP 请求预算,
而一个汇总批次只发一次请求,两者本不该相乘。稳态下更糟:rate_per_min=20
的渠道在 3 秒的 tick 里只补得到 1 个令牌,于是每条汇总消息只装 1 个漏洞,
头部还写着「近 30 分钟新增 1 个漏洞」——digest 退化成带汇总文案的实时推送,
MaxDigestBatchSize(500) 永不可达。
改为统一按**消息条数**计量:一批漏洞合成一条消息、消耗一个令牌,
rate_per_min 对 digest 依然生效(每分钟最多这么多条汇总消息),
而批次大小只受 MaxDigestBatchSize 这个内存上界约束。
ClaimDigestBatch 原先的注释声称「单批同时受限流额度与内存上界约束」,
那正是本问题的来源——限流额度本不该充当批次大小。注释一并改掉,
免得下次又按「rate_per_min 对 digest 不生效」把它改回去。
顺带让 takeTokens 接受 want 上限:原先整桶抽空后才由调用方截断,
多出来的令牌(飞书默认 100/min 时是 95 个)直接丢弃,渠道这一轮
没有待发投递时也照扣,注释声称的突发容量在任何情况下都做不到。
决策收在 digestTickPlan 里由新增用例直接钉住。现有端到端用例都手动给
stepDigest 传一个够大的 limit,绕过了 step 里的额度计算,所以覆盖不到这里。
|
2026-10-01 06:43:29 -04:00 |
|
Autumn
|
50b7b2a05b
|
Merge pull request #184 from Autumn-27/fix/finding-asset-tree-scroll
fix(findings): 「按资产」视图资产列表溢出时补回滚动条
|
2026-09-30 16:17:08 +08:00 |
|
Autumn-27
|
4b1eda8e92
|
fix(findings): 「按资产」视图资产列表溢出时补回滚动条
左侧资产树的滚动容器靠 height:100% 取高,但外层卡片只给了 max-height
没有确定高度,百分比高度解析失败,资产多时列表撑破卡片或被截断且无法
滚动。改为把高度上限直接放到资产树的原生滚动容器上(overflow-y-auto +
max-h,随窗口自适应),资产少随内容收缩、资产多封顶并出滚动条。
Closes #170
|
2026-09-30 04:16:43 -04:00 |
|
Autumn
|
b590898d1f
|
Merge pull request #183 from Autumn-27/feat/intercept-delete-path
feat(intercept): 新增内置拦截规则「删除类接口路径」
|
2026-09-30 16:15:15 +08:00 |
|
Autumn-27
|
527092f23b
|
feat(intercept): 新增内置拦截规则「删除类接口路径」
内置的 HTTP 破坏性规则只认 DELETE 方法(curl -X DELETE、requests.delete(、
method:'DELETE'),路径类规则的词表又只有 /clear /wipe /flush /purge /truncate
/drop /destroy /factory-reset /reset-all。而多数应用的删除接口用 GET/POST 就能
触发,于是 `curl 'http://t/api/user/delete?id=1'` 不命中任何内置规则,会真实删掉
目标数据。
补一条 deny 规则覆盖 /delete /del /remove /unlink /erase /destroy,允许
/deleteAll、/delete_user、/delete-user 这类后缀形式(destroy 是重复覆盖:v1 那条
不允许后缀,/destroyAll 是漏的)。动词后强制跟分隔符,/delivery、/details、
/delta、/delegate 不会被误拦。
种子走独立标记位 intercept_default_rules_v3,已有实例升级后也会拿到——改 v1 的
字面量对老库无效(标记位已是 done)。插入带 WHERE NOT EXISTS 兜底,标记位丢失也
不会插重复。正则提为包级常量,配纯正则单测(不依赖 DB)覆盖命中与误伤两侧。
|
2026-09-30 04:12:57 -04:00 |
|
Autumn
|
a8afd0bb98
|
Merge pull request #182 from Autumn-27/feat/traffic-clear-all
feat(traffic): 流量列表新增「清空全部」,并借空库时机压实索引
|
2026-09-30 14:55:47 +08:00 |
|
Autumn-27
|
2f5f7c0227
|
feat(traffic): 流量列表新增「清空全部」,并借空库时机压实索引
一次删除全部流量记录,忽略当前筛选条件。与按 host 删除的两条路径相比多做
两件事:
- 清理索引已不再记录的历史 host 目录。按 host 删除只能从索引反查目录,
行已消失的孤立目录会一直留着;「清空全部」既然语义是不留残余,就直接
扫顶层目录(跳过 _index/_blobs/_ca/_delete_staging)。
- 收尾做一次全量压实(optimize + VACUUM + wal_checkpoint(TRUNCATE)),把
索引占用的磁盘空间还给系统,并把实际释放量返回给前端提示。
VACUUM 的耗时与临时空间只和它保留的内容成正比,所以空库是做全量压实唯一
免费的时机——也正因如此,这一步顺带成为已有实例的转换途径:auto_vacuum
只能通过 VACUUM 生效,清空一次之后旧库即转为增量回收模式,此后日常按
host 删除就能自行回收空间(TestDeleteAllConvertsLegacyIndex 覆盖)。
已绑定到漏洞的流量证据保存在独立的证据库中,不受影响——绑定时已拷出独立
副本,正是为了让热流量可以随时清空而不带走证据。确认弹窗里明确写了这点。
前端把「清空全部」做成 outline 样式而非第二个 destructive 按钮:它忽略一切
筛选条件,不该看起来和「删除该目标」只差一次误点;无流量时禁用。
测试:新增 TestDeleteAllPurgesAndCompacts(清空后索引、正文、blob 引用与
孤立目录全清,空间回收到 1/8 以下,清空后仍可继续录制)与
TestDeleteAllConvertsLegacyIndex(旧库经清空后转为增量回收,随后普通删除
即可回收)。
|
2026-09-30 02:50:49 -04:00 |
|
Autumn
|
61d486160e
|
Merge pull request #180 from Autumn-27/fix/traffic-index-reclaim
fix(traffic): 删除流量后把索引空间真正还给操作系统
|
2026-09-30 13:54:28 +08:00 |
|
Autumn-27
|
3227f2e54c
|
fix(traffic): 删除流量后把索引空间真正还给操作系统
删除流量只让数据不可见,磁盘占用从不下降。两处原因叠加:
1. SQLite 删行仅把页挂到 freelist,而索引库建库时未启用 auto_vacuum,
文件永不收缩。256KB 以下的正文全部内联在这个库里,所以体积主体就在
这里,且只增不减。
2. ex_fts 是 contentless_delete 全文索引,DELETE 只写 tombstone、不回收
原 postings,从来没有合并过——删流量反而让索引变大(实测 exchanges
清零后 ex_fts_data 仍占 3.3MB / 840 行)。
trigram 索引约为正文体积的 2 倍,加上内联正文,抓包量大的实例会为早已
删掉的流量长期占用数倍磁盘:实测抓 6MB 文本正文 → 索引 16.2MB,删光后
仍是 16.2MB。
修复:
- 新建索引库在建表前启用 auto_vacuum=incremental。该 pragma 只在库中尚
无表时可设,且只有紧随的 VACUUM 才把它写入文件头,两步都必须落在同一
条连接上,故新增 initIndex 固定一条 *sql.Conn 串起 pragma 与建表。
- 新增 reclaim/reclaimChunk:删除提交后在后台分块执行全文索引增量合并、
incremental_vacuum 与 wal_checkpoint(TRUNCATE)(不做 TRUNCATE 则空间
留在 WAL 里、文件大小不变,PASSIVE 也清不掉)。接入 DeleteHost、
HostDeleteStage.Commit 与 RecoverHostDeleteStages 三条路径。
- 回收分块进行并在块间释放写锁:record() 由 go-mitmproxy 在把响应写回
客户端之前同步调用,一次性回收数 GB 会连带卡住被测请求。Close 先发停止
信号,剩余预算留给下次删除,不拖住进程退出。
- 终止条件按「是否有进展」判定:incremental_vacuum 只能释放挪得到文件
末尾的页,残留少量空闲页是正常结果;另加步数上限兜底。fts5 无法查询
索引是否已合并完(其特殊 INSERT 自身即计一次 changes),故改为固定合并
预算,未做完的留给后续删除。
- busy_timeout 改由 DSN 提供:它是每连接设置,原先的 db.Exec 只配到池中
碰巧被选中的那一条,其余连接在有写者时会立即失败而非等待。驱动按第一个
'?' 切分 DSN,故数据目录路径含 '?' 时退回裸路径 DSN。
已有实例的索引库仍是旧模式(auto_vacuum 无法事后开启),incremental_vacuum
在其上为空操作,启动时打印提示;此类库的 tombstone 增长已止住,已占体积
待后续「存储压缩」入口一次性回收。
测试:新增 reclaim_test.go(空间回收回归、tombstone 合并、新库模式、旧库
不卡死)与 upgrade_test.go(旧装机升级后同库同数据、全文与正文可用、
legacy path 行不受影响;以及降级回旧二进制仍可读写)。
|
2026-09-30 01:44:44 -04:00 |
|
Autumn
|
ca5512b48f
|
Merge pull request #179 from Autumn-27/feat/traffic-search-filter-sort
feat(traffic): 流量列表支持内容检索、路径/状态码/长度筛选与列排序 (#177)
|
2026-09-30 10:04:15 +08:00 |
|
Autumn-27
|
a4960b514e
|
feat(traffic): 流量列表支持内容检索、路径/状态码/长度筛选与列排序 (#177)
- 后端 traffic.Page 改为 PageQuery:新增响应内容(FTS)、路径(url_template)、
状态码(精确/Nxx 分桶)、响应长度范围筛选,并支持按 ts/status/resp_len 排序
(尾随 id DESC 保证分页稳定);补 status/resp_len 两个索引(IF NOT EXISTS,旧库自动生效)
- server getTraffic 解析 body/path/status/resp_min/resp_max/sort/order 参数
- 前端流量页新增高级筛选行(响应内容/路径/状态码/长度范围)与可排序表头,
排序偏好持久化到 localStorage;抽出公共组件 ui/sortable-head
- 仅改动前端页走的 Page,不动 Agent 工具的 query 契约
|
2026-09-29 21:58:17 -04:00 |
|
Autumn-27
|
02b1dbe6f8
|
chore(deps): 升级 norma 到 v0.4.3——工具输出全局兜底截断(harness 统一 CaptureOnce),任何工具都不再溢爆上下文
|
2026-09-29 21:14:08 -04:00 |
|
Autumn-27
|
71794729fc
|
fix(tools): MCP/自定义工具输出统一走 Capture 截断,修复 mcp 截断不生效 (#176)
|
2026-09-29 10:09:23 -04:00 |
|
Autumn-27
|
69fe9357d3
|
chore(deps): 升级 norma 到 v0.4.2——修复 noa 压缩后 thinking/tool 消息被 provider 拒绝(#174)
|
2026-09-29 04:18:58 -04:00 |
|
Autumn-27
|
86162d7eda
|
docs(changelog): 定版 0.3.14
|
2026-09-24 13:35:48 -04:00 |
|
Autumn-27
|
87b3c3c770
|
feat(tasks): 漏洞列改为按严重度分档显示 严/高/中/低
- TaskListMetricsAll 用 COUNT(*) FILTER 按 severity 分四档统计(同一条查询)
- TaskListMetrics.Findings 及 TaskDTO.findings 由数字改为 {critical,high,medium,low}
- 列表页「漏洞」列渲染 x/x/x/x,配色沿用 severity 语义、为 0 的档位弱化
- severity 为空/白名单外的记录不计入任一档;mock 同步为对象结构
|
2026-09-24 13:32:45 -04:00 |
|
Autumn-27
|
e65d3e5202
|
feat(tasks): 任务列表新增漏洞数量列,描述/目标列收窄
- 任务列表接口 TaskListMetricsAll 批量统计每任务的漏洞数(findings 表,
按 task_id),经 TaskDTO.findings 下发;列表页新增「漏洞」列,>0 高亮
- 描述/目标列宽 max-w-xs → max-w-40,目标列补 title 悬浮全文
- mock data/handler 同步补 findings 字段
|
2026-09-24 13:26:22 -04:00 |
|
Autumn-27
|
9bc8d16a0b
|
fix(graph): 折叠后消除 digest↔finding 的反向重复边
yields(A→B) 与 derived_from(B→A) 互为逆关系,原图因产出/引用的 intent 不同
不成环;折叠进同一 digest 后两条边塌缩到 digest↔finding 同一对节点,分层布局
把其中一条画成叠着的反向箭头。重连后丢弃已存在正向 yields 的反向 derived_from,
保留生产方向(→成员)。
|
2026-09-24 13:23:06 -04:00 |
|
Autumn-27
|
b5704eb361
|
refactor(graph_overview): related_tasks 冷区统一走 coldDigestsRecent 并封顶
- coldDigestsRecent 改为接收 store 的自由函数,主概览与关联任务概览共用
- related_tasks 的 cold_digests 由无上限的 activeDigestBodies 换成
coldDigestsRecent(ts, 6):按最新成员时间排序、每源截 6,溢出 digest id
带 inherited/source_task_id 入 cold_digests_more,仍可 expand_digest 展开
- 删除随之无用的 activeDigestBodies
|
2026-09-24 13:11:28 -04:00 |
|
Autumn-27
|
3aac6754a8
|
refactor(graph_overview): 概览各列表加数量上限,止住上下文膨胀
用"最新一窗 + 计数/pull 兜底"替换 hot/cold 拆分与 balancedCap:
- recent_facts 20、recent_done_intents 12、open_intents 30(按 priority)
- cold_digests 15,按最新成员时间(max member id)降序,溢出的更旧 digest
只给裸 id(cold_digests_more),仍可 expand_digest 展开
- 新增 CountOpenIntents,frontier_open 报开放意图真实总数(与截断视图解耦)
- 删除 balancedCap/unfoldedCap/unfolded_truncated 及其测试
掉出窗口的节点不丢:facts/done_intents_total/frontier_open/findings_total
计数在,list_facts/list_findings/node_detail/expand_digest 可按需回捞
|
2026-09-24 13:05:27 -04:00 |
|
Autumn-27
|
43d1743dc0
|
refactor(graph_overview): finding_list 限最新 10 条,findings 计数改名 findings_total
- finding_list 只带最新一窗(≤10,vulnNodes 按 id 降序即最新在前),
全量/更早的用 list_findings 取
- 顶层计数字段 findings → findings_total,与 done_intents_total 命名惯例
一致、并与 finding_list 明确区分计数/明细;同步 planner 验收提示文案
|
2026-09-24 12:32:43 -04:00 |
|
Autumn-27
|
06a43f37ff
|
refactor(graph_overview): 精简态势概览字段
- 删除 cold_index 字段及其 expand_index 工具(含两处注册),移除
仅服务它的 coldDigestOverview 分桶逻辑(改用 activeDigestBodies)
- 删除 covered_members 字段(悬空血缘解析表)
- 删除 coverage.scope 字段(范围根资产 + company 富化)
- finding_list 每条仅保留 id/summary/from_intent,去掉 evidence/assets,
并清理随之无用的 findingMeta 预计算与 assetValue 辅助函数
|
2026-09-24 12:24:01 -04:00 |
|
Autumn
|
bf7f414477
|
Update CHANGELOG.md
|
2026-09-19 23:37:57 +08:00 |
|
Autumn-27
|
7b92395aa0
|
docs(changelog): 版本号改为 0.3.13
|
2026-09-19 11:23:33 -04:00 |
|
Autumn-27
|
2943eb2ea6
|
docs(changelog): 定版 0.4.0
|
2026-09-19 11:20:03 -04:00 |
|
Autumn-27
|
37950f4a6f
|
fix(task-archive): 遇到符号链接跳过而非整包失败
归档格式端到端只支持普通文件与目录(解包端对其它类型直接报错),原打包器遇到
任何 symlink 即整包失败(task archive refuses symlink),导致工作目录里一条软链
就卡死整个任务归档。改为跳过该符号链接并记日志:lstat 不跟随、不越出目录树、
不写 symlink 条目;链接指向树内时目标文件仍会被单独遍历归档。安全防护不变。
新增 TestTaskArchivePackageSkipsSymlink 覆盖。
|
2026-09-19 11:08:15 -04:00 |
|
Autumn-27
|
33c26dc72a
|
fix(intercept): 收紧裁判输出协议,减少 1024 截断导致的 fail-open
- 裁判 comment 上限 500→120 汉字,每段一句话、宁短勿长,合规裁决远低于
MaxTokens=1024,基本消除截断(截断会致输出无法解析而按失败策略放行)。
- 硬化「只输出 JSON、不带思考/前言/代码块包裹」,减少非 JSON 前言吃掉 token
预算。保留 实际操作/成功后的后果/命中规则 三段结构,与 ParseVerdict 一致。
- docs(readme): 精简审批详情/上下文模型审查一节。
|
2026-09-19 10:24:08 -04:00 |
|
Autumn-27
|
777730e255
|
feat: 任务模板支持预设分类与任务级拦截/允许规则
- db: task_templates 加 category_id(FK task_categories, ON DELETE SET NULL)
与 intercept_rules JSONB(规则快照);带幂等 ALTER 补旧库。
- db/task_templates.go: 用 JSONB 存取规则;PATCH 用 Set 标志区分改/清。
- server: 模板请求体加 category_id + intercept_rules,复用 buildTaskInterceptRules
校验;PATCH 靠原始 key presence 判断是否更新(可清分类为 null)。
- web: 抽共享组件 asset-intercept-rules-editor(NativeSelect 版,避免 Sheet 内
下拉 portal 误关抽屉),创建表单与模板管理器共用;模板管理器新增分类下拉与
规则编辑区,另存为模板带当前分类/规则;应用模板回填分类与规则。
|
2026-09-19 09:27:03 -04:00 |
|
Autumn-27
|
d5359e1f04
|
feat: 资产拦截接入执行链,新增任务级拦截/允许规则
在 agent 下发意图(add_intent)与插入资产(insert_assets)两处接入资产闸门;
并新增任务级规则(拦截 block + 允许 allow 白名单),创建任务时录入、任务详情
总览里可编辑。
- 匹配/执行(db/asset_intercept_match.go):MatchAssetInterceptRules 纯匹配
(exact/fuzzy 的 域名·IP·URL + CIDR,URL host 会拆出归类);EvaluateAssetGate
「先拦截后允许」闸门——命中拦截即禁止;未命中但存在启用的允许规则且都不命中→
不允许测试;无启用允许规则则不启用白名单。附单元测试。
- 执行点:add_intent 命中即不下发意图;insert_assets 命中即跳过 Upsert 及
AddAutoScope 副作用。均合并 全局∪任务级 规则。
- 任务级规则:表 task_intercept_rules(task_id FK CASCADE + action block/allow,
幂等 ALTER 补旧库);db/task_intercept.go 提供 List/Split/CRUD/事务插入;
创建任务随 intercept_rules 提交;CRUD 路由 /api/tasks/{id}/intercept-rules。
- 前端:新建任务抽屉多行录入(拦截/允许 + 类型,用 NativeSelect 避免 Sheet 内
下拉 portal 导致误关抽屉);任务详情总览新增规则管理卡片(增删改+启用开关)。
|
2026-09-19 09:06:22 -04:00 |
|
Autumn-27
|
dfc9d2fa2e
|
feat: 新增资产拦截规则(全局黑名单)增删改查
新增独立于命令拦截(intercept_rules)的资产拦截功能,仅提供规则的
存储与管理;具体匹配/拦截逻辑另行实现。
- db: 新增 asset_intercept_rules 表(schema.sql,幂等)与 CRUD 层
(db/asset_intercept.go);kind 支持全等/模糊的 域名·IP·URL 及 CIDR
- db: 首启动 seed 内置模糊拦截政府(.gov/.gov.cn)与教育(.edu/.edu.cn)
网站,settings 标记位门控,可禁用/删除且重启不复活
- server: /api/asset-intercept/rules 的 list/create/update/delete/toggle;
cidr、exact_ip 做格式校验
- web: 新增「资产拦截」页(/system/intercept/assets)与侧边栏入口、
api 与类型定义
|
2026-09-19 07:58:23 -04:00 |
|
Autumn-27
|
a590b415ba
|
chore(deps): 升级 norma 至 v0.4.1
|
2026-09-19 07:26:47 -04:00 |
|
Autumn-27
|
6f6be46480
|
feat(web): 登录前新增使用须知与免责声明弹窗,须勾选同意后方可登录
|
2026-09-18 08:09:05 -04:00 |
|
Autumn-27
|
9b82b02fe2
|
docs: 采用 AGPL-3.0 开源协议
|
2026-09-18 07:47:13 -04:00 |
|
Autumn-27
|
2951e10a4d
|
docs(readme): 完善许可与免责声明
|
2026-09-18 07:43:58 -04:00 |
|
Autumn-27
|
0ec51e3799
|
docs(changelog): 定版 0.3.12
|
2026-09-17 13:17:39 -04:00 |
|
Autumn
|
ec0ae108c4
|
Merge pull request #150 from Autumn-27/feat/broadcast-search-node-id
feat(web): 播报板搜索支持按节点 id 筛选
|
2026-09-18 01:09:30 +08:00 |
|
Autumn
|
8a3f40b6f8
|
Merge pull request #149 from Autumn-27/feat/intent-delete-modes
feat(intent): 意图删除支持假删除/真删除两种模式
|
2026-09-18 01:05:03 +08:00 |
|
Autumn-27
|
4756bb1c45
|
feat(intent): 意图删除支持假删除/真删除两种模式
删除入口区分两种模式(待领/运行中/已暂停的意图均可删除):
- 假删除(默认):意图置 state='deleted'、删除原因记入新字段 delete_reason,
保留节点与全部产出/血缘,不再在图上另挂 fact。
- 真删除:物理删除意图及「仅由它支撑」的独占子孙(沿 yields/derived_from
级联到叶子),避免孤立数据;共享节点、目标、任务根事实保留。被删意图先做
token rollup 并清理 activity/副会话,被删 finding 先删 findings 行。
两种模式都照常用 cancelled 触发通知 planner(带删除前捕获的意图摘要 + 原因),
planner 文案不再声称原因挂为事实。
- DB: 新增 SoftDeleteIntent、重写 CancelIntent 为深度独占级联;schema 加
delete_reason 列与 intent 的 deleted 状态(含旧库迁移)。
- 前端: 删除对话框加模式切换与动态说明,状态徽章/图标新增「已删除」,
播报板展开展示删除原因。
|
2026-09-17 12:52:57 -04:00 |
|
Autumn-27
|
6e3dbf6452
|
fix(web): 修复新对话未创建时上传文件报「缺少上传文件」
Composer 的 file input onChange 里同步执行 e.target.value = "" 清空了与
input 活绑定的 FileList。DraftChat 的 pickFiles 要先 await 建会话才取文件,
恢复执行时 FileList 已空,FormData 里没有 file 字段,后端返回 400。
改为在清空 value 之前把 FileList 快照成 File[] 再回调,onPickFiles 签名
随之改为 (files: File[]),调用方去掉各自的 Array.from。
|
2026-09-17 12:40:38 -04:00 |
|
Autumn-27
|
e2ada7e494
|
feat(web): 播报板搜索支持按节点 id 筛选
搜索框在内容/来源之外,新增节点 id 匹配:纯数字或 UI 展示的「#41」形式
都会精确命中该节点。服务端 NodesPage 在 payload/origin ILIKE 的 OR 组里
追加 id 精确匹配;mock 同步;补 NodesPage id 搜索测试。
|
2026-09-17 11:31:27 -04:00 |
|
Autumn
|
c6c5329a18
|
Merge pull request #147 from Autumn-27/feat/broadcast-node-detail
feat(web): 播报板节点详情展示上游节点信息与锚定资产
|
2026-09-17 23:28:03 +08:00 |
|
Autumn-27
|
d95f0d002d
|
feat(web): 播报板节点详情展示上游节点信息与锚定资产
上游/下游节点从只显示 id 改为悬停弹出节点名片(类型/状态/来源/时间/摘要/payload);
展开时顺带展示该节点锚定的资产(类型标签 + 可辨识文本)。
服务端 /exploration/nodes 新增 assets 字段(节点id→资产),读 exploration_anchors
并复用发现列表的资产打标逻辑;同页节点互引时用本页 items 兜底 refs 查找表。
|
2026-09-17 11:23:53 -04:00 |
|
Autumn-27
|
3b60191e86
|
refactor(engine): 移除从不执行的全局 planner/worker 空壳,就绪信号改用谓词
权威解析器(SetAuthoritativeAgentResolver)落地后,引擎每轮规划/worker 都走
per-task 的 agentsForTask 路由;applyLLM 经 buildPlannerWorker 构建、UseLLM 装入
的全局 planner/worker 从不被执行,仅充当 Ready() 的'已配置'探针。这层空壳是
功能容易被错误接线的温床(冷节点压缩此前就误接在它上面)。
改动:
- 删除 buildPlannerWorker、providerForAgent(仅前者调用)、Engine.UseLLM/snapshot/
Mode、Engine.planner/worker/mu 字段。
- Ready() 改为读 SetReadiness 注入的谓词(基于 s.llmOn);snapshotFor 去掉全局
兜底,权威解析器返回 nil 即表示该任务不可用(语义不变)。
- applyLLM 不再构建全局 pair;NewServer 注入就绪谓词。
- 相应更新 3 处依赖旧注入方式的测试(改用权威解析器注入)。
生产行为不变(全局 pair 本就从不执行);go build/vet 通过,server 测试失败集合
与基线一致(均为需 DB 的既有用例),无新增失败。
|
2026-09-17 09:40:06 -04:00 |
|
Autumn
|
cd5e779a24
|
Merge pull request #145 from Autumn-27/feat/broadcast-node-id
feat(web): 播报板每行显示节点 id
|
2026-09-17 21:19:50 +08:00 |
|
Autumn-27
|
3cde43f64f
|
feat(web): 播报板每行显示节点 id
|
2026-09-17 09:17:30 -04:00 |
|
Autumn-27
|
e78b35869c
|
chore(server): 删除已死的全局 mainAgent 与 agentsForProfile 等冗余构建
per-task 路由(agentsForTask)落地后,这些全局副本已无人使用:
- 全局 mainAgent(字段 + applyLLM 里的构造 + mainAgentRef getter):真正在跑的是
agentsForTask(t).main,全局那份从不被读取,mainAgentRef 无调用者。
- agentsForProfile:旧的任务 pin 路径,已被 agentsForTask 取代,无调用者。
- 随之失活的 profBundle 类型与 profAgents 缓存(仅初始化/清空、再无存取)一并移除。
均为编译器可确认的死代码,不改变任何执行路径;chat 的全局兜底(chatAgent/
chatAgentForProfile)、provider 缓存(provByProfile)等仍在用,保留不动。
全局 planner/worker 空壳与 Ready()/Mode() 改造留待第二步。
|
2026-09-17 09:07:40 -04:00 |
|
Autumn-27
|
564096c063
|
fix(web): 修复静态导出版任务列表页丢失全局头部
判断任务详情页的前缀 "/function/tasks/" 在 trailingSlash 静态导出下
会把列表页自身(pathname 为 "/function/tasks/")也匹配进去,导致发布
二进制里的列表页走了 full-bleed 分支,侧边栏折叠、搜索、版本号、主题
与账号入口整条 header 都不渲染;dev 与 mock demo 未开 trailingSlash
故看不出问题。判前缀前先剥掉尾部斜杠。
|
2026-09-17 08:55:04 -04:00 |
|
Autumn-27
|
55869705ad
|
Merge fix/cold-digest-wire-per-task-planner: 给 per-task planner 接上 Compactor,修复冷节点压缩从不触发
|
2026-09-17 08:53:30 -04:00 |
|
Autumn-27
|
96ff07579e
|
fix(digest): 给 per-task planner 接上 Compactor,修复冷节点压缩从不触发
引擎经权威解析器实际驱动的是 agentsForTask 构建的 per-task planner,但
cold-digest 落地时只在 buildPlannerWorker(全局 fallback pair)接了
SetCompactor,而该 pair 被解析器旁路、从不跑规划轮。结果 per-task planner
的 compactor 恒为 nil,OnPlannerRound 每轮直接 no-op —— round_no 不递增、
cold_since_round 从不盖章、digest 从不生成,与阈值无关。
在 agentsForTask 补上 SetCompactor,provider 用 plannerRuntime、model 用
task-router,与该 planner 实际运行所用模型一致(§4)。
|
2026-09-17 08:52:52 -04:00 |
|
Autumn
|
357ef6a5ab
|
Merge pull request #144 from Autumn-27/feat/exploration-broadcast-board
feat(web): 任务详情页新增探索链路播报板
|
2026-09-17 20:50:17 +08:00 |
|
Autumn-27
|
c03e008d7b
|
feat(web): 任务详情页新增探索链路播报板
按创建时间分页平铺展示探索节点,作为探索链路图的时间轴视图,
复用同一份 exploration_nodes 数据,不影响链路图。
- 后端 NodesPage/NodesByIDs/EdgesTouching:分页下推 SQL,
支持 kind/state 过滤、payload/origin 搜索、正倒序,
并补出当页节点的相邻边与对端节点
- 新增 GET /api/exploration/nodes(仅本任务节点,不含继承)
- 播报板:时间轴分行、按天分组、类型快筛、搜索防抖、
自动刷新、直播位未读提示、展开看上下游与 payload
- 补 mock,NEXT_PUBLIC_MOCK=1 下可无后端预览
|
2026-09-17 08:42:49 -04:00 |
|
Autumn-27
|
13ce2ea6e3
|
Merge PR #139: 支持按状态和判定来源筛选审批记录
合并 codex/approval-record-filters,解决与 #133 在
web/src/components/approval-records.tsx 的冲突:
- 导入同时保留 InterceptApprovalFilter 与 InterceptPending。
- load() 采用 #133 的独立待审批队列(Promise.allSettled 拉取
/intercept/pending),并把 #139 的 filter 参数透传给历史分页调用;
筛选只作用于历史记录,待处理队列不受 filter 影响,保证跨页/被筛
记录仍可审批。
- decide() 保留 #133 的乐观更新(移除 pendingRows 对应项)叠加 #139
决策后重新拉取以对齐筛选后的计数与行。
验证:前端 tsc 通过、Biome 仅剩预存告警;go build/vet 通过;
db TestInterceptApprovalFilters(8 子用例)与 server
TestInterceptFilterHTTP 在本地 dev 库均通过。
Closes #139
|
2026-09-16 11:16:26 -04:00 |
|
Autumn-27
|
a15285a7ae
|
Merge remote-tracking branch 'origin/main'
|
2026-09-16 11:07:02 -04:00 |
|
Autumn-27
|
6d0614ae79
|
Merge branch 'fix/demo-finding-traffic-mock':修 demo 漏洞详情页关联流量白屏
|
2026-09-16 11:06:12 -04:00 |
|
Autumn-27
|
5fbeb35b8c
|
fix(web): 补齐 demo 漏洞详情页关联流量 mock,修白屏
PR #102 给详情页加了 FindingTrafficPanel 并请求
GET /exploration/findings/{id}/traffic,但 demo mock handler 没有
对应路由,请求落到读兜底返回 {},前端读 data.bindings.length 时
因 undefined 崩掉整个概览 Tab —— 漏洞详情页白屏、展示不出信息。
补齐关联流量的全套 mock 路由(列表/绑定/编辑/解绑/排序/报文详情/
正文分页),返回与后端 db.FindingTraffic 一致的结构并维护内存态;
为 5 条代表性漏洞预置语义匹配的流量证据,其余走空状态;列表与详情
接口补上 traffic_count。
|
2026-09-16 11:05:21 -04:00 |
|
Autumn-27
|
7f71f77d16
|
fix(changelog): 移除历史遗留的裸 NUL 字节,恢复文本格式
0.3.10 的 /btw 条目把 NUL 字符本身字面写进了反引号,导致整个
CHANGELOG.md 被 git 和编辑器判为二进制/显示乱码。改为可读的 \u0000。
|
2026-09-15 12:39:49 -04:00 |
|
Autumn-27
|
8ee890771f
|
docs(changelog): 定版 0.3.11
|
2026-09-15 12:37:19 -04:00 |
|
Autumn-27
|
95bcd4ef9c
|
Merge branch 'feat/noa-experimental':noa 实验性上下文压缩
|
2026-09-15 12:09:24 -04:00 |
|
Autumn-27
|
c4579637dc
|
refactor(noa): 归档集中到 <workDir>/noa 下,不再分散在任务目录
各 agent 的 noa 归档基目录由本 run 的工作目录改为全局 workDir,
统一落在 <workDir>/noa/<SessionID>/。SessionID 全局唯一,同一基目录
内互不冲突。
|
2026-09-15 12:01:38 -04:00 |
|
Autumn-27
|
865d52267d
|
feat(settings): 增加实验功能开关,可开启 noa 上下文压缩
系统设置新增「实验功能」区块,内含 noa 模型驱动上下文压缩开关(默认关)。
开启后平台接入的四类 agent(planner / worker / 主 agent / 对话)由 noa 接管
上下文压缩,取代内置 compaction;关闭即恢复内置压缩。
- agent: 新增 enableNoa 共享接入器(noaadapter.Enable 唯一入口,all-or-nothing),
四类 agent 各加 noaEnabledFn 解析器 + SetNoaEnabled,每 run 读一次,切换只影响
之后启动的 run,无需重建 agent。归档落在各 agent 本 run 工作目录下(任务级持久),
session id 与 transcript 同规则。启用失败经 onWarn 上报并回退内置压缩,不中断任务。
- server: settings key noa_compaction + Manager 读写;8 处 agent 装配点注入平台级
解析器(server 5 + task_llm 3);GET/PUT /api/settings 增加字段。
- web: 系统设置页新增实验功能卡片与开关(乐观更新、失败回滚),类型与 mock 补字段。
官方默认行为不变:开关默认关闭时 noaadapter.Enable 不被调用,内置 compaction
原样工作。
|
2026-09-15 09:20:35 -04:00 |
|
Autumn-27
|
4ae319feca
|
chore(deps): 升级 norma 至 v0.4.0(引入 noa 上下文压缩能力)
|
2026-09-15 09:11:55 -04:00 |
|
Autumn
|
0d6fa880b8
|
fix(intercept): 模型裁决被代码块包裹时不再静默放行 (#126)
ParseVerdict 要求裸 JSON,而模型把 JSON 套进 markdown 围栏是常见偏差。
围栏导致解析失败后,reviewer 返回错误、Judge 走 FailAction,其默认值是
allow —— 模型判定的 DENY 会被静默降级为放行,审批记录只显示“模型输出
无法解析”,看不到模型其实给了拒绝。
解析入口前置一次围栏解包。这是确定性解包而非修复:载荷仍交由原
ParseVerdict 严格校验,重复字段、多余字段、多个对象、尾部残留的判定
全部不变。
要求开围栏与闭围栏同时存在。回复在 MaxTokens 处被截断时的形态正是
“有开围栏、无闭围栏”,对其补全会造出模型从未给出的裁决,因此这种输入
继续视为无法解析。
测试:原先断言“围栏必须拒绝”的用例改为接受,另补未闭合围栏、围栏后
带尾随文本、散文夹 JSON 三条必拒用例。
|
2026-09-15 20:40:41 +08:00 |
|
Autumn-27
|
234bd8bf8e
|
test(side): SSE 扫描出错直接失败,不再误判为未收到累积请求
|
2026-09-15 07:54:33 -04:00 |
|
Autumn-27
|
5963281582
|
fix(agent): 探索图工具在无任务上下文时拒绝而非 nil 崩溃
buildDomainReg 构造的 server 级 ToolSet 恒持 nil ExplorationStore(taskID=0),
tools 表可把其中任一工具绑给不在任务内运行的 agent(auto/pentest/reporter/
自定义/旁路提问)。node_detail 等探索图工具直接解引用 t.ts,被这类 agent 调用即
nil deref;panic 发生在 harness 自己的 goroutine 上,server 侧任何 recover 都
够不到,整进程退出,重启后调度器又拉起同一 agent 再崩,形成崩溃循环。
- 新增 readExpTool/writeExpTool + needExploration:t.ts==nil 时返回可读的工具
错误(提示改用带 task_id 的跨任务读取工具),把 17 个探索图工具切过去
- anchorOwner 补判空
- AugmentTools 出口给每个工具套 guardPanic:handler panic 降级成工具错误并打
stack,覆盖域工具/SDK/MCP/skill,进程不再陪葬
- 注明 buildDomainReg 的 nil-store 契约
|
2026-09-14 13:56:56 -04:00 |
|
Autumn-27
|
5db71f7c53
|
fix(evidence): traffic_search 描述迁移出错不再中断后续 reporter 迁移
description UPDATE 失败时原会 return 整个 seedFindingWorkflowTools,连累
independent 的 v2_reporter 迁移一起被跳过。改为出错仅 log、不置 flag(下次
启动重试),继续执行后续迁移。
|
2026-09-14 12:44:15 -04:00 |
|
Autumn-27
|
f2589ad47c
|
fix(web): 修复 demo 任务详情页旁路提问历史缺失导致的整页崩溃
mock 模式下 GET /api/tasks/<id>/side-questions 无路由,被读兜底当集合返回
[],data.items 为 undefined,旁路 hook 的 merge() 迭代抛 TypeError: t is not
iterable,异常在 setState updater 中经 render 重抛、catch 接不住,整页被错误
边界接管。mock handler 显式返回空旁路历史,sideAPI.history 同时归一化返回值。
|
2026-09-14 09:37:08 -04:00 |
|
Autumn-27
|
90f31577f2
|
docs(changelog): 定版 0.3.10
|
2026-09-13 12:37:37 -04:00 |
|
Autumn-27
|
9eefeb3f32
|
docs(changelog): 补齐 Unreleased —— worker 回看工具/node_detail/add_hint 播报、回看工具补绑修复、/btw NUL 修复、合并触发去重
|
2026-09-13 12:22:21 -04:00 |
|
Autumn-27
|
a5abe8ec3c
|
style(agent): 清理 compaction.go 静态检查提示
- generationFor 移除未使用的 genBySig 参数(连同只写不读的 map 构造)
- 两处 WriteString(x+"\n") 改为 WriteString + WriteByte,避免多余拼接
- 一处 WriteString(fmt.Sprintf(...)) 改为 fmt.Fprintf
|
2026-09-13 12:05:11 -04:00 |
|
Autumn-27
|
3480760d4e
|
chore(bench): 补 .dockerignore 忽略项,bench 容器不再挂持久化卷
|
2026-09-13 11:39:05 -04:00 |
|
Autumn-27
|
edbc296e29
|
feat(agent): add_hint 触发的规划轮显式播报「本轮由新增 hint 触发」
此前 add_hint 走裸 notify,触发的规划轮 triggers 为空,开场白说"无具体变动",
hint 只折在 graph_overview 里让 planner 自己发现。仿照 set_goals/NotifyGoal,
让 add_hint 记一条 hint 触发事件并带上提示文本。
- TriggerEvent 增加 Hints 字段;renderTriggers 增加 hint 分支,播报「人新增了
N 条战略提示:…」
- ToolSet 增加 notifyHint 回调 + SetNotifyHint;add_hint 整批写完统一唤醒一次
(优先 notifyHint,未接则退回裸 notify),notify 从 addOneHint 上移到 handler
- 主 agent(server.go) 与跨任务编排(orchestration.go) 均接上 Task.NotifyHint
|
2026-09-13 11:36:31 -04:00 |
|
Autumn-27
|
0b9341ac8b
|
refactor(agent): 精简 worker 边界#2 措辞,聚焦"绕过手段走完再下结论"
|
2026-09-13 10:08:34 -04:00 |
|
Autumn-27
|
c9bfa35113
|
feat(agent): node_detail 也默认给 worker,并随回看工具一起补绑
worker 已能通过 search_all_worker_traces / get_worker_trace 拿到 intent_id/
节点 id,配套把 node_detail 也下放给 worker,便于就地查节点完整详情。
- WorkerTools() 增加 node_detail
- 从 seedWorkerReadToolsUnbind 解绑清单去掉 node_detail(保留 list_facts/
list_companies/list_worker_traces)
- 原 seedWorkerCrossTraceRebind 泛化为 seedWorkerReadbackRebind,补绑清单追加
node_detail,flag 升到 v2 让已跑过旧迁移的库也补上
|
2026-09-13 09:35:18 -04:00 |
|
Autumn-27
|
2ba395856d
|
fix(agent): worker 跨 work 回看工具被旧迁移误删,改绑定并补绑回
seedWorkerReadToolsUnbind 的解绑清单里仍列着 search_all_worker_traces /
get_worker_trace,而 d531ea9 已把这两个加进 WorkerTools()——新库启动时先
seed 进去又被这段迁移撸掉,导致 worker(含 benchmark 镜像)实际拿不到。
- 从解绑清单去掉这两个,只保留 list_facts/node_detail/list_companies/list_worker_traces
- 新增一次性 seedWorkerCrossTraceRebind:把这两个补绑回 worker,修复已跑过旧
v1 迁移、被误删的现存库;新库为无害 no-op
|
2026-09-13 08:58:17 -04:00 |
|
Autumn-27
|
d531ea9850
|
feat(agent): worker 增加跨 work 回看工具 search_all_worker_traces / get_worker_trace
worker 也可复用其他 work 的观察、避免重复劳动:search_all 无需先知 intent_id 按关键字全局捞命中步骤,get_worker_trace 锁定某条 work 后列步骤/就地搜/取完整内容。list_worker_traces 仍归 planner/main。
|
2026-09-12 13:05:01 -04:00 |
|
Autumn-27
|
44194a9ebc
|
fix(trigger): 合并触发会话按任务去重任务描述/目标,避免长目标重复撑爆消息
on_tool_call 等事件触发在 merge 时,每条事件都重复整段任务描述+目标;
当任务目标很长(如续跑继承事实)且短时间多次触发时,合并消息体积爆炸
(实测 39 条 submit_flag 连击 → 十几万字)。
- triggeredRun 拆出 taskDesc/taskGoal 任务级字段,message 只留事件正文
- by_task 合并:同任务头只写一次
- all 合并:按任务分组(首次出现排序、任务内保序),每任务头只写一次,
交错触发也不重复
- 单条触发由 finalTriggerMessage 补一次任务头
- 任务描述截 200 字、目标截 500 字,单份也有界
- 新增 trigger_merge_test.go 覆盖去重/交错/截断/定时无头
|
2026-09-12 09:26:38 -04:00 |
|
Autumn-27
|
e4c744a318
|
feat(search): 网络搜索新增 DeepSeek 官方来源
不单独配置凭据,直接复用当前激活的 LLM 配置(base_url/api_key/model)。
这个来源与 ddgs/brave/tavily 性质不同:DeepSeek 没有可直接调用的搜索接口,
搜索只存在于其 Anthropic 兼容 messages 接口内部,以 web_search_20250305
服务端工具的形式由 DeepSeek 服务端执行。由此带来几个必须让用户知道的差异,
已在设置页写明:
- 仅支持 DeepSeek 官方端点 + anthropic 协议。实测其 OpenAI 协议端点会直接以
"unknown variant, expected `function`" 拒绝一切服务端工具,web_search_options
之类的顶层字段则被静默忽略,没有可用的替代写法。
- 每次搜索额外消耗一次模型调用。
- 搜索请求由 DeepSeek 服务端发出,不经过搜索出口代理,也不计入流量留痕。
- 返回结果只有标题与链接,没有摘要(DeepSeek 只给 encrypted_content),需要正文
时仍由 WebFetch 抓取。
上述条件不做程序校验,仅在界面说明,由用户自行确认——配置不满足时搜索会在实际
调用时报错,与其它来源填错 Key 的反馈路径一致,可用「测试搜索」按钮实跑验证。
依赖 norma v0.3.8。
|
2026-09-12 07:13:46 -04:00 |
|
Autumn-27
|
abf701e03c
|
refactor(agent): 全局态势提示改松绑口吻,鼓励发散与跨意图线索上报
原措辞连用 4 个"绝不",且把上报写成"最多写进 fact"的退让,易让
worker 为自保而不敢深想、漏报跨意图关键线索。改为:唯一红线收窄到
"别真去执行别的意图",明确"发散是好事",上报改为"务必写进 fact"。
|
2026-09-12 06:12:55 -04:00 |
|
Autumn-27
|
159c587c2e
|
fix(script): start.bat 改用 CRLF 并切 UTF-8 代码页
start.bat 之前是 LF 换行。cmd.exe 解析批处理按字节偏移边读边执行,
只认 \r\n,全 LF 时会读串行,表现为 goto loop 被截断成 'oop'、
"75"( 不是内部或外部命令、: 运算符不存在等一连串报错,脚本根本跑不起来。
同时文件是 UTF-8 无 BOM,中文控制台默认 GBK(936),注释和 echo 全是乱码。
- 顶部加 chcp 65001,中文提示正常显示(artex 本身输出也是 UTF-8)
- 新增 .gitattributes:*.bat 钉 eol=crlf、*.sh 钉 eol=lf,
避免在 Linux 上编辑或重新 checkout 后又被打回 LF
|
2026-09-12 05:32:09 -04:00 |
|
Autumn-27
|
4ccb8f4ff2
|
fix(agent): list_assets 按任务范围过滤,修复任务间资产互串 (#59)
list_assets 此前把任务 id 写死为 0、裸查整个共享资产库,模型又无从写出
范围过滤条件,于是把别的任务的资产(尤其 IP)当成本任务目标,测试方向
被带偏。
- 新增 QueryDSLInScope / GetByIDsInScope:只返回落在【本任务及直接关联
任务】task_scope 内的资产,按归属匹配而非字面值(根域范围含其全部子域/
服务/接口,网段范围含段内主机及服务);越权 id 静默丢弃
- 新增 scopeTargetCTE(纯 scope 归属判定,不含 anchor/tested);whereBuilder
加占位符偏移,$1 留给 taskID
- 修复 IP 直连主机(http://1.2.3.4/api)无法被网段范围命中的盲区:谓词加
OR ts.net >>= try_inet(a.domain)
- 非任务上下文(Auto/pentest, taskID<=0)无范围可依,回退全库
- QueryDSL/CountDSL 原样未动,UI 的「测试资产」视图(按生产者过滤)不受影响
|
2026-09-12 03:25:47 -04:00 |
|
Autumn-27
|
16e87b48c2
|
fix(db): side_question checkpoint 入库前剥除 jsonb 不支持的 NUL 转义
HTTP/工具响应含裸 NUL 字节时,json.Marshal 将其编码为 \u0000 转义,
PostgreSQL jsonb 列拒绝并抛 SQLSTATE 22P05,导致 SaveSideSnapshot 的
INSERT 每秒失败数十次刷屏。新增 jsonbClean 在 marshal 后剥除真正的
\u0000 转义(按前置反斜杠奇偶判断,避免误伤字面 \\u0000),并订正
exploration.go 中 "json.Marshal already sanitizes" 的错误注释。
Closes #111, Closes #112
|
2026-09-12 03:00:28 -04:00 |
|
Autumn-27
|
42f0ff97d3
|
refactor(agent): 测试范围与资产覆盖度开关解耦,移除 insert_assets 的 related 入参
task_scope 是任务的授权边界、资产查询的过滤基准,覆盖度开关只该决定要不要
拿它当分母算指标,不该决定要不要累积范围本身。此前关闭覆盖度会让 auto 与
agent 两条写入路径同时失效,task_scope 只剩界面手工添加的行。
- insert_assets 的自动入范围(source='auto')无条件执行,不再判 coverageDisabled
- add_task_scope 移出 coverageOnlyTools,planner / 任务内主 Agent / 目标拆解
Agent 在覆盖度关闭时照样持有;list_untested_assets 仍随开关隐藏(纯覆盖度视角)
- 移除 insert_assets 每条资产的 related 入参:唯一作用是决定要不要入范围,值又
不落库(同一资产再次登记即作废、界面上也看不出谁被判为无关),连带删除
StripCoverageParams 及其专用的 deepCopyJSONMap / nestedMap
- add_task_scope 与 goalsScopeTail 的描述改为「授权边界」优先、「覆盖度分母」其次
|
2026-09-11 13:33:44 -04:00 |
|
Autumn-27
|
33d3d00c4b
|
docs(changelog): 定版 0.3.9
|
2026-09-11 12:59:32 -04:00 |
|
Autumn-27
|
aa3ef63121
|
docs(changelog): 补齐 0.3.8 以来的变更条目
|
2026-09-11 12:45:23 -04:00 |
|
Autumn-27
|
f5c38da8dc
|
Merge feat/one-click-update: 页面一键更新 + 守护启动脚本
|
2026-09-11 12:41:31 -04:00 |
|
Autumn-27
|
d69ab3b0f8
|
Merge remote-tracking branch 'origin/main' into feat/one-click-update
|
2026-09-11 12:41:02 -04:00 |
|
Autumn-27
|
44156a0a4c
|
feat(update): 页面一键更新 + 守护启动脚本
系统配置页新增「版本与更新」卡片,顶栏版本号旁在有新版时亮出提示胶囊。
更新链路:下载发布包 → 比对 SHA256SUMS → -h 冒烟测试 → 暂存 artex.new
→ 以退出码 75 退出 → 守护脚本重新拉起并完成换装,页面轮询 /api/health
等版本号变化后自动刷新。
新增 start.sh / start.bat 作为正式启动入口,只按退出码决定是否重新拉起
(0 停止 / 75 应用新版 / 其余崩溃退避)。校验、冒烟、换装、回滚全部收在
selfupdate 包里而不写进脚本:这些逻辑在 sh 和 bat 上要写两套,而它们恰恰
最不能出错——换上跑不起来的二进制后守护进程会反复拉起它,只能上机器手工救。
Docker 的 ENTRYPOINT 一并改为该脚本,并由它转发 SIGTERM,否则 docker stop
只发给 PID 1,artex 做不了优雅关闭会被 SIGKILL 硬杀。
失败保护两道闸门互补:无法 exec 由换装前的冒烟挡住,能执行但初始化崩溃
由启动计数兜住(连续 3 次失败自动回滚 artex.old,坏的留作 artex.failed)。
GitHub 查询结果后端缓存 30 分钟(失败 2 分钟)。未认证 API 是每 IP 每小时
60 次,且这 60 次是服务器 IP 上所有用户共用的,顶栏每次整页加载都查一次,
不缓存会很快耗光配额导致真想更新时反而查不动。手动「检查更新」带 force=1
绕过缓存。
安全:只认 GitHub 域名且强制 HTTPS(逐跳校验重定向),发布源写死不可配置;
升级文件挂在可执行文件所在目录而非 CWD(服务化运行时 CWD 可能是 /);
开发构建版本号不可比较,禁用一键更新。
走完整 zip 而非裸二进制,因为现有 Release 的 SHA256SUMS 只覆盖 zip,
这样无需改 CI,也兼容已发布的历史版本。
已知限制:Docker 下只换程序不换镜像(工具链不同步、重建容器会退回镜像
版本);不同步发布包里的 skills/;更新即重启会中断运行中的任务。
|
2026-09-11 12:39:59 -04:00 |
|
Autumn
|
3f8f072202
|
Merge pull request #110 from Autumn-27/feat/task-assets-dsl-search
feat(assets): 任务测试资产支持 DSL 搜索
|
2026-09-12 00:04:19 +08:00 |
|
Autumn-27
|
557317491b
|
feat(assets): 任务测试资产支持 DSL 搜索
任务详情「测试资产」接口/服务多时不好找。复用资产管理页的 DSL
搜索(字段自动补全 + 分页),搜索始终限定在当前任务范围内。
- 抽出共享组件 asset-dsl-search.tsx,资产页与任务页复用,UI/交互一致
- QueryDSL/CountDSL 增加 taskID 参数,taskID>0 时强制 AND $N = ANY(task_ids)
并补 task 来源信息;即便 DSL 内写 task_id 也无法越出当前任务
- 任务资产 tab 接入搜索框:有 DSL 走 searchTaskAssets,否则走 taskAssets
Closes #107
|
2026-09-11 11:59:46 -04:00 |
|
Autumn
|
1f258837f5
|
Merge pull request #109 from Autumn-27/fix/mcp-insecure-tls
fix(mcp): http 传输支持跳过 TLS 证书校验(自签证书)
|
2026-09-11 23:38:36 +08:00 |
|
Autumn-27
|
25b82f2544
|
fix(mcp): http 传输支持跳过 TLS 证书校验(自签证书)
MCP server 走 HTTPS 且用自签证书时,客户端 TLS 校验失败,报
"tls: failed to verify certificate" 无法连接。
mcp_servers 增加 insecure 开关(默认 false),置 true 时远程 MCP
客户端使用 InsecureSkipVerify 的 transport。stdio 传输不受影响。
- mcphttp.New 增加 insecure 参数
- db: MCPServer.Insecure 字段 + schema 加列(补 ALTER 兼容旧库)
- create_mcp/update_mcp 工具与前端 http 配置项增加勾选框
Closes #108
|
2026-09-11 11:37:56 -04:00 |
|
Autumn-27
|
cde3ce9b25
|
fix(btw): 非安全上下文降级生成旁路请求 ID
crypto.randomUUID 仅在 https/localhost 可用,经 IP+http 访问 Web UI 时
为 undefined,导致 /btw 提问抛 "crypto.randomUUID is not a function"。
改用与 sessions-tab / tasks 页面一致的降级写法。
|
2026-09-11 11:13:21 -04:00 |
|
Autumn-27
|
151bedcdf5
|
fix(btw): 无 Postgres 时跳过旁路测试,go.mod 补 uuid 直接依赖
server/side_questions_test.go 的 fixture 在拿不到数据库配置时走 t.Fatal,
导致未设置 ARTEX_PG_DSN 的环境跑 go test ./server 直接失败,掩盖真实回归。
改为 t.Skipf,与 server 包其余测试一致。
db/side_questions.go 直接引用 github.com/google/uuid,go mod tidy 将其
从 indirect 移到 direct。
|
2026-09-11 11:10:32 -04:00 |
|
Autumn
|
4d7d65a1cf
|
Merge pull request #106 from RuoJi6/codex/btw-side-question
feat: add /btw side questions
|
2026-09-11 23:08:46 +08:00 |
|