Names and scoping
This page describes how sprig resolves names, and how ambiguity is handled.
The goal is simple: allow short names when a universe is small, and clear, explicit paths as it grows—without forcing a structural rewrite along the way.
Names are semantic, not structural
In sprig, names are resolved based on meaningful relationships, not file layout or block placement.
An entity does not need to be nested inside its parent block to belong to that parent. Nesting is a convenience, not a requirement.
This is valid:
universe Universe { }
series Series1 in Universe { }
book BookName in Series1 { } And it is equivalent to the nested form:
universe Universe {
series Series1 {
book BookName { }
}
} Both describe the same universe. The choice is purely about how you want to organize your prose.
Identity and paths
Every entity in a universe has a path identity.
A path identity is formed by the semantic parentage of an entity, not by where it appears in a file.
For example:
Series1.BookNameSeries2.BookName
These are different entities, even if they share the same local name.
The compiler always works with fully-qualified paths internally, even when the prose uses short names.
Local names
Inside a container, entities may be referenced by their local name.
series Series1 {
book BookName { }
chapter Chapter3 in BookName { }
} In this context, BookName resolves to Series1.BookName.
Local names are preferred when they are unambiguous.
Name resolution order
When resolving a name, sprig follows a simple, predictable search order:
- The current container
- The parent container
- Continuing outward through enclosing containers
- The universe
The first matching entity found in this search is used.
If no matching entity is found, the reference is invalid.
Qualification
When a name is not local, or when multiple entities share the same name, it must be qualified.
Qualification uses dot notation to describe a path:
Series2.BookName Qualification may be partial or full, as long as it uniquely identifies the target.
Inside Series1, this is valid:
relates BookName and Series2.BookName { } Here:
BookNameresolves locallySeries2.BookNameresolves by qualification
Ambiguity
If a name resolves to multiple entities at the same search level, the reference is ambiguous.
Ambiguous references are errors.
Sprig does not guess, prefer, or reorder candidates.
Instead, the compiler reports the ambiguity and requires qualification.
This keeps name resolution boring and predictable.
Duplicate names
Duplicate names are allowed as long as they are unambiguous.
This is common and expected:
series Series1 {
book BookName { }
}
series Series2 {
book BookName { }
} These entities are distinct because their paths differ.
Declaring entities in multiple places
An entity may be declared in more than one block if all declarations resolve to the same path identity.
These declarations are merged.
If two declarations attempt to assign different parentage to the same entity, this is an error.
Design intent
Name resolution in sprig is designed to:
- Encourage short, readable prose early
- Allow overlap without collision
- Scale naturally as universes grow
- Make ambiguity explicit instead of implicit
If a reference ever feels unclear, qualification is the intended solution.
Aliases
Aliases allow you to introduce local vocabulary for declaration kinds.
They only change how declarations are written within a scope.
Aliases are most useful when modeling a specific domain where certain words are more natural or more legible than the canonical declaration kinds.
Declaring aliases
Aliases may be declared using an aliases block:
aliases {
team { book }
person { concept }
} Or individually:
alias team { book }
alias person { concept } Both forms are equivalent.
Using aliases
Once declared, an alias may be used anywhere a declaration kind is expected within the same scope:
team FrontendTeam { }
person Michael { } Here is a more concrete example showing where aliases apply.
anthology Organization {
alias team { book }
team FrontendTeam { }
series InternalSeries {
team ReportingTeam { }
}
}
series ExternalSeries in Organization {
team DatabaseTeam { }
} What comes next
Now that we can name things in our universe, the next thing we might want to do is point to things outside of our universe.
You can do that by using references.