swc-project/swc · error
UnsafeId.to_id() is not allowed because it is very likely to
Error message
UnsafeId.to_id() is not allowed because it is very likely to be unsafe
What it means
UnsafeId (swc_ecma_ast) is a performance-oriented IdentLike implementation created through the unsafe unsafe_id_from_ident path; converting it back to an Id via IdentLike::to_id()/into_id() is deliberately blocked with unreachable! because such a conversion would be 'very likely to be unsafe' given how UnsafeId instances are constructed. The panic is an intentional guard against misusing the fast identifier type in generic code.
Source
Thrown at crates/swc_ecma_utils/src/ident.rs:79
#[inline]
fn to_id(&self) -> Id {
(self.sym.clone(), self.ctxt)
}
#[inline]
fn into_id(self) -> Id {
(self.sym, self.ctxt)
}
}
impl IdentLike for UnsafeId {
fn from_ident(i: &Ident) -> Self {
unsafe { unsafe_id_from_ident(i) }
}
fn to_id(&self) -> Id {
unreachable!("UnsafeId.to_id() is not allowed because it is very likely to be unsafe")
}
fn into_id(self) -> Id {
unreachable!("UnsafeId.into_id() is not allowed because it is very likely to be unsafe")
}
}
View on GitHub (pinned to 5176682b65)
Solutions
- Key your maps/scopes by Id (or (Atom, SyntaxContext)) wherever downstream code needs to_id/into_id; keep UnsafeId only in leaf passes that never convert back.
- Extract the Id at the boundary before switching to UnsafeId: store `(sym.clone(), ctxt)` while you still have the Ident.
- Audit call sites with `rg '\.to_id\(\)|\.into_id\(\)'` in code generic over `I: IdentLike`.
- If a public swc API forces the conversion, report it as a bug against that API.
Example fix
// before: UnsafeId flows into code that converts keys back to Id let mut usage: IdentUsageFinder<UnsafeId> = ...; // later calls .to_id() // after: convert while the Ident is still around, key by Id let key: Id = (ident.sym.clone(), ident.ctxt); let mut usage: IdentUsageFinder<Id> = ...;
Defensive patterns
Strategy: type-guard
Validate before calling
// Extract the Id while a real Ident is available, before switching to UnsafeId
use swc_ecma_ast::Ident; use swc_ecma_utils::IdentLike;
fn id_of(i: &Ident) -> Id { (i.sym.clone(), i.ctxt) }
// store id_of(&ident) as the map key; pass UnsafeId only through code that never converts Type guard
// Compile-time discipline: any API that will call to_id/into_id must be
// instantiated with Id (or (Atom, SyntaxContext)), never UnsafeId.
fn takes_convertible_key<I: IdentLike>(k: &I) -> Id where I: Clone { k.to_id() } // OK for Id, PANICS for UnsafeId — keep UnsafeId out of these call paths Prevention
- Grep for `.to_id()` / `.into_id()` in code generic over `I: IdentLike` before swapping Id for UnsafeId.
- Convert identifiers to Id at the boundary where the Ident still exists.
- Reserve UnsafeId for leaf hot paths proven never to convert back.
When it happens
Trigger: Instantiating generic utilities bound by IdentLike (scopes, ident-usage collectors, caches in swc_ecma_utils etc.) with UnsafeId and letting them call .to_id() or .into_id() on their keys/values — typically when someone swaps Id for UnsafeId for speed and forgets a downstream conversion.
Common situations: Contributors optimizing hot passes by keying maps with UnsafeId; copying Id-based code and only changing the type parameter; using APIs whose default type parameter is UnsafeId on a version where that became opt-in.
Related errors
- Invalid attempt to iterate non-iterable instance. In order t
- Duplicated methods (${element.key}) can't be decorated.
- Decorators can't be placed on different accessors with for t
- Duplicated element (${element.key})
- Duplicated element (${elements[j].key})
AI-assisted analysis of swc-project/swc@5176682b65 (2026-08-17).
Data as JSON: /api/errors/4e84288faf5af3cf.
Report an issue: GitHub.