diff --git a/cmd/object-api-options-replication_test.go b/cmd/object-api-options-replication_test.go index e4bcee269..6ee25f4ac 100644 --- a/cmd/object-api-options-replication_test.go +++ b/cmd/object-api-options-replication_test.go @@ -1,7 +1,6 @@ -// Copyright (c) 2015-2025 MinIO, Inc. -// Copyright (c) 2025-2026 PGSTY +// Copyright (c) 2026 Feng Ruohang // -// This file is part of MinIO Object Storage stack +// This file is part of Silo Object Storage stack // // This program is free software: you can redistribute it and/or modify // it under the terms of the GNU Affero General Public License as published by diff --git a/cmd/object-copy-replication-tagging_test.go b/cmd/object-copy-replication-tagging_test.go index f5538c9f5..e187663d6 100644 --- a/cmd/object-copy-replication-tagging_test.go +++ b/cmd/object-copy-replication-tagging_test.go @@ -1,7 +1,6 @@ -// Copyright (c) 2015-2025 MinIO, Inc. -// Copyright (c) 2025-2026 PGSTY +// Copyright (c) 2026 Feng Ruohang // -// This file is part of MinIO Object Storage stack +// This file is part of Silo Object Storage stack // // This program is free software: you can redistribute it and/or modify // it under the terms of the GNU Affero General Public License as published by diff --git a/docs/investigations/r4/implementation-review.md b/docs/investigations/r4/implementation-review.md new file mode 100644 index 000000000..67f5e7bae --- /dev/null +++ b/docs/investigations/r4/implementation-review.md @@ -0,0 +1,39 @@ +已完成独立复核:读了三份改动文件在 HEAD 的实际内容、`putOptsFromHeaders` 全函数与两条返回路径、`CopyObjectHandler` 的默认加密与标签排序段、`reconcileStoredObjectTags` 的三处生产调用点,以及全部指定日志与证据文件。 + +# R4 实现复核结论 + +**Verdict: GO_WITH_NONBLOCKING_NOTES(0 阻断项)** + +- 复核 HEAD:`dbcf8dec589deb5d91e17d295cb70997635f5b55` +- 代码/测试 diff SHA-256(按提供值记录):`c8cd6648f8ecea835ec74a038cdeaa82acaa3f36250395f97ead3260dc2fc0a5` + - 本会话无 shell,未重算该哈希;改为逐行比对 diff 与工作树三份文件,内容完全一致(`cmd/object-api-options.go`、`cmd/object-api-options-replication_test.go`、`cmd/object-copy-replication-tagging_test.go`)。 + +## 核验到的事实 + +- 生产改动确为一个字段 + 相邻注释:`cmd/object-api-options.go:459` 的 `ReplicationSourceTaggingTimestamp: taggingtimestmp`,变量来自 `:419-425` 已解析值,与非 KMS 路径 `:473` 对齐。未动解析、信任判定、KMS key/context、返回结构。 +- 影响面封闭:全仓该字段唯一消费点是 `cmd/object-handlers.go:1820`(COPY 标签排序)。PUT/POST/multipart 虽同经 `putOptsFromReq`,但无消费者,故不可能回归——与 R4/R5 切分一致。 +- 三条 KMS 触发路径真实可达:`object-handlers.go:1428-1433` 在 `copyDstOpts`(`:1454`)之前套用目的端默认;`bucket-sse-config.go:139-151` 在 `nil 配置 + AutoEncrypt` 与桶默认 KMS 两种情况下都写入 `aws:kms`,因此 explicit / auto / bucket 三种模式均进入 KMS 分支。 +- 回归证明成立:`baseline-final.log` 用 `-overlay` 换回未修复 constructor,失败面精确为「trusted × 有效标签时间戳 × SSE-KMS / SSE-KMS-context」和 6 个 KMS COPY 子测试(`tags="key=old"`、`kms=true`、HTTP 200),`none`/`SSE-S3`/`SSE-C`/非 trusted 全通过。修复后 `focused.log:194-204` 全 PASS。 +- 测试确实覆盖被要求的维度:信任边界(trusted=false 时 mtime/ETag/三时间戳全归零)、错误路径(trusted + 畸形值必须报错且错误串含头名)、SSE 序列化回环(KMS keyID/context 原样还原)、磁盘终态(每事件 `obj.GetObjectInfo` 读真实盘)、版本一致性、签名 GET 明文可读。全局 `GlobalKMS`/`globalAutoEncryption`/`set.getDisks` 均 defer 还原。 +- `race` exit 0、`vet` 空输出、`golangci-lint` 0 issues,均记录了与 HEAD 一致的三文件哈希。 +- 未发现 `verification.md` / `verification.json` / `consensus.md` 中与日志矛盾的陈述。(评审者版本/模型/effort 这类 provenance 声明不在我可验证范围,未作背书。) + +## 发现清单 + +| ID | 内容 | 阻断 | +|---|---|---| +| IMPL-01 | 单字段修复正确且充分,位置、变量、注释与 `:473` 语义一致 | 否(确认项) | +| IMPL-02 | 基线失败/修复通过的判别力成立,对照组不误报 | 否(确认项) | +| IMPL-03 | KMS 字面量相对 `getDefaultOpts` 仍缺 `ProxyHeaderSet`/`ProxyRequest`/`Speedtest`(`object-api-options.go:40-44` vs `:449-460`)。R4 范围外,已登记为 R4-06 | 否,不设为新合并门槛 | +| IMPL-04 | `metadata-directive: REPLACE` 下 `getCpObjMetadataFromHeader`(`:1143-1156`)返回全新 map,故 `:1818` 的 `lastTaggingTimestamp` 为空、`:1822` 解析失败使 handler 侧比较恒「incoming 胜」;真正的 stale 拒绝发生在写锁内的 `reconcileStoredObjectTags`(`erasure-object.go:1312-1315`)。测试终态断言仍正确,文档 R4-07 已明示此分工 | 否(R5 上下文) | +| IMPL-05 | 测试卫生:`bucket-kms` 模式写入的 `bucketSSEConfig` 未还原,仅因它是最后一个 mode、且 `ExecObjectLayerAPITest` 每后端重建对象层并 `resetTestGlobals()` 才安全;后续若在其后追加 mode 会继承默认 KMS | 否 | +| IMPL-06 | `object-api-options-replication_test.go:35` 局部变量名 `context` 遮蔽标准包名(本文件未导入该包),纯观感 | 否 | +| IMPL-07 | `focused.log` exit 1 的唯一失败是既有 `TestAPICopyObjectReplicaRetentionRemovalUnderBucketKMS`(`replication-trust_test.go:1284`,"Storage reached its minimum free drive threshold"),属本机磁盘余量环境问题,非本次引入;容量 overlay 是测试专用、未提交。新增 COPY 测试自带 `tagTestCapacityDisk` 包装,不受该阈值影响 | 否 | + +**没有发现阻断性正确性问题。** 生产语义、存储格式、API 与既有排序规则均未改变,无任何既有测试断言旧(缺陷)行为。 + +## 合并适配性 + +`dbcf8dec5` 直接位于实时 main `9ebe81c1b` 之上,可快进合并。按仓库 CI 通过为前提,本实现适合合入 main。 + +*(我未运行任何测试,也未查询 GitHub;以上仅基于源码阅读与所提供日志。)* diff --git a/docs/investigations/r4/implementation-review.metadata.json b/docs/investigations/r4/implementation-review.metadata.json new file mode 100644 index 000000000..f81bef75e --- /dev/null +++ b/docs/investigations/r4/implementation-review.metadata.json @@ -0,0 +1,33 @@ +{ + "baseline": "9ebe81c1b3611f9cc73e676b5b741c2be62c467a", + "reviewed_head": "dbcf8dec589deb5d91e17d295cb70997635f5b55", + "requested_model": "claude-opus-5", + "requested_effort": "max", + "cli_version": "2.1.270", + "diff_sha256": "c8cd6648f8ecea835ec74a038cdeaa82acaa3f36250395f97ead3260dc2fc0a5", + "started_at": "2026-09-15T15:59:41.004963+00:00", + "status": "completed", + "command": "/opt/homebrew/bin/claude --print --model claude-opus-5 --effort max --safe-mode --permission-mode plan --tools Read,Grep,Glob --strict-mcp-config --no-session-persistence --add-dir /Users/vonng/tmp/silo-r4-evidence-20260915-a9cb --output-format stream-json --verbose", + "completed_at": "2026-09-15T16:03:52.331640+00:00", + "assistant_models": [ + "claude-opus-5" + ], + "observed_model": "claude-opus-5", + "verdict": "GO_WITH_NONBLOCKING_NOTES", + "blocking_findings": 0, + "session_id": "c09bc4fb-85f1-4af8-a1de-c453398e4a20", + "duration_ms": 161469, + "subtype": "success", + "is_error": false, + "used_tools": { + "Read": 20, + "Glob": 3, + "Grep": 14, + "ExitPlanMode": 1 + }, + "raw_stream": "/Users/vonng/tmp/silo-r4-evidence-20260915-a9cb/merge-review-1/opus.jsonl", + "stream_sha256": "875f617454b27e15ab44d9b777de89643ee352e0ccb948faad570fc546261acc", + "review_sha256": "962ff88d2ffcb75cd692ec17017411d624de80dc120f8dedc675e0fe25009335", + "prompt_sha256": "e1341c721161229431b943ba18d89b740e94470803c099b9ae3d597fd50544a4", + "review_extraction": "The substantive review is an earlier assistant text block; result.result only repeats CLI plan-mode merge limitations. Full raw stream and all assistant text are retained." +} diff --git a/docs/investigations/r4/merge-verification.json b/docs/investigations/r4/merge-verification.json new file mode 100644 index 000000000..51deb4a3e --- /dev/null +++ b/docs/investigations/r4/merge-verification.json @@ -0,0 +1,84 @@ +{ + "original_reviewed_head": "dbcf8dec589deb5d91e17d295cb70997635f5b55", + "dco_signed_equivalent_head": "03027727d1d1b97d8beb83ac55569ea9a83dab23", + "notice_equivalence": { + "cmd/object-api-options-replication_test.go": { + "before_sha256": "1ea2a060987e32a4c76fce96ee974df475944c2d6ab482a4893e33daf7bca849", + "after_sha256": "c21fc8889a079085d9a882499a1cbe868278a3517580651f3bed1102e2a6aef8", + "package_body_sha256": "096f143c0b0a068581f9bb892f35ded0d65b6b60ab711f043236d27fbf51ca33", + "body_unchanged": true + }, + "cmd/object-copy-replication-tagging_test.go": { + "before_sha256": "5437a77e68736b4ce69de9c777675251fef24b0352dfe30bd8a836fc7ee810e3", + "after_sha256": "73f066ed7258d430f078ecc90e551ece878bd3d4672bc762094d434ff8fec23d", + "package_body_sha256": "6b5173db2ded2d54055073c3259be208a4d7c8eac0367687082877f1fd3bef15", + "body_unchanged": true + } + }, + "checks": { + "verifiers": { + "command": [ + "make", + "verifiers", + "GOLANGCI=/Users/vonng/tmp/silo-r4-evidence-20260915-a9cb/merge-review-1/golangci-serial" + ], + "exit_code": 0, + "started_at": "2026-09-15T16:04:55.536605+00:00", + "finished_at": "2026-09-15T16:07:03.252820+00:00", + "cwd": "/Users/vonng/.codex/worktrees/a9cb/silo", + "env_override": { + "GOMAXPROCS": "2", + "GOFLAGS": "-p=2" + }, + "source_sha256": { + "cmd/object-api-options.go": "25e2e9484fafd94d1b2c857b94373758e481893ad93fb1a063edf7746277accc", + "cmd/object-api-options-replication_test.go": "c21fc8889a079085d9a882499a1cbe868278a3517580651f3bed1102e2a6aef8", + "cmd/object-copy-replication-tagging_test.go": "73f066ed7258d430f078ecc90e551ece878bd3d4672bc762094d434ff8fec23d" + }, + "log_sha256": "e42a5bb55f5c1ebfcf02cebebf6d82cf1ec5a2d74590cdf838deba16dd80bfdf" + }, + "build": { + "command": [ + "make", + "build" + ], + "exit_code": 0, + "started_at": "2026-09-15T16:07:03.253715+00:00", + "finished_at": "2026-09-15T16:07:35.594062+00:00", + "cwd": "/Users/vonng/.codex/worktrees/a9cb/silo", + "env_override": { + "GOMAXPROCS": "2", + "GOFLAGS": "-p=2" + }, + "source_sha256": { + "cmd/object-api-options.go": "25e2e9484fafd94d1b2c857b94373758e481893ad93fb1a063edf7746277accc", + "cmd/object-api-options-replication_test.go": "c21fc8889a079085d9a882499a1cbe868278a3517580651f3bed1102e2a6aef8", + "cmd/object-copy-replication-tagging_test.go": "73f066ed7258d430f078ecc90e551ece878bd3d4672bc762094d434ff8fec23d" + }, + "log_sha256": "6ba9b545236be964861749c72e7609edf12b8f470df30d1ede8fd62f497e629b" + }, + "binary-version": { + "command": [ + "./silo", + "--version" + ], + "exit_code": 0, + "started_at": "2026-09-15T16:07:35.594918+00:00", + "finished_at": "2026-09-15T16:07:37.616706+00:00", + "cwd": "/Users/vonng/.codex/worktrees/a9cb/silo", + "env_override": { + "GOMAXPROCS": "2", + "GOFLAGS": "-p=2" + }, + "source_sha256": { + "cmd/object-api-options.go": "25e2e9484fafd94d1b2c857b94373758e481893ad93fb1a063edf7746277accc", + "cmd/object-api-options-replication_test.go": "c21fc8889a079085d9a882499a1cbe868278a3517580651f3bed1102e2a6aef8", + "cmd/object-copy-replication-tagging_test.go": "73f066ed7258d430f078ecc90e551ece878bd3d4672bc762094d434ff8fec23d" + }, + "log_sha256": "36317d06b691593fe0d74f88d053a24485500c15fc2001e857f2fc6fa5ba752a" + } + }, + "binary_version": "silo version DEVELOPMENT.2026-09-15T16-03-52Z (commit-id=03027727d1d1b97d8beb83ac55569ea9a83dab23)\nRuntime: go1.27.1 darwin/arm64\nLicense: GNU AGPLv3 - https://www.gnu.org/licenses/agpl-3.0.html\nCopyright: 2015-2025 MinIO, Inc.\nModifications: Copyright 2025-2026 PGSTY\nSource compatibility: based on MinIO technology\n", + "raw_evidence_directory": "/Users/vonng/tmp/silo-r4-evidence-20260915-a9cb/merge-review-1", + "all_function_and_test_bodies_identical_to_opus_reviewed_version": true +} diff --git a/docs/investigations/r4/merge-verification.md b/docs/investigations/r4/merge-verification.md new file mode 100644 index 000000000..2cc353368 --- /dev/null +++ b/docs/investigations/r4/merge-verification.md @@ -0,0 +1,36 @@ +# R4 合并前复核 + +用户已明确追加授权:使用 Opus 5 max 核实最终实现,确认无误后合并 main。本轮授权取代此前只交付本地补丁的范围限制。 + +## 真实实现评审 + +- 独立新调用:Claude Code 2.1.270,`--model claude-opus-5 --effort max`。 +- 复核代码提交:`dbcf8dec589deb5d91e17d295cb70997635f5b55`;当时实时 main 与 fetch 结果均为 `9ebe81c1b3611f9cc73e676b5b741c2be62c467a`。 +- 实际 assistant 模型只有 `claude-opus-5`。结论 **GO_WITH_NONBLOCKING_NOTES,0 阻断项**,明确表示仓库 CI 通过后适合合入 main。 +- [原始实现评审正文](implementation-review.md)、[实际模型与输出哈希](implementation-review.metadata.json) 已保存。 +- 原始流、全部 assistant 正文与最终 result 位于 `/Users/vonng/tmp/silo-r4-evidence-20260915-a9cb/merge-review-1/`。实质评审出现在较早的 assistant 消息;最终 result 只重复 Claude 只读会话不能自行合并的工具限制,不是对修复结论的撤回。本任务由 Codex 按用户明确授权完成合并。 + +## 意见处置 + +| 条目 | 处置 | +|---|---| +| IMPL-01 / IMPL-02 | 确认单字段修复和基线失败/修复通过的测试判别力,无需追加修改。 | +| IMPL-03 | Proxy/Speedtest 选项遗漏已交父任务单独核验,维持范围外,不纳入 R4 合并。 | +| IMPL-04 | REPLACE 请求的旧标签拒绝由写锁内对账完成,测试断言真实落盘状态,已有文档准确说明。 | +| IMPL-05 | 当前测试固定以 bucket-kms 为最后一种模式,且每后端重新初始化;现有执行顺序安全。后续增添模式需同步隔离桶默认配置,本次保持已评审测试逻辑。 | +| IMPL-06 | 局部变量 context 命名建议为可选观感项,不改动已评审逻辑。 | +| IMPL-07 | 既有锁测试的磁盘余量限制及仅测试容量 overlay 已如实记录;新测试和 race 不使用生产代码 overlay。 | + +## 提交规范调整 + +按 `CONTRIBUTING.md` 补齐提交作者对应的 DCO sign-off,并将两个新原创测试文件的文件头改为 `Copyright (c) 2026 Feng Ruohang`,保留 AGPL-3.0-or-later。原有生产文件的继承声明保持原样。 + +生产函数和测试的 `package cmd` 之后内容与 Opus 审查版本逐字节相同。`merge-review-1/notice-equivalence.json` 记录了旧/新文件哈希及不变的代码正文哈希。原 `verification.json` 保留当时原始验证记录,不覆盖历史哈希;本轮 PR 的 CI 对最终提交重新验证。 + +## 合并门槛 + +`make verifiers` 已通过:全仓 lint 为 0 issues,生成文件检查通过,rebrand 兼容性清单未变化,交付/运行时标识检查和 entrypoint 参数兼容性测试通过。首次执行曾遇到其他任务持有 golangci-lint 进程锁;使用工具自带 `--allow-serial-runners` 串行等待后完成全部检查。可选 typos 工具未安装,由仓库 Makefile 按既有规则跳过。 + +`make build` 通过,已生成本地 `silo` 并成功执行 `./silo --version`。最终三个源文件哈希与本轮校验记录一致,详情见 [本轮验证清单](merge-verification.json)。 + +接下来由 PR CI 验证最终候选,并在合并前再次核对 main 和精确 PR head。CI 与合并事实以 GitHub PR 状态和本机原始合并证据为准,评审意见不等同于合并或发布。 diff --git a/docs/investigations/r4/verification.md b/docs/investigations/r4/verification.md index c787fd08a..6242ae644 100644 --- a/docs/investigations/r4/verification.md +++ b/docs/investigations/r4/verification.md @@ -1,5 +1,7 @@ # R4 修复与本地验收 +这是 2026-09-15 的本地验收快照。用户后续授权的实现级复核、提交规范调整与合并流程见 [合并前复核](merge-verification.md);以下原始测试记录及哈希保留当时状态。 + ## 结果 在 `putOptsFromHeaders` 的 SSE-KMS 选项构造中补齐 `ReplicationSourceTaggingTimestamp`。目的端使用显式 SSE-KMS、桶默认 KMS 或自动加密时,可信复制 COPY 现在能消费来源标签时间戳,并在现有存储锁内完成排序。