프로젝트

일반

사용자정보

통계
| 개정판:

root / HServer / 00.Server / 00.Program / node_modules / kareem / README.md

이력 | 보기 | 이력해설 | 다운로드 (8.99 KB)

1 39 HKM
# kareem
2
3
  [![Build Status](https://travis-ci.org/vkarpov15/kareem.svg?branch=master)](https://travis-ci.org/vkarpov15/kareem)
4
  [![Coverage Status](https://img.shields.io/coveralls/vkarpov15/kareem.svg)](https://coveralls.io/r/vkarpov15/kareem)
5
6
Re-imagined take on the [hooks](http://npmjs.org/package/hooks) module, meant to offer additional flexibility in allowing you to execute hooks whenever necessary, as opposed to simply wrapping a single function.
7
8
Named for the NBA's all-time leading scorer Kareem Abdul-Jabbar, known for his mastery of the [hook shot](http://en.wikipedia.org/wiki/Kareem_Abdul-Jabbar#Skyhook)
9
10
<img src="http://upload.wikimedia.org/wikipedia/commons/0/00/Kareem-Abdul-Jabbar_Lipofsky.jpg" width="220">
11
12
# API
13
14
## pre hooks
15
16
Much like [hooks](https://npmjs.org/package/hooks), kareem lets you define
17
pre and post hooks: pre hooks are called before a given function executes.
18
Unlike hooks, kareem stores hooks and other internal state in a separate
19
object, rather than relying on inheritance. Furthermore, kareem exposes
20
an `execPre()` function that allows you to execute your pre hooks when
21
appropriate, giving you more fine-grained control over your function hooks.
22
23
24
#### It runs without any hooks specified
25
26
```javascript
27
28
    hooks.execPre('cook', null, function() {
29
      done();
30
    });
31
32
```
33
34
#### It runs basic serial pre hooks
35
36
pre hook functions take one parameter, a "done" function that you execute
37
when your pre hook is finished.
38
39
40
```javascript
41
42
    var count = 0;
43
44
    hooks.pre('cook', function(done) {
45
      ++count;
46
      done();
47
    });
48
49
    hooks.execPre('cook', null, function() {
50
      assert.equal(1, count);
51
      done();
52
    });
53
54
```
55
56
#### It can run multipe pre hooks
57
58
```javascript
59
60
    var count1 = 0;
61
    var count2 = 0;
62
63
    hooks.pre('cook', function(done) {
64
      ++count1;
65
      done();
66
    });
67
68
    hooks.pre('cook', function(done) {
69
      ++count2;
70
      done();
71
    });
72
73
    hooks.execPre('cook', null, function() {
74
      assert.equal(1, count1);
75
      assert.equal(1, count2);
76
      done();
77
    });
78
79
```
80
81
#### It can run fully synchronous pre hooks
82
83
If your pre hook function takes no parameters, its assumed to be
84
fully synchronous.
85
86
87
```javascript
88
89
    var count1 = 0;
90
    var count2 = 0;
91
92
    hooks.pre('cook', function() {
93
      ++count1;
94
    });
95
96
    hooks.pre('cook', function() {
97
      ++count2;
98
    });
99
100
    hooks.execPre('cook', null, function(error) {
101
      assert.equal(null, error);
102
      assert.equal(1, count1);
103
      assert.equal(1, count2);
104
      done();
105
    });
106
107
```
108
109
#### It properly attaches context to pre hooks
110
111
Pre save hook functions are bound to the second parameter to `execPre()`
112
113
114
```javascript
115
116
    hooks.pre('cook', function(done) {
117
      this.bacon = 3;
118
      done();
119
    });
120
121
    hooks.pre('cook', function(done) {
122
      this.eggs = 4;
123
      done();
124
    });
125
126
    var obj = { bacon: 0, eggs: 0 };
127
128
    // In the pre hooks, `this` will refer to `obj`
129
    hooks.execPre('cook', obj, function(error) {
130
      assert.equal(null, error);
131
      assert.equal(3, obj.bacon);
132
      assert.equal(4, obj.eggs);
133
      done();
134
    });
135
136
```
137
138
#### It can execute parallel (async) pre hooks
139
140
Like the hooks module, you can declare "async" pre hooks - these take two
141
parameters, the functions `next()` and `done()`. `next()` passes control to
142
the next pre hook, but the underlying function won't be called until all
143
async pre hooks have called `done()`.
144
145
146
```javascript
147
148
    hooks.pre('cook', true, function(next, done) {
149
      this.bacon = 3;
150
      next();
151
      setTimeout(function() {
152
        done();
153
      }, 5);
154
    });
155
156
    hooks.pre('cook', true, function(next, done) {
157
      next();
158
      var _this = this;
159
      setTimeout(function() {
160
        _this.eggs = 4;
161
        done();
162
      }, 10);
163
    });
164
165
    hooks.pre('cook', function(next) {
166
      this.waffles = false;
167
      next();
168
    });
169
170
    var obj = { bacon: 0, eggs: 0 };
171
172
    hooks.execPre('cook', obj, function() {
173
      assert.equal(3, obj.bacon);
174
      assert.equal(4, obj.eggs);
175
      assert.equal(false, obj.waffles);
176
      done();
177
    });
178
179
```
180
181
#### It supports returning a promise
182
183
You can also return a promise from your pre hooks instead of calling
184
`next()`. When the returned promise resolves, kareem will kick off the
185
next middleware.
186
187
188
```javascript
189
190
    hooks.pre('cook', function() {
191
      return new Promise(resolve => {
192
        setTimeout(() => {
193
          this.bacon = 3;
194
          resolve();
195
        }, 100);
196
      });
197
    });
198
199
    var obj = { bacon: 0 };
200
201
    hooks.execPre('cook', obj, function() {
202
      assert.equal(3, obj.bacon);
203
      done();
204
    });
205
206
```
207
208
## post hooks
209
210
#### It runs without any hooks specified
211
212
```javascript
213
214
    hooks.execPost('cook', null, [1], function(error, eggs) {
215
      assert.ifError(error);
216
      assert.equal(1, eggs);
217
      done();
218
    });
219
220
```
221
222
#### It executes with parameters passed in
223
224
```javascript
225
226
    hooks.post('cook', function(eggs, bacon, callback) {
227
      assert.equal(1, eggs);
228
      assert.equal(2, bacon);
229
      callback();
230
    });
231
232
    hooks.execPost('cook', null, [1, 2], function(error, eggs, bacon) {
233
      assert.ifError(error);
234
      assert.equal(1, eggs);
235
      assert.equal(2, bacon);
236
      done();
237
    });
238
239
```
240
241
#### It can use synchronous post hooks
242
243
```javascript
244
245
    var execed = {};
246
247
    hooks.post('cook', function(eggs, bacon) {
248
      execed.first = true;
249
      assert.equal(1, eggs);
250
      assert.equal(2, bacon);
251
    });
252
253
    hooks.post('cook', function(eggs, bacon, callback) {
254
      execed.second = true;
255
      assert.equal(1, eggs);
256
      assert.equal(2, bacon);
257
      callback();
258
    });
259
260
    hooks.execPost('cook', null, [1, 2], function(error, eggs, bacon) {
261
      assert.ifError(error);
262
      assert.equal(2, Object.keys(execed).length);
263
      assert.ok(execed.first);
264
      assert.ok(execed.second);
265
      assert.equal(1, eggs);
266
      assert.equal(2, bacon);
267
      done();
268
    });
269
270
```
271
272
## wrap()
273
274
#### It wraps pre and post calls into one call
275
276
```javascript
277
278
    hooks.pre('cook', true, function(next, done) {
279
      this.bacon = 3;
280
      next();
281
      setTimeout(function() {
282
        done();
283
      }, 5);
284
    });
285
286
    hooks.pre('cook', true, function(next, done) {
287
      next();
288
      var _this = this;
289
      setTimeout(function() {
290
        _this.eggs = 4;
291
        done();
292
      }, 10);
293
    });
294
295
    hooks.pre('cook', function(next) {
296
      this.waffles = false;
297
      next();
298
    });
299
300
    hooks.post('cook', function(obj) {
301
      obj.tofu = 'no';
302
    });
303
304
    var obj = { bacon: 0, eggs: 0 };
305
306
    var args = [obj];
307
    args.push(function(error, result) {
308
      assert.ifError(error);
309
      assert.equal(null, error);
310
      assert.equal(3, obj.bacon);
311
      assert.equal(4, obj.eggs);
312
      assert.equal(false, obj.waffles);
313
      assert.equal('no', obj.tofu);
314
315
      assert.equal(obj, result);
316
      done();
317
    });
318
319
    hooks.wrap(
320
      'cook',
321
      function(o, callback) {
322
        assert.equal(3, obj.bacon);
323
        assert.equal(4, obj.eggs);
324
        assert.equal(false, obj.waffles);
325
        assert.equal(undefined, obj.tofu);
326
        callback(null, o);
327
      },
328
      obj,
329
      args);
330
331
```
332
333
## createWrapper()
334
335
#### It wraps wrap() into a callable function
336
337
```javascript
338
339
    hooks.pre('cook', true, function(next, done) {
340
      this.bacon = 3;
341
      next();
342
      setTimeout(function() {
343
        done();
344
      }, 5);
345
    });
346
347
    hooks.pre('cook', true, function(next, done) {
348
      next();
349
      var _this = this;
350
      setTimeout(function() {
351
        _this.eggs = 4;
352
        done();
353
      }, 10);
354
    });
355
356
    hooks.pre('cook', function(next) {
357
      this.waffles = false;
358
      next();
359
    });
360
361
    hooks.post('cook', function(obj) {
362
      obj.tofu = 'no';
363
    });
364
365
    var obj = { bacon: 0, eggs: 0 };
366
367
    var cook = hooks.createWrapper(
368
      'cook',
369
      function(o, callback) {
370
        assert.equal(3, obj.bacon);
371
        assert.equal(4, obj.eggs);
372
        assert.equal(false, obj.waffles);
373
        assert.equal(undefined, obj.tofu);
374
        callback(null, o);
375
      },
376
      obj);
377
378
    cook(obj, function(error, result) {
379
      assert.ifError(error);
380
      assert.equal(3, obj.bacon);
381
      assert.equal(4, obj.eggs);
382
      assert.equal(false, obj.waffles);
383
      assert.equal('no', obj.tofu);
384
385
      assert.equal(obj, result);
386
      done();
387
    });
388
389
```
390
391
## clone()
392
393
#### It clones a Kareem object
394
395
```javascript
396
397
    var k1 = new Kareem();
398
    k1.pre('cook', function() {});
399
    k1.post('cook', function() {});
400
401
    var k2 = k1.clone();
402
    assert.deepEqual(['cook'], Object.keys(k2._pres));
403
    assert.deepEqual(['cook'], Object.keys(k2._posts));
404
405
```
406
407
## merge()
408
409
#### It pulls hooks from another Kareem object
410
411
```javascript
412
413
    var k1 = new Kareem();
414
    var test1 = function() {};
415
    k1.pre('cook', test1);
416
    k1.post('cook', function() {});
417
418
    var k2 = new Kareem();
419
    var test2 = function() {};
420
    k2.pre('cook', test2);
421
    var k3 = k2.merge(k1);
422
    assert.equal(k3._pres['cook'].length, 2);
423
    assert.equal(k3._pres['cook'][0].fn, test2);
424
    assert.equal(k3._pres['cook'][1].fn, test1);
425
    assert.equal(k3._posts['cook'].length, 1);
426
427
```