From e3de3bfb080e5fc2899e27a45a75813bdc5f862d Mon Sep 17 00:00:00 2001 From: Raymond Feng Date: Mon, 20 Jan 2020 09:01:40 -0800 Subject: [PATCH] feat(docs): update docs for context event handling --- docs/site/Context.md | 54 +++++++++++++++++++++++++++++++++++++++++--- 1 file changed, 51 insertions(+), 3 deletions(-) diff --git a/docs/site/Context.md b/docs/site/Context.md index 15ae8a19b2b9..ed86cfe7ab7e 100644 --- a/docs/site/Context.md +++ b/docs/site/Context.md @@ -240,7 +240,7 @@ the form of metadata) to your intent. ## Context events -The `Context` emits the following events: +An instance of `Context` can emit the following events: - `bind`: Emitted when a new binding is added to the context. - binding: the newly added binding object @@ -252,12 +252,51 @@ The `Context` emits the following events: process - err: the error object thrown +The bind/unbind events are represented as the following type: + +```ts +/** + * Events emitted by a context + */ +export type ContextEvent = { + /** + * Source context that emits the event + */ + context: Context; + /** + * Binding that is being added/removed/updated + */ + binding: Readonly>; + /** + * Event type + */ + type: string; // 'bind' or 'unbind' +}; +``` + When an existing binding key is replaced with a new one, an `unbind` event is emitted for the existing binding followed by a `bind` event for the new binding. If a context has a parent, binding events from the parent are re-emitted on the context when the binding key does not exist within the current context. +A context event listener should conform to the following signature: + +```ts +/** + * Synchronous event listener for the `Context` as en event emitter + */ +export type ContextEventListener = (event: ContextEvent) => void; +``` + +By default, `maxListeners` is set to `Infinity` for context objects to avoid +[memory leak warnings](https://github.com/strongloop/loopback-next/issues/4363). +The value can be reset as follows: + +```ts +ctx.setMaxListeners(128); +``` + ## Context observers Bindings can be added or removed to a context object. With emitted context @@ -275,7 +314,7 @@ come and go. There are a few caveats associated with that: .bind('foo') .to('foo-value') .tag('foo-tag'); - ctx.on('bind', binding => { + ctx.on('bind', {binding} => { console.log(binding.tagNames); // returns an empty array `[]` }); ``` @@ -293,7 +332,7 @@ come and go. There are a few caveats associated with that: .to('foo-value') .tag('foo-tag'); ctx.add(binding); - ctx.on('bind', binding => { + ctx.on('bind', {binding} => { console.log(binding.tagMap); // returns `['foo-tag']` }); ``` @@ -344,6 +383,15 @@ export type ContextEventObserver = ContextObserver | ContextObserverFn; If `filter` is not required, we can simply use `ContextObserverFn`. +Please note that `ContextEventObserver` is different from +`ContextEventListener`: + +- A `ContextEventListener` is synchronous and it's invoked when the event is + emitted (before `emit` returns). + +- A `ContextEventObserver` is asynchronous and it's invoked by the notification + queue after the event is emitted (after `emit` returns). + 2. Context APIs - `subscribe(observer: ContextEventObserver)`