IsolatePool class
A fixed pool of long-lived worker isolates with a persistent reply port.
Why this is faster than the naive ReceivePort-per-call approach
The old implementation allocated and closed a ReceivePort on every
dispatch call. Each allocation involves an OS-level port registration,
and each close involves a deregistration — costs that dominate latency for
short FFI tasks. With a pool size of 4 and 50,000 calls/second that is
100,000 OS operations per second just for port bookkeeping.
This implementation opens exactly one ReceivePort per pool at
creation time. Every response is tagged with a monotonically-increasing
_callIdCounter; a Map<int, _PendingCall> routes each response to the
correct Completer without any per-call OS interaction.
Least-busy scheduling
Workers are chosen by the least-busy algorithm: _inflight tracks the
number of in-flight calls per worker and the dispatcher always picks the
worker with the smallest count. This prevents a slow JNI or Swift call on
one worker from blocking the next task that would have landed there via
round-robin.
Properties
- hashCode → int
-
The hash code for this object.
no setterinherited
- runtimeType → Type
-
A representation of the runtime type of the object.
no setterinherited
Methods
-
dispatch<
T> (Function fn, List< Object?> args, {Pointer<NativeFunction< ? getError, Pointer<Pointer< >NitroErrorFfi> Function()>NativeFunction< ? clearError}) → Future<Void Function()> >T> - Dispatches fn to the least-busy worker.
-
dispose(
) → void - Kills all worker isolates and closes the reply port.
-
noSuchMethod(
Invocation invocation) → dynamic -
Invoked when a nonexistent method or property is accessed.
inherited
-
toString(
) → String -
A string representation of this object.
inherited
Operators
-
operator ==(
Object other) → bool -
The equality operator.
inherited
Static Methods
-
create(
int size) → Future< IsolatePool> -
Spawns
sizeworker isolates, wires a single persistent reply port, and returns a ready pool.