From 2ab460f0a872a27f3444cb0d66754de0b6c3130c Mon Sep 17 00:00:00 2001 From: nyash-codex Date: Wed, 17 Dec 2025 23:45:40 +0900 Subject: [PATCH] feat(joinir): error_tags freeze_with_hint MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - Add freeze_with_hint(tag, msg, hint) API - Format: "[joinir/] Hint: " - Panic on empty hint (must provide actionable suggestion) - Keep existing freeze() for backward compatibility 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude Opus 4.5 --- src/mir/join_ir/lowering/error_tags.rs | 39 ++++++++++++++++++++++++++ 1 file changed, 39 insertions(+) diff --git a/src/mir/join_ir/lowering/error_tags.rs b/src/mir/join_ir/lowering/error_tags.rs index b3c4e1ab..0b09e97c 100644 --- a/src/mir/join_ir/lowering/error_tags.rs +++ b/src/mir/join_ir/lowering/error_tags.rs @@ -34,6 +34,27 @@ pub fn freeze(diagnostic: &str) -> String { format!("[joinir/freeze] {}", diagnostic) } +/// Create error message with hint (Phase 109) +/// +/// Format: "[joinir//] Hint: " +/// +/// # Panics +/// Panics if hint is empty (must provide actionable fix suggestion) +/// +/// # Example +/// ```rust,ignore +/// return Err(freeze_with_hint( +/// "phase107/balanced_depth_scan/missing_tail_inc", +/// "tail increment not found", +/// "add 'i = i + 1' at top-level" +/// )); +/// // Output: "[joinir/phase107/balanced_depth_scan/missing_tail_inc] tail increment not found Hint: add 'i = i + 1' at top-level" +/// ``` +pub fn freeze_with_hint(tag: &str, msg: &str, hint: &str) -> String { + assert!(!hint.is_empty(), "hint must not be empty (tag: {})", tag); + format!("[joinir/{}] {} Hint: {}", tag, msg, hint) +} + /// ExitLine contract violation - Phase 81+ exit metadata contract broken /// /// Used when exit line reconnection or exit PHI construction violates @@ -133,4 +154,22 @@ mod tests { assert!(err.contains("[joinir/lowering/boundary]")); assert!(err.contains("Invalid block")); } + + #[test] + fn test_freeze_with_hint_format() { + let result = freeze_with_hint( + "phase107/balanced_depth_scan/missing_tail_inc", + "tail increment not found", + "add 'i = i + 1' at top-level", + ); + assert!(result.contains("[joinir/phase107/balanced_depth_scan/missing_tail_inc]")); + assert!(result.contains("Hint:")); + assert!(result.contains("add 'i = i + 1'")); + } + + #[test] + #[should_panic(expected = "hint must not be empty")] + fn test_freeze_with_hint_empty_hint_panics() { + freeze_with_hint("test/tag", "message", ""); + } }