ies/music-topos/.agents/skills/type-inference-validation/SKILL.md
Static type inference and validation for navigation paths
npx skillsauth add plurigrid/asi type-inference-validationInstall this skill globally with one command. Works with Claude Code, Cursor, and Windsurf.
3 of 9 scanners reported clean
Some scanners were skipped, did not run, or reported a non-clean status. Review each row below.
Static type validation that rejects invalid path compositions before caching. Every Navigator path must prove type compatibility with its input structure—this skill enforces that proof.
Works alongside Möbius filtering as a second line of defense: Möbius eliminates topological impossibilities, Type Inference eliminates structural impossibilities.
Consider this dangerous scenario:
data_numbers = [1, 2, 3, 4, 5]
data_dict = Dict("x" => 10, "y" => 20)
# This path makes sense for numbers
nav1 = @late_nav([ALL, pred(iseven)]) # Type ✓: Vector → Numbers → Numbers
# But what if someone mistakenly uses it on the dict?
nav_select(nav1, data_dict, x -> [x])
# => IndexError! (dicts don't support ALL enumeration this way)
Type Inference Validation prevents this at compile time, not runtime.
Each Navigator carries a type signature:
Navigator{InputType, OutputType, PathSteps}
Examples:
nav_vector = Navigator{Vector, Vector, [ALL, pred(f)]}
nav_dict = Navigator{Dict, Vector, [keypath(k), ALL]}
nav_sexp = Navigator{SExpression, Symbol, [sexp_nth(2), SEXP_HEAD]}
Input Type
↓
@late_nav(path_expr) triggers validation
↓
Type each step in path:
[ALL] : Vector{T} → T
[keypath(k)] : Dict{K,V} → V
[pred(f)] : T → T (preserves type)
[INDEX(i)] : Vector{T} → T
[SEXP_HEAD] : SExpr → Symbol
↓
Unify step outputs with next step inputs
↓
Final output type computed
↓
Cache with type signature
↓
Accept or Reject
| Step | Input Type | Output Type | Valid? |
|------|-----------|------------|--------|
| [ALL] | Vector{T} | T | ✓ |
| [ALL] | Dict{K,V} | ⚠️ (ambiguous) | ✗ |
| [keypath(k)] | Dict{K,V} | V | ✓ |
| [keypath(k)] | Vector{T} | ✗ | ✗ |
| [pred(f)] | T | T | ✓ |
| [INDEX(i)] | Vector{T} | T | ✓ |
| [INDEX(i)] | Dict | ✗ | ✗ |
infer_type(path_expr, input_type) :: Result{OutputType, Error}
Computes the output type of a path given an input type.
infer_type([ALL, pred(iseven)], Vector{Int})
# => Result(Int) # outputs Int values
infer_type([keypath("x"), ALL], Dict{String, Vector{Int}})
# => Result(Int) # navigates to x, then enumerates integers
infer_type([keypath("x")], Vector{Int})
# => Result(TypeError("Cannot apply keypath to Vector"))
validate_path(navigator::Navigator, input_type) :: Bool
Checks if a Navigator is compatible with a given input type.
nav = @late_nav([ALL, pred(f)])
validate_path(nav, Vector{Int}) # => true
validate_path(nav, Dict{String, Int}) # => false ✗
# Causes @late_nav to reject the Navigator before caching
navigator_signature(nav::Navigator) :: TypeSignature
Returns the full type signature of a cached Navigator.
nav = @late_nav([ALL, pred(iseven)])
sig = navigator_signature(nav)
# => TypeSignature(
# input: Vector{T},
# output: T,
# constraints: [iseven(T)],
# steps: [[ALL], [pred(iseven)]],
# valid_for: Vector{Int}, Vector{BigInt}, ...
# )
polymorphic_infer(path_expr) :: PolymorphicType
Infers the most general type for a path (before knowing input type).
polymorphic_infer([ALL, pred(iseven)])
# => ∀T. (T ∈ Enumerable, T ∈ HasEven) → T
# This means: works for ANY type T that:
# - Can be enumerated (Vector, Set, List, etc.)
# - Has an iseven() method defined
Cache keys now include type information:
cache_key = hash((path_expr, inferred_type))
# Different input types → different cache entries
nav_vec = @late_nav([ALL, pred(f)]) # cache for Vector
nav_set = @late_nav([ALL, pred(f)]) # cache for Set (if compatible)
# => Different NavigatorObjects, despite same path!
Supports refinement types for predicates:
# pred(iseven) refines Int → EvenInt
# pred(x -> x > 5) refines Int → IntGt5
nav = @late_nav([ALL, pred(x -> x > 5)])
# Type: Vector{Int} → IntGt5
# (output is proven to be > 5)
Refinement types enable:
nav = @late_nav([keypath("name"), ALL])
# Type error: keypath returns a string, ALL requires enumerable
# KeyPath{Dict, String} → String
# ALL{String} → ✗ (String not enumerable in that way)
nav = @late_nav([ALL, pred(x -> x > 5)])
# If input is Vector{String}, predicate fails
# Type error: `(String > 5)` is nonsense
nav = @late_nav([ALL, pred(identity)]) # identity always works
# Type: ∀T. Vector{T} → T
# Works for ANY vector type
Type validation errors are clear:
TypeError: Path composition invalid
Step 1: [ALL]
Input: Vector{Int}
Output: Int
✓ Type check passed
Step 2: [keypath("x")]
Input: Int
Output: ???
✗ TypeError: Cannot apply keypath to Int
keypath requires Dict or record type
Got: Int
Suggestion: Remove [keypath("x")] or ensure input is Dict/Struct
All type checking happens at compile time (during @late_nav expansion):
| Operation | Complexity | Notes |
|-----------|-----------|-------|
| infer_type | O(|path|) | Single pass through steps |
| validate_path | O(1) | Cached signature lookup |
| polymorphic_infer | O(|path|) | Compute most general type |
| Runtime overhead | O(0) | Zero cost—all checks are static |
Works with Möbius Filtering:
Works with Color Envelopes: Type signatures include color trit information:
nav = @late_nav([ALL, pred(f)]) # trit = -1 (filtering)
sig = navigator_signature(nav)
# => TypeSignature(..., trit: -1)
# Type system respects color: composition must balance trits AND types
Enables Constraint Generalization (next skill): Once types are proven, constraints can be composed and generalized safely.
development
BDD-Driven Mathematical Content Verification Skill Combines Behavior-Driven Development with mathematical formula extraction, verification, and transformation using: - Cucumber/Gherkin for specification - RSpec for implementation verification - mathpix-gem for LaTeX/mathematical content extraction - Pattern matching on syntax trees for formula validation Enables iterative discovery and verification of mathematical properties through executable specifications.
tools
Meta-skill that generates domain-specific AI skills from tool documentation
development
Code Query with AI-enhanced deterministic analysis via SplitMix ternary classification
development
Directed Yoneda lemma as directed path induction. Riehl-Shulman's key insight for synthetic ∞-categories.