UNPKG

5.62 kBMarkdownView Raw
1# Hookable
2
3[![npm version][npm-version-src]][npm-version-href]
4[![npm downloads][npm-downloads-src]][npm-downloads-href]
5[![packagephobia][packagephobia-src]][packagephobia-href]
6[![Github Actions CI][github-actions-ci-src]][github-actions-ci-href]
7> Awaitable hook system
8
9## Install
10
11Using yarn:
12
13```bash
14yarn add sync-hookable
15```
16
17Using npm:
18
19```bash
20npm install sync-hookable
21```
22
23## Usage
24
25**Method A: Create a sync-hookable instance:**
26
27```js
28import { createHooks } from 'sync-hookable'
29
30// Create a sync-hookable instance
31const hooks = createHooks()
32
33// Hook on 'hello'
34hooks.hook('hello', () => { console.log('Hello World' )})
35
36// Call 'hello' hook
37hooks.callHook('hello')
38```
39
40**Method B: Extend your base class from Hookable:**
41
42```js
43import { Hookable } from 'sync-hookable'
44
45export default class FooLib extends Hookable {
46 constructor() {
47 // Call to parent to initialize
48 super()
49 // Initialize Hookable with custom logger
50 // super(consola)
51 }
52
53 someFunction() {
54 // Call for `hook1` hooks (if any) sequential
55 this.callHook('hook1')
56 }
57}
58```
59
60**Inside plugins, register for any hook:**
61
62```js
63const lib = new FooLib()
64
65// Register a handler for `hook2`
66lib.hook('hook2', () => { /* ... */ })
67
68// Register multiply handlers at once
69lib.addHooks({
70 hook1: () => { /* ... */ },
71 hook2: [ /* can be also an array */ ]
72})
73```
74
75**Unregistering hooks:**
76
77```js
78const lib = new FooLib()
79
80const hook0 = () => { /* ... */ }
81const hook1 = () => { /* ... */ }
82const hook2 = () => { /* ... */ }
83
84// The hook() method returns an "unregister" function
85const unregisterHook0 = lib.hook('hook0', hook0)
86const unregisterHooks1and2 = lib.addHooks({ hook1, hook2 })
87
88/* ... */
89
90unregisterHook0()
91unregisterHooks1and2()
92
93// or
94
95lib.removeHooks({ hook0, hook1 })
96lib.removeHook('hook2', hook2)
97```
98
99**Triggering a hook handler once:**
100
101```js
102const lib = new FooLib()
103
104const unregister = lib.hook('hook0', () => {
105 // Unregister as soon as the hook is executed
106 unregister()
107
108 /* ... */
109})
110```
111
112
113## Hookable class
114
115### `constructor()`
116
117### `hook (name, fn)`
118
119Register a handler for a specific hook. `fn` must be a function.
120
121Returns an `unregister` function that, when called, will remove the registered handler.
122
123### `hookOnce (name, fn)`
124
125Similar to `hook` but unregisters hook once called.
126
127Returns an `unregister` function that, when called, will remove the registered handler before first call.
128
129### `addHooks(configHooks)`
130
131Flatten and register hooks object.
132
133Example:
134
135```js
136hookable.addHooks({
137 test: {
138 before: () => {},
139 after: () => {}
140 }
141})
142
143```
144
145This registers `test:before` and `test:after` hooks at bulk.
146
147Returns an `unregister` function that, when called, will remove all the registered handlers.
148
149### `callHook (name, ...args)`
150
151Used by class itself to **sequentially** call handlers of a specific hook.
152
153### `callHookWith (name, callerFn)`
154
155If you need custom control over how hooks are called, you can provide a custom function that will receive an array of handlers of a specific hook.
156
157`callerFn` if a callback function that accepts two arguments, `hooks` and `args`:
158- `hooks`: Array of user hooks to be called
159- `args`: Array of arguments that should be passed each time calling a hook
160
161### `deprecateHook (old, name)`
162
163Deprecate hook called `old` in favor of `name` hook.
164
165### `deprecateHooks (deprecatedHooks)`
166
167Deprecate all hooks from an object (keys are old and values or newer ones).
168
169### `removeHook (name, fn)`
170
171Remove a particular hook handler, if the `fn` handler is present.
172
173### `removeHooks (configHooks)`
174
175Remove multiple hook handlers.
176
177Example:
178
179```js
180const handler = () => { /* ... */ }
181
182hookable.hook('test:before', handler)
183hookable.addHooks({ test: { after: handler } })
184
185// ...
186
187hookable.removeHooks({
188 test: {
189 before: handler,
190 after: handler
191 }
192})
193```
194
195### `beforeEach (syncCallback)`
196
197Registers a (sync) callback to be called before each hook is being called.
198
199```js
200hookable.beforeEach((event) => { console.log(`${event.name} hook is being called with ${event.args}`)})
201hookable.hook('test', () => { console.log('running test hook') })
202
203// test hook is being called with []
204// running test hook
205hookable.callHook('test')
206```
207
208### `afterEach (syncCallback)`
209
210Registers a (sync) callback to be called after each hook is being called.
211
212```js
213hookable.afterEach((event) => { console.log(`${event.name} hook called with ${event.args}`)})
214hookable.hook('test', () => { console.log('running test hook') })
215
216// running test hook
217// test hook called with []
218hookable.callHook('test')
219```
220
221### `createDebugger`
222
223Automatically logs each hook that is called and how long it takes to run.
224
225```js
226const debug = hookable.createDebugger(hooks, { tag: 'something' })
227
228hooks.callHook('some-hook', 'some-arg')
229// [something] some-hook: 0.21ms
230
231debug.close()
232```
233
234## Credits
235
236Extracted from [Nuxt](https://github.com/nuxt/nuxt.js) hooks system originally introduced by [Sébastien Chopin](https://github.com/Atinux)
237
238## License
239
240MIT - Made with 💖
241
242<!-- Badges -->
243[npm-version-src]: https://flat.badgen.net/npm/dt/sync-hookable
244[npm-version-href]: https://npmjs.com/package/sync-hookable
245
246[npm-downloads-src]: https://flat.badgen.net/npm/v/sync-hookable
247[npm-downloads-href]: https://npmjs.com/package/sync-hookable
248
249[github-actions-ci-src]: https://flat.badgen.net/github/checks/Vinccool96/sync-hookable/master
250[github-actions-ci-href]: https://github.com/Vinccool96/sync-hookable/actions
251
252[packagephobia-src]: https://flat.badgen.net/packagephobia/install/sync-hookable
253[packagephobia-href]: https://packagephobia.now.sh/result?p=sync-hookable