3.3 KiB
G-051 cmdinfo truthful cmdtype for doc-only pseudo-commands and space-form docid prefix parity
Status: proposed Scope: src/modules/punk/ns-999999.0a1.0.tm (cmdinfo, cmd_traverse), src/tests/modules/punk/ns/testsuites/ns/cmdhelp.test, src/tests/modules/punk/ns/testsuites/ns/cmdflow.test Acceptance: see GOALS.md index entry (canonical).
Context
Two related defects in the doc-lookup walk, characterized 2026-07-10:
Pseudo-command cmdtype. A space-delimited punk::args id can document a "command"
below the real implementation level - e.g. ::tcl::string::is true documents a level
below the ::tcl::string::is proc (the class words are arguments, not subcommands).
cmdinfo resolves such docids correctly but reports cmdtype notfound because cmdwhich
finds no real command at the multiword path (cmdinfo's final cmdwhich is on the
space-joined finalcommand). Consumers cannot distinguish "genuinely no such command" from
"documentation-only level below a real command".
Pins: cmdhelp_GAP_pseudo_command_cmdtype_notfound (fixture),
cmdhelp_GAP_string_is_true_pseudo (real tclcore docs, constraint have_tclcoredocs).
The documented-method oo case shows the same shape: cmdinfo $obj docmeth reports
cmdtype notfound with docid " docmeth" (see cmdhelp_oo_documented_method - its
docid assertion holds through this goal; whether the method case adopts the new cmdtype
or a method-specific one is a design decision for this goal, coordinated with G-052).
Space-form docid prefix parity. The jump to a space-delimited child docid
(cmd_traverse: punk::args::id_exists "$origin [lindex $args $i]") requires the exact
word. The parser accepts a unique choice prefix for the same word (G-040 landed
choiceword_match parity for the choiceinfo/subhelp path, but the space-form id_exists
jump happens BEFORE choice matching and never sees prefixes). Real-world effect:
Tcl's string is tr 1 works, but 'i string is tr' stays at the parent docid.
Pins: cmdhelp_GAP_spaceform_docid_prefix_not_honoured (fixture),
cmdhelp_GAP_string_is_prefix_not_honoured (real tclcore docs).
Approach
- Introduce a distinct cmdtype value (candidate:
doconly) returned by cmdinfo when the final resolution has an empty/notfound cmdwhich but a non-empty docid whose id maps below a real command. Audit consumers (cmdhelp, synopsis, eg, anything switching on cmdtype) - most treat docid as authoritative already, so the change should be additive. - For prefix parity: when the exact-word space-form lookup fails and the current docid's definition has a choices-bearing leader for the subcommand word, resolve the word via punk::args::choiceword_match FIRST (the shared resolver - honouring -choiceprefix, denylist, reservelist, aliases) and retry the space-form lookup with the resolved word. No second matching rule: if parse would reject the prefix, the walk must too (the G-040 parity contract, already pinned by cmdflow.test).
Notes
- The cmdinfo result shape (keys origin cmdtype args_resolved args_remaining docid stack) is pinned by cmdhelp_cmdinfo_result_shape - the new cmdtype is a value change on an existing key, not a shape change.
- 'string is' has a second wrinkle out of scope here: its per-class ids are generated from the parent's -choicelabels at tclcore load time; prefix parity must come from the walk, not from generating extra prefix ids.