"""Internal multi-pass schemas, prompts, and validation; no client fields added.""" from __future__ import annotations import copy import re from collections import Counter from suite_contract import FIELDS, Problem, SCHEMA, SYSTEM, encoded, validate_partition from suite_assignments import WIRE_INSTRUCTIONS, decision_keys, wire_schema POLICY_REVISION = "implementation-five-v1-20260929" MAX_GROUP = 5 BASE_NAME_LIMIT = 56 # Leaves room for ' (80/80)' at the 400-case input limit. STAGES = ("proposal_a", "proposal_b", "reconciliation", "large_family_review", "decision_audit") DISCOVERY = ( "Discover natural implementation families across this COMPLETE suite, without any " "task-size cap. Do not split a coherent family for a numerical quota. Names normally " "use two to five words describing test machinery; never repeat the hierarchy. " "Use distinct meaningful mechanism names, not numbering to hide collisions. " "Use StructuredOutput directly when available; do not first emit a prose draft." ) RECONCILE = ( "Independently reassess two complete candidate partitions using ALL original cases. " "Compare memberships, never proposal names or group numbers. Resolve disagreements " "against success_criteria and shared test machinery. Do not vote, count majority " "co-memberships, or take transitive connected components. Agreement is not proof. " "Return one coherent NATURAL partition, with no size cap. Review cross-family merges " "and unjustified splits. Record concise engineering rationales and unresolved " "uncertainty, not private reasoning traces. Evidence must quote a short exact substring " "from a named source field of an assigned alias. Prefer success_criteria when present. " "common_work must describe ONLY machinery applicable to EVERY assigned member, " "without enumerating objectives/variations that apply to only some members. " "variation_sets partition each family's aliases into closely related variations; " "these are ordering hints, not additional task levels or semantic families. " "Keep identical case content together in variation_sets. Never impose five-member " "limits on natural discovery. Use unique mechanism names, normally two to five words " "and at most 56 characters, without numbered suffixes. Rewrite long/colliding names " "meaningfully; do not blindly truncate or add arbitrary identifiers. " "Use StructuredOutput directly when available; no prose draft." ) REVIEW = ( "Review EVERY listed oversized family against its original source case fields, " "especially success_criteria. Decide whether different control/measurement/evidence " "mechanisms warrant separate natural families with meaningful distinct names. " "Do not split by source order, quota, nominal/fault labels alone, or cheap assertion " "variations. If coherent, explicitly explain the common machinery and why differences " "are inexpensive variations. Preserve that coherent natural family even if it has " "more than five members: deterministic work sizing happens later. Return a complete " "natural partition of the whole suite and one explicit decision per reviewed family. " "Decisions refer to the exact reviewed source_members, not names. Splits must partition " "that family's members; do not cross existing family boundaries during this review. " "Retain and improve concise source-field support and uncertainty." ) AUDIT = ( "Perform ONE bounded additional review of the previous large-family decisions. " "Using all original fields, challenge unjustified semantic splits, unjustified broad " "merges, and assertions that would need different machinery. You may correct the " "decision by merging/splitting only within each ORIGINAL oversized family. Re-examine " "all its descendants even if each is now small. Return the complete final NATURAL " "partition and final decisions for every original oversized family. There will be " "no loop seeking agreement; explicitly retain unresolved uncertainty. Preserve " "coherent large families for deterministic capacity division afterwards." ) def text_schema(limit): """Return a bounded string schema for internal model output.""" return {"type": "string", "minLength": 1, "maxLength": limit} ALIAS_LIST = {"type": "array", "minItems": 1, "items": text_schema(53)} EVIDENCE = {"type": "array", "minItems": 1, "maxItems": 3, "items": { "type": "object", "additionalProperties": False, "required": ["alias", "field", "quote"], "properties": { "alias": text_schema(53), "field": {"type": "string", "enum": sorted(FIELDS)}, "quote": text_schema(160)}}} DISCOVERY_SCHEMA = copy.deepcopy(SCHEMA) DISCOVERY_SCHEMA["properties"]["groups"]["items"]["properties"]["members"].pop("maxItems", None) DISCOVERY_SCHEMA["properties"]["groups"]["items"]["properties"]["name"]["maxLength"] = BASE_NAME_LIMIT NATURAL_SCHEMA = copy.deepcopy(DISCOVERY_SCHEMA) GROUP_PROPERTIES = NATURAL_SCHEMA["properties"]["groups"]["items"]["properties"] GROUP_PROPERTIES["name"]["maxLength"] = BASE_NAME_LIMIT GROUP_PROPERTIES.update({ "common_work": text_schema(160), "rationale": text_schema(320), "uncertainty": {"type": "string", "maxLength": 240}, "evidence": EVIDENCE, "variation_sets": {"type": "array", "minItems": 1, "items": ALIAS_LIST}, }) NATURAL_SCHEMA["properties"]["groups"]["items"]["required"] = list(GROUP_PROPERTIES) REVIEW_SCHEMA = copy.deepcopy(NATURAL_SCHEMA) REVIEW_SCHEMA["required"].append("decisions") REVIEW_SCHEMA["properties"]["decisions"] = {"type": "array", "minItems": 1, "items": { "type": "object", "additionalProperties": False, "required": ["source_members", "decision", "rationale", "evidence"], "properties": { "source_members": ALIAS_LIST, "decision": {"type": "string", "enum": ["keep", "split"]}, "rationale": text_schema(320), "evidence": EVIDENCE}}} def invocation(stage, request, context=None): """Build one full-input pass; independent discovery has no proposal context.""" original_stage = stage stage = {"profile_proposal_a": "proposal_a", "profile_proposal_b": "proposal_b", "profile_reconciliation": "proposal_a", "source_review": "reconciliation"}.get(stage, stage) if stage not in STAGES: raise ValueError("unknown internal stage") discovery = stage in STAGES[:2] if discovery and context and original_stage != "profile_reconciliation": raise ValueError("discovery must be independent") schema = DISCOVERY_SCHEMA if discovery else NATURAL_SCHEMA if stage == "reconciliation" else REVIEW_SCHEMA instruction = DISCOVERY if discovery else RECONCILE if stage == "large_family_review": instruction += "\n" + REVIEW if stage == "decision_audit": instruction += "\n" + REVIEW + "\n" + AUDIT if request.get("_profile_source"): instruction += ("\nThe supplied cases are compact implementation profiles, not verbatim source. " "Compare across ALL profiles and batches. Original fields will be reopened " "before accepting natural families. Retain uncertainty.") if original_stage == "profile_reconciliation": instruction += ("\nReconcile the two supplied independent profile partitions across every alias. " "Compare memberships and machinery, not votes or connected components.") if original_stage == "source_review": instruction = instruction.replace( "Independently reassess two complete candidate partitions using ALL original cases.", "Reassess the supplied candidate partition using ALL original cases in this review.") instruction += ("\nReopen ALL original fields for every candidate family supplied here. " "Reject compression-induced compatibility; split genuinely different machinery. " "Do not cross candidate-family boundaries in this source verification pass. " "Use original source evidence, not profile quotations.") source = {k: request[k] for k in ("campaign", "suite", "cases")} context = dict(context or {}) if context.get("review_batch"): instruction += ( "\nThis is a capacity-bounded review batch of already reconciled natural families. " "Both independent proposals and reconciliation considered the whole suite. " "All source fields for every member of these families are supplied here. " "Other families are reviewed separately. Return exactly this batch's aliases; " "do not rediscover cross-family groupings or invent missing outside cases. " "This execution batch introduces no additional semantic grouping boundary." ) keys = decision_keys(context) if stage in STAGES[3:] else {} if keys: context["review_keys"] = keys return {"stage": original_stage, "schema": wire_schema(schema, request, context), "review_keys": keys, "input": encoded({"suite": source, "review_material": context}).decode(), "system": SYSTEM + "\n\nPASS INSTRUCTIONS:\n" + instruction + "\n\n" + WIRE_INSTRUCTIONS} def projection(value): """Extract only the unchanged public group shape from a natural partition.""" return {"groups": [{k: group[k] for k in ("name", "description", "members")} for group in value["groups"]]} def bounded_string(value, limit, *, empty=False): """Reject invalid internal strings without echoing their contents.""" if type(value) is not str or len(value) > limit or (not empty and not value.strip()): raise Problem("invalid_review_output", 502) def evidence(value, members, by_alias): """Require short exact source-field support within the explained membership.""" if not isinstance(value, list) or not 1 <= len(value) <= 3: raise Problem("invalid_review_evidence", 502) for item in value: if not isinstance(item, dict) or set(item) != {"alias", "field", "quote"}: raise Problem("invalid_review_evidence", 502) alias, field, quote = item["alias"], item["field"], item["quote"] if type(alias) is not str or alias not in members or type(field) is not str or field not in FIELDS: raise Problem("invalid_review_evidence", 502) bounded_string(quote, 160) source = by_alias[alias].get(field) if not isinstance(source, str) or quote not in source: raise Problem("invalid_review_evidence", 502) def validate_natural(value, request, originals=None): """Validate complete natural assignments and bounded explanations, without a cap.""" expected_keys = {"groups", "decisions"} if originals is not None else {"groups"} if not isinstance(value, dict) or set(value) != expected_keys or not isinstance(value["groups"], list): raise Problem("invalid_review_output", 502) required = set(GROUP_PROPERTIES) for group in value["groups"]: if not isinstance(group, dict) or set(group) != required: raise Problem("invalid_review_output", 502) validate_partition(projection(value), request, name_limit=BASE_NAME_LIMIT) by_alias = {case["alias"]: case for case in request["cases"]} for group in value["groups"]: members = set(group["members"]) for field, limit in (("common_work", 160), ("rationale", 320), ("uncertainty", 240)): bounded_string(group[field], limit, empty=field == "uncertainty") if re.search(r"\(\s*\d+\s*/\s*\d+\s*\)$", group["name"]): raise Problem("invalid_natural_family_name", 502) evidence(group["evidence"], members, by_alias) variations = group["variation_sets"] if not isinstance(variations, list) or not variations or any( not isinstance(part, list) or not part or any(type(a) is not str for a in part) for part in variations): raise Problem("invalid_variation_assignments", 502) if Counter(a for part in variations for a in part) != Counter(group["members"]): raise Problem("invalid_variation_assignments", 502) if originals is not None: validate_decisions(value, originals, by_alias) return value def validate_decisions(value, originals, by_alias): """Audit every original oversized family and forbid cross-family review drift.""" decisions = value["decisions"] large = {frozenset(g["members"]): g for g in originals if len(g["members"]) > MAX_GROUP} if not isinstance(decisions, list) or len(decisions) != len(large): raise Problem("incomplete_large_family_review", 502) seen = set() for decision in decisions: if not isinstance(decision, dict) or set(decision) != {"source_members", "decision", "rationale", "evidence"}: raise Problem("invalid_review_output", 502) members = decision["source_members"] if not isinstance(members, list) or any(type(a) is not str for a in members): raise Problem("invalid_review_output", 502) key = frozenset(members) if key not in large or key in seen or len(key) != len(members): raise Problem("incomplete_large_family_review", 502) seen.add(key) descendants = [g for g in value["groups"] if set(g["members"]) <= key] split = len(descendants) > 1 if not descendants or decision["decision"] != ("split" if split else "keep"): raise Problem("invalid_review_decision", 502) bounded_string(decision["rationale"], 320) evidence(decision["evidence"], key, by_alias) for group in value["groups"]: parents = [g for g in originals if set(group["members"]) <= set(g["members"])] if len(parents) != 1 or (len(parents[0]["members"]) <= MAX_GROUP and set(group["members"]) != set(parents[0]["members"])): raise Problem("review_crossed_family_boundary", 502)