infoductor/Infoductor/Test.lean
Maximus Gorog 511d564a55 Add MetaCTerm structural mirror, .cterm artifact arm, MetaPosition.binder
Foundation.Meta gains an 8-constructor MetaCTerm inductive that mirrors
the cubical CTerm's generic shape (ident/sym/app/lam/plam plus dedicated
comp/transp arms; cubical-specific operators encode via .ident-headed
.app chains). MetaArtifact picks up a .cterm arm for structure-preserving
artifact content. MetaPosition gets an Option Lean.Name binder field so
the dim-binder of a comp/transp can be threaded structurally instead of
folded into the classifier.

These additions back the cubical-bridge's Embed.lean overhaul: a real
coreflection between the cubical universe (CType/CTerm/FaceFormula/
DimExpr) and the meta-mirror, with partial inverses and per-constructor
round-trip theorems.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-01 09:08:01 -06:00

154 lines
6.4 KiB
Text
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

/-
Infoductor.Test — generic Foundation end-to-end tests
=====================================================
Compile-time exercise of the Foundation layer (Phases AD'.5).
Cubical-transport-specific tests live downstream in
`infoductor-cubical/InfoductorCubical/Test.lean`.
- Phase A: meta-mirror types.
- Phase B: Edit monad + restructure.
- Phase C: @[macroAlias].
- Phase D'/D'.5: @[methodology] + @[metaPath] + cubical_search.
-/
import Infoductor.Foundation.Methodology
import Infoductor.Foundation.MetaPath
namespace Infoductor.Test
open Infoductor
-- ── Phase A: meta-mirror types ─────────────────────────────────────────────
/-- Meta-mirror types are inhabited and well-formed. -/
example : MetaCType := .theorem_
example : MetaCType := .file
example : MetaCType := .classifierSet
example : MetaClassifier := .always
example : MetaClassifier := .never
example : MetaClassifier := .meet (.atDecl `Foo) (.inFile "Bar.lean")
example : MetaArtifact := .source "def x := 1"
example : MetaArtifact := .empty
example : MetaArtifact := .refTo `Existing
example : MetaPosition :=
{ declName := `Test, filePath := "Test.lean", range := none }
/-- DecidableEq fires correctly on MetaClassifier. -/
example : decide (MetaClassifier.always = .always) = true := by decide
example : decide (MetaClassifier.always = .never) = false := by decide
example : decide ((.meet .always (.atDecl `Foo) : MetaClassifier) =
(.meet .always (.atDecl `Foo))) = true := by decide
-- ── Phase B: Edit + Context + restructure ───────────────────────────────────
/-- A simple restructure call produces an Edit with one op. -/
example :
let pos : MetaPosition := { declName := `Foo, filePath := "F.lean", range := none }
let e := restructure pos .theorem_ .always (.source "def x := 1") .empty
e.ops.length = 1 := by
rfl
/-- The restructure picks `witness` when the classifier is `.always`. -/
example :
let pos : MetaPosition := { declName := `Foo, filePath := "F.lean", range := none }
let e := restructure pos .theorem_ .always (.source "yes") (.source "no")
(e.ops.head?).isSome = true := by
rfl
/-- The restructure picks `fallback` when the classifier is `.never`. -/
example :
let pos : MetaPosition := { declName := `Foo, filePath := "F.lean", range := none }
let e := restructure pos .theorem_ .never (.source "yes") (.source "no")
(e.ops.head?).isSome = true := by
rfl
/-- Self-consistency check on a single restructure op. -/
example :
let pos : MetaPosition := { declName := `Foo, filePath := "F.lean", range := none }
let e := restructure pos .theorem_ .always (.source "x") .empty
e.selfConsistent = true := by
rfl
/-- A batch that removes a decl AND references it by `refTo` is
flagged as inconsistent. -/
example :
let pos₁ : MetaPosition := { declName := `Foo, filePath := "F.lean", range := none }
let pos₂ : MetaPosition := { declName := `Bar, filePath := "F.lean", range := none }
let e : Edit Unit := do
restructure pos₁ .theorem_ .always .empty .empty -- removes Foo
restructure pos₂ .theorem_ .always (.refTo `Foo) .empty -- refs Foo
e.selfConsistent = false := by
rfl
-- ── Frozen aliases ──────────────────────────────────────────────────────────
/-- The `transport_artifact` alias produces a single Edit op. -/
example :
let pos : MetaPosition := { declName := `Foo, filePath := "F.lean", range := none }
let e := transport_artifact pos .theorem_ (.source "x")
e.ops.length = 1 := by rfl
/-- The `materialize` alias emits raw Lean source. -/
example :
let pos : MetaPosition := { declName := `Foo, filePath := "F.lean", range := none }
let e := materialize pos .theorem_ "theorem x : True := trivial"
e.ops.length = 1 := by rfl
-- ── Phase C: @[macroAlias] registration ─────────────────────────────────────
/-- A custom alias for testing. Registered via the attribute below. -/
@[macroAlias]
def custom_alias_test (i : MetaPosition) : Edit Unit :=
restructure i .definition .always (.source "test") .empty
-- ── Phase D': @[methodology] registration ───────────────────────────────────
/-- A trivial methodology: solves `True` goals. Registered against
a placeholder classifier name `IsTrueGoal`. -/
@[methodology IsTrueGoal]
theorem trueMethodology : True := True.intro
/-- `cubical_search` finds the registered methodology for `True`
goals. Demonstrates the dispatch loop end-to-end. -/
example : True := by cubical_search
/-- Methodology for `Eq.refl`-shaped goals. Demonstrates that
`cubical_search` can dispatch to non-trivial universe-equality
goals. -/
@[methodology IsReflGoal]
theorem reflMethodologyNat (n : Nat) : n = n := rfl
example : 7 = 7 := by cubical_search
-- ── Phase D'.5: @[metaPath] + methodology-transport ─────────────────────────
/-- A trivial structural Path: every reflexivity goal is also a
"trivial-truth" goal. Declares the meta-Path so methodology-
transport can lift `IsTrueGoal` methodologies onto `IsReflGoal`
targets and vice versa. -/
@[metaPath IsReflGoal IsTrueGoal]
theorem refl_path_to_true (n : Nat) (_ : n = n) : True := True.intro
/-- An identity methodology that closes any `Iff.refl`-shaped goal. -/
@[methodology IsIffReflGoal]
theorem iffRefl (P : Prop) : P ↔ P := Iff.rfl
example : True ↔ True := by cubical_search
-- ── Compile-time registry diagnostics ───────────────────────────────────────
/-- A diagnostic action that prints registry sizes. Run via `#eval`
inside a Lean session to verify that @[methodology] /
@[macroAlias] / @[metaPath] declarations have populated the
EnvExtensions. -/
def printRegistrySizes : Lean.CoreM Unit := do
let aliases ← getAliases
let methodologies ← getMethodologies
let paths ← getMetaPaths
IO.println s!"[Infoductor.Test] aliases={aliases.size} \
methodologies={methodologies.size} paths={paths.size}"
end Infoductor.Test