Use this issue to propose an RFC topic and get early alignment.
If accepted, we’ll typically ask for a PR adding an RFC document under docs/RFCs/ based on the RFC template.
RFCs are user-facing only (language features, documentation, CLI/tooling, runtime surface area).
If your proposal is about Rust internals/compiler architecture, please open a bug/chore/feature issue instead.
Area
- Incan Language (syntax/semantics)
- Runtime / Core crates (stdlib/core/derive)
- Documentation
Summary
RFC 098 proposes native associated types for Incan traits: trait-owned named type members that each implementation binds, with checked projection through Self.Item, H.Digest, or similar type-position syntax. The goal is to let Incan-authored traits express implementer-selected type relationships directly instead of multiplying helper traits, wrapper functions, or runtime dispatch paths.
Motivation
The current trait system can express method requirements, generic bounds, supertraits, and Rust trait adoption, but it cannot express a native Incan trait where the implementer chooses a type that other methods and generic helpers can recover. That gap showed up in std.hash, where a streaming hasher has shared update(...) behavior but different digest shapes, and also applies to iterators, parsers, codecs, resource readers, adapters, graph traversal, and Rust interop. RFC 023 and RFC 042 already identify associated types as future trait-system work; RFC 098 turns that into a source-level Incan feature rather than keeping it as a Rust-only interop detail.
Proposal sketch
Add associated type declarations inside native traits:
pub trait PullIterator:
type Item
def next(mut self) -> Option[Self.Item]: ...
Concrete adopters bind those members:
pub class Lines with PullIterator:
type Item = str
def next(mut self) -> Option[str]:
...
Generic code can project the implementer's chosen type through a bound:
def next_or_default[I with PullIterator](mut input: I, default: I.Item) -> I.Item:
match input.next():
Some(value) => return value
None => return default
The RFC also defines missing-binding diagnostics, ambiguous projection rules, targeted bindings for same-name associated types, method signature compatibility, supertrait interactions, and the relationship to adjacent features such as generic associated types, associated constants, default associated types, specialization, trait objects, and equality constraints.
Draft RFC file: workspaces/docs-site/docs/RFCs/098_native_associated_types.md.
Alternatives considered
Keep using ordinary generic trait parameters for implementer-selected type families. That works when the caller chooses the type, but it forces APIs to carry generic arguments that are not real inputs to the capability.
Split traits by final value shape, such as byte-digest versus integer-digest hashers. That can work for tiny surfaces, but scales poorly and prevents one generic helper from returning the implementer's selected type.
Use union return types. That moves a static type relationship into runtime narrowing and makes callers branch even when the concrete implementation type is known.
Treat associated types as a Rust-only interop detail. That is insufficient because stdlib and user-authored Incan traits need the same modeling power without involving an external Rust trait.
Impact / compatibility
This is additive. Existing traits without associated types continue to work unchanged, and existing Rust trait associated type support from RFC 043 remains valid. The main impact is on the trait/typechecker model, generated backend signatures, formatter/LSP support, and stdlib APIs that can remove duplicated shape-specific abstractions once associated types exist.
Implementation notes (optional)
Likely layers: parser/AST for type Name in trait and adopter bodies, typechecker/symbol resolution for associated type metadata and projection, IR lowering/emission for preserving projected types, stdlib/runtime docs and APIs that dogfood the feature, formatter support, and LSP hover/completion/diagnostics.
Checklist
Use this issue to propose an RFC topic and get early alignment.
If accepted, we’ll typically ask for a PR adding an RFC document under
docs/RFCs/based on the RFC template.RFCs are user-facing only (language features, documentation, CLI/tooling, runtime surface area).
If your proposal is about Rust internals/compiler architecture, please open a bug/chore/feature issue instead.
Area
Summary
RFC 098 proposes native associated types for Incan traits: trait-owned named type members that each implementation binds, with checked projection through
Self.Item,H.Digest, or similar type-position syntax. The goal is to let Incan-authored traits express implementer-selected type relationships directly instead of multiplying helper traits, wrapper functions, or runtime dispatch paths.Motivation
The current trait system can express method requirements, generic bounds, supertraits, and Rust trait adoption, but it cannot express a native Incan trait where the implementer chooses a type that other methods and generic helpers can recover. That gap showed up in
std.hash, where a streaming hasher has sharedupdate(...)behavior but different digest shapes, and also applies to iterators, parsers, codecs, resource readers, adapters, graph traversal, and Rust interop. RFC 023 and RFC 042 already identify associated types as future trait-system work; RFC 098 turns that into a source-level Incan feature rather than keeping it as a Rust-only interop detail.Proposal sketch
Add associated type declarations inside native traits:
Concrete adopters bind those members:
Generic code can project the implementer's chosen type through a bound:
The RFC also defines missing-binding diagnostics, ambiguous projection rules, targeted bindings for same-name associated types, method signature compatibility, supertrait interactions, and the relationship to adjacent features such as generic associated types, associated constants, default associated types, specialization, trait objects, and equality constraints.
Draft RFC file:
workspaces/docs-site/docs/RFCs/098_native_associated_types.md.Alternatives considered
Keep using ordinary generic trait parameters for implementer-selected type families. That works when the caller chooses the type, but it forces APIs to carry generic arguments that are not real inputs to the capability.
Split traits by final value shape, such as byte-digest versus integer-digest hashers. That can work for tiny surfaces, but scales poorly and prevents one generic helper from returning the implementer's selected type.
Use union return types. That moves a static type relationship into runtime narrowing and makes callers branch even when the concrete implementation type is known.
Treat associated types as a Rust-only interop detail. That is insufficient because stdlib and user-authored Incan traits need the same modeling power without involving an external Rust trait.
Impact / compatibility
This is additive. Existing traits without associated types continue to work unchanged, and existing Rust trait associated type support from RFC 043 remains valid. The main impact is on the trait/typechecker model, generated backend signatures, formatter/LSP support, and stdlib APIs that can remove duplicated shape-specific abstractions once associated types exist.
Implementation notes (optional)
Likely layers: parser/AST for
type Namein trait and adopter bodies, typechecker/symbol resolution for associated type metadata and projection, IR lowering/emission for preserving projected types, stdlib/runtime docs and APIs that dogfood the feature, formatter support, and LSP hover/completion/diagnostics.Checklist