fix: patch checks full target span + marker injection/integrity (algo #8)
This commit is contained in:
@@ -19,6 +19,8 @@ from loguru import logger
|
||||
from core.evolution.patch import (
|
||||
APPENDIX_END,
|
||||
APPENDIX_START,
|
||||
MOMENTUM_END,
|
||||
MOMENTUM_START,
|
||||
append_to_appendix,
|
||||
apply_patch_with_report,
|
||||
extract_appendix_notes,
|
||||
@@ -293,10 +295,39 @@ def _tool_protected_spans(text: str) -> list[str]:
|
||||
# =========================================================================
|
||||
|
||||
|
||||
def _check_marker_integrity(evolved: str) -> list[str]:
|
||||
"""校验 evolved 中冻结区 marker 的完整性(成对、至多一对、START 先于 END)。
|
||||
|
||||
进化写入可能破坏 appendix/momentum marker 配对,破坏后 append_to_appendix /
|
||||
replace_momentum 等下游会静默误拼或抛错。此处集中拦截:任一 marker 对违反
|
||||
「START 数==END 数、各至多一对、START 在 END 前」即整体 reject。
|
||||
|
||||
参数:
|
||||
evolved: 改写后的全文。
|
||||
返回:
|
||||
错误信息列表(空列表表示 marker 完整)。
|
||||
"""
|
||||
errors: list[str] = []
|
||||
for name, start_m, end_m in (
|
||||
("APPENDIX", APPENDIX_START, APPENDIX_END),
|
||||
("MOMENTUM", MOMENTUM_START, MOMENTUM_END),
|
||||
):
|
||||
s = evolved.count(start_m)
|
||||
e = evolved.count(end_m)
|
||||
if s != e:
|
||||
errors.append(f"{name} marker 不配对:START={s} END={e}")
|
||||
elif s > 1:
|
||||
errors.append(f"{name} marker 出现多对({s}),至多一对")
|
||||
elif s == 1 and evolved.index(start_m) > evolved.index(end_m):
|
||||
errors.append(f"{name} marker 顺序错误:END 出现在 START 之前")
|
||||
return errors
|
||||
|
||||
|
||||
def validate_skill(original: str, evolved: str) -> ValidationResult:
|
||||
"""校验 Skill 改写结果。
|
||||
|
||||
检查项: frontmatter 三字段保留(name / description / task_type)、
|
||||
marker 完整性(appendix/momentum 成对且至多一对、顺序正确)、
|
||||
长度比在 [0.3, 2.0]、代码块闭合。
|
||||
|
||||
参数:
|
||||
@@ -305,6 +336,11 @@ def validate_skill(original: str, evolved: str) -> ValidationResult:
|
||||
|
||||
返回:
|
||||
ValidationResult 实例。
|
||||
|
||||
关键实现细节:
|
||||
marker 完整性先于长度校验——长度校验经 _strip_protected_regions 调用
|
||||
momentum_region_bounds,对损坏 marker 会抛 ValueError;故 marker 破坏时先
|
||||
返回失败,避免异常穿透且明确 reject 该候选。
|
||||
"""
|
||||
errors: list[str] = []
|
||||
orig_fm = _parse_frontmatter(original)
|
||||
@@ -319,6 +355,10 @@ def validate_skill(original: str, evolved: str) -> ValidationResult:
|
||||
errors.append(
|
||||
f"frontmatter 字段 {key} 被修改: {orig_fm.get(key)!r} → {evol_fm.get(key)!r}"
|
||||
)
|
||||
marker_errors = _check_marker_integrity(evolved)
|
||||
if marker_errors:
|
||||
errors.extend(marker_errors)
|
||||
return ValidationResult(passed=False, errors=errors)
|
||||
errors.extend(_check_length(original, evolved))
|
||||
errors.extend(_check_code_blocks(evolved))
|
||||
return ValidationResult(passed=len(errors) == 0, errors=errors)
|
||||
|
||||
Reference in New Issue
Block a user