From 794822aa3fb1e3b99729c58e73d04aef1f5af3e8 Mon Sep 17 00:00:00 2001 From: Haodi Fan Date: Mon, 27 Jul 2026 16:19:43 +0800 Subject: [PATCH 1/2] chore: upgrade EvoZeus harness to v0.12.1 --- .../2026-07-27-v0.11.4-to-v0.12.1.md | 26 +++ .evozeus-wrapper/policies/audit-rule.md | 7 + .../policies/feedback-policy.json | 8 +- .../scripts/evozeus_wrapper_preflight.py | 186 ++++++++++++++++++ .evozeus-wrapper/wrapper.json | 4 +- skills/using-engineering-everything/SKILL.md | 19 +- 6 files changed, 244 insertions(+), 6 deletions(-) create mode 100644 .evozeus-wrapper/docs/migrations/2026-07-27-v0.11.4-to-v0.12.1.md diff --git a/.evozeus-wrapper/docs/migrations/2026-07-27-v0.11.4-to-v0.12.1.md b/.evozeus-wrapper/docs/migrations/2026-07-27-v0.11.4-to-v0.12.1.md new file mode 100644 index 0000000..92e3876 --- /dev/null +++ b/.evozeus-wrapper/docs/migrations/2026-07-27-v0.11.4-to-v0.12.1.md @@ -0,0 +1,26 @@ +# EvoZeus-CoEvolve Harness Refresh:v0.11.4 -> v0.12.1 + +- 日期:2026-07-27 +- Wrapper 版本:v0.11.4 -> v0.12.1 +- 新事实源:`.evozeus-wrapper/wrapper.json` +- 目标:修复 consolidated-v2 harness 并刷新 wrapper-managed contract。 + +## 移动记录 + +- 无文件移动;刷新 consolidated-v2 managed files。 + +## 保留的宿主接点 + +- `.codex/hooks.json` +- `.github/ISSUE_TEMPLATE/` +- `.github/pull_request_template.md` +- `.github/workflows/evozeus-wrapper-preflight.yml` + +## 验证 + +- `python3 .evozeus-wrapper/scripts/evozeus_wrapper_preflight.py structure` +- `python3 .evozeus-wrapper/scripts/evozeus_wrapper_preflight.py runtime` + +## 回滚 + +- 回滚包含本次迁移的 Git commit。 diff --git a/.evozeus-wrapper/policies/audit-rule.md b/.evozeus-wrapper/policies/audit-rule.md index 1fbfeca..4607df8 100644 --- a/.evozeus-wrapper/policies/audit-rule.md +++ b/.evozeus-wrapper/policies/audit-rule.md @@ -5,9 +5,16 @@ Use this rule at the end of any Skill turn when the user corrected the result, e Return a concise JSON decision with: - `should_capture`: whether this feedback should become a tracked issue. +- `signal_id`: a non-sensitive short id for the current invocation. +- `capture_state`: `LOCAL_PENDING_CONFIRMATION` when feedback is detected. +- `capture_marker`: `🧙🏻‍♂️ [EvoZeus][进化信号已捕获|本地待确认|]`. - `reason`: the specific reusable failure or improvement opportunity. - `route`: `target_skill`, `wrapper`, or `both`. - `severity`: `low`, `medium`, or `high`. - `evidence_boundary`: what evidence can be recorded without exposing private session text, customer secrets, credentials, or unreleased commercial context. +- `writes`: always `false` during feedback audit. +- `next_action`: continue the original business flow and wait for explicit feedback-submission confirmation. Capture when the issue is reusable beyond the current chat. Do not capture one-off user preferences unless they change the target Skill contract. + +The capture state exists only in the current invocation and is not a persistent ledger entry. Do not create an Issue until the user explicitly confirms submission. Issue submission does not authorize a fix, branch, design doc, PR, release, or Harness change; each later write requires its own authorization. diff --git a/.evozeus-wrapper/policies/feedback-policy.json b/.evozeus-wrapper/policies/feedback-policy.json index dca7817..98c96f8 100644 --- a/.evozeus-wrapper/policies/feedback-policy.json +++ b/.evozeus-wrapper/policies/feedback-policy.json @@ -3,13 +3,19 @@ "strictness": "medium", "audit_rule": ".evozeus-wrapper/policies/audit-rule.md", "capture_evidence_regex": [ + "\\[EvoZeus\\]\\[进化信号已捕获|本地待确认|sig_[0-9A-F]{8}\\]", + "LOCAL_PENDING_CONFIRMATION", "Skill Feedback Issue", - "gh issue create", "created issue", "lesson captured", "经验已上传", "自进化记录" ], + "authorization": { + "capture": "no_external_write", + "issue_submission": "explicit_confirmation_required", + "fix_execution": "separate_confirmation_required" + }, "routing": { "target_skill_issue_when": [ "domain_rule_missing", diff --git a/.evozeus-wrapper/scripts/evozeus_wrapper_preflight.py b/.evozeus-wrapper/scripts/evozeus_wrapper_preflight.py index 6d30dd4..afcd7ec 100755 --- a/.evozeus-wrapper/scripts/evozeus_wrapper_preflight.py +++ b/.evozeus-wrapper/scripts/evozeus_wrapper_preflight.py @@ -84,6 +84,7 @@ ["source discovery", "源头发现", "source of truth", "事实源"], ["~/.evozeus/.projects"], ["version --repo"], + ["identity --json", "runtime_identity.display_line"], ["Skill Feedback Issue", "feedback issue"], [TARGET_DESIGNS_DIR, "design doc"], [TARGET_MIGRATIONS_DIR, "wrapper migration"], @@ -939,6 +940,181 @@ def latest_changelog_tag(changelog: str) -> str | None: return None +CHANNEL_LABELS = { + "development": "开发版", + "uat": "UAT", + "stable": "正式版", +} + + +def classify_runtime_channel( + *, + branch: str, + clean: bool, + head: str | None, + skill_release: str | None, + latest_release_tag: str | None, + latest_release_commit: str | None, + declared_channel: str | None = None, +) -> str: + if not clean: + return "development" + if declared_channel == "uat" or branch.startswith("uat/"): + return "uat" + if ( + branch in {"", "main", "master"} + and head + and skill_release + and latest_release_tag == skill_release + and latest_release_commit == head + ): + return "stable" + return "development" + + +def latest_release_for_identity(repo: str) -> dict[str, object]: + result = run_command(["gh", "release", "view", "--repo", repo, "--json", "tagName,url,publishedAt"]) + if result.returncode != 0: + return { + "available": False, + "tag": None, + "url": None, + "error": (result.stderr or result.stdout).strip() or "latest release unavailable", + } + try: + data = json.loads(result.stdout) + except json.JSONDecodeError: + return {"available": False, "tag": None, "url": None, "error": "invalid release response"} + tag = data.get("tagName") + if not isinstance(tag, str) or not tag: + return {"available": False, "tag": None, "url": data.get("url"), "error": "release tag missing"} + return {"available": True, "tag": tag, "url": data.get("url"), "error": None} + + +def collect_runtime_git_facts(target: Path, release_tag: str | None) -> dict[str, object]: + def output(args: list[str]) -> str | None: + result = run_command(["git", "-C", str(target), *args]) + if result.returncode != 0: + return None + return result.stdout.strip() + + status = output(["status", "--porcelain"]) + return { + "branch": output(["branch", "--show-current"]) or "", + "clean": status == "" if status is not None else False, + "head": output(["rev-parse", "HEAD"]), + "release_commit": output(["rev-list", "-n", "1", release_tag]) if release_tag else None, + "origin_repo": git_origin_repo(target), + } + + +def runtime_channel_reason( + *, + channel: str, + branch: str, + clean: bool, + skill_release: str | None, + latest_release_tag: str | None, + head: str | None, + latest_release_commit: str | None, +) -> str: + if not clean: + return "dirty_worktree" + if channel == "uat": + return "declared_uat_channel" + if channel == "stable": + return "exact_release_commit" + if not skill_release: + return "skill_unpublished" + if not latest_release_tag: + return "release_unverified" + if branch not in {"", "main", "master"}: + return "development_branch" + if not head or not latest_release_commit or head != latest_release_commit: + return "head_not_release_commit" + return "development_fallback" + + +def build_runtime_identity( + target: Path, + *, + latest_release: dict[str, object] | None = None, + git_facts: dict[str, object] | None = None, +) -> dict[str, object]: + target = target.expanduser().resolve() + manifest = load_wrapper_manifest(target) + if not manifest: + fail(f"missing wrapper manifest: {TARGET_WRAPPER_MANIFEST}") + + canonical_repo = manifest.get("canonical_repo") + if not isinstance(canonical_repo, str) or not GITHUB_REPO_RE.fullmatch(canonical_repo): + fail(f"{TARGET_WRAPPER_MANIFEST} must contain canonical_repo in OWNER/REPO format") + harness_version = manifest.get("wrapper_version") + if not isinstance(harness_version, str) or not VERSION_RE.fullmatch(harness_version): + fail(f"{TARGET_WRAPPER_MANIFEST} must contain wrapper_version in vMAJOR.MINOR.PATCH format") + + changelog_path = target / TARGET_CHANGELOG + skill_release = ( + latest_changelog_tag(changelog_path.read_text(encoding="utf-8")) + if changelog_path.is_file() + else None + ) + release = latest_release if latest_release is not None else latest_release_for_identity(canonical_repo) + latest_release_tag = release.get("tag") if release.get("available") else None + if not isinstance(latest_release_tag, str): + latest_release_tag = None + facts = git_facts if git_facts is not None else collect_runtime_git_facts(target, latest_release_tag) + origin_repo = facts.get("origin_repo") + if origin_repo != canonical_repo: + fail(f"canonical repo origin {origin_repo or 'missing'} does not match wrapper canonical_repo {canonical_repo}") + + branch = facts.get("branch") if isinstance(facts.get("branch"), str) else "" + clean = facts.get("clean") is True + head = facts.get("head") if isinstance(facts.get("head"), str) else None + release_commit = ( + facts.get("release_commit") if isinstance(facts.get("release_commit"), str) else None + ) + declared_channel = manifest.get("runtime_channel") + channel = classify_runtime_channel( + branch=branch, + clean=clean, + head=head, + skill_release=skill_release, + latest_release_tag=latest_release_tag, + latest_release_commit=release_commit, + declared_channel=declared_channel if isinstance(declared_channel, str) else None, + ) + channel_label = CHANNEL_LABELS[channel] + skill_display = skill_release or "未发布" + canonical_url = f"https://github.com/{canonical_repo}" + display_line = ( + f"🧙🏻‍♂️ [EvoZeus 自进化维护] [{canonical_repo}]({canonical_url}) · " + f"Skill {skill_display} · Harness {harness_version} · {channel_label}" + ) + return { + "schema_version": "v1", + "managed_by": "EvoZeus-CoEvolve", + "icon": "🧙🏻‍♂️", + "canonical_repo": canonical_repo, + "canonical_url": canonical_url, + "skill_release": skill_display, + "harness_version": harness_version, + "channel": channel, + "channel_label": channel_label, + "channel_reason": runtime_channel_reason( + channel=channel, + branch=branch, + clean=clean, + skill_release=skill_release, + latest_release_tag=latest_release_tag, + head=head, + latest_release_commit=release_commit, + ), + "display_once_scope": "skill_invocation", + "display_line": display_line, + } + + def release_body_from_gh(tag: str, repo: str | None) -> str | None: cmd = ["gh", "release", "view", tag, "--json", "body", "-q", ".body"] if repo: @@ -1063,6 +1239,10 @@ def main() -> int: help="Explicitly allow local changelog to be ahead when the change does not affect the installable artifact.", ) + identity = sub.add_parser("identity", help="Render the EvoZeus runtime identity for this Skill invocation.") + identity.add_argument("--target", default=".", help="Target wrapped Skill repo path.") + identity.add_argument("--json", action="store_true", help="Return the versioned runtime_identity JSON object.") + args = parser.parse_args() if args.command == "doctor": check_doctor(args) @@ -1080,6 +1260,12 @@ def main() -> int: check_release(args) elif args.command == "version": check_version(args) + elif args.command == "identity": + runtime_identity = build_runtime_identity(Path(args.target)) + if args.json: + print(json.dumps({"runtime_identity": runtime_identity}, ensure_ascii=False)) + else: + print(runtime_identity["display_line"]) return 0 diff --git a/.evozeus-wrapper/wrapper.json b/.evozeus-wrapper/wrapper.json index b153086..28ad560 100644 --- a/.evozeus-wrapper/wrapper.json +++ b/.evozeus-wrapper/wrapper.json @@ -1,7 +1,7 @@ { "wrapper_repo": "MetaInFLow/EvoZeus-CoEvolve", - "wrapper_version": "v0.11.4", - "applied_at": "2026-07-26", + "wrapper_version": "v0.12.1", + "applied_at": "2026-07-27", "canonical_repo": "HaodiFan/engineering-everything", "instruction_surface": "skills/using-engineering-everything/SKILL.md", "managed_files": [ diff --git a/skills/using-engineering-everything/SKILL.md b/skills/using-engineering-everything/SKILL.md index 2518e88..5b21da0 100644 --- a/skills/using-engineering-everything/SKILL.md +++ b/skills/using-engineering-everything/SKILL.md @@ -19,15 +19,21 @@ metadata: - 如果 GitHub latest release 更新:先更新 canonical repo,并确认 runtime install 仍指向 canonical repo。 - 如果本地版本领先 GitHub release:先完成 changelog、验证和 `vMAJOR.MINOR.PATCH` release,再把它当作稳定运行版本。 2. Wrapper harness 状态 - - 当前 wrapper 版本:`v0.11.4` + - 当前 wrapper 版本:`v0.12.1` - 事实源:`.evozeus-wrapper/wrapper.json` - 检查命令:在 EvoZeus-CoEvolve repo 运行 `python3 scripts/evozeus_wrapper.py harness upgrade-check --target --json` - - 如果 wrapper 落后:先运行 `harness upgrade --dry-run` 生成迁移方案,再按状态检查前置、其他 wrapper 内容 append-only 的规则迁移。 + - 如果 wrapper 落后且 `upgrade-check` 未发现冲突或不兼容:报告当前与最新版本;兼容的旧 wrapper 只作为维护提醒,不阻塞业务主链路。 + - 普通 Skill 调用不授权 Harness 升级或其他维护写入。只有用户明确请求 Harness 维护或升级后,才运行 `harness upgrade --dry-run` 生成方案;实际写入仍需单独确认。 3. Source contract 状态 - 检查命令:`python3 .evozeus-wrapper/scripts/evozeus_wrapper_preflight.py doctor --repo HaodiFan/engineering-everything` - 如果 `~/.evozeus/.projects`、git origin 或 runtime install 不一致:先修复为同一个 canonical repo,再继续。 +4. 调用身份头 + - 检查命令:`python3 .evozeus-wrapper/scripts/evozeus_wrapper_preflight.py identity --json` + - 读取 `runtime_identity.display_line`,并将其原样放在本次 Skill invocation 第一条用户可见输出的第一行。 + - 身份头固定以 `🧙🏻‍♂️` 开始;禁止使用 HTML、自定义图片或 shortcode 替代。 + - 同一次 invocation 的后续 commentary 和 final 不重复;下一次 invocation 再展示一次。 -解决顺序:先修 source contract,再修 wrapper harness,最后处理 Skill release;状态已确认或已记录为 runtime-only fallback 后,再进入主链路。 +解决顺序:Source contract 损坏、manifest 无效、迁移冲突或已确认不兼容时停止业务流程并说明原因;其他情况完成只读检查后直接进入主链路。 # Using Engineering Everything / 启动器 @@ -103,3 +109,10 @@ metadata: - Layout: `consolidated-v2 -> consolidated-v2` - Host hook registration, status prelude, manifest integration, and managed links were refreshed. - Target business rules were preserved. + +## EvoZeus-CoEvolve Version Refresh Note: v0.11.4 -> v0.12.1 + +- Wrapper harness: `v0.11.4 -> v0.12.1` +- Layout: `consolidated-v2 -> consolidated-v2` +- Host hook registration, status prelude, manifest integration, and managed links were refreshed. +- Target business rules were preserved. From 947db3f1ccbfd58a4f737efff830628e04611d0f Mon Sep 17 00:00:00 2001 From: Haodi Fan Date: Mon, 27 Jul 2026 16:21:29 +0800 Subject: [PATCH 2/2] docs: record v0.12.1 harness upgrade evidence --- .evozeus-wrapper/CHANGELOG.md | 15 ++++++++++++++- 1 file changed, 14 insertions(+), 1 deletion(-) diff --git a/.evozeus-wrapper/CHANGELOG.md b/.evozeus-wrapper/CHANGELOG.md index eab8349..c051e53 100644 --- a/.evozeus-wrapper/CHANGELOG.md +++ b/.evozeus-wrapper/CHANGELOG.md @@ -6,7 +6,20 @@ Wrapper harness migrations are recorded under `.evozeus-wrapper/docs/migrations/ ## [Unreleased] -- None yet. +### Skill changes + +- Upgraded the managed EvoZeus-CoEvolve Harness from `v0.11.4` to `v0.12.1`. +- Added the per-invocation EvoZeus runtime identity header and staged feedback authorization contract to the wrapper-owned bootloader prelude. + +### Feedback / Issues + +- Owner-authorized batch Harness upgrade following the EvoZeus-CoEvolve `v0.12.1` release. + +### Verification + +- `python3 .evozeus-wrapper/scripts/evozeus_wrapper_preflight.py structure` +- `python3 .evozeus-wrapper/scripts/evozeus_wrapper_preflight.py identity --json` +- `git diff --check` ## [v0.13.0] - 2026-07-25