Skip to content

Conversation

@wilfreddenton
Copy link
Contributor

#2418

There are two strategies I've explored for giving consumers access to source locations:

  1. Make spans available on resolved items so consumers can inspect them after resolution. There are two ways I found to do this

    1. Spans on structs (wit-parser-spans-in-structs) - Add span: Option<Span> directly to TypeDef, Function, Interface, World
      • Pros: Direct access pattern; spans travel with the data automatically during merges
      • Cons: Breaking change to public struct layouts
    2. Spans in HashMaps (wit-parser-spans-in-resolve) - Store spans in HashMap<Id, Span> fields on Resolve
      • Pros: No changes to existing struct layouts (Resolve derives Default so not likely to break consumers)
      • Cons: Indirect lookup; requires explicit remapping during merges
  2. Hook into internal validation (this PR)

    Keep spans private but let consumers hook into the resolution process via a Validator trait with callbacks.

    • Pros: No breaking changes; opt-in complexity; zero cost for users who don't need spans
    • Cons: Validation must happen during push_* calls, not after-the-fact inspection

This PR implements Strategy 2 because it avoids breaking changes and has zero cost for existing. However, I'm happy to go with one of the other strategies or something totally new that I haven't considered.

Here's an example of how a consumer would use this new features:

use wit_parser::{Error, Resolve, Span, Validator};

struct NoEmptyRecords;

impl Validator for NoEmptyRecords {
    fn validate_type(&mut self, resolve: &Resolve, id: TypeId, span: Span) -> Result<(), Error> {
        let ty = &resolve.types[id];
        if let TypeDefKind::Record(r) = &ty.kind {
            if r.fields.is_empty() {
                return Err(Error::new(span, "empty records are not allowed"));
            }
        }
        Ok(())
    }
}

let mut resolve = Resolve::default();
let mut validator = NoEmptyRecords;
resolve.push_source_with_validator("test.wit", source, &mut validator)?;

@wilfreddenton wilfreddenton requested a review from a team as a code owner January 16, 2026 16:27
@wilfreddenton wilfreddenton requested review from fitzgen and removed request for a team January 16, 2026 16:27
@wilfreddenton wilfreddenton changed the title Wit parser validation wit-parser: Add validation hooks for custom linting Jan 16, 2026
@wilfreddenton wilfreddenton marked this pull request as draft January 16, 2026 16:31
@fitzgen fitzgen requested review from pchickey and removed request for fitzgen January 16, 2026 19:29
@fitzgen
Copy link
Member

fitzgen commented Jan 16, 2026

Redirecting review because I'm not familiar with wit-parser

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

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants