diff --git a/crates/ailang-core/src/workspace.rs b/crates/ailang-core/src/workspace.rs index fb98c24..061295d 100644 --- a/crates/ailang-core/src/workspace.rs +++ b/crates/ailang-core/src/workspace.rs @@ -452,6 +452,12 @@ pub fn load_workspace(entry_path: &Path) -> Result 0 }`) inside - /// a method signature must fire `KindMismatch`. Decision 11 axis - /// 5 forbids HKTs — class params are kind `*` only, never - /// constructors. + /// ct.1: a class whose parameter `f` appears as a `Type::Con` + /// name (the malformed-but-historically-test-fixture shape used + /// to trigger `KindMismatch` pre-ct.1) is now caught earlier by + /// the canonical-type-names validator: `f` is bare, + /// non-primitive, and not a TypeDef in the owning module, so + /// `BareCrossModuleTypeRef` fires before `validate_classdefs` + /// gets a chance to run. The `KindMismatch` path stays in the + /// codebase as dead-but-defensive code; a future tidy may + /// retire it. #[test] - fn class_param_in_applied_position_fires_kind_mismatch() { + fn class_param_in_applied_position_fires_canonical_form_rejection() { let entry = std::path::PathBuf::from( "../../examples/test_22b2_kind_mismatch.ail.json", ); let err = load_workspace(&entry) - .expect_err("must fire kind-mismatch"); + .expect_err("must fire canonical-form rejection"); match err { - WorkspaceLoadError::KindMismatch { class, param, method, .. } => { - assert_eq!(class, "Functor"); - assert_eq!(param, "f"); - assert_eq!(method, "fmap"); + WorkspaceLoadError::BareCrossModuleTypeRef { module, name, .. } => { + assert_eq!(module, "test_22b2_kind_mismatch"); + assert_eq!(name, "f"); } - other => panic!("expected KindMismatch, got {other:?}"), + other => panic!( + "expected BareCrossModuleTypeRef (validator now fires first), got {other:?}", + ), } }