Registry<T> class Null safety

An isolate-compatible object registry.

Objects can be stored as elements of a registry, have "tags" assigned to them, and be looked up by tag.

Since the registry is identity based, the objects must not be numbers, strings, booleans or null. See Expando for description of which objects are not treated as having a clear identity.

A Registry object caches objects found using the lookup method, or added using add, and returns the same object every time it is requested. A different Registry object that works on the same underlying registry, will not preserve the identity of elements

It is recommended to only have one Registry object working on the same registry in each isolate.

When the registry is shared across isolates, both elements and tags must be sendable between the isolates. See SendPort for details on the restrictions on objects which can be sent between isolates.

A registry can be used to make a number of objects available to separate workers in different isolates, for example ones created using IsolateRunner, without sending all the objects to all the isolates. A worker can then request the data it needs, and it can add new data to the registry that will also be shared with all other workers. Example:

main() {
  Registry<List<String>> dictionaryByFirstLetter = Registry();
  for (var letter in alphabet) {
    registry.add(
        allWords.where((w) => w.startsWith(letter).toList,
        tags: [letter]);
  }
  var loadBalancer = LoadBalancer(10);
  for (var task in tasks) {
    loadBalancer.run(_runTask, [task, dictionaryByFirstLetter]);
  }
}
_runTask(task, Registry<List<String>> dictionaryByFirstLetter) async {
  ...
  // Fetch just the words starting with the needed letter.
  var aWords = await dictionaryByFirstLetter.lookup(tags: [task.letter]);
  ...
}

A registry can be treated like a distributed multimap from tags to objects, if each tag is only used once. Example:

Registry<Capability> capabilities = Registry();
// local code:
  ...
  capabilities.add(Capability(), ["create"]);
  capabilities.add(Capability(), ["read"]);
  capabilities.add(Capability(), ["update"]);
  capabilities.add(Capability(), ["delete"]);
  ...
  sendPort.send(capabilities);

// other isolate code:
  Registry<Capability> capabilities = await receiveFromPort();

  Future<Capability> get createCapability => (await
     capabilities.lookup(tags: const ["create"])).first;

Constructors

Registry.fromPort(SendPort commandPort, {Duration timeout = const Duration(seconds: 5)})
Create a registry linked to a RegistryManager through commandPort. [...]

Properties

hashCode int
The hash code for this object. [...]
read-only, inherited
runtimeType Type
A representation of the runtime type of the object.
read-only, inherited

Methods

add(T element, {Iterable? tags}) Future<Capability>
Adds element to the registry with the provided tags. [...]
addTags(Iterable<T> elements, Iterable<Object?> tags) Future
Add tags to objects in the registry. [...]
lookup({Iterable<Object?>? tags, int? max}) Future<List<T>>
Finds a number of elements that have all the desired tags. [...]
noSuchMethod(Invocation invocation) → dynamic
Invoked when a non-existent method or property is accessed. [...]
inherited
remove(T element, Capability removeCapability) Future<bool>
Removes the element from the registry. [...]
removeTags(Iterable<T> elements, Iterable<Object?> tags) Future<void>
Remove tags from objects in the registry. [...]
toString() String
A string representation of this object. [...]
inherited

Operators

operator ==(Object other) bool
The equality operator. [...]
inherited