Skip to content

autoform search refinements from the #171 review #200

Closed

Description

@zibo-yang

Four small items from the final review of #171 at 22d1c02. None gives a wrong result on an ordinary query.

  1. --declaration refuses a union when one kind is unused. autoform search foo --declaration theorem --declaration instance on a blueprint with theorems and no instances exits 2 and returns none of the theorem hits. The skills tell agents that exit 2 means "do not add the article", so this blocks a legitimate query. Refuse only when every requested kind is unused, or warn on stderr and exit 0.
  2. A primed name does not rank its owner first when the unprimed name also exists. With Project.foo and Project.foo' both declared, the query Project.foo' ranks the owner of Project.foo first on the node-ID tie-break. An exact match on the query word as typed, used as an extra tie-break, would fix it.
  3. A space inside «» turns a namespace into a lean match. With lean: Project.«weird name».bar, the query Project.weird returns the article with matched_fields of lean; it should be qualified_names. The index joins names with a space; a separator that cannot occur in a name, such as a newline, fixes it.
  4. The README's "Search contract" lists the filler words and stemming rules. That makes any later tuning a contract change. State that the JSON shape is the contract and the matching rules may change.

Activity

  1. Deicyde commented on Oct 13, 2026

    @Deicyde
    Contributor

    Triage note: all four items look small (about 85 changed lines with tests), and nobody has claimed them. One coordination point first: draft #204 edits the same _ranks lookup in search.py, and its new library/search.py builds lean_names with a trailing space. Item 3's fix ends each name with a newline instead, so whichever of the two lands second has to switch that separator, or library Lean-name matches quietly fall back to weaker fields. Folding these items into #204 would avoid that.

    A sketch, in case it helps:

    1. Union refusal: refuse only when every requested kind is unused. The trade-off is that a misspelled kind inside a union (--declaration theorem --declaration lemmma) is then dropped without a refusal.
    2. Exact-name tie-break: right after max(ranks), rank first an owner whose Lean name a query word spells in full, primes, ? and ! included. That needs an unquoting helper split out of _lean_name, because _QUOTING strips those marks.
    3. Quoted namespaces: end each name with \n in lean_names and in the _ranks lookup, and also add the unquoted names to qualified_names; with the separator change alone, Project.weird matches nothing.
    4. The contract sentence in the README: the JSON shape, the exit codes and the every-term rule are the contract, and the matching details may change.

    Posted by issue triage

  2. Deicyde commented on Oct 15, 2026

    @Deicyde
    Contributor

    @zibo-yang, a plan for the site search that touches the matching code this issue covers, and a question before anyone starts on it.

    Context. #90 (the Canvas dependency explorer) has its own search box over dependencies/index.json, which matches differently from autoform search. #90 also shipped a title-only MkDocs search hook, which turned out to drop article titles from Material's header search. #90 will delete that hook, so header search works as it does on main.

    Plan: a follow-up PR after #90, "Site search follows autoform search". search.py becomes the single definition of what matches, for both the CLI and the explorer.

    • Stage A (names and titles):
      • search.py exposes its field builder as a public pure function, plus a small JSON spec of the matcher's rules (filler words, word endings, quoting, punctuation, casefolding). CLI output does not change, and library/search.py moves to the public names.
      • Render writes the explorer's index from that field builder, with the fields already folded.
      • A JavaScript port of the query side uses tables generated from the Python spec.
      • A parity test checks the port against search_blueprint's order.
    • Stage B (statements): render folds each visible statement with the CLI's own helpers into a separate file, fetched on the first keystroke.

    Question. Should the four fixes in this issue land first, so the port copies the final rules? Item 4 matters most here. If the README states that the JSON shape is the contract and the matching rules may change, the generated tables can follow the rules instead of freezing them. If you'd rather build the follow-up yourself, say so; it is your code.

    Posted by PR swarm: Swarm Manager

  3. Deicyde commented on Oct 19, 2026

    @Deicyde
    Contributor

    The site-search plan from the comment above now lives in #393, so it stays tracked after #376 closes this issue.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    enhancementNew feature or request

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions