Expand description
Definition-form annotation (ADR-0019).
A best-effort utility layer over the reader’s Datum tree —
not part of the reader-only core (ADR-0001). It recognizes definition forms
(defun, defmacro, cl-defun, define-minor-mode, project-local
def-macros, …) and tags their parts with Roles (name, arglist, docstring,
body) so a consumer can locate a definition’s pieces without hard-coding
every macro.
Two pieces:
- a
RegistryofFormSpecs keyed by head symbol: start from the bundled per-dialect core (bundled_registry, ADR-0020), extend with the harvester (harvest_source_for, ADR-0032) — which reads a def-macro’s own arglist parameter names across every macro-defining Lisp, plus, for Emacs Lisp, itsdeclaremetadata — and layer consumer-authored specs (FormSpec::define) on top; - the annotator (
annotate_form/annotate_tree), the dialect-agnostic mechanism that applies a spec to a form.
It never expands or evaluates macros; it only interprets declared/structural metadata.
§Examples
Locate a definition’s parts using the bundled per-dialect core:
use lispexp::annotate::{annotate_form, bundled_registry, Category, Role};
use lispexp::{parse, Dialect, Options};
let reg = bundled_registry(Dialect::EmacsLisp);
let parsed = parse("(defun square (x) \"Square X.\" (* x x))", &Options::emacs_lisp());
let def = annotate_form(&parsed.data[0], ®).unwrap();
assert_eq!(def.category, Some(Category::Function));
assert_eq!(def.first(Role::Name).unwrap().as_symbol(), Some("square"));
assert!(def.first(Role::Docstring).is_some());Teach the registry a project-local def-macro from its own arglist, then annotate a use of it:
use lispexp::annotate::{annotate_form, bundled_registry, harvest_source_for, Role};
use lispexp::{parse, Dialect, Options};
let mut reg = bundled_registry(Dialect::EmacsLisp);
harvest_source_for("(defmacro defthing (name &rest body) nil)", Dialect::EmacsLisp, &mut reg);
let parsed = parse("(defthing widget (render))", &Options::emacs_lisp());
let def = annotate_form(&parsed.data[0], ®).unwrap();
assert_eq!(def.first(Role::Name).unwrap().as_symbol(), Some("widget"));Structs§
- Annotated
- An annotated definition form.
- Form
Spec - A description of how to interpret a definition form’s arguments.
- Part
- One role-tagged child of an annotated form.
- Registry
- A set of
FormSpecs keyed by head symbol. - Specialized
Param - A required parameter of a specialized arglist, split into its variable token and optional specializer (ADR-0021).
Enums§
- Category
- An optional, normalized classification hint on a
FormSpec(ADR-0020). - Confidence
- How confidently a
FormSpecwas determined — also a coarse provenance. - Dispatch
- How a dispatch/method form carries its dispatch signature, right after the name (ADR-0021).
- Docstring
- Where a form’s optional docstring sits, and when a string counts as one.
- Role
- The role of an argument within a definition form.
Functions§
- annotate_
form - Annotate a single form if its head is a known definition form.
- annotate_
tree - Annotate every definition form reachable in code position in
data, in source order (outer forms before the inner forms they contain). - bundled_
registry - The bundled conservative core
Registryfordialect(ADR-0020). - harvest_
source - Harvest definition-form specs from Emacs Lisp
sourceintoreg. - harvest_
source_ for - Harvest definition-form specs from
dialectsourceintoreg. - split_
specialized_ arglist - Split a specialized arglist’s required parameters into
(variable, specializer)pairs (ADR-0021). Stops at the first lambda-list marker (&optional,&rest,&key, …); those tail parameters are not specialized.