- Start Date: 2026-02-27
- Target Major Version: 10.x
Criticisms:
- "I can't prove the performance envelope."
- "Debugging across JS<->native is not deterministic enough."
- "Memory and lifecycle rules feel too implicit."
- "Tooling doesn't show me where time and memory went."
This RFC proposes a runtime roadmap that directly addresses those concerns by making boundary costs measurable and cheap, ownership explicit, and profiling first-class.
-
Performance Predictability
Reduce tail latency and eliminate random jank spikes. -
Explicit Ownership & Lifecycle
Make object lifetime across JS and native deterministic and enforceable. -
Observability-First Runtime
Make it easy to answer: "Why did this hitch?"
- Startup Consistency
- Safe Migration Path
- Rewriting the UI paradigm
- Boundary overhead is too dynamic (reflection, runtime dispatch).
- Ownership between JS and native is ambiguous.
- Threading rules are insufficiently enforced.
- Tooling does not unify JS and native execution clearly.
- Make the fast path the default path.
- Pay costs once, not per call.
- Ownership must be explicit and enforceable.
- Everything must be measurable.
Move core bindings to a code-generated interface layer with static dispatch.
Deliverables: - Binding schema format - JS wrappers + native stubs - Marshaling fast paths - Tracepoints per binding
Acceptance Criteria: - Top 100 APIs use codegen path - Profiler reports dynamic vs codegen usage
Introduce ownership policies:
- Borrowed
- Owned
- Pinned
Use stable numeric handles with handle tables internally.
Deliverables: - Handle table implementation - dispose() /
close() lifecycle hooks - Ownership annotations in schema - Dev-time
misuse warnings
Acceptance Criteria: - Leak snapshots identify retained native objects - Misuse triggers actionable errors
- Zero-copy typed arrays and buffers
- Packed structs for common value types
- Batched UI transactions
Acceptance Criteria: - Reduced boundary call count - Improved p95/p99 frame times
- Enforce UI-thread-only objects
- Provide explicit scheduling primitives
Acceptance Criteria: - Clear errors for thread misuse
- Unified JS + native timeline tracing
- Boundary profiler (top bindings, call counts, costs)
- Memory correlation (JS heap + native heap + handles)
Acceptance Criteria: - Performance issues diagnosable from captured traces
- Bytecode caching / snapshotting
- Precomputed binding tables
- Lazy loading of native APIs
Acceptance Criteria: - Improved cold-start p95
- Phase 1: Ship with npm tag during acceptance cycle
- Phase 2: Dual-path bindings (codegen + fallback)
- Phase 3: Tooling for plugin migration
- Phase 4: Default for new apps
Scenarios: - List scroll stress - Startup & first render - Navigation churn - Animation/gesture pressure - Memory retention cycles
Metrics: - Frame time p50 / p95 / p99 - Boundary calls/sec - Marshaling allocations/sec - Cold-start p95 - Retained native handles
- Engineering scope
- API surface complexity
- Plugin inertia
- Instrumentation overhead
- Target engine constraints?
- Current top boundary hot paths?
- Ecosystem keystone plugins?
- Schema ergonomics?
We are making the runtime predictable:
- Static, measurable boundary calls
- Explicit ownership
- Unified profiling
- Reasonable, enforceable semantics