@eggjs/mock 6.0.0-beta.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (159) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +547 -0
  3. package/README.zh_CN.md +512 -0
  4. package/dist/commonjs/app/extend/agent.d.ts +33 -0
  5. package/dist/commonjs/app/extend/agent.js +49 -0
  6. package/dist/commonjs/app/extend/application.d.ts +175 -0
  7. package/dist/commonjs/app/extend/application.js +448 -0
  8. package/dist/commonjs/app/middleware/cluster_app_mock.d.ts +3 -0
  9. package/dist/commonjs/app/middleware/cluster_app_mock.js +100 -0
  10. package/dist/commonjs/app.d.ts +6 -0
  11. package/dist/commonjs/app.js +20 -0
  12. package/dist/commonjs/bootstrap.d.ts +4 -0
  13. package/dist/commonjs/bootstrap.js +58 -0
  14. package/dist/commonjs/index.d.ts +76 -0
  15. package/dist/commonjs/index.js +99 -0
  16. package/dist/commonjs/index.test-d.d.ts +1 -0
  17. package/dist/commonjs/index.test-d.js +43 -0
  18. package/dist/commonjs/lib/agent_handler.d.ts +3 -0
  19. package/dist/commonjs/lib/agent_handler.js +28 -0
  20. package/dist/commonjs/lib/app.d.ts +28 -0
  21. package/dist/commonjs/lib/app.js +303 -0
  22. package/dist/commonjs/lib/app_handler.d.ts +5 -0
  23. package/dist/commonjs/lib/app_handler.js +67 -0
  24. package/dist/commonjs/lib/cluster.d.ts +114 -0
  25. package/dist/commonjs/lib/cluster.js +337 -0
  26. package/dist/commonjs/lib/context.d.ts +1 -0
  27. package/dist/commonjs/lib/context.js +16 -0
  28. package/dist/commonjs/lib/format_options.d.ts +5 -0
  29. package/dist/commonjs/lib/format_options.js +100 -0
  30. package/dist/commonjs/lib/inject_context.d.ts +6 -0
  31. package/dist/commonjs/lib/inject_context.js +132 -0
  32. package/dist/commonjs/lib/mock_agent.d.ts +5 -0
  33. package/dist/commonjs/lib/mock_agent.js +49 -0
  34. package/dist/commonjs/lib/mock_custom_loader.d.ts +1 -0
  35. package/dist/commonjs/lib/mock_custom_loader.js +37 -0
  36. package/dist/commonjs/lib/mock_http_server.d.ts +2 -0
  37. package/dist/commonjs/lib/mock_http_server.js +24 -0
  38. package/dist/commonjs/lib/mock_httpclient.d.ts +35 -0
  39. package/dist/commonjs/lib/mock_httpclient.js +147 -0
  40. package/dist/commonjs/lib/parallel/agent.d.ts +20 -0
  41. package/dist/commonjs/lib/parallel/agent.js +125 -0
  42. package/dist/commonjs/lib/parallel/app.d.ts +20 -0
  43. package/dist/commonjs/lib/parallel/app.js +115 -0
  44. package/dist/commonjs/lib/parallel/util.d.ts +3 -0
  45. package/dist/commonjs/lib/parallel/util.js +77 -0
  46. package/dist/commonjs/lib/prerequire.d.ts +1 -0
  47. package/dist/commonjs/lib/prerequire.js +26 -0
  48. package/dist/commonjs/lib/request_call_function.d.ts +1 -0
  49. package/dist/commonjs/lib/request_call_function.js +52 -0
  50. package/dist/commonjs/lib/restore.d.ts +1 -0
  51. package/dist/commonjs/lib/restore.js +16 -0
  52. package/dist/commonjs/lib/start-cluster.d.ts +2 -0
  53. package/dist/commonjs/lib/start-cluster.js +23 -0
  54. package/dist/commonjs/lib/supertest.d.ts +11 -0
  55. package/dist/commonjs/lib/supertest.js +48 -0
  56. package/dist/commonjs/lib/tmp/empty.d.ts +1 -0
  57. package/dist/commonjs/lib/tmp/empty.js +3 -0
  58. package/dist/commonjs/lib/types.d.ts +60 -0
  59. package/dist/commonjs/lib/types.js +3 -0
  60. package/dist/commonjs/lib/utils.d.ts +9 -0
  61. package/dist/commonjs/lib/utils.js +80 -0
  62. package/dist/commonjs/package.json +3 -0
  63. package/dist/commonjs/register.d.ts +8 -0
  64. package/dist/commonjs/register.js +80 -0
  65. package/dist/esm/app/extend/agent.d.ts +33 -0
  66. package/dist/esm/app/extend/agent.js +46 -0
  67. package/dist/esm/app/extend/application.d.ts +175 -0
  68. package/dist/esm/app/extend/application.js +442 -0
  69. package/dist/esm/app/middleware/cluster_app_mock.d.ts +3 -0
  70. package/dist/esm/app/middleware/cluster_app_mock.js +98 -0
  71. package/dist/esm/app.d.ts +6 -0
  72. package/dist/esm/app.js +17 -0
  73. package/dist/esm/bootstrap.d.ts +4 -0
  74. package/dist/esm/bootstrap.js +16 -0
  75. package/dist/esm/index.d.ts +76 -0
  76. package/dist/esm/index.js +90 -0
  77. package/dist/esm/index.test-d.d.ts +1 -0
  78. package/dist/esm/index.test-d.js +42 -0
  79. package/dist/esm/lib/agent_handler.d.ts +3 -0
  80. package/dist/esm/lib/agent_handler.js +24 -0
  81. package/dist/esm/lib/app.d.ts +28 -0
  82. package/dist/esm/lib/app.js +295 -0
  83. package/dist/esm/lib/app_handler.d.ts +5 -0
  84. package/dist/esm/lib/app_handler.js +61 -0
  85. package/dist/esm/lib/cluster.d.ts +114 -0
  86. package/dist/esm/lib/cluster.js +328 -0
  87. package/dist/esm/lib/context.d.ts +1 -0
  88. package/dist/esm/lib/context.js +13 -0
  89. package/dist/esm/lib/format_options.d.ts +5 -0
  90. package/dist/esm/lib/format_options.js +94 -0
  91. package/dist/esm/lib/inject_context.d.ts +6 -0
  92. package/dist/esm/lib/inject_context.js +126 -0
  93. package/dist/esm/lib/mock_agent.d.ts +5 -0
  94. package/dist/esm/lib/mock_agent.js +45 -0
  95. package/dist/esm/lib/mock_custom_loader.d.ts +1 -0
  96. package/dist/esm/lib/mock_custom_loader.js +34 -0
  97. package/dist/esm/lib/mock_http_server.d.ts +2 -0
  98. package/dist/esm/lib/mock_http_server.js +18 -0
  99. package/dist/esm/lib/mock_httpclient.d.ts +35 -0
  100. package/dist/esm/lib/mock_httpclient.js +144 -0
  101. package/dist/esm/lib/parallel/agent.d.ts +20 -0
  102. package/dist/esm/lib/parallel/agent.js +117 -0
  103. package/dist/esm/lib/parallel/app.d.ts +20 -0
  104. package/dist/esm/lib/parallel/app.js +110 -0
  105. package/dist/esm/lib/parallel/util.d.ts +3 -0
  106. package/dist/esm/lib/parallel/util.js +73 -0
  107. package/dist/esm/lib/prerequire.d.ts +1 -0
  108. package/dist/esm/lib/prerequire.js +25 -0
  109. package/dist/esm/lib/request_call_function.d.ts +1 -0
  110. package/dist/esm/lib/request_call_function.js +47 -0
  111. package/dist/esm/lib/restore.d.ts +1 -0
  112. package/dist/esm/lib/restore.js +13 -0
  113. package/dist/esm/lib/start-cluster.d.ts +2 -0
  114. package/dist/esm/lib/start-cluster.js +18 -0
  115. package/dist/esm/lib/supertest.d.ts +11 -0
  116. package/dist/esm/lib/supertest.js +40 -0
  117. package/dist/esm/lib/tmp/empty.d.ts +1 -0
  118. package/dist/esm/lib/tmp/empty.js +2 -0
  119. package/dist/esm/lib/types.d.ts +60 -0
  120. package/dist/esm/lib/types.js +2 -0
  121. package/dist/esm/lib/utils.d.ts +9 -0
  122. package/dist/esm/lib/utils.js +69 -0
  123. package/dist/esm/package.json +3 -0
  124. package/dist/esm/register.d.ts +8 -0
  125. package/dist/esm/register.js +75 -0
  126. package/dist/package.json +4 -0
  127. package/package.json +131 -0
  128. package/src/app/extend/agent.ts +56 -0
  129. package/src/app/extend/application.ts +512 -0
  130. package/src/app/middleware/cluster_app_mock.ts +101 -0
  131. package/src/app.ts +18 -0
  132. package/src/bootstrap.ts +25 -0
  133. package/src/index.d.ts +193 -0
  134. package/src/index.test-d.ts +47 -0
  135. package/src/index.ts +110 -0
  136. package/src/lib/agent_handler.ts +28 -0
  137. package/src/lib/app.ts +313 -0
  138. package/src/lib/app_handler.ts +69 -0
  139. package/src/lib/cluster.ts +363 -0
  140. package/src/lib/context.ts +14 -0
  141. package/src/lib/format_options.ts +103 -0
  142. package/src/lib/inject_context.ts +134 -0
  143. package/src/lib/mock_agent.ts +57 -0
  144. package/src/lib/mock_custom_loader.ts +36 -0
  145. package/src/lib/mock_http_server.ts +19 -0
  146. package/src/lib/mock_httpclient.ts +181 -0
  147. package/src/lib/parallel/agent.ts +128 -0
  148. package/src/lib/parallel/app.ts +123 -0
  149. package/src/lib/parallel/util.ts +66 -0
  150. package/src/lib/prerequire.ts +25 -0
  151. package/src/lib/request_call_function.ts +49 -0
  152. package/src/lib/restore.ts +14 -0
  153. package/src/lib/start-cluster.ts +23 -0
  154. package/src/lib/supertest.ts +45 -0
  155. package/src/lib/tmp/.gitkeep +0 -0
  156. package/src/lib/tmp/empty.ts +0 -0
  157. package/src/lib/types.ts +72 -0
  158. package/src/lib/utils.ts +82 -0
  159. package/src/register.ts +80 -0
@@ -0,0 +1,512 @@
1
+ # @eggjs/mock
2
+
3
+ [![NPM version][npm-image]][npm-url]
4
+ [![Node.js CI](https://github.com/eggjs/mock/actions/workflows/nodejs.yml/badge.svg)](https://github.com/eggjs/mock/actions/workflows/nodejs.yml)
5
+ [![Test coverage][codecov-image]][codecov-url]
6
+ [![npm download][download-image]][download-url]
7
+
8
+ [npm-image]: https://img.shields.io/npm/v/@eggjs/mock.svg?style=flat-square
9
+ [npm-url]: https://npmjs.org/package/@eggjs/mock
10
+ [codecov-image]: https://codecov.io/github/eggjs/mock/coverage.svg?branch=master
11
+ [codecov-url]: https://codecov.io/github/eggjs/mock?branch=master
12
+ [download-image]: https://img.shields.io/npm/dm/@eggjs/mock.svg?style=flat-square
13
+ [download-url]: https://npmjs.org/package/@eggjs/mock
14
+
15
+ 一个数据模拟的库,更方便地测试 Egg 应用、插件及自定义 Egg 框架。
16
+ `@eggjs/mock` 拓展自 [node_modules/mm](https://github.com/node-modules/mm),你可以使用所有 `mm` 包含的 API。
17
+
18
+ ## Install
19
+
20
+ ```bash
21
+ npm i egg-mock --save-dev
22
+ ```
23
+
24
+ ## Usage
25
+
26
+ ### 创建测试用例
27
+
28
+ 通过 `mm.app` 启动应用,可以使用 App 的 API 模拟数据
29
+
30
+ ```js
31
+ // test/index.test.js
32
+ const path = require('path');
33
+ const mm = require('@eggjs/mock');
34
+
35
+ describe('some test', () => {
36
+ let app;
37
+ before(() => {
38
+ app = mm.app({
39
+ baseDir: 'apps/foo'
40
+ });
41
+ return app.ready();
42
+ })
43
+ after(() => app.close());
44
+
45
+ it('should request /', () => {
46
+ return app.httpRequest()
47
+ .get('/')
48
+ .expect(200);
49
+ });
50
+ });
51
+ ```
52
+
53
+ 使用 `mm.app` 启动后可以通过 `app.agent` 访问到 agent 对象。
54
+
55
+ 使用 `mm.cluster` 启动多进程测试,API 与 `mm.app` 一致。
56
+
57
+ ### 应用开发者
58
+
59
+ 应用开发者不需要传入 baseDir,其为当前路径
60
+
61
+ ```js
62
+ before(() => {
63
+ app = mm.app({
64
+ framework: path.join(__dirname, '../node_modules/egg'),
65
+ });
66
+ return app.ready();
67
+ });
68
+ ```
69
+
70
+ ### 框架开发者
71
+
72
+ 框架开发者需要指定 `framework`,会将当前路径指定为框架入口
73
+
74
+ ```js
75
+ before(() => {
76
+ app = mm.app({
77
+ baseDir: 'apps/demo',
78
+ framework: true,
79
+ });
80
+ return app.ready();
81
+ });
82
+ ```
83
+
84
+ ### 插件开发者
85
+
86
+ 在插件目录下执行测试用例时,只要 `package.json` 中有 `eggPlugin.name` 字段,就会自动把当前目录加到插件列表中。
87
+
88
+ ```js
89
+ before(() => {
90
+ app = mm.app({
91
+ baseDir: 'apps/demo',
92
+ });
93
+ return app.ready();
94
+ });
95
+ ```
96
+
97
+ 也可以通过 `framework` 指定其他框架,比如希望在 aliyun-egg 和 framework-b 同时测试此插件。
98
+
99
+ ```js
100
+ describe('aliyun-egg', () => {
101
+ let app;
102
+ before(() => {
103
+ app = mm.app({
104
+ baseDir: 'apps/demo',
105
+ framework: path.join(__dirname, 'node_modules/aliyun-egg'),
106
+ });
107
+ return app.ready();
108
+ });
109
+ });
110
+
111
+ describe('framework-b', () => {
112
+ let app;
113
+ before(() => {
114
+ app = mm.app({
115
+ baseDir: 'apps/demo',
116
+ framework: path.join(__dirname, 'node_modules/framework-b'),
117
+ });
118
+ return app.ready();
119
+ });
120
+ });
121
+ ```
122
+
123
+ 如果当前目录确实是一个 egg 插件,但是又不想当它是一个插件来测试,可以通过 `options.plugin` 选项来关闭:
124
+
125
+ ```js
126
+ before(() => {
127
+ app = mm.app({
128
+ baseDir: 'apps/demo',
129
+ plugin: false,
130
+ });
131
+ return app.ready();
132
+ });
133
+ ```
134
+
135
+ ## API
136
+
137
+ ### mm.app(options)
138
+
139
+ 创建一个 mock 的应用。
140
+
141
+ ### mm.cluster(options)
142
+
143
+ 创建一个多进程应用,因为是多进程应用,无法获取 worker 的属性,只能通过 supertest 请求。
144
+
145
+ ```js
146
+ const mm = require('@eggjs/mock');
147
+
148
+ describe('test/app.js', () => {
149
+ let app, config;
150
+ before(() => {
151
+ app = mm.cluster();
152
+ return app.ready();
153
+ });
154
+ after(() => app.close());
155
+
156
+ it('some test', () => {
157
+ return app.httpRequest()
158
+ .get('/config')
159
+ .expect(200)
160
+ });
161
+ });
162
+ ```
163
+
164
+ 默认会启用覆盖率,因为覆盖率比较慢,可以设置 coverage 关闭
165
+
166
+ ```js
167
+ mm.cluster({
168
+ coverage: false,
169
+ });
170
+ ```
171
+
172
+ ### mm.env(env)
173
+
174
+ 设置环境变量,主要用于启动阶段,运行阶段可以使用 app.mockEnv。
175
+
176
+ ```js
177
+ // 模拟生成环境
178
+ mm.env('prod');
179
+ mm.app({
180
+ cache: false,
181
+ });
182
+ ```
183
+
184
+ 具体值见 <https://github.com/eggjs/egg-core/blob/master/lib/loader/egg_loader.js#L82>
185
+
186
+ ### mm.consoleLevel(level)
187
+
188
+ mock 终端日志打印级别
189
+
190
+ ```js
191
+ // 不输出到终端
192
+ mm.consoleLevel('NONE');
193
+ ```
194
+
195
+ 可选 level 为 `DEBUG`, `INFO`, `WARN`, `ERROR`, `NONE`
196
+
197
+ ### mm.home(homePath)
198
+
199
+ 模拟操作系统用户目录
200
+
201
+ ### mm.restore
202
+
203
+ 还原所有 mock 数据,一般需要结合 `afterEach(mm.restore)` 使用
204
+
205
+ ### options
206
+
207
+ mm.app 和 mm.cluster 的配置参数
208
+
209
+ #### baseDir {String}
210
+
211
+ 当前应用的目录,如果是应用本身的测试可以不填默认为 $CWD。
212
+
213
+ 指定完整路径
214
+
215
+ ```js
216
+ mm.app({
217
+ baseDir: path.join(__dirname, 'fixtures/apps/demo'),
218
+ });
219
+ ```
220
+
221
+ 也支持缩写,找 test/fixtures 目录下的
222
+
223
+ ```js
224
+ mm.app({
225
+ baseDir: 'apps/demo',
226
+ });
227
+ ```
228
+
229
+ #### framework {String/Boolean}
230
+
231
+ 指定框架路径
232
+
233
+ ```js
234
+ mm.app({
235
+ baseDir: 'apps/demo',
236
+ framework: path.join(__dirname, 'fixtures/egg'),
237
+ });
238
+ ```
239
+
240
+ 对于框架的测试用例,可以指定 true,会自动加载当前路径。
241
+
242
+ #### plugin
243
+
244
+ 指定插件的路径,只用于插件测试。设置为 true 会将当前路径设置到插件列表。
245
+
246
+ ```js
247
+ mm.app({
248
+ baseDir: 'apps/demo',
249
+ plugin: true,
250
+ })
251
+ ```
252
+
253
+ #### plugins {Object}
254
+
255
+ 传入插件列表,可以自定义多个插件
256
+
257
+ #### cache {Boolean}
258
+
259
+ 是否需要缓存,默认开启。
260
+
261
+ 是通过 baseDir 缓存的,如果不需要可以关闭,但速度会慢。
262
+
263
+ #### clean {Boolean}
264
+
265
+ 是否需要清理 log 目录,默认开启。
266
+
267
+ 如果是通过 ava 等并行测试框架进行测试,需要手动在执行测试前进行统一的日志清理,不能通过 mm 来处理,设置 `clean` 为 `false`。
268
+
269
+ ### app.mockLog([logger]) and app.expectLog(str[, logger]), app.notExpectLog(str[, logger])
270
+
271
+ 断言指定的字符串记录在指定的日志中。
272
+ 建议 `app.mockLog()` 和 `app.expectLog()` 或者 `app.notExpectLog()` 配对使用。
273
+ 单独使用 `app.expectLog()` 或者 `app.notExpectLog()` 需要依赖日志的写入速度,在服务器磁盘高 IO 的时候,会出现不稳定的结果。
274
+
275
+ ```js
276
+ it('should work', async () => {
277
+ // 将日志记录到内存,用于下面的 expectLog
278
+ app.mockLog();
279
+ await app.httpRequest()
280
+ .get('/')
281
+ .expect('hello world')
282
+ .expect(200);
283
+
284
+ app.expectLog('foo in logger');
285
+ app.expectLog('foo in coreLogger', 'coreLogger');
286
+ app.expectLog('foo in myCustomLogger', 'myCustomLogger');
287
+
288
+ app.notExpectLog('bar in logger');
289
+ app.notExpectLog('bar in coreLogger', 'coreLogger');
290
+ app.notExpectLog('bar in myCustomLogger', 'myCustomLogger');
291
+ });
292
+ ```
293
+
294
+ ### app.httpRequest()
295
+
296
+ 请求当前应用 http 服务的辅助工具。
297
+
298
+ ```js
299
+ it('should work', () => {
300
+ return app.httpRequest()
301
+ .get('/')
302
+ .expect('hello world')
303
+ .expect(200);
304
+ });
305
+ ```
306
+
307
+ 更多信息请查看 [supertest](https://github.com/visionmedia/supertest) 的 API 说明。
308
+
309
+ #### .unexpectHeader(name)
310
+
311
+ 断言当前请求响应不包含指定 header
312
+
313
+ ```js
314
+ it('should work', () => {
315
+ return app.httpRequest()
316
+ .get('/')
317
+ .unexpectHeader('set-cookie')
318
+ .expect(200);
319
+ });
320
+ ```
321
+
322
+ #### .expectHeader(name)
323
+
324
+ 断言当前请求响应包含指定 header
325
+
326
+ ```js
327
+ it('should work', () => {
328
+ return app.httpRequest()
329
+ .get('/')
330
+ .expectHeader('set-cookie')
331
+ .expect(200);
332
+ });
333
+ ```
334
+
335
+ ### app.mockContext(options)
336
+
337
+ 模拟上下文数据
338
+
339
+ ```js
340
+ const ctx = app.mockContext({
341
+ user: {
342
+ name: 'Jason'
343
+ }
344
+ });
345
+ console.log(ctx.user.name); // Jason
346
+ ```
347
+
348
+ ### app.mockContextScope(fn, options)
349
+
350
+ 安全的模拟上下文数据,同一用例用多次调用 mockContext 可能会造成 AsyncLocalStorage 污染
351
+
352
+ ```js
353
+ await app.mockContextScope(async ctx => {
354
+ console.log(ctx.user.name); // Jason
355
+ }, {
356
+ user: {
357
+ name: 'Jason'
358
+ }
359
+ });
360
+ ```
361
+
362
+ ### app.mockCookies(data)
363
+
364
+ ```js
365
+ app.mockCookies({
366
+ foo: 'bar'
367
+ });
368
+ const ctx = app.mockContext();
369
+ console.log(ctx.getCookie('foo'));
370
+ ```
371
+
372
+ ### app.mockHeaders(data)
373
+
374
+ 模拟请求头
375
+
376
+ ### app.mockSession(data)
377
+
378
+ ```js
379
+ app.mockSession({
380
+ foo: 'bar'
381
+ });
382
+ const ctx = app.mockContext();
383
+ console.log(ctx.session.foo);
384
+ ```
385
+
386
+ ### app.mockService(service, methodName, fn)
387
+
388
+ ```js
389
+ it('should mock user name', async function() {
390
+ app.mockService('user', 'getName', async function(ctx, methodName, args) {
391
+ return 'popomore';
392
+ });
393
+ const ctx = app.mockContext();
394
+ await ctx.service.user.getName();
395
+ });
396
+ ```
397
+
398
+ ### app.mockServiceError(service, methodName, error)
399
+
400
+ 可以模拟一个错误
401
+
402
+ ```js
403
+ app.mockServiceError('user', 'home', new Error('mock error'));
404
+ ```
405
+
406
+ ### app.mockCsrf()
407
+
408
+ 模拟 csrf,不用传递 token
409
+
410
+ ```js
411
+ app.mockCsrf();
412
+
413
+ return app.httpRequest()
414
+ .post('/login')
415
+ .expect(302);
416
+ ```
417
+
418
+ ### app.mockHttpclient(url, method, data)
419
+
420
+ 模拟 httpclient 的请求,例如 `ctx.curl`
421
+
422
+ ```js
423
+ app.get('/', async ctx => {
424
+ const ret = await ctx.curl('https://eggjs.org');
425
+ this.body = ret.data.toString();
426
+ });
427
+
428
+ app.mockHttpclient('https://eggjs.org', {
429
+ // 模拟的参数,可以是 buffer / string / json / function
430
+ // 都会转换成 buffer
431
+ // 按照请求时的 options.dataType 来做对应的转换
432
+ data: 'mock egg',
433
+ });
434
+
435
+ return app.httpRequest()
436
+ .post('/')
437
+ .expect('mock egg');
438
+ ```
439
+
440
+ ## Bootstrap
441
+
442
+ 我们提供了一个 bootstrap 来减少单测中的重复代码:
443
+
444
+ ```js
445
+ const { app, mock, assert } = require('@eggjs/mock/bootstrap');
446
+
447
+ describe('test app', () => {
448
+ it('should request success', () => {
449
+ // mock data will be restored each case
450
+ mock.data(app, 'method', { foo: 'bar' });
451
+ return app.httpRequest()
452
+ .get('/foo')
453
+ .expect(res => {
454
+ assert(!res.headers.foo);
455
+ })
456
+ .expect(/bar/);
457
+ });
458
+ });
459
+
460
+ describe('test ctx', () => {
461
+ it('can use ctx', async function() {
462
+ const res = await this.ctx.service.foo();
463
+ assert(res === 'foo');
464
+ });
465
+ });
466
+ ```
467
+
468
+ 我们将会在每个 case 中自定注入 ctx, 可以通过 `app.currentContext` 来获取当前的 ctx。
469
+ 并且第一次使用 `app.mockContext` 会自动复用当前 case 的上下文。
470
+
471
+ ```js
472
+ const { app, mock, assert } = require('@eggjs/mock/bootstrap');
473
+
474
+ describe('test ctx', () => {
475
+ it('should can use ctx', () => {
476
+ const ctx = app.currentContext;
477
+ assert(ctx);
478
+ });
479
+
480
+ it('should reuse ctx', () => {
481
+ const ctx = app.currentContext;
482
+ // 第一次调用会复用上下文
483
+ const mockCtx = app.mockContext();
484
+ assert(ctx === mockCtx);
485
+ // 后续调用会新建上下文
486
+ // 极不建议多次调用 app.mockContext
487
+ // 这会导致上下文污染
488
+ // 建议使用 app.mockContextScope
489
+ const mockCtx2 = app.mockContext();
490
+ assert(ctx !== mockCtx);
491
+ });
492
+ });
493
+ ```
494
+
495
+ ### env for custom bootstrap
496
+
497
+ EGG_BASE_DIR: the base dir of egg app
498
+ EGG_FRAMEWORK: the framework of egg app
499
+
500
+ ## Questions & Suggestions
501
+
502
+ Please open an issue [here](https://github.com/eggjs/egg/issues).
503
+
504
+ ## License
505
+
506
+ [MIT](LICENSE)
507
+
508
+ ## Contributors
509
+
510
+ [![Contributors](https://contrib.rocks/image?repo=eggjs/mock)](https://github.com/eggjs/mock/graphs/contributors)
511
+
512
+ Made with [contributors-img](https://contrib.rocks).
@@ -0,0 +1,33 @@
1
+ import { mock, restore } from 'mm';
2
+ import { EggCore } from '@eggjs/core';
3
+ import { MockResultFunction, MockResultOptions, MockHttpClientMethod } from '../../lib/mock_httpclient.js';
4
+ export default abstract class AgentUnittest extends EggCore {
5
+ _mockHttpClient: MockHttpClientMethod;
6
+ /**
7
+ * mock httpclient
8
+ * @alias mockHttpClient
9
+ * @function App#mockHttpclient
10
+ */
11
+ mockHttpclient(mockUrl: string | RegExp, mockMethod: string | string[] | MockResultOptions | MockResultFunction, mockResult?: MockResultOptions | MockResultFunction | string): void;
12
+ /**
13
+ * mock httpclient
14
+ * @function App#mockHttpClient
15
+ */
16
+ mockHttpClient(mockUrl: string | RegExp, mockMethod: string | string[] | MockResultOptions | MockResultFunction, mockResult?: MockResultOptions | MockResultFunction | string): void;
17
+ /**
18
+ * get mock httpclient agent
19
+ * @function Agent#mockHttpclientAgent
20
+ */
21
+ mockAgent(): import("_urllib@4.6.11@urllib").MockAgent<import("_urllib@4.6.11@urllib").MockAgent.Options>;
22
+ mockAgentRestore(): Promise<void>;
23
+ /**
24
+ * @see mm#restore
25
+ * @function Agent#mockRestore
26
+ */
27
+ mockRestore: typeof restore;
28
+ /**
29
+ * @see mm
30
+ * @function Agent#mm
31
+ */
32
+ mm: typeof mock;
33
+ }
@@ -0,0 +1,49 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ const mm_1 = require("mm");
4
+ const core_1 = require("@eggjs/core");
5
+ const mock_httpclient_js_1 = require("../../lib/mock_httpclient.js");
6
+ const mock_agent_js_1 = require("../../lib/mock_agent.js");
7
+ class AgentUnittest extends core_1.EggCore {
8
+ _mockHttpClient;
9
+ /**
10
+ * mock httpclient
11
+ * @alias mockHttpClient
12
+ * @function App#mockHttpclient
13
+ */
14
+ mockHttpclient(mockUrl, mockMethod, mockResult) {
15
+ return this.mockHttpClient(mockUrl, mockMethod, mockResult);
16
+ }
17
+ /**
18
+ * mock httpclient
19
+ * @function App#mockHttpClient
20
+ */
21
+ mockHttpClient(mockUrl, mockMethod, mockResult) {
22
+ if (!this._mockHttpClient) {
23
+ this._mockHttpClient = (0, mock_httpclient_js_1.createMockHttpClient)(this);
24
+ }
25
+ return this._mockHttpClient(mockUrl, mockMethod, mockResult);
26
+ }
27
+ /**
28
+ * get mock httpclient agent
29
+ * @function Agent#mockHttpclientAgent
30
+ */
31
+ mockAgent() {
32
+ return (0, mock_agent_js_1.getMockAgent)(this);
33
+ }
34
+ async mockAgentRestore() {
35
+ await (0, mock_agent_js_1.restoreMockAgent)();
36
+ }
37
+ /**
38
+ * @see mm#restore
39
+ * @function Agent#mockRestore
40
+ */
41
+ mockRestore = mm_1.restore;
42
+ /**
43
+ * @see mm
44
+ * @function Agent#mm
45
+ */
46
+ mm = mm_1.mock;
47
+ }
48
+ exports.default = AgentUnittest;
49
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiYWdlbnQuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi9zcmMvYXBwL2V4dGVuZC9hZ2VudC50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiOztBQUFBLDJCQUFtQztBQUNuQyxzQ0FBc0M7QUFDdEMscUVBSXNDO0FBQ3RDLDJEQUF5RTtBQUV6RSxNQUE4QixhQUFjLFNBQVEsY0FBTztJQUN6RCxlQUFlLENBQXVCO0lBRXRDOzs7O09BSUc7SUFDSCxjQUFjLENBQUMsT0FBd0IsRUFBRSxVQUFzRSxFQUFFLFVBQTREO1FBQzNLLE9BQU8sSUFBSSxDQUFDLGNBQWMsQ0FBQyxPQUFPLEVBQUUsVUFBVSxFQUFFLFVBQVUsQ0FBQyxDQUFDO0lBQzlELENBQUM7SUFFRDs7O09BR0c7SUFDSCxjQUFjLENBQUMsT0FBd0IsRUFBRSxVQUFzRSxFQUFFLFVBQTREO1FBQzNLLElBQUksQ0FBQyxJQUFJLENBQUMsZUFBZSxFQUFFLENBQUM7WUFDMUIsSUFBSSxDQUFDLGVBQWUsR0FBRyxJQUFBLHlDQUFvQixFQUFDLElBQUksQ0FBQyxDQUFDO1FBQ3BELENBQUM7UUFDRCxPQUFPLElBQUksQ0FBQyxlQUFlLENBQUMsT0FBTyxFQUFFLFVBQVUsRUFBRSxVQUFVLENBQUMsQ0FBQztJQUMvRCxDQUFDO0lBRUQ7OztPQUdHO0lBQ0gsU0FBUztRQUNQLE9BQU8sSUFBQSw0QkFBWSxFQUFDLElBQVcsQ0FBQyxDQUFDO0lBQ25DLENBQUM7SUFFRCxLQUFLLENBQUMsZ0JBQWdCO1FBQ3BCLE1BQU0sSUFBQSxnQ0FBZ0IsR0FBRSxDQUFDO0lBQzNCLENBQUM7SUFFRDs7O09BR0c7SUFDSCxXQUFXLEdBQUcsWUFBTyxDQUFDO0lBRXRCOzs7T0FHRztJQUNILEVBQUUsR0FBRyxTQUFJLENBQUM7Q0FDWDtBQTlDRCxnQ0E4Q0MifQ==