vite-plugin-mock-dev-server 1.3.0 → 1.3.2
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.
- package/README.md +136 -2
- package/README.zh-CN.md +102 -1
- package/dist/index.cjs +21 -18
- package/dist/index.d.cts +102 -4
- package/dist/index.d.ts +102 -4
- package/dist/index.js +19 -16
- package/package.json +12 -12
package/README.md
CHANGED
|
@@ -142,7 +142,7 @@ export default defineConfig({
|
|
|
142
142
|
|
|
143
143
|
- `options.wsPrefix`
|
|
144
144
|
|
|
145
|
-
|
|
145
|
+
**Type:** `string | string[]`
|
|
146
146
|
|
|
147
147
|
Configure the matching rules for the WebSocket service. Any request path starting with the value of `wsPrefix` and using the `ws/wss` protocol will be proxied to the corresponding target.
|
|
148
148
|
|
|
@@ -187,7 +187,7 @@ export default defineConfig({
|
|
|
187
187
|
|
|
188
188
|
- `options.log`
|
|
189
189
|
|
|
190
|
-
**Type:** `
|
|
190
|
+
**Type:** `boolean | 'info' | 'warn' | 'error' | 'silent'`
|
|
191
191
|
|
|
192
192
|
Enable log and configure log level.
|
|
193
193
|
|
|
@@ -235,6 +235,12 @@ export default defineConfig({
|
|
|
235
235
|
}
|
|
236
236
|
```
|
|
237
237
|
|
|
238
|
+
- `options.priority`
|
|
239
|
+
|
|
240
|
+
Custom path matching rule priority。[read more](#Custom-Path-Matching-Priority)
|
|
241
|
+
|
|
242
|
+
**Default:** `undefined`
|
|
243
|
+
|
|
238
244
|
### defineMock(config)
|
|
239
245
|
|
|
240
246
|
Mock Type Helper
|
|
@@ -469,6 +475,103 @@ type Response = http.ServerResponse<http.IncomingMessage> & {
|
|
|
469
475
|
> the 'response' method is not supported,
|
|
470
476
|
> as is the function form that uses other fields.
|
|
471
477
|
|
|
478
|
+
## Share Mock Data
|
|
479
|
+
|
|
480
|
+
Due to each `mock` file being compiled as a separate entry point, the local files they depend on are also compiled within. Additionally, each mock file has an independent scope. This means that even if multiple mock files collectively depend on a `data.ts` file, they cannot share data. If one mock file modifies the data in `data.ts`, other mock files will not receive the updated data.
|
|
481
|
+
|
|
482
|
+
To address this, the plugin offers a `defineMockData` function, which allows using `data.ts` as a shared data source within mock files.
|
|
483
|
+
|
|
484
|
+
```ts
|
|
485
|
+
type defineMockData<T> = (
|
|
486
|
+
key: string, // key
|
|
487
|
+
initialData: T, // initial data
|
|
488
|
+
) => [getter, setter] & { value: T }
|
|
489
|
+
```
|
|
490
|
+
|
|
491
|
+
#### Exp:
|
|
492
|
+
`data.ts`
|
|
493
|
+
```ts
|
|
494
|
+
import { defineMockData } from 'vite-plugin-mock-dev-server'
|
|
495
|
+
|
|
496
|
+
export default defineMockData('posts', [
|
|
497
|
+
{ id: '1', title: 'title1', content: 'content1' },
|
|
498
|
+
{ id: '2', title: 'title2', content: 'content2' },
|
|
499
|
+
])
|
|
500
|
+
```
|
|
501
|
+
`*.mock.ts`
|
|
502
|
+
```ts
|
|
503
|
+
import { defineMock } from 'vite-plugin-mock-dev-server'
|
|
504
|
+
import posts from './data'
|
|
505
|
+
|
|
506
|
+
export default defineMock([
|
|
507
|
+
{
|
|
508
|
+
url: '/api/posts',
|
|
509
|
+
body: () => posts.value
|
|
510
|
+
},
|
|
511
|
+
{
|
|
512
|
+
url: '/api/posts/delete/:id',
|
|
513
|
+
body: (params) => {
|
|
514
|
+
const id = params.id
|
|
515
|
+
posts.value = posts.value.filter((post) => post.id !== id)
|
|
516
|
+
return { success: true }
|
|
517
|
+
}
|
|
518
|
+
}
|
|
519
|
+
])
|
|
520
|
+
```
|
|
521
|
+
|
|
522
|
+
> **Tips:**
|
|
523
|
+
>
|
|
524
|
+
> The `defineMockData` function relies solely on the shared data support provided by `memory`.
|
|
525
|
+
> If persistent mock data is required, it is recommended to use a `nosql` database like `lowdb` or `level`.
|
|
526
|
+
|
|
527
|
+
## Custom-Path-Matching-Priority
|
|
528
|
+
|
|
529
|
+
> Custom rules only affect links with dynamic parameters, such as: `/api/user/:id`
|
|
530
|
+
|
|
531
|
+
The priority of the path matching rules built into the plugin can already meet most needs, but if you need more flexible customization of the matching rule priority, you can use the `priority` parameter.
|
|
532
|
+
|
|
533
|
+
Exp:
|
|
534
|
+
```ts
|
|
535
|
+
import { defineConfig } from 'vite'
|
|
536
|
+
import mockPlugin from 'vite-plugin-mock-dev-server'
|
|
537
|
+
|
|
538
|
+
export default defineConfig({
|
|
539
|
+
plugins: [
|
|
540
|
+
mockPlugin({
|
|
541
|
+
priority: {
|
|
542
|
+
// The priority of matching rules is global.
|
|
543
|
+
// The rules declared in this option will take priority over the default rules.
|
|
544
|
+
// The higher the position of the rule in the array, the higher the priority.
|
|
545
|
+
global: ['/api/:a/b/c', '/api/a/:b/c', '/api/a/b/:c'],
|
|
546
|
+
// For some special cases where the priority of certain rules needs to be adjusted,
|
|
547
|
+
// this option can be used. For example, when a request matches both Rule A and Rule B,
|
|
548
|
+
// and Rule A has a higher priority than Rule B, but it is desired for Rule B to take effect.
|
|
549
|
+
special: {
|
|
550
|
+
// When both A and B or C match, and B or C is at the top of the sort order,
|
|
551
|
+
// insert A into the top position.
|
|
552
|
+
// The `when` option is used to further constrain the priority adjustment to
|
|
553
|
+
// be effective only for certain requests.
|
|
554
|
+
'/api/:a/:b/c': {
|
|
555
|
+
rules: ['/api/a/:b/:c', '/api/a/b/:c'],
|
|
556
|
+
when: ['/api/a/b/c']
|
|
557
|
+
},
|
|
558
|
+
// If no `when` is specified, it means that all requests matching the rules need to have their priorities adjusted. It can be abbreviated as `[key]: [...rules]`
|
|
559
|
+
'/api/:a/b': ['/api/a/:b'],
|
|
560
|
+
}
|
|
561
|
+
}
|
|
562
|
+
})
|
|
563
|
+
]
|
|
564
|
+
})
|
|
565
|
+
```
|
|
566
|
+
|
|
567
|
+
> **Tip:**
|
|
568
|
+
>
|
|
569
|
+
> `priority` although it can adjust the priority,
|
|
570
|
+
> most of the time you do not need to do so. For some special requests,
|
|
571
|
+
> you can use static rules instead of `priority`,
|
|
572
|
+
> as static rules always have the highest priority.
|
|
573
|
+
|
|
574
|
+
|
|
472
575
|
## Example
|
|
473
576
|
|
|
474
577
|
`mock/**/*.mock.{ts,js,mjs,cjs,json,json5}`
|
|
@@ -803,6 +906,37 @@ You can access related `mock` interfaces through `localhost:8080/`.
|
|
|
803
906
|
|
|
804
907
|
[awesome-vite](https://github.com/vitejs/awesome-vite#helpers)
|
|
805
908
|
|
|
909
|
+
## Contributors
|
|
910
|
+
|
|
911
|
+
<!-- ALL-CONTRIBUTORS-BADGE:START - Do not remove or modify this section -->
|
|
912
|
+
[](#contributors-)
|
|
913
|
+
<!-- ALL-CONTRIBUTORS-BADGE:END -->
|
|
914
|
+
|
|
915
|
+
<!-- ALL-CONTRIBUTORS-LIST:START - Do not remove or modify this section -->
|
|
916
|
+
<!-- prettier-ignore-start -->
|
|
917
|
+
<!-- markdownlint-disable -->
|
|
918
|
+
<table>
|
|
919
|
+
<tbody>
|
|
920
|
+
<tr>
|
|
921
|
+
<td align="center" valign="top" width="14.28%"><a href="https://pengzhanbo.cn"><img src="https://avatars.githubusercontent.com/u/16745751?v=4?s=100" width="100px;" alt="pengzhanbo"/><br /><sub><b>pengzhanbo</b></sub></a><br /><a href="https://github.com/pengzhanbo/vite-plugin-mock-dev-server/commits?author=pengzhanbo" title="Documentation">📖</a> <a href="#ideas-pengzhanbo" title="Ideas, Planning, & Feedback">🤔</a> <a href="#example-pengzhanbo" title="Examples">💡</a> <a href="https://github.com/pengzhanbo/vite-plugin-mock-dev-server/commits?author=pengzhanbo" title="Code">💻</a></td>
|
|
922
|
+
<td align="center" valign="top" width="14.28%"><a href="https://github.com/jiadesen"><img src="https://avatars.githubusercontent.com/u/22772994?v=4?s=100" width="100px;" alt="jiadesen"/><br /><sub><b>jiadesen</b></sub></a><br /><a href="#ideas-jiadesen" title="Ideas, Planning, & Feedback">🤔</a> <a href="https://github.com/pengzhanbo/vite-plugin-mock-dev-server/issues?q=author%3Ajiadesen" title="Bug reports">🐛</a></td>
|
|
923
|
+
<td align="center" valign="top" width="14.28%"><a href="https://github.com/yogibaba"><img src="https://avatars.githubusercontent.com/u/152670?v=4?s=100" width="100px;" alt="yogibaba"/><br /><sub><b>yogibaba</b></sub></a><br /><a href="https://github.com/pengzhanbo/vite-plugin-mock-dev-server/commits?author=yogibaba" title="Code">💻</a></td>
|
|
924
|
+
</tr>
|
|
925
|
+
</tbody>
|
|
926
|
+
</table>
|
|
927
|
+
|
|
928
|
+
<!-- markdownlint-restore -->
|
|
929
|
+
<!-- prettier-ignore-end -->
|
|
930
|
+
|
|
931
|
+
<!-- ALL-CONTRIBUTORS-LIST:END -->
|
|
932
|
+
<!-- prettier-ignore-start -->
|
|
933
|
+
<!-- markdownlint-disable -->
|
|
934
|
+
|
|
935
|
+
<!-- markdownlint-restore -->
|
|
936
|
+
<!-- prettier-ignore-end -->
|
|
937
|
+
|
|
938
|
+
<!-- ALL-CONTRIBUTORS-LIST:END -->
|
|
939
|
+
|
|
806
940
|
## LICENSE
|
|
807
941
|
|
|
808
942
|
[MIT](/LICENSE)
|
package/README.zh-CN.md
CHANGED
|
@@ -183,7 +183,7 @@ export default defineConfig({
|
|
|
183
183
|
|
|
184
184
|
- `options.log`
|
|
185
185
|
|
|
186
|
-
**Type:** `
|
|
186
|
+
**Type:** `boolean | 'info' | 'warn' | 'error' | 'silent'`
|
|
187
187
|
|
|
188
188
|
启动日志,以及配置日志打印级别
|
|
189
189
|
|
|
@@ -230,6 +230,12 @@ export default defineConfig({
|
|
|
230
230
|
}
|
|
231
231
|
```
|
|
232
232
|
|
|
233
|
+
- `options.priority`
|
|
234
|
+
|
|
235
|
+
自定义 路径匹配规则优先级。[查看更多](#自定义匹配优先级)
|
|
236
|
+
|
|
237
|
+
**默认值:** `undefined`
|
|
238
|
+
|
|
233
239
|
### defineMock(config)
|
|
234
240
|
|
|
235
241
|
mock 配置帮助函数,提供类型检查帮助
|
|
@@ -457,6 +463,101 @@ type Response = http.ServerResponse<http.IncomingMessage> & {
|
|
|
457
463
|
>
|
|
458
464
|
> 如果使用 json/json5 编写 mock文件,则不支持使用 `response` 方法,以及不支持使用其他字段的函数形式。
|
|
459
465
|
|
|
466
|
+
## 共享 Mock 数据
|
|
467
|
+
|
|
468
|
+
由于每个mock文件都是作为独立的入口进行编译,其依赖的本地文件也编译在内,
|
|
469
|
+
且每个mock文件拥有独立的作用域,这使得即使多个 mock文件共同依赖某一个`data.ts`文件,也无法共享数据。
|
|
470
|
+
某个 `mock` 文件对 `data.ts` 中的数据进行修改,其它`mock`文件不会获取到修改后的数据。
|
|
471
|
+
|
|
472
|
+
为此,插件提供了一个 `defineMockData` 函数,用于在 `mock` 文件中使用 `data.ts` 作为共享数据源。
|
|
473
|
+
|
|
474
|
+
```ts
|
|
475
|
+
type defineMockData<T> = (
|
|
476
|
+
key: string, // 数据唯一标识符
|
|
477
|
+
initialData: T, // 初始化数据
|
|
478
|
+
) => [getter, setter] & { value: T }
|
|
479
|
+
```
|
|
480
|
+
|
|
481
|
+
#### 用法:
|
|
482
|
+
`data.ts`
|
|
483
|
+
```ts
|
|
484
|
+
import { defineMockData } from 'vite-plugin-mock-dev-server'
|
|
485
|
+
|
|
486
|
+
export default defineMockData('posts', [
|
|
487
|
+
{ id: '1', title: 'title1', content: 'content1' },
|
|
488
|
+
{ id: '2', title: 'title2', content: 'content2' },
|
|
489
|
+
])
|
|
490
|
+
```
|
|
491
|
+
`*.mock.ts`
|
|
492
|
+
```ts
|
|
493
|
+
import { defineMock } from 'vite-plugin-mock-dev-server'
|
|
494
|
+
import posts from './data'
|
|
495
|
+
|
|
496
|
+
export default defineMock([
|
|
497
|
+
{
|
|
498
|
+
url: '/api/posts',
|
|
499
|
+
body: () => posts.value
|
|
500
|
+
},
|
|
501
|
+
{
|
|
502
|
+
url: '/api/posts/delete/:id',
|
|
503
|
+
body: (params) => {
|
|
504
|
+
const id = params.id
|
|
505
|
+
posts.value = posts.value.filter((post) => post.id !== id)
|
|
506
|
+
return { success: true }
|
|
507
|
+
}
|
|
508
|
+
}
|
|
509
|
+
])
|
|
510
|
+
```
|
|
511
|
+
|
|
512
|
+
> **注意:**
|
|
513
|
+
>
|
|
514
|
+
> `defineMockData` 仅是基于 `memory` 提供的共享数据支持,
|
|
515
|
+
> 如果需要做 mock 数据持久化,建议使用 `nosql`, 如 `lowdb` 或 `level` 等。
|
|
516
|
+
|
|
517
|
+
|
|
518
|
+
## 自定义匹配优先级
|
|
519
|
+
|
|
520
|
+
> 自定义规则仅影响包含动态参数的链接,如: `/api/user/:id`
|
|
521
|
+
|
|
522
|
+
插件内置的路径匹配规则优先级,已经能够满足大部分需求,但如果你需要更加灵活的自定义匹配规则优先级,
|
|
523
|
+
可以使用 `priority` 参数。
|
|
524
|
+
|
|
525
|
+
示例:
|
|
526
|
+
```ts
|
|
527
|
+
import { defineConfig } from 'vite'
|
|
528
|
+
import mockPlugin from 'vite-plugin-mock-dev-server'
|
|
529
|
+
|
|
530
|
+
export default defineConfig({
|
|
531
|
+
plugins: [
|
|
532
|
+
mockPlugin({
|
|
533
|
+
priority: {
|
|
534
|
+
// 匹配规则优先级, 全局生效。声明在该选项中的规则将优先于默认规则生效。
|
|
535
|
+
// 规则在数组越靠前的位置,优先级越高。
|
|
536
|
+
global: ['/api/:a/b/c', '/api/a/:b/c', '/api/a/b/:c'],
|
|
537
|
+
// 对于一些特殊情况,需要调整部分规则的优先级,可以使用此选项。
|
|
538
|
+
// 比如一个请求同时命中了规则 A 和 B,且 A 比 B 优先级高, 但期望规则 B 生效时。
|
|
539
|
+
special: {
|
|
540
|
+
// 当请求同时命中 [key] 和 rules 中的任意一个时,优先匹配 [key] 。
|
|
541
|
+
// when 用于进一步约束具体是哪些请求需要调整优先级。
|
|
542
|
+
'/api/:a/:b/c': {
|
|
543
|
+
rules: ['/api/a/:b/:c', '/api/a/b/:c'],
|
|
544
|
+
when: ['/api/a/b/c']
|
|
545
|
+
},
|
|
546
|
+
// 如果不需要 when, 则表示命中规则的请求都需要调整优先级。
|
|
547
|
+
// 可以简写为 [key]: [...rules]
|
|
548
|
+
'/api/:a/b': ['/api/a/:b'],
|
|
549
|
+
}
|
|
550
|
+
}
|
|
551
|
+
})
|
|
552
|
+
]
|
|
553
|
+
})
|
|
554
|
+
```
|
|
555
|
+
|
|
556
|
+
> **注意:**
|
|
557
|
+
>
|
|
558
|
+
> `priority` 虽然可以调整优先级,但大多数时候,你都没有必要这么做。
|
|
559
|
+
> 对于一些特殊情况的请求,可以使用 静态规则来替代 `priority`,静态规则总是拥有最高优先级。
|
|
560
|
+
|
|
460
561
|
## Example
|
|
461
562
|
|
|
462
563
|
`mock/**/*.mock.{ts,js,mjs,cjs,json,json5}`
|
package/dist/index.cjs
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
"use strict";var
|
|
1
|
+
"use strict";var kt=Object.create;var se=Object.defineProperty;var ht=Object.getOwnPropertyDescriptor;var yt=Object.getOwnPropertyNames;var vt=Object.getPrototypeOf,Mt=Object.prototype.hasOwnProperty;var bt=(o,t)=>{for(var e in t)se(o,e,{get:t[e],enumerable:!0})},De=(o,t,e,r)=>{if(t&&typeof t=="object"||typeof t=="function")for(let s of yt(t))!Mt.call(o,s)&&s!==e&&se(o,s,{get:()=>t[s],enumerable:!(r=ht(t,s))||r.enumerable});return o};var h=(o,t,e)=>(e=o!=null?kt(vt(o)):{},De(t||!o||!o.__esModule?se(e,"default",{value:o,enumerable:!0}):e,o)),xt=o=>De(se({},"__esModule",{value:!0}),o);var ro={};bt(ro,{baseMiddleware:()=>xe,createDefineMock:()=>Zt,default:()=>oo,defineMock:()=>Yt,defineMockData:()=>to,mockDevServerPlugin:()=>Re,mockWebSocket:()=>Ce,transformMockData:()=>we});module.exports=xt(ro);var wt=()=>typeof document>"u"?new URL("file:"+__filename).href:document.currentScript&&document.currentScript.src||new URL("main.js",document.baseURI).href,O=wt();var ft=require("@pengzhanbo/utils");var Qe=h(require("fs"),1),Z=h(require("fs/promises"),1),B=h(require("path"),1),ee=require("@pengzhanbo/utils"),Ve=h(require("fast-glob"),1),Ke=h(require("is-core-module"),1),ge=require("vite");var Ee="vite-plugin-mock-dev-server",_e="1.3.2";var q=h(require("fs"),1),Ue=require("module"),ue=h(require("path"),1),qe=require("url"),Be=require("esbuild"),Je=h(require("json5"),1);var ie=h(require("fs"),1),ce=h(require("path"),1),Te=require("querystring"),ae=require("url"),Ie=h(require("debug"),1),Ne=require("path-to-regexp"),St=o=>o!==null&&typeof o=="object"&&typeof o.pipe=="function",He=o=>St(o)&&o.readable!==!1&&typeof o._read=="function"&&typeof o._readableState=="object";function Fe(o){return ce.default.dirname((0,ae.fileURLToPath)(o))}var pe=(0,Ie.default)("vite:mock-dev-server");function X(o,t,e){for(let s of t){let n=ce.default.join(o,s);if(ie.default.existsSync(n)&&ie.default.statSync(n).isFile()){let i=e!=null&&e.pathOnly?n:ie.default.readFileSync(n,"utf-8");if(!(e!=null&&e.predicate)||e.predicate(i))return i}}let r=ce.default.dirname(o);if(r!==o&&(!(e!=null&&e.rootDir)||r.startsWith(e==null?void 0:e.rootDir)))return X(r,t,e)}var le=(o={})=>{let t=[],e=[];return Object.keys(o).forEach(r=>{var n,i;let s=o[r];typeof s=="string"||!s.ws&&!((n=s.target)!=null&&n.toString().startsWith("ws:"))&&!((i=s.target)!=null&&i.toString().startsWith("wss:"))?t.push(r):e.push(r)}),{httpProxies:t,wsProxies:e}};function G(o,t){return o[0]==="^"&&new RegExp(o).test(t)||t.startsWith(o)}function Y(o,t){return((0,Ne.match)(o,{decode:decodeURIComponent})(t)||{params:{}}).params||{}}function D(o){let t=new ae.URL(o,"http://example.com"),e=decodeURIComponent(t.pathname),r=(0,Te.parse)(t.search.replace(/^\?/,""));return{pathname:e,query:r}}var Ot={name:"externalize-deps",setup(o){o.onResolve({filter:/.*/},({path:t})=>{if(t[0]!=="."&&!ue.default.isAbsolute(t))return{external:!0}})}},Ct={name:"json5-loader",setup(o){o.onLoad({filter:/\.json5$/},async({path:t})=>{let e=await q.promises.readFile(t,"utf-8");return{contents:`export default ${JSON.stringify(Je.default.parse(e))}`,loader:"js"}})}},Pt={name:"json-loader",setup(o){o.onLoad({filter:/\.json$/},async({path:t})=>({contents:`export default ${await q.promises.readFile(t,"utf-8")}`,loader:"js"}))}},Rt=o=>({name:"alias-plugin",setup(t){t.onResolve({filter:/.*/},async({path:e})=>{let r=o.find(({find:c})=>Wt(c,e));if(!r)return null;let{find:s,replacement:n}=r;return{path:(await t.resolve(e.replace(s,n),{kind:"import-statement",resolveDir:n,namespace:"file"})).path,external:!1}})}});function Wt(o,t){return o instanceof RegExp?o.test(t):t.length<o.length?!1:t===o?!0:t.startsWith(`${o}/`)}async function me(o,t){var n;let{isESM:e=!0,define:r,alias:s}=t;try{let i=await(0,Be.build)({entryPoints:[o],outfile:"out.js",write:!1,target:["node14.18","node16"],platform:"node",bundle:!0,metafile:!0,format:e?"esm":"cjs",define:r,plugins:[Rt(s),Ot,Pt,Ct]});return{code:i.outputFiles[0].text,deps:((n=i.metafile)==null?void 0:n.inputs)||{}}}catch(i){console.error(i)}return{code:"",deps:{}}}var jt=Fe(O),U=(0,Ue.createRequire)(jt);async function Ae(o,t,e,r){if(e){let s=`${o}.timestamp-${Date.now()}`,n=`${s}.mjs`,i=`${(0,qe.pathToFileURL)(s)}.mjs`;await q.promises.writeFile(n,t,"utf8");try{return await import(i)}finally{try{q.default.unlinkSync(n)}catch{}}}else{o=ue.default.resolve(r,o);let s=ue.default.extname(o),n=q.default.realpathSync(o),i=s in U.extensions?s:".js",c=U.extensions[i];U.extensions[i]=(p,m)=>{m===n?p._compile(t,m):c(p,m)},delete U.cache[U.resolve(o)];let a=U(o);return U.extensions[i]=c,a.__esModule?a:{default:a}}}var ye=h(require("picocolors"),1);var Ge=require("@pengzhanbo/utils"),L=h(require("picocolors"),1),ze={silent:0,error:1,warn:2,info:3,debug:4};function de(o,t="info"){o=`[${o}]`;function e(s,n,i){if(i=(0,Ge.isBoolean)(i)?i?t:"error":i,ze[i]>=ze[s]){let a=s==="info"||s==="debug"?"log":s,p=s==="debug"?L.default.magenta(L.default.bold(o)):s==="info"?L.default.cyan(L.default.bold(o)):s==="warn"?L.default.yellow(L.default.bold(o)):L.default.red(L.default.bold(o)),m=`${L.default.dim(new Date().toLocaleTimeString())} ${p} ${n}`;console[a](m)}}return{debug(s,n=t){e("debug",s,n)},info(s,n=t){e("info",s,n)},warn(s,n=t){e("warn",s,n)},error(s,n=t){e("error",s,n)}}}var $t=/import\.meta\.env\.(.+)/;function fe(o){let t=de("vite:mock-dev-server","warn"),e={},r=process.env.NODE_ENV||o.mode;Object.assign(e,{"process.env.NODE_ENV":JSON.stringify(r),"global.process.env.NODE_ENV":JSON.stringify(r),"globalThis.process.env.NODE_ENV":JSON.stringify(r),__vite_process_env_NODE_ENV:JSON.stringify(r)});let s={},n={},i=[];for(let p in o.define){let m=o.define[p];if(typeof m=="string")try{JSON.parse(m),s[p]=m}catch{i.push(p)}else s[p]=JSON.stringify(m);let d=p.match($t);d&&s[p]&&(n[d[1]]=`__vite__define__${s[p]}`)}i.length&&t.warn(`The following keys: ${ye.default.yellow(ye.default.underline(i.join(", ")))} declared in 'define' cannot be parsed as regular code snippets.`);let c={},a={};c["import.meta.hot"]="undefined";for(let p in o.env)c[`import.meta.env.${p}`]=JSON.stringify(o.env[p]);return Object.assign(a,{"import.meta.env":JSON.stringify({...o.env,...n}).replace(/"__vite__define__(.+?)"([,}])/g,(p,m,d)=>`${m.replace(/(^\\")|(\\"$)/g,'"')}${d}`)}),{...c,...s,...a,...e}}async function Xe(o,t,e){let r=(0,ee.toArray)(e.include),s=(0,ee.toArray)(e.exclude),n=fe(t),{httpProxies:i}=le(t.server.proxy||{});i.push(...(0,ee.toArray)(e.prefix));let c=(0,ee.toArray)(e.wsPrefix),a={};try{let l=X(t.root,["package.json"]);l&&(a=JSON.parse(l))}catch{}let p=e.build.dist,m=await _t(process.cwd(),r,s),d=B.default.join(t.root,`mock-data-${Date.now()}.js`);await Z.default.writeFile(d,m,"utf-8");let{code:y,deps:v}=await me(d,{define:n,alias:t.resolve.alias}),W=Dt(v);await Z.default.unlink(d);let u=[{filename:B.default.join(p,"mock-data.js"),source:y},{filename:B.default.join(p,"index.js"),source:Et(i,c,e.cookiesOptions,e.priority,e.build.serverPort)},{filename:B.default.join(p,"package.json"),source:Lt(a,W)}];try{if(B.default.isAbsolute(p)){await Z.default.rm(p,{recursive:!0}),Qe.default.mkdirSync(p,{recursive:!0});for(let{filename:l,source:f}of u)await Z.default.writeFile(l,f,"utf-8")}else for(let{filename:l,source:f}of u)o.emitFile({type:"asset",fileName:l,source:f})}catch{}}function Dt(o){let t=new Set,e=[Ee,"connect","cors"];return Object.keys(o).forEach(r=>{o[r].imports.filter(n=>n.external&&!n.path.startsWith("<define:")).map(n=>n.path).forEach(n=>{!e.includes(n)&&!(0,Ke.default)(n)&&t.add(n)})}),Array.from(t)}function Lt(o,t){let{dependencies:e={},devDependencies:r={}}=o,s={...e,...r},n={name:"mock-server",type:"module",scripts:{start:"node index.js"},dependencies:{connect:"^3.7.0","vite-plugin-mock-dev-server":`^${_e}`,cors:"^2.8.5"},pnpm:{peerDependencyRules:{ignoreMissing:["vite"]}}};return t.forEach(i=>{n.dependencies[i]=s[i]||"latest"}),JSON.stringify(n,null,2)}function Et(o,t,e={},r={},s=8080){return`import { createServer } from 'node:http';
|
|
2
2
|
import connect from 'connect';
|
|
3
3
|
import corsMiddleware from 'cors';
|
|
4
4
|
import { baseMiddleware, mockWebSocket } from 'vite-plugin-mock-dev-server';
|
|
@@ -6,9 +6,10 @@ import mockData from './mock-data.js';
|
|
|
6
6
|
|
|
7
7
|
const app = connect();
|
|
8
8
|
const server = createServer(app);
|
|
9
|
-
const httpProxies = ${JSON.stringify(
|
|
10
|
-
const wsProxies = ${JSON.stringify(
|
|
9
|
+
const httpProxies = ${JSON.stringify(o)};
|
|
10
|
+
const wsProxies = ${JSON.stringify(t)};
|
|
11
11
|
const cookiesOptions = ${JSON.stringify(e)};
|
|
12
|
+
const priority = ${JSON.stringify(r)};
|
|
12
13
|
|
|
13
14
|
mockWebSocket({ mockData }, server, wsProxies, cookiesOptions);
|
|
14
15
|
|
|
@@ -16,13 +17,14 @@ app.use(corsMiddleware());
|
|
|
16
17
|
app.use(baseMiddleware({ mockData }, {
|
|
17
18
|
formidableOptions: { multiples: true },
|
|
18
19
|
proxies: httpProxies,
|
|
20
|
+
priority,
|
|
19
21
|
cookiesOptions,
|
|
20
22
|
}));
|
|
21
23
|
|
|
22
|
-
server.listen(${
|
|
24
|
+
server.listen(${s});
|
|
23
25
|
|
|
24
|
-
console.log('listen: http://localhost:${
|
|
25
|
-
`}async function
|
|
26
|
+
console.log('listen: http://localhost:${s}');
|
|
27
|
+
`}async function _t(o,t,e){let r=await(0,Ve.default)(t,{cwd:o}),s=(0,ge.createFilter)(t,e,{resolve:!1}),n=r.filter(s),i="",c="";return n.forEach((a,p)=>{let m=(0,ge.normalizePath)(B.default.join(o,a));i+=`import * as m${p} from '${m}';
|
|
26
28
|
`,c+=`m${p}, `}),`import { transformMockData } from 'vite-plugin-mock-dev-server';
|
|
27
29
|
${i}
|
|
28
30
|
const exporters = [${c}];
|
|
@@ -40,18 +42,19 @@ const mockList = exporters.map((raw) => {
|
|
|
40
42
|
}
|
|
41
43
|
return mockConfig
|
|
42
44
|
});
|
|
43
|
-
export default transformMockData(mockList);`}var
|
|
44
|
-
${
|
|
45
|
-
|
|
46
|
-
${
|
|
47
|
-
|
|
45
|
+
export default transformMockData(mockList);`}var A=require("@pengzhanbo/utils"),mt=h(require("cors"),1),dt=require("path-to-regexp");var be=require("buffer"),S=require("@pengzhanbo/utils"),nt=h(require("cookies"),1),st=h(require("http-status"),1),re=h(require("mime-types"),1),it=require("path-to-regexp"),g=h(require("picocolors"),1);var P=require("@pengzhanbo/utils"),te=require("path-to-regexp"),ve={};function oe(o){if(ve[o])return ve[o];let t=(0,te.parse)(o),e=[];for(let r of t)if(!(0,P.isString)(r))e.push(r);else{let s=r[0]==="/",n=s?r.slice(1).split("/"):r.split("/");e.push(`${s?"/":""}${n[0]}`,...n.slice(1).map(i=>`/${i}`))}return ve[o]=e,e}function Tt(o){let t=o.map(e=>oe(e).length);return t=t.length===0?[1]:t,Math.max(...t)+2}function It(o){let t=oe(o),e=0;for(let r=0;r<t.length;r++){let s=t[r];(0,P.isString)(s)||(e+=10**(r+1)),e+=10**(r+1)}return e}function Nt(o){let t=[],e=[];for(let r of o){let n=oe(r).filter(i=>typeof i!="string").length;e[n]||(e[n]=[]),e[n].push(r)}for(let r of e.filter(s=>s&&s.length>0))t=[...t,...(0,P.sortBy)(r,It)];return t}function Ht(o){let t=Tt(o);return(0,P.sortBy)(o,e=>{let r=oe(e),s=r.filter(c=>typeof c!="string");if(s.length===0)return 0;let n=s.length,i=0;for(let c=0;c<r.length;c++){let a=r[c],p=!(0,P.isString)(a),{pattern:m="",modifier:d,prefix:y,name:v}=p?a:{},W=m&&m.includes(".*"),u=y==="/",l=(0,P.isString)(v);i+=p&&u?1:0,c===r.length-1&&W?n+=5*10**t:W?n+=3*10**(t-1):m&&(u?n+=(l?2:1)*10**(i+1):n-=1*10**i),d==="+"&&(n+=1*10**(t-1)),d==="*"&&(n+=1*10**(t-1)+1),d==="?"&&(n+=1*10**(i+(u?1:0)))}return n})}function Ye(o,t,e){let r=Ht(Nt(o.filter(v=>(0,te.pathToRegexp)(v).test(t)))),{global:s=[],special:n={}}=e;if(s.length===0&&(0,P.isEmptyObject)(n)||r.length===0)return r;let[i,c]=Ft(r),a=s.filter(v=>c.includes(v));if(a.length>0&&(r=(0,P.uniq)([...i,...a,...c])),(0,P.isEmptyObject)(n))return r;let p=Object.keys(n).filter(v=>r.includes(v))[0];if(!p)return r;let m=n[p],{rules:d,when:y}=(0,P.isArray)(m)?{rules:m,when:[]}:m;return d.includes(r[0])&&(y.length===0||y.some(v=>(0,te.pathToRegexp)(v).test(t)))&&(r=(0,P.uniq)([p,...r])),r}function Ft(o){let t=[],e=[];for(let r of o)oe(r).filter(i=>typeof i!="string").length>0?e.push(r):t.push(r);return[t,e]}var ke=h(require("co-body"),1),Ze=h(require("formidable"),1);async function et(o,t){var s;let e=o.method.toUpperCase();if(["GET","DELETE","HEAD"].includes(e))return;let r=((s=o.headers["content-type"])==null?void 0:s.toLocaleLowerCase())||"";try{if(r.startsWith("application/json"))return await ke.default.json(o);if(r.startsWith("application/x-www-form-urlencoded"))return await ke.default.form(o);if(r.startsWith("text/plain"))return await ke.default.text(o);if(r.startsWith("multipart/form-data"))return await Ut(o,t)}catch(n){console.error(n)}}async function Ut(o,t){let e=(0,Ze.default)(t);return new Promise((r,s)=>{e.parse(o,(n,i,c)=>{if(n){s(n);return}r({...i,...c})})})}var Q=require("@pengzhanbo/utils");function tt(o,t){return T(o.headers,t.headers)&&T(o.body,t.body)&&T(o.params,t.params)&&T(o.query,t.query)&&T(o.refererQuery,t.refererQuery)}function T(o,t){if(!t)return!0;for(let e in t)if(!ot(o[e],t[e]))return!1;return!0}function ot(o,t){if((0,Q.isArray)(o)&&(0,Q.isArray)(t)){let e=new Set;return t.every(r=>o.some((s,n)=>{if(e.has(n))return!1;let i=ot(s,r);return i&&e.add(n),i}))}return(0,Q.isObject)(o)&&(0,Q.isObject)(t)?T(o,t):Object.is(o,t)}function xe(o,{formidableOptions:t={},proxies:e,cookiesOptions:r,logger:s,priority:n={}}){return async function(i,c,a){let p=(0,S.timestamp)(),{query:m,pathname:d}=D(i.url);if(!d||e.length===0||!e.some(w=>G(w,i.url)))return a();let y=o.mockData,v=Ye(Object.keys(y),d,n);if(v.length===0)return a();let{query:W}=D(i.headers.referer||""),u=await et(i,t),l=new nt.default(i,c,r),f=l.get.bind(l),M=i.method.toUpperCase(),b,R;for(let w of v)if(b=qt(y[w],s,{pathname:d,method:M,request:{query:m,refererQuery:W,body:u,headers:i.headers,getCookie:f}}),b){R=w;break}if(!b){let w=v.map(K=>K===R?g.default.underline(g.default.bold(K)):g.default.dim(K)).join(", ");return s.warn(`${g.default.green(d)} matches ${w} , but mock data is not found.`),a()}let k=i,x=c;k.body=u,k.query=m,k.refererQuery=W,k.params=Y(b.url,d),k.getCookie=f,x.setCookie=l.set.bind(l);let{body:j,delay:H,type:F="json",response:_,status:E=200,statusText:ne,log:V,__filepath__:C}=b;if(Me(x,E,ne),await Bt(k,x,b,s),await Jt(k,x,b,s),s.info(Gt(k,C),V),s.debug(`${g.default.magenta("DEBUG")} ${g.default.underline(d)} matches: [ ${v.map(w=>w===R?g.default.underline(g.default.bold(w)):g.default.dim(w)).join(", ")} ]
|
|
46
|
+
`),j){try{let w=(0,S.isFunction)(j)?await j(k):j;await rt(p,H),At(x,w,F)}catch(w){s.error(`${g.default.red(`mock error at ${d}`)}
|
|
47
|
+
${w}
|
|
48
|
+
at body (${g.default.underline(C)})`,V),Me(x,500),c.end("")}return}if(_){try{await rt(p,H),await _(k,x,a)}catch(w){s.error(`${g.default.red(`mock error at ${d}`)}
|
|
49
|
+
${w}
|
|
50
|
+
at response (${g.default.underline(C)})`,V),Me(x,500),c.end("")}return}c.end("")}}function qt(o,t,{pathname:e,method:r,request:s}){return o.find(n=>{if(!e||!n||!n.url||n.ws===!0||!(n.method?(0,S.isArray)(n.method)?n.method:[n.method]:["GET","POST"]).includes(r))return!1;let c=(0,it.pathToRegexp)(n.url).test(e);if(c&&n.validator){let a=Y(n.url,e);if((0,S.isFunction)(n.validator))return n.validator({params:a,...s});try{return tt({params:a,...s},n.validator)}catch(p){let m=n.__filepath__;return t.error(`${g.default.red(`mock error at ${e}`)}
|
|
48
51
|
${p}
|
|
49
|
-
at validator (${
|
|
52
|
+
at validator (${g.default.underline(m)})`,n.log),!1}}return c})}function Me(o,t=200,e){o.statusCode=t,o.statusMessage=e||zt(t)}async function Bt(o,t,e,r){let{headers:s,type:n="json"}=e,i=e.__filepath__,c=re.contentType(n)||re.contentType(re.lookup(n)||"");if(c&&t.setHeader("Content-Type",c),t.setHeader("Cache-Control","no-cache,max-age=0"),t.setHeader("X-Mock-Power-By","vite-plugin-mock-dev-server"),t.setHeader("X-File-Path",i),!!s)try{let a=(0,S.isFunction)(s)?await s(o):s;Object.keys(a).forEach(p=>{t.setHeader(p,a[p])})}catch(a){r.error(`${g.default.red(`mock error at ${o.url.split("?")[0]}`)}
|
|
50
53
|
${a}
|
|
51
|
-
at headers (${
|
|
54
|
+
at headers (${g.default.underline(i)})`,e.log)}}async function Jt(o,t,e,r){let{cookies:s}=e,n=e.__filepath__;if(s)try{let i=(0,S.isFunction)(s)?await s(o):s;Object.keys(i).forEach(c=>{let a=i[c];if((0,S.isArray)(a)){let[p,m]=a;t.setCookie(c,p,m)}else t.setCookie(c,a)})}catch(i){r.error(`${g.default.red(`mock error at ${o.url.split("?")[0]}`)}
|
|
52
55
|
${i}
|
|
53
|
-
at cookies (${
|
|
54
|
-
${
|
|
55
|
-
at setup (${
|
|
56
|
-
${
|
|
57
|
-
at setup (${
|
|
56
|
+
at cookies (${g.default.underline(n)})`,e.log)}}function At(o,t,e){if(He(t))t.pipe(o);else if(be.Buffer.isBuffer(t))o.end(e==="text"||e==="json"?t.toString("utf-8"):t);else{let r=typeof t=="string"?t:JSON.stringify(t);o.end(e==="buffer"?be.Buffer.from(r):r)}}async function rt(o,t){if(!t||typeof t=="number"&&t<=0||(0,S.isArray)(t)&&t.length!==2)return;let e=0;if((0,S.isArray)(t)){let[r,s]=t;e=(0,S.random)(r,s)}else e=t-((0,S.timestamp)()-o);e>0&&await(0,S.sleep)(e)}function zt(o){return st.default[o]||"Unknown"}function Gt(o,t){let{url:e,method:r,query:s,params:n,body:i}=o,{pathname:c}=new URL(e,"http://example.com");c=g.default.green(decodeURIComponent(c));let a=(W,u)=>!u||(0,S.isEmptyObject)(u)?"":` ${g.default.gray(`${W}:`)}${JSON.stringify(u)}`,p=g.default.magenta(g.default.bold(r)),m=a("query",s),d=a("params",n),y=a("body",i),v=` ${g.default.dim(g.default.underline(`(${t})`))}`;return`${p} ${c}${m}${d}${y}${v}`}var ct=h(require("events"),1),N=require("@pengzhanbo/utils"),Se=h(require("chokidar"),1),at=h(require("fast-glob"),1),I=require("vite");var $=require("@pengzhanbo/utils");function we(o){let t=[];for(let[,r]of o.entries())r&&((0,$.isArray)(r)?t.push(...r):t.push(r));let e={};return t.filter(r=>(0,$.isObject)(r)&&r.enabled!==!1&&r.url).forEach(r=>{let{pathname:s,query:n}=D(r.url),i=e[s]??=[],c={...r,url:s};if(c.ws!==!0){let a=c.validator;(0,$.isEmptyObject)(n)||((0,$.isFunction)(a)?c.validator=function(p){return T(p.query,n)&&a(p)}:a?(c.validator={...a},c.validator.query=c.validator.query?{...n,...c.validator.query}:n):c.validator={query:n})}i.push(c)}),Object.keys(e).forEach(r=>{e[r]=(0,$.sortBy)(e[r],s=>{if(s.ws===!0)return 0;let{validator:n}=s;return!n||(0,$.isEmptyObject)(n)?2:(0,$.isFunction)(n)?0:1/Object.keys(n).reduce((c,a)=>c+Qt(n[a]),0)})}),e}function Qt(o){return o?Object.keys(o).length:0}var he=class extends ct.default{constructor(e){super();this.options=e;this.cwd=e.cwd||process.cwd();try{let r=X(this.cwd,["package.json"]);this.moduleType=r&&JSON.parse(r).type==="module"?"esm":"cjs"}catch{}}moduleCache=new Map;moduleDeps=new Map;cwd;mockWatcher;depsWatcher;moduleType="cjs";_mockData={};get mockData(){return this._mockData}load(){let{include:e,exclude:r}=this.options,s=(0,I.createFilter)(e,r,{resolve:!1});(0,at.default)(e,{cwd:this.cwd}).then(i=>i.filter(s).map(c=>()=>this.loadMock(c))).then(i=>(0,N.promiseParallel)(i,10)).then(()=>this.updateMockList()),this.watchMockEntry(),this.watchDeps();let n=null;this.on("mock:update",async i=>{s(i)&&(await this.loadMock(i),n&&clearImmediate(n),n=setImmediate(()=>{this.updateMockList(),this.emit("mock:update-end",i),n=null}))}),this.on("mock:unlink",async i=>{s(i)&&(this.moduleCache.delete(i),this.updateMockList(),this.emit("mock:update-end",i))})}watchMockEntry(){let{include:e}=this.options,[r,...s]=e,n=this.mockWatcher=Se.default.watch(r,{ignoreInitial:!0,cwd:this.cwd});s.length>0&&s.forEach(i=>n.add(i)),n.on("add",async i=>{i=(0,I.normalizePath)(i),this.emit("mock:update",i),pe("watcher:add",i)}),n.on("change",async i=>{i=(0,I.normalizePath)(i),this.emit("mock:update",i),pe("watcher:change",i)}),n.on("unlink",async i=>{i=(0,I.normalizePath)(i),this.emit("mock:unlink",i),pe("watcher:unlink",i)})}watchDeps(){let e=[];this.depsWatcher=Se.default.watch([],{ignoreInitial:!0,cwd:this.cwd}),this.depsWatcher.on("change",r=>{r=(0,I.normalizePath)(r);let s=this.moduleDeps.get(r);s&&s.forEach(n=>{this.emit("mock:update",n)})}),this.depsWatcher.on("unlink",r=>{r=(0,I.normalizePath)(r),this.moduleDeps.delete(r)}),this.on("update:deps",()=>{let r=[];for(let[n]of this.moduleDeps.entries())r.push(n);let s=r.filter(n=>!e.includes(n));s.length>0&&this.depsWatcher.add(s)})}close(){var e,r;(e=this.mockWatcher)==null||e.close(),(r=this.depsWatcher)==null||r.close()}updateMockList(){this._mockData=we(this.moduleCache)}updateModuleDeps(e,r){Object.keys(r).forEach(s=>{r[s].imports.map(i=>i.path).forEach(i=>{this.moduleDeps.has(i)||this.moduleDeps.set(i,new Set),this.moduleDeps.get(i).add(e)})}),this.emit("update:deps")}async loadMock(e){if(!e)return;let r=!1;/\.m[jt]s$/.test(e)?r=!0:/\.c[jt]s$/.test(e)?r=!1:r=this.moduleType==="esm";let{define:s,alias:n}=this.options,{code:i,deps:c}=await me(e,{isESM:r,define:s,alias:n});try{let a=await Ae(e,i,r,this.cwd)||{},p;(0,N.hasOwn)(a,"default")?p=a.default:(p=[],Object.keys(a).forEach(m=>p.push(...(0,N.toArray)(a[m])))),(0,N.isArray)(p)?p.forEach(m=>m.__filepath__=e):p.__filepath__=e,this.moduleCache.set(e,p),this.updateModuleDeps(e,c)}catch(a){console.error(a)}}};var lt=h(require("cookies"),1),Oe=require("path-to-regexp"),J=h(require("picocolors"),1),ut=require("ws");function Ce({loader:o,httpServer:t,proxies:e,cookiesOptions:r,logger:s}){var W;let n=new Map,i=new Map,c=new WeakMap,a=u=>{let l=i.get(u);return!l&&i.set(u,l=new Map),l},p=(u,l)=>{let f=u.get(l);return!f&&u.set(l,f=new ut.WebSocketServer({noServer:!0})),f},m=(u,l)=>{let f=n.get(u);!f&&n.set(u,f=new Set),f.add(l)},d=(u,l,f,M,b,R)=>{var k;try{(k=f.setup)==null||k.call(f,l,M),l.on("close",()=>u.delete(b)),l.on("error",x=>{s.error(`${J.default.red(`WebSocket mock error at ${l.path}`)}
|
|
57
|
+
${x}
|
|
58
|
+
at setup (${R})`,f.log)})}catch(x){s.error(`${J.default.red(`WebSocket mock error at ${l.path}`)}
|
|
59
|
+
${x}
|
|
60
|
+
at setup (${R})`,f.log)}},y=(u,l,f,M)=>{u.emit("connection",l,f),l.on("close",()=>{let b=M.findIndex(R=>R.ws===l);b!==-1&&M.splice(b,1)})},v=(u,l,f,M,b)=>{let{cleanupList:R,connectionList:k,context:x}=c.get(l);pt(R),k.forEach(({ws:j})=>j.removeAllListeners()),l.removeAllListeners(),d(u,l,f,x,M,b),k.forEach(({ws:j,req:H})=>y(l,j,H,k))};(W=o.on)==null||W.call(o,"mock:update-end",u=>{if(!n.has(u))return;let l=n.get(u);if(l)for(let f of l.values())for(let M of o.mockData[f]){if(!M.ws||M.__filepath__!==u)return;let b=a(f);for(let[R,k]of b.entries())v(b,k,M,R,u)}}),t==null||t.on("upgrade",(u,l,f)=>{let{pathname:M,query:b}=D(u.url);if(!M||e.length===0||!e.some(C=>G(C,u.url)))return;let R=o.mockData,k=Object.keys(R).find(C=>(0,Oe.pathToRegexp)(C).test(M));if(!k)return;let x=R[k].find(C=>C.url&&C.ws&&(0,Oe.pathToRegexp)(C.url).test(M));if(!x)return;let j=x.__filepath__;m(j,k);let H=a(k),F=p(H,M),_=c.get(F);if(!_){let C=[],w={onCleanup:K=>C.push(K)};_={cleanupList:C,context:w,connectionList:[]},c.set(F,_),d(H,F,x,w,M,j)}let E=u,ne=new lt.default(u,u,r),{query:V}=D(u.headers.referer||"");E.query=b,E.refererQuery=V,E.params=Y(k,M),E.getCookie=ne.get.bind(ne),F.handleUpgrade(E,l,f,C=>{s.info(`${J.default.magenta(J.default.bold("WebSocket"))} ${J.default.green(u.url)} connected ${J.default.dim(`(${j})`)}`,x.log),_.connectionList.push({req:E,ws:C}),y(F,C,E,_.connectionList)})}),t==null||t.on("close",()=>{for(let u of i.values()){for(let l of u.values()){let f=c.get(l);pt(f.cleanupList),l.close()}u.clear()}i.clear(),n.clear()})}function pt(o){let t;for(;t=o.shift();)t==null||t()}function Pe(o,t,e,r){let s=de("vite:mock",(0,A.isBoolean)(t.log)?t.log?"info":"error":t.log),n=new he({include:(0,A.toArray)(t.include),exclude:(0,A.toArray)(t.exclude),define:fe(o),alias:o.resolve.alias});n.load(),n.on("mock:update-end",()=>{t.reload&&(r==null||r.send({type:"full-reload"}))}),e==null||e.on("close",()=>n.close());let{httpProxies:i}=le(o.server.proxy||{}),a=[...(0,A.toArray)(t.prefix),...i];Ce({loader:n,httpServer:e,proxies:(0,A.toArray)(t.wsPrefix),cookiesOptions:t.cookiesOptions,logger:s});let p=[];return p.push(Vt(n,a,o,t),xe(n,{formidableOptions:t.formidableOptions,proxies:a,cookiesOptions:t.cookiesOptions,priority:t.priority,logger:s})),p.filter(Boolean)}function Vt(o,t,e,r){let s={},n=r.cors===!1?!1:e.server.cors!==!1;return n&&e.server.cors!==!1&&(s={...s,...typeof e.server.cors=="boolean"?{}:e.server.cors}),n&&r.cors!==!1&&(s={...s,...typeof r.cors=="boolean"?{}:r.cors}),n?function(i,c,a){let{pathname:p}=D(i.url);if(!p||t.length===0||!t.some(y=>G(y,i.url)))return a();let m=o.mockData;if(!Object.keys(m).find(y=>(0,dt.pathToRegexp)(y).test(p)))return a();(0,mt.default)(s)(i,c,a)}:void 0}function Re({prefix:o=[],wsPrefix:t=[],include:e=["mock/**/*.mock.{js,ts,cjs,mjs,json,json5}"],exclude:r=["**/node_modules/**","**/.vscode/**","**/.git/**"],reload:s=!1,log:n="info",cors:i=!0,formidableOptions:c={},build:a=!1,cookiesOptions:p={},priority:m={}}={}){let d={prefix:o,wsPrefix:t,include:e,exclude:r,reload:s,cors:i,cookiesOptions:p,log:n,formidableOptions:{multiples:!0,...c},priority:m,build:a?Object.assign({serverPort:8080,dist:"mockServer"},typeof a=="object"?a:{}):!1},y=[Xt(d)];return d.build&&y.push(Kt(d)),y}function Kt(o){let t={};return{name:"vite-plugin-mock-dev-server-generator",enforce:"post",apply:"build",configResolved(e){t=e,e.logger.warn("")},async buildEnd(e){e||t.command==="build"&&await Xe(this,t,o)}}}function Xt(o){let t={};return{name:"vite-plugin-mock-dev-server",enforce:"pre",apply:"serve",config(e){var n;let r=(0,ft.toArray)(o.wsPrefix);if(r.length===0||!((n=e.server)!=null&&n.proxy)||Object.keys(e.server.proxy).length===0)return;let s={};Object.keys(e.server.proxy).forEach(i=>{r.includes(i)||(s[i]=e.server.proxy[i])}),e.server.proxy=s},configResolved(e){t=e,e.logger.warn("")},configureServer({middlewares:e,config:r,httpServer:s,ws:n}){Pe(r,o,s,n).forEach(c=>e.use(c))},configurePreviewServer({middlewares:e,httpServer:r}){Pe(t,o,r).forEach(n=>e.use(n))}}}var gt=require("@pengzhanbo/utils");function Yt(o){return o}function Zt(o){return e=>((0,gt.isArray)(e)?e=e.map(r=>o(r)||r):e=o(e)||e,e)}var z=require("@pengzhanbo/utils"),We=new Map,je=new WeakMap,eo=70,$e=class{value;#e;#t;constructor(t){this.value=t,this.#e=(0,z.deepClone)(t),this.#t=Date.now()}hotUpdate(t){Date.now()-this.#t<eo||(0,z.deepEqual)(t,this.#e)||(this.value=t,this.#e=(0,z.deepClone)(t),this.#t=Date.now())}};function to(o,t){We.has(o)||We.set(o,new $e(t));let e=We.get(o);if(e.hotUpdate(t),je.has(e))return je.get(e);let r=[()=>e.value,s=>{(0,z.isFunction)(s)&&(s=s(e.value)??e.value),e.value=s}];return Object.defineProperty(r,"value",{get(){return e.value},set(s){e.value=s}}),je.set(e,r),r}var oo=Re;0&&(module.exports={baseMiddleware,createDefineMock,defineMock,defineMockData,mockDevServerPlugin,mockWebSocket,transformMockData});
|
package/dist/index.d.cts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { Connect, Plugin, ResolvedConfig } from 'vite';
|
|
2
2
|
import { Buffer } from 'node:buffer';
|
|
3
3
|
import http from 'node:http';
|
|
4
4
|
import { Readable } from 'node:stream';
|
|
@@ -97,6 +97,83 @@ interface MockServerPluginOptions {
|
|
|
97
97
|
* @default false
|
|
98
98
|
*/
|
|
99
99
|
build?: boolean | ServerBuildOption;
|
|
100
|
+
/**
|
|
101
|
+
* Priority sorting for path matching rules is valid only for rules containing dynamic parameters.
|
|
102
|
+
* In most cases, the default sorting rules can meet the needs.
|
|
103
|
+
* However, in some cases where custom sorting rules are required, this option can be used.
|
|
104
|
+
*
|
|
105
|
+
* 路径匹配规则优先级排序,仅对包含动态参数的规则有效。
|
|
106
|
+
* 大部分情况下默认的排序规则都可以满足需求。
|
|
107
|
+
* 但有些情况下,需要自定义排序规则时,可以使用此选项。
|
|
108
|
+
*
|
|
109
|
+
* @example
|
|
110
|
+
* ```ts
|
|
111
|
+
* export default {
|
|
112
|
+
* priority: {
|
|
113
|
+
* global: ['/api/:a/b/c', '/api/a/:b/c', '/api/a/b/:c'],
|
|
114
|
+
* special: {
|
|
115
|
+
* '/api/:a/:b/c': {
|
|
116
|
+
* rules: ['/api/a/:b/:c', '/api/a/b/:c'],
|
|
117
|
+
* when: ['/api/a/b/c']
|
|
118
|
+
* }
|
|
119
|
+
* }
|
|
120
|
+
* }
|
|
121
|
+
* }
|
|
122
|
+
* ```
|
|
123
|
+
*/
|
|
124
|
+
priority?: MockMatchPriority;
|
|
125
|
+
}
|
|
126
|
+
interface MockMatchPriority {
|
|
127
|
+
/**
|
|
128
|
+
* The priority of matching rules is global.
|
|
129
|
+
* The rules declared in this option will take priority over the default rules.
|
|
130
|
+
* The higher the position of the rule in the array, the higher the priority.
|
|
131
|
+
*
|
|
132
|
+
* Do not declare general rules in this option, such as /api/(.*),
|
|
133
|
+
* as it will prevent subsequent rules from taking effect.
|
|
134
|
+
* Unless you are clear about the priority of the rules,
|
|
135
|
+
* most of the time you do not need to configure this option.
|
|
136
|
+
|
|
137
|
+
* 匹配规则优先级, 全局生效。
|
|
138
|
+
* 声明在该选项中的规则将优先于默认规则生效。
|
|
139
|
+
* 规则在数组越靠前的位置,优先级越高。
|
|
140
|
+
*
|
|
141
|
+
* 不要在此选项中声明通用性的规则,比如 `/api/(.*)`,这将导致后续的规则无法生效。
|
|
142
|
+
* 除非你明确知道规则的优先级,否则大多数情况下都不需要配置该选项。
|
|
143
|
+
* @default []
|
|
144
|
+
*/
|
|
145
|
+
global?: string[];
|
|
146
|
+
/**
|
|
147
|
+
* For some special cases where the priority of certain rules needs to be adjusted,
|
|
148
|
+
* this option can be used. For example, when a request matches both Rule A and Rule B,
|
|
149
|
+
* and Rule A has a higher priority than Rule B, but it is desired for Rule B to take effect.
|
|
150
|
+
*
|
|
151
|
+
* 对于一些特殊情况,需要调整部分规则的优先级,可以使用此选项。
|
|
152
|
+
* 比如一个请求同时命中了规则 A 和 B,且 A 比 B 优先级高, 但期望规则 B 生效时。
|
|
153
|
+
*/
|
|
154
|
+
special?: MockMatchSpecialPriority;
|
|
155
|
+
}
|
|
156
|
+
interface MockMatchSpecialPriority {
|
|
157
|
+
/**
|
|
158
|
+
* When both A and B or C match, and B or C is at the top of the sort order,
|
|
159
|
+
* insert A into the top position.The `when` option is used to further constrain
|
|
160
|
+
* the priority adjustment to be effective only for certain requests.
|
|
161
|
+
*
|
|
162
|
+
* 当 A 与 B或 C 同时满足匹配,且 B或 C在排序首位时,将A插入到首位。
|
|
163
|
+
* when 选项用于进一步约束该优先级调整仅针对哪些请求有效。
|
|
164
|
+
*
|
|
165
|
+
* @example
|
|
166
|
+
* ```ts
|
|
167
|
+
* {
|
|
168
|
+
* A: ['B', 'C'],
|
|
169
|
+
* A: { rules: ['B', 'C'], when: ['/api/a/b/c'] }
|
|
170
|
+
* }
|
|
171
|
+
* ```
|
|
172
|
+
*/
|
|
173
|
+
[key: string]: string[] | {
|
|
174
|
+
rules: string[];
|
|
175
|
+
when: string[];
|
|
176
|
+
};
|
|
100
177
|
}
|
|
101
178
|
interface ServerBuildOption {
|
|
102
179
|
/**
|
|
@@ -443,8 +520,10 @@ interface WebSocketSetupContext {
|
|
|
443
520
|
}
|
|
444
521
|
type MockOptions = (MockHttpItem | MockWebsocketItem)[];
|
|
445
522
|
type FormidableFile = formidable.File | formidable.File[];
|
|
523
|
+
type LogType = 'info' | 'warn' | 'error' | 'debug';
|
|
524
|
+
type LogLevel = LogType | 'silent';
|
|
446
525
|
|
|
447
|
-
declare function mockDevServerPlugin({ prefix, wsPrefix, include, exclude, reload, log, cors, formidableOptions, build, cookiesOptions, }?: MockServerPluginOptions): Plugin[];
|
|
526
|
+
declare function mockDevServerPlugin({ prefix, wsPrefix, include, exclude, reload, log, cors, formidableOptions, build, cookiesOptions, priority, }?: MockServerPluginOptions): Plugin[];
|
|
448
527
|
|
|
449
528
|
/**
|
|
450
529
|
* mock config Type helper
|
|
@@ -496,7 +575,25 @@ declare function defineMock(config: MockOptions): MockOptions;
|
|
|
496
575
|
*/
|
|
497
576
|
declare function createDefineMock(transformer: (mock: MockHttpItem | MockWebsocketItem) => MockHttpItem | MockWebsocketItem | void): typeof defineMock;
|
|
498
577
|
|
|
578
|
+
type MockData<T = any> = readonly [
|
|
579
|
+
/**
|
|
580
|
+
* getter
|
|
581
|
+
*/
|
|
582
|
+
() => T,
|
|
583
|
+
/**
|
|
584
|
+
* setter
|
|
585
|
+
*/
|
|
586
|
+
(val: T | ((val: T) => T | void)) => void
|
|
587
|
+
] & {
|
|
588
|
+
/**
|
|
589
|
+
* @property getter/setter
|
|
590
|
+
*/
|
|
591
|
+
value: T;
|
|
592
|
+
};
|
|
593
|
+
declare function defineMockData<T = any>(key: string, initialData: T): MockData<T>;
|
|
594
|
+
|
|
499
595
|
interface Logger {
|
|
596
|
+
debug(msg: string, level?: boolean | LogLevel): void;
|
|
500
597
|
info(msg: string, level?: boolean | LogLevel): void;
|
|
501
598
|
warn(msg: string, level?: boolean | LogLevel): void;
|
|
502
599
|
error(msg: string, level?: boolean | LogLevel): void;
|
|
@@ -541,8 +638,9 @@ interface BaseMiddlewareOptions {
|
|
|
541
638
|
cookiesOptions: MockServerPluginOptions['cookiesOptions'];
|
|
542
639
|
proxies: string[];
|
|
543
640
|
logger: Logger;
|
|
641
|
+
priority: MockServerPluginOptions['priority'];
|
|
544
642
|
}
|
|
545
|
-
declare function baseMiddleware(mockLoader: MockLoader, { formidableOptions, proxies, cookiesOptions, logger, }: BaseMiddlewareOptions): Connect.NextHandleFunction;
|
|
643
|
+
declare function baseMiddleware(mockLoader: MockLoader, { formidableOptions, proxies, cookiesOptions, logger, priority, }: BaseMiddlewareOptions): Connect.NextHandleFunction;
|
|
546
644
|
|
|
547
645
|
/**
|
|
548
646
|
* 不复用 `viteConfig.server.proxy` 中 websocket proxy的原因是,
|
|
@@ -567,4 +665,4 @@ declare function mockWebSocket({ loader, httpServer, proxies, cookiesOptions, lo
|
|
|
567
665
|
|
|
568
666
|
declare function transformMockData(mockList: Map<string, MockHttpItem | MockWebsocketItem | MockOptions> | (MockHttpItem | MockWebsocketItem | MockOptions)[]): Record<string, MockOptions>;
|
|
569
667
|
|
|
570
|
-
export { BaseMiddlewareOptions, FormidableFile, MockHttpItem, MockOptions, MockRequest, MockServerPluginOptions, MockSocketOptions, MockWebsocketItem, baseMiddleware, createDefineMock, mockDevServerPlugin as default, defineMock, mockDevServerPlugin, mockWebSocket, transformMockData };
|
|
668
|
+
export { BaseMiddlewareOptions, FormidableFile, MockData, MockHttpItem, MockOptions, MockRequest, MockServerPluginOptions, MockSocketOptions, MockWebsocketItem, baseMiddleware, createDefineMock, mockDevServerPlugin as default, defineMock, defineMockData, mockDevServerPlugin, mockWebSocket, transformMockData };
|
package/dist/index.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { Connect, Plugin, ResolvedConfig } from 'vite';
|
|
2
2
|
import { Buffer } from 'node:buffer';
|
|
3
3
|
import http from 'node:http';
|
|
4
4
|
import { Readable } from 'node:stream';
|
|
@@ -97,6 +97,83 @@ interface MockServerPluginOptions {
|
|
|
97
97
|
* @default false
|
|
98
98
|
*/
|
|
99
99
|
build?: boolean | ServerBuildOption;
|
|
100
|
+
/**
|
|
101
|
+
* Priority sorting for path matching rules is valid only for rules containing dynamic parameters.
|
|
102
|
+
* In most cases, the default sorting rules can meet the needs.
|
|
103
|
+
* However, in some cases where custom sorting rules are required, this option can be used.
|
|
104
|
+
*
|
|
105
|
+
* 路径匹配规则优先级排序,仅对包含动态参数的规则有效。
|
|
106
|
+
* 大部分情况下默认的排序规则都可以满足需求。
|
|
107
|
+
* 但有些情况下,需要自定义排序规则时,可以使用此选项。
|
|
108
|
+
*
|
|
109
|
+
* @example
|
|
110
|
+
* ```ts
|
|
111
|
+
* export default {
|
|
112
|
+
* priority: {
|
|
113
|
+
* global: ['/api/:a/b/c', '/api/a/:b/c', '/api/a/b/:c'],
|
|
114
|
+
* special: {
|
|
115
|
+
* '/api/:a/:b/c': {
|
|
116
|
+
* rules: ['/api/a/:b/:c', '/api/a/b/:c'],
|
|
117
|
+
* when: ['/api/a/b/c']
|
|
118
|
+
* }
|
|
119
|
+
* }
|
|
120
|
+
* }
|
|
121
|
+
* }
|
|
122
|
+
* ```
|
|
123
|
+
*/
|
|
124
|
+
priority?: MockMatchPriority;
|
|
125
|
+
}
|
|
126
|
+
interface MockMatchPriority {
|
|
127
|
+
/**
|
|
128
|
+
* The priority of matching rules is global.
|
|
129
|
+
* The rules declared in this option will take priority over the default rules.
|
|
130
|
+
* The higher the position of the rule in the array, the higher the priority.
|
|
131
|
+
*
|
|
132
|
+
* Do not declare general rules in this option, such as /api/(.*),
|
|
133
|
+
* as it will prevent subsequent rules from taking effect.
|
|
134
|
+
* Unless you are clear about the priority of the rules,
|
|
135
|
+
* most of the time you do not need to configure this option.
|
|
136
|
+
|
|
137
|
+
* 匹配规则优先级, 全局生效。
|
|
138
|
+
* 声明在该选项中的规则将优先于默认规则生效。
|
|
139
|
+
* 规则在数组越靠前的位置,优先级越高。
|
|
140
|
+
*
|
|
141
|
+
* 不要在此选项中声明通用性的规则,比如 `/api/(.*)`,这将导致后续的规则无法生效。
|
|
142
|
+
* 除非你明确知道规则的优先级,否则大多数情况下都不需要配置该选项。
|
|
143
|
+
* @default []
|
|
144
|
+
*/
|
|
145
|
+
global?: string[];
|
|
146
|
+
/**
|
|
147
|
+
* For some special cases where the priority of certain rules needs to be adjusted,
|
|
148
|
+
* this option can be used. For example, when a request matches both Rule A and Rule B,
|
|
149
|
+
* and Rule A has a higher priority than Rule B, but it is desired for Rule B to take effect.
|
|
150
|
+
*
|
|
151
|
+
* 对于一些特殊情况,需要调整部分规则的优先级,可以使用此选项。
|
|
152
|
+
* 比如一个请求同时命中了规则 A 和 B,且 A 比 B 优先级高, 但期望规则 B 生效时。
|
|
153
|
+
*/
|
|
154
|
+
special?: MockMatchSpecialPriority;
|
|
155
|
+
}
|
|
156
|
+
interface MockMatchSpecialPriority {
|
|
157
|
+
/**
|
|
158
|
+
* When both A and B or C match, and B or C is at the top of the sort order,
|
|
159
|
+
* insert A into the top position.The `when` option is used to further constrain
|
|
160
|
+
* the priority adjustment to be effective only for certain requests.
|
|
161
|
+
*
|
|
162
|
+
* 当 A 与 B或 C 同时满足匹配,且 B或 C在排序首位时,将A插入到首位。
|
|
163
|
+
* when 选项用于进一步约束该优先级调整仅针对哪些请求有效。
|
|
164
|
+
*
|
|
165
|
+
* @example
|
|
166
|
+
* ```ts
|
|
167
|
+
* {
|
|
168
|
+
* A: ['B', 'C'],
|
|
169
|
+
* A: { rules: ['B', 'C'], when: ['/api/a/b/c'] }
|
|
170
|
+
* }
|
|
171
|
+
* ```
|
|
172
|
+
*/
|
|
173
|
+
[key: string]: string[] | {
|
|
174
|
+
rules: string[];
|
|
175
|
+
when: string[];
|
|
176
|
+
};
|
|
100
177
|
}
|
|
101
178
|
interface ServerBuildOption {
|
|
102
179
|
/**
|
|
@@ -443,8 +520,10 @@ interface WebSocketSetupContext {
|
|
|
443
520
|
}
|
|
444
521
|
type MockOptions = (MockHttpItem | MockWebsocketItem)[];
|
|
445
522
|
type FormidableFile = formidable.File | formidable.File[];
|
|
523
|
+
type LogType = 'info' | 'warn' | 'error' | 'debug';
|
|
524
|
+
type LogLevel = LogType | 'silent';
|
|
446
525
|
|
|
447
|
-
declare function mockDevServerPlugin({ prefix, wsPrefix, include, exclude, reload, log, cors, formidableOptions, build, cookiesOptions, }?: MockServerPluginOptions): Plugin[];
|
|
526
|
+
declare function mockDevServerPlugin({ prefix, wsPrefix, include, exclude, reload, log, cors, formidableOptions, build, cookiesOptions, priority, }?: MockServerPluginOptions): Plugin[];
|
|
448
527
|
|
|
449
528
|
/**
|
|
450
529
|
* mock config Type helper
|
|
@@ -496,7 +575,25 @@ declare function defineMock(config: MockOptions): MockOptions;
|
|
|
496
575
|
*/
|
|
497
576
|
declare function createDefineMock(transformer: (mock: MockHttpItem | MockWebsocketItem) => MockHttpItem | MockWebsocketItem | void): typeof defineMock;
|
|
498
577
|
|
|
578
|
+
type MockData<T = any> = readonly [
|
|
579
|
+
/**
|
|
580
|
+
* getter
|
|
581
|
+
*/
|
|
582
|
+
() => T,
|
|
583
|
+
/**
|
|
584
|
+
* setter
|
|
585
|
+
*/
|
|
586
|
+
(val: T | ((val: T) => T | void)) => void
|
|
587
|
+
] & {
|
|
588
|
+
/**
|
|
589
|
+
* @property getter/setter
|
|
590
|
+
*/
|
|
591
|
+
value: T;
|
|
592
|
+
};
|
|
593
|
+
declare function defineMockData<T = any>(key: string, initialData: T): MockData<T>;
|
|
594
|
+
|
|
499
595
|
interface Logger {
|
|
596
|
+
debug(msg: string, level?: boolean | LogLevel): void;
|
|
500
597
|
info(msg: string, level?: boolean | LogLevel): void;
|
|
501
598
|
warn(msg: string, level?: boolean | LogLevel): void;
|
|
502
599
|
error(msg: string, level?: boolean | LogLevel): void;
|
|
@@ -541,8 +638,9 @@ interface BaseMiddlewareOptions {
|
|
|
541
638
|
cookiesOptions: MockServerPluginOptions['cookiesOptions'];
|
|
542
639
|
proxies: string[];
|
|
543
640
|
logger: Logger;
|
|
641
|
+
priority: MockServerPluginOptions['priority'];
|
|
544
642
|
}
|
|
545
|
-
declare function baseMiddleware(mockLoader: MockLoader, { formidableOptions, proxies, cookiesOptions, logger, }: BaseMiddlewareOptions): Connect.NextHandleFunction;
|
|
643
|
+
declare function baseMiddleware(mockLoader: MockLoader, { formidableOptions, proxies, cookiesOptions, logger, priority, }: BaseMiddlewareOptions): Connect.NextHandleFunction;
|
|
546
644
|
|
|
547
645
|
/**
|
|
548
646
|
* 不复用 `viteConfig.server.proxy` 中 websocket proxy的原因是,
|
|
@@ -567,4 +665,4 @@ declare function mockWebSocket({ loader, httpServer, proxies, cookiesOptions, lo
|
|
|
567
665
|
|
|
568
666
|
declare function transformMockData(mockList: Map<string, MockHttpItem | MockWebsocketItem | MockOptions> | (MockHttpItem | MockWebsocketItem | MockOptions)[]): Record<string, MockOptions>;
|
|
569
667
|
|
|
570
|
-
export { BaseMiddlewareOptions, FormidableFile, MockHttpItem, MockOptions, MockRequest, MockServerPluginOptions, MockSocketOptions, MockWebsocketItem, baseMiddleware, createDefineMock, mockDevServerPlugin as default, defineMock, mockDevServerPlugin, mockWebSocket, transformMockData };
|
|
668
|
+
export { BaseMiddlewareOptions, FormidableFile, MockData, MockHttpItem, MockOptions, MockRequest, MockServerPluginOptions, MockSocketOptions, MockWebsocketItem, baseMiddleware, createDefineMock, mockDevServerPlugin as default, defineMock, defineMockData, mockDevServerPlugin, mockWebSocket, transformMockData };
|
package/dist/index.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import{toArray as
|
|
1
|
+
import{toArray as co}from"@pengzhanbo/utils";import ft from"node:fs";import Z from"node:fs/promises";import N from"node:path";import{toArray as ee}from"@pengzhanbo/utils";import gt from"fast-glob";import kt from"is-core-module";import{createFilter as ht,normalizePath as yt}from"vite";var ye="vite-plugin-mock-dev-server",ve="1.3.2";import xe,{promises as pe}from"node:fs";import{createRequire as ot}from"node:module";import ae from"node:path";import{pathToFileURL as rt}from"node:url";import{build as nt}from"esbuild";import st from"json5";import ie from"node:fs";import ce from"node:path";import{parse as Ke}from"node:querystring";import{URL as Xe,fileURLToPath as Ye}from"node:url";import Ze from"debug";import{match as et}from"path-to-regexp";var tt=o=>o!==null&&typeof o=="object"&&typeof o.pipe=="function",Me=o=>tt(o)&&o.readable!==!1&&typeof o._read=="function"&&typeof o._readableState=="object";function be(o){return ce.dirname(Ye(o))}var Q=Ze("vite:mock-dev-server");function q(o,t,e){for(let s of t){let n=ce.join(o,s);if(ie.existsSync(n)&&ie.statSync(n).isFile()){let i=e!=null&&e.pathOnly?n:ie.readFileSync(n,"utf-8");if(!(e!=null&&e.predicate)||e.predicate(i))return i}}let r=ce.dirname(o);if(r!==o&&(!(e!=null&&e.rootDir)||r.startsWith(e==null?void 0:e.rootDir)))return q(r,t,e)}var V=(o={})=>{let t=[],e=[];return Object.keys(o).forEach(r=>{var n,i;let s=o[r];typeof s=="string"||!s.ws&&!((n=s.target)!=null&&n.toString().startsWith("ws:"))&&!((i=s.target)!=null&&i.toString().startsWith("wss:"))?t.push(r):e.push(r)}),{httpProxies:t,wsProxies:e}};function I(o,t){return o[0]==="^"&&new RegExp(o).test(t)||t.startsWith(o)}function B(o,t){return(et(o,{decode:decodeURIComponent})(t)||{params:{}}).params||{}}function W(o){let t=new Xe(o,"http://example.com"),e=decodeURIComponent(t.pathname),r=Ke(t.search.replace(/^\?/,""));return{pathname:e,query:r}}var it={name:"externalize-deps",setup(o){o.onResolve({filter:/.*/},({path:t})=>{if(t[0]!=="."&&!ae.isAbsolute(t))return{external:!0}})}},ct={name:"json5-loader",setup(o){o.onLoad({filter:/\.json5$/},async({path:t})=>{let e=await pe.readFile(t,"utf-8");return{contents:`export default ${JSON.stringify(st.parse(e))}`,loader:"js"}})}},at={name:"json-loader",setup(o){o.onLoad({filter:/\.json$/},async({path:t})=>({contents:`export default ${await pe.readFile(t,"utf-8")}`,loader:"js"}))}},pt=o=>({name:"alias-plugin",setup(t){t.onResolve({filter:/.*/},async({path:e})=>{let r=o.find(({find:c})=>lt(c,e));if(!r)return null;let{find:s,replacement:n}=r;return{path:(await t.resolve(e.replace(s,n),{kind:"import-statement",resolveDir:n,namespace:"file"})).path,external:!1}})}});function lt(o,t){return o instanceof RegExp?o.test(t):t.length<o.length?!1:t===o?!0:t.startsWith(`${o}/`)}async function K(o,t){var n;let{isESM:e=!0,define:r,alias:s}=t;try{let i=await nt({entryPoints:[o],outfile:"out.js",write:!1,target:["node14.18","node16"],platform:"node",bundle:!0,metafile:!0,format:e?"esm":"cjs",define:r,plugins:[pt(s),it,at,ct]});return{code:i.outputFiles[0].text,deps:((n=i.metafile)==null?void 0:n.inputs)||{}}}catch(i){console.error(i)}return{code:"",deps:{}}}var ut=be(import.meta.url),T=ot(ut);async function we(o,t,e,r){if(e){let s=`${o}.timestamp-${Date.now()}`,n=`${s}.mjs`,i=`${rt(s)}.mjs`;await pe.writeFile(n,t,"utf8");try{return await import(i)}finally{try{xe.unlinkSync(n)}catch{}}}else{o=ae.resolve(r,o);let s=ae.extname(o),n=xe.realpathSync(o),i=s in T.extensions?s:".js",c=T.extensions[i];T.extensions[i]=(p,m)=>{m===n?p._compile(t,m):c(p,m)},delete T.cache[T.resolve(o)];let a=T(o);return T.extensions[i]=c,a.__esModule?a:{default:a}}}import Oe from"picocolors";import{isBoolean as mt}from"@pengzhanbo/utils";import $ from"picocolors";var Se={silent:0,error:1,warn:2,info:3,debug:4};function X(o,t="info"){o=`[${o}]`;function e(s,n,i){if(i=mt(i)?i?t:"error":i,Se[i]>=Se[s]){let a=s==="info"||s==="debug"?"log":s,p=s==="debug"?$.magenta($.bold(o)):s==="info"?$.cyan($.bold(o)):s==="warn"?$.yellow($.bold(o)):$.red($.bold(o)),m=`${$.dim(new Date().toLocaleTimeString())} ${p} ${n}`;console[a](m)}}return{debug(s,n=t){e("debug",s,n)},info(s,n=t){e("info",s,n)},warn(s,n=t){e("warn",s,n)},error(s,n=t){e("error",s,n)}}}var dt=/import\.meta\.env\.(.+)/;function Y(o){let t=X("vite:mock-dev-server","warn"),e={},r=process.env.NODE_ENV||o.mode;Object.assign(e,{"process.env.NODE_ENV":JSON.stringify(r),"global.process.env.NODE_ENV":JSON.stringify(r),"globalThis.process.env.NODE_ENV":JSON.stringify(r),__vite_process_env_NODE_ENV:JSON.stringify(r)});let s={},n={},i=[];for(let p in o.define){let m=o.define[p];if(typeof m=="string")try{JSON.parse(m),s[p]=m}catch{i.push(p)}else s[p]=JSON.stringify(m);let d=p.match(dt);d&&s[p]&&(n[d[1]]=`__vite__define__${s[p]}`)}i.length&&t.warn(`The following keys: ${Oe.yellow(Oe.underline(i.join(", ")))} declared in 'define' cannot be parsed as regular code snippets.`);let c={},a={};c["import.meta.hot"]="undefined";for(let p in o.env)c[`import.meta.env.${p}`]=JSON.stringify(o.env[p]);return Object.assign(a,{"import.meta.env":JSON.stringify({...o.env,...n}).replace(/"__vite__define__(.+?)"([,}])/g,(p,m,d)=>`${m.replace(/(^\\")|(\\"$)/g,'"')}${d}`)}),{...c,...s,...a,...e}}async function Ce(o,t,e){let r=ee(e.include),s=ee(e.exclude),n=Y(t),{httpProxies:i}=V(t.server.proxy||{});i.push(...ee(e.prefix));let c=ee(e.wsPrefix),a={};try{let l=q(t.root,["package.json"]);l&&(a=JSON.parse(l))}catch{}let p=e.build.dist,m=await xt(process.cwd(),r,s),d=N.join(t.root,`mock-data-${Date.now()}.js`);await Z.writeFile(d,m,"utf-8");let{code:h,deps:y}=await K(d,{define:n,alias:t.resolve.alias}),P=vt(y);await Z.unlink(d);let u=[{filename:N.join(p,"mock-data.js"),source:h},{filename:N.join(p,"index.js"),source:bt(i,c,e.cookiesOptions,e.priority,e.build.serverPort)},{filename:N.join(p,"package.json"),source:Mt(a,P)}];try{if(N.isAbsolute(p)){await Z.rm(p,{recursive:!0}),ft.mkdirSync(p,{recursive:!0});for(let{filename:l,source:f}of u)await Z.writeFile(l,f,"utf-8")}else for(let{filename:l,source:f}of u)o.emitFile({type:"asset",fileName:l,source:f})}catch{}}function vt(o){let t=new Set,e=[ye,"connect","cors"];return Object.keys(o).forEach(r=>{o[r].imports.filter(n=>n.external&&!n.path.startsWith("<define:")).map(n=>n.path).forEach(n=>{!e.includes(n)&&!kt(n)&&t.add(n)})}),Array.from(t)}function Mt(o,t){let{dependencies:e={},devDependencies:r={}}=o,s={...e,...r},n={name:"mock-server",type:"module",scripts:{start:"node index.js"},dependencies:{connect:"^3.7.0","vite-plugin-mock-dev-server":`^${ve}`,cors:"^2.8.5"},pnpm:{peerDependencyRules:{ignoreMissing:["vite"]}}};return t.forEach(i=>{n.dependencies[i]=s[i]||"latest"}),JSON.stringify(n,null,2)}function bt(o,t,e={},r={},s=8080){return`import { createServer } from 'node:http';
|
|
2
2
|
import connect from 'connect';
|
|
3
3
|
import corsMiddleware from 'cors';
|
|
4
4
|
import { baseMiddleware, mockWebSocket } from 'vite-plugin-mock-dev-server';
|
|
@@ -9,6 +9,7 @@ const server = createServer(app);
|
|
|
9
9
|
const httpProxies = ${JSON.stringify(o)};
|
|
10
10
|
const wsProxies = ${JSON.stringify(t)};
|
|
11
11
|
const cookiesOptions = ${JSON.stringify(e)};
|
|
12
|
+
const priority = ${JSON.stringify(r)};
|
|
12
13
|
|
|
13
14
|
mockWebSocket({ mockData }, server, wsProxies, cookiesOptions);
|
|
14
15
|
|
|
@@ -16,13 +17,14 @@ app.use(corsMiddleware());
|
|
|
16
17
|
app.use(baseMiddleware({ mockData }, {
|
|
17
18
|
formidableOptions: { multiples: true },
|
|
18
19
|
proxies: httpProxies,
|
|
20
|
+
priority,
|
|
19
21
|
cookiesOptions,
|
|
20
22
|
}));
|
|
21
23
|
|
|
22
|
-
server.listen(${
|
|
24
|
+
server.listen(${s});
|
|
23
25
|
|
|
24
|
-
console.log('listen: http://localhost:${
|
|
25
|
-
`}async function
|
|
26
|
+
console.log('listen: http://localhost:${s}');
|
|
27
|
+
`}async function xt(o,t,e){let r=await gt(t,{cwd:o}),s=ht(t,e,{resolve:!1}),n=r.filter(s),i="",c="";return n.forEach((a,p)=>{let m=yt(N.join(o,a));i+=`import * as m${p} from '${m}';
|
|
26
28
|
`,c+=`m${p}, `}),`import { transformMockData } from 'vite-plugin-mock-dev-server';
|
|
27
29
|
${i}
|
|
28
30
|
const exporters = [${c}];
|
|
@@ -40,18 +42,19 @@ const mockList = exporters.map((raw) => {
|
|
|
40
42
|
}
|
|
41
43
|
return mockConfig
|
|
42
44
|
});
|
|
43
|
-
export default transformMockData(mockList);`}import{isBoolean as
|
|
44
|
-
${
|
|
45
|
-
|
|
46
|
-
${
|
|
47
|
-
|
|
45
|
+
export default transformMockData(mockList);`}import{isBoolean as ro,toArray as se}from"@pengzhanbo/utils";import no from"cors";import{pathToRegexp as so}from"path-to-regexp";import{Buffer as Ie}from"node:buffer";import{isArray as oe,isEmptyObject as Dt,isFunction as re,random as Et,sleep as Lt,timestamp as He}from"@pengzhanbo/utils";import _t from"cookies";import Tt from"http-status";import*as A from"mime-types";import{pathToRegexp as It}from"path-to-regexp";import k from"picocolors";import{isArray as wt,isEmptyObject as Pe,isString as te,sortBy as je,uniq as Re}from"@pengzhanbo/utils";import{parse as St,pathToRegexp as We}from"path-to-regexp";var le={};function J(o){if(le[o])return le[o];let t=St(o),e=[];for(let r of t)if(!te(r))e.push(r);else{let s=r[0]==="/",n=s?r.slice(1).split("/"):r.split("/");e.push(`${s?"/":""}${n[0]}`,...n.slice(1).map(i=>`/${i}`))}return le[o]=e,e}function Ot(o){let t=o.map(e=>J(e).length);return t=t.length===0?[1]:t,Math.max(...t)+2}function Ct(o){let t=J(o),e=0;for(let r=0;r<t.length;r++){let s=t[r];te(s)||(e+=10**(r+1)),e+=10**(r+1)}return e}function Pt(o){let t=[],e=[];for(let r of o){let n=J(r).filter(i=>typeof i!="string").length;e[n]||(e[n]=[]),e[n].push(r)}for(let r of e.filter(s=>s&&s.length>0))t=[...t,...je(r,Ct)];return t}function Rt(o){let t=Ot(o);return je(o,e=>{let r=J(e),s=r.filter(c=>typeof c!="string");if(s.length===0)return 0;let n=s.length,i=0;for(let c=0;c<r.length;c++){let a=r[c],p=!te(a),{pattern:m="",modifier:d,prefix:h,name:y}=p?a:{},P=m&&m.includes(".*"),u=h==="/",l=te(y);i+=p&&u?1:0,c===r.length-1&&P?n+=5*10**t:P?n+=3*10**(t-1):m&&(u?n+=(l?2:1)*10**(i+1):n-=1*10**i),d==="+"&&(n+=1*10**(t-1)),d==="*"&&(n+=1*10**(t-1)+1),d==="?"&&(n+=1*10**(i+(u?1:0)))}return n})}function $e(o,t,e){let r=Rt(Pt(o.filter(y=>We(y).test(t)))),{global:s=[],special:n={}}=e;if(s.length===0&&Pe(n)||r.length===0)return r;let[i,c]=Wt(r),a=s.filter(y=>c.includes(y));if(a.length>0&&(r=Re([...i,...a,...c])),Pe(n))return r;let p=Object.keys(n).filter(y=>r.includes(y))[0];if(!p)return r;let m=n[p],{rules:d,when:h}=wt(m)?{rules:m,when:[]}:m;return d.includes(r[0])&&(h.length===0||h.some(y=>We(y).test(t)))&&(r=Re([p,...r])),r}function Wt(o){let t=[],e=[];for(let r of o)J(r).filter(i=>typeof i!="string").length>0?e.push(r):t.push(r);return[t,e]}import ue from"co-body";import jt from"formidable";async function De(o,t){var s;let e=o.method.toUpperCase();if(["GET","DELETE","HEAD"].includes(e))return;let r=((s=o.headers["content-type"])==null?void 0:s.toLocaleLowerCase())||"";try{if(r.startsWith("application/json"))return await ue.json(o);if(r.startsWith("application/x-www-form-urlencoded"))return await ue.form(o);if(r.startsWith("text/plain"))return await ue.text(o);if(r.startsWith("multipart/form-data"))return await $t(o,t)}catch(n){console.error(n)}}async function $t(o,t){let e=jt(t);return new Promise((r,s)=>{e.parse(o,(n,i,c)=>{if(n){s(n);return}r({...i,...c})})})}import{isArray as Ee,isObject as Le}from"@pengzhanbo/utils";function _e(o,t){return E(o.headers,t.headers)&&E(o.body,t.body)&&E(o.params,t.params)&&E(o.query,t.query)&&E(o.refererQuery,t.refererQuery)}function E(o,t){if(!t)return!0;for(let e in t)if(!Te(o[e],t[e]))return!1;return!0}function Te(o,t){if(Ee(o)&&Ee(t)){let e=new Set;return t.every(r=>o.some((s,n)=>{if(e.has(n))return!1;let i=Te(s,r);return i&&e.add(n),i}))}return Le(o)&&Le(t)?E(o,t):Object.is(o,t)}function Fe(o,{formidableOptions:t={},proxies:e,cookiesOptions:r,logger:s,priority:n={}}){return async function(i,c,a){let p=He(),{query:m,pathname:d}=W(i.url);if(!d||e.length===0||!e.some(x=>I(x,i.url)))return a();let h=o.mockData,y=$e(Object.keys(h),d,n);if(y.length===0)return a();let{query:P}=W(i.headers.referer||""),u=await De(i,t),l=new _t(i,c,r),f=l.get.bind(l),v=i.method.toUpperCase(),M,C;for(let x of y)if(M=Nt(h[x],s,{pathname:d,method:v,request:{query:m,refererQuery:P,body:u,headers:i.headers,getCookie:f}}),M){C=x;break}if(!M){let x=y.map(U=>U===C?k.underline(k.bold(U)):k.dim(U)).join(", ");return s.warn(`${k.green(d)} matches ${x} , but mock data is not found.`),a()}let g=i,b=c;g.body=u,g.query=m,g.refererQuery=P,g.params=B(M.url,d),g.getCookie=f,b.setCookie=l.set.bind(l);let{body:R,delay:L,type:_="json",response:D,status:j=200,statusText:G,log:F,__filepath__:w}=M;if(me(b,j,G),await Ht(g,b,M,s),await Ft(g,b,M,s),s.info(Bt(g,w),F),s.debug(`${k.magenta("DEBUG")} ${k.underline(d)} matches: [ ${y.map(x=>x===C?k.underline(k.bold(x)):k.dim(x)).join(", ")} ]
|
|
46
|
+
`),R){try{let x=re(R)?await R(g):R;await Ne(p,L),Ut(b,x,_)}catch(x){s.error(`${k.red(`mock error at ${d}`)}
|
|
47
|
+
${x}
|
|
48
|
+
at body (${k.underline(w)})`,F),me(b,500),c.end("")}return}if(D){try{await Ne(p,L),await D(g,b,a)}catch(x){s.error(`${k.red(`mock error at ${d}`)}
|
|
49
|
+
${x}
|
|
50
|
+
at response (${k.underline(w)})`,F),me(b,500),c.end("")}return}c.end("")}}function Nt(o,t,{pathname:e,method:r,request:s}){return o.find(n=>{if(!e||!n||!n.url||n.ws===!0||!(n.method?oe(n.method)?n.method:[n.method]:["GET","POST"]).includes(r))return!1;let c=It(n.url).test(e);if(c&&n.validator){let a=B(n.url,e);if(re(n.validator))return n.validator({params:a,...s});try{return _e({params:a,...s},n.validator)}catch(p){let m=n.__filepath__;return t.error(`${k.red(`mock error at ${e}`)}
|
|
48
51
|
${p}
|
|
49
|
-
at validator (${
|
|
52
|
+
at validator (${k.underline(m)})`,n.log),!1}}return c})}function me(o,t=200,e){o.statusCode=t,o.statusMessage=e||qt(t)}async function Ht(o,t,e,r){let{headers:s,type:n="json"}=e,i=e.__filepath__,c=A.contentType(n)||A.contentType(A.lookup(n)||"");if(c&&t.setHeader("Content-Type",c),t.setHeader("Cache-Control","no-cache,max-age=0"),t.setHeader("X-Mock-Power-By","vite-plugin-mock-dev-server"),t.setHeader("X-File-Path",i),!!s)try{let a=re(s)?await s(o):s;Object.keys(a).forEach(p=>{t.setHeader(p,a[p])})}catch(a){r.error(`${k.red(`mock error at ${o.url.split("?")[0]}`)}
|
|
50
53
|
${a}
|
|
51
|
-
at headers (${
|
|
54
|
+
at headers (${k.underline(i)})`,e.log)}}async function Ft(o,t,e,r){let{cookies:s}=e,n=e.__filepath__;if(s)try{let i=re(s)?await s(o):s;Object.keys(i).forEach(c=>{let a=i[c];if(oe(a)){let[p,m]=a;t.setCookie(c,p,m)}else t.setCookie(c,a)})}catch(i){r.error(`${k.red(`mock error at ${o.url.split("?")[0]}`)}
|
|
52
55
|
${i}
|
|
53
|
-
at cookies (${
|
|
54
|
-
${
|
|
55
|
-
at setup (${
|
|
56
|
-
${
|
|
57
|
-
at setup (${
|
|
56
|
+
at cookies (${k.underline(n)})`,e.log)}}function Ut(o,t,e){if(Me(t))t.pipe(o);else if(Ie.isBuffer(t))o.end(e==="text"||e==="json"?t.toString("utf-8"):t);else{let r=typeof t=="string"?t:JSON.stringify(t);o.end(e==="buffer"?Ie.from(r):r)}}async function Ne(o,t){if(!t||typeof t=="number"&&t<=0||oe(t)&&t.length!==2)return;let e=0;if(oe(t)){let[r,s]=t;e=Et(r,s)}else e=t-(He()-o);e>0&&await Lt(e)}function qt(o){return Tt[o]||"Unknown"}function Bt(o,t){let{url:e,method:r,query:s,params:n,body:i}=o,{pathname:c}=new URL(e,"http://example.com");c=k.green(decodeURIComponent(c));let a=(P,u)=>!u||Dt(u)?"":` ${k.gray(`${P}:`)}${JSON.stringify(u)}`,p=k.magenta(k.bold(r)),m=a("query",s),d=a("params",n),h=a("body",i),y=` ${k.dim(k.underline(`(${t})`))}`;return`${p} ${c}${m}${d}${h}${y}`}import Qt from"node:events";import{hasOwn as Vt,isArray as Kt,promiseParallel as Xt,toArray as Yt}from"@pengzhanbo/utils";import Je from"chokidar";import Zt from"fast-glob";import{createFilter as eo,normalizePath as z}from"vite";import{isArray as Jt,isEmptyObject as Ue,isFunction as qe,isObject as At,sortBy as zt}from"@pengzhanbo/utils";function Be(o){let t=[];for(let[,r]of o.entries())r&&(Jt(r)?t.push(...r):t.push(r));let e={};return t.filter(r=>At(r)&&r.enabled!==!1&&r.url).forEach(r=>{let{pathname:s,query:n}=W(r.url),i=e[s]??=[],c={...r,url:s};if(c.ws!==!0){let a=c.validator;Ue(n)||(qe(a)?c.validator=function(p){return E(p.query,n)&&a(p)}:a?(c.validator={...a},c.validator.query=c.validator.query?{...n,...c.validator.query}:n):c.validator={query:n})}i.push(c)}),Object.keys(e).forEach(r=>{e[r]=zt(e[r],s=>{if(s.ws===!0)return 0;let{validator:n}=s;return!n||Ue(n)?2:qe(n)?0:1/Object.keys(n).reduce((c,a)=>c+Gt(n[a]),0)})}),e}function Gt(o){return o?Object.keys(o).length:0}var ne=class extends Qt{constructor(e){super();this.options=e;this.cwd=e.cwd||process.cwd();try{let r=q(this.cwd,["package.json"]);this.moduleType=r&&JSON.parse(r).type==="module"?"esm":"cjs"}catch{}}moduleCache=new Map;moduleDeps=new Map;cwd;mockWatcher;depsWatcher;moduleType="cjs";_mockData={};get mockData(){return this._mockData}load(){let{include:e,exclude:r}=this.options,s=eo(e,r,{resolve:!1});Zt(e,{cwd:this.cwd}).then(i=>i.filter(s).map(c=>()=>this.loadMock(c))).then(i=>Xt(i,10)).then(()=>this.updateMockList()),this.watchMockEntry(),this.watchDeps();let n=null;this.on("mock:update",async i=>{s(i)&&(await this.loadMock(i),n&&clearImmediate(n),n=setImmediate(()=>{this.updateMockList(),this.emit("mock:update-end",i),n=null}))}),this.on("mock:unlink",async i=>{s(i)&&(this.moduleCache.delete(i),this.updateMockList(),this.emit("mock:update-end",i))})}watchMockEntry(){let{include:e}=this.options,[r,...s]=e,n=this.mockWatcher=Je.watch(r,{ignoreInitial:!0,cwd:this.cwd});s.length>0&&s.forEach(i=>n.add(i)),n.on("add",async i=>{i=z(i),this.emit("mock:update",i),Q("watcher:add",i)}),n.on("change",async i=>{i=z(i),this.emit("mock:update",i),Q("watcher:change",i)}),n.on("unlink",async i=>{i=z(i),this.emit("mock:unlink",i),Q("watcher:unlink",i)})}watchDeps(){let e=[];this.depsWatcher=Je.watch([],{ignoreInitial:!0,cwd:this.cwd}),this.depsWatcher.on("change",r=>{r=z(r);let s=this.moduleDeps.get(r);s&&s.forEach(n=>{this.emit("mock:update",n)})}),this.depsWatcher.on("unlink",r=>{r=z(r),this.moduleDeps.delete(r)}),this.on("update:deps",()=>{let r=[];for(let[n]of this.moduleDeps.entries())r.push(n);let s=r.filter(n=>!e.includes(n));s.length>0&&this.depsWatcher.add(s)})}close(){var e,r;(e=this.mockWatcher)==null||e.close(),(r=this.depsWatcher)==null||r.close()}updateMockList(){this._mockData=Be(this.moduleCache)}updateModuleDeps(e,r){Object.keys(r).forEach(s=>{r[s].imports.map(i=>i.path).forEach(i=>{this.moduleDeps.has(i)||this.moduleDeps.set(i,new Set),this.moduleDeps.get(i).add(e)})}),this.emit("update:deps")}async loadMock(e){if(!e)return;let r=!1;/\.m[jt]s$/.test(e)?r=!0:/\.c[jt]s$/.test(e)?r=!1:r=this.moduleType==="esm";let{define:s,alias:n}=this.options,{code:i,deps:c}=await K(e,{isESM:r,define:s,alias:n});try{let a=await we(e,i,r,this.cwd)||{},p;Vt(a,"default")?p=a.default:(p=[],Object.keys(a).forEach(m=>p.push(...Yt(a[m])))),Kt(p)?p.forEach(m=>m.__filepath__=e):p.__filepath__=e,this.moduleCache.set(e,p),this.updateModuleDeps(e,c)}catch(a){console.error(a)}}};import to from"cookies";import{pathToRegexp as Ae}from"path-to-regexp";import H from"picocolors";import{WebSocketServer as oo}from"ws";function Ge({loader:o,httpServer:t,proxies:e,cookiesOptions:r,logger:s}){var P;let n=new Map,i=new Map,c=new WeakMap,a=u=>{let l=i.get(u);return!l&&i.set(u,l=new Map),l},p=(u,l)=>{let f=u.get(l);return!f&&u.set(l,f=new oo({noServer:!0})),f},m=(u,l)=>{let f=n.get(u);!f&&n.set(u,f=new Set),f.add(l)},d=(u,l,f,v,M,C)=>{var g;try{(g=f.setup)==null||g.call(f,l,v),l.on("close",()=>u.delete(M)),l.on("error",b=>{s.error(`${H.red(`WebSocket mock error at ${l.path}`)}
|
|
57
|
+
${b}
|
|
58
|
+
at setup (${C})`,f.log)})}catch(b){s.error(`${H.red(`WebSocket mock error at ${l.path}`)}
|
|
59
|
+
${b}
|
|
60
|
+
at setup (${C})`,f.log)}},h=(u,l,f,v)=>{u.emit("connection",l,f),l.on("close",()=>{let M=v.findIndex(C=>C.ws===l);M!==-1&&v.splice(M,1)})},y=(u,l,f,v,M)=>{let{cleanupList:C,connectionList:g,context:b}=c.get(l);ze(C),g.forEach(({ws:R})=>R.removeAllListeners()),l.removeAllListeners(),d(u,l,f,b,v,M),g.forEach(({ws:R,req:L})=>h(l,R,L,g))};(P=o.on)==null||P.call(o,"mock:update-end",u=>{if(!n.has(u))return;let l=n.get(u);if(l)for(let f of l.values())for(let v of o.mockData[f]){if(!v.ws||v.__filepath__!==u)return;let M=a(f);for(let[C,g]of M.entries())y(M,g,v,C,u)}}),t==null||t.on("upgrade",(u,l,f)=>{let{pathname:v,query:M}=W(u.url);if(!v||e.length===0||!e.some(w=>I(w,u.url)))return;let C=o.mockData,g=Object.keys(C).find(w=>Ae(w).test(v));if(!g)return;let b=C[g].find(w=>w.url&&w.ws&&Ae(w.url).test(v));if(!b)return;let R=b.__filepath__;m(R,g);let L=a(g),_=p(L,v),D=c.get(_);if(!D){let w=[],x={onCleanup:U=>w.push(U)};D={cleanupList:w,context:x,connectionList:[]},c.set(_,D),d(L,_,b,x,v,R)}let j=u,G=new to(u,u,r),{query:F}=W(u.headers.referer||"");j.query=M,j.refererQuery=F,j.params=B(g,v),j.getCookie=G.get.bind(G),_.handleUpgrade(j,l,f,w=>{s.info(`${H.magenta(H.bold("WebSocket"))} ${H.green(u.url)} connected ${H.dim(`(${R})`)}`,b.log),D.connectionList.push({req:j,ws:w}),h(_,w,j,D.connectionList)})}),t==null||t.on("close",()=>{for(let u of i.values()){for(let l of u.values()){let f=c.get(l);ze(f.cleanupList),l.close()}u.clear()}i.clear(),n.clear()})}function ze(o){let t;for(;t=o.shift();)t==null||t()}function de(o,t,e,r){let s=X("vite:mock",ro(t.log)?t.log?"info":"error":t.log),n=new ne({include:se(t.include),exclude:se(t.exclude),define:Y(o),alias:o.resolve.alias});n.load(),n.on("mock:update-end",()=>{t.reload&&(r==null||r.send({type:"full-reload"}))}),e==null||e.on("close",()=>n.close());let{httpProxies:i}=V(o.server.proxy||{}),a=[...se(t.prefix),...i];Ge({loader:n,httpServer:e,proxies:se(t.wsPrefix),cookiesOptions:t.cookiesOptions,logger:s});let p=[];return p.push(io(n,a,o,t),Fe(n,{formidableOptions:t.formidableOptions,proxies:a,cookiesOptions:t.cookiesOptions,priority:t.priority,logger:s})),p.filter(Boolean)}function io(o,t,e,r){let s={},n=r.cors===!1?!1:e.server.cors!==!1;return n&&e.server.cors!==!1&&(s={...s,...typeof e.server.cors=="boolean"?{}:e.server.cors}),n&&r.cors!==!1&&(s={...s,...typeof r.cors=="boolean"?{}:r.cors}),n?function(i,c,a){let{pathname:p}=W(i.url);if(!p||t.length===0||!t.some(h=>I(h,i.url)))return a();let m=o.mockData;if(!Object.keys(m).find(h=>so(h).test(p)))return a();no(s)(i,c,a)}:void 0}function Qe({prefix:o=[],wsPrefix:t=[],include:e=["mock/**/*.mock.{js,ts,cjs,mjs,json,json5}"],exclude:r=["**/node_modules/**","**/.vscode/**","**/.git/**"],reload:s=!1,log:n="info",cors:i=!0,formidableOptions:c={},build:a=!1,cookiesOptions:p={},priority:m={}}={}){let d={prefix:o,wsPrefix:t,include:e,exclude:r,reload:s,cors:i,cookiesOptions:p,log:n,formidableOptions:{multiples:!0,...c},priority:m,build:a?Object.assign({serverPort:8080,dist:"mockServer"},typeof a=="object"?a:{}):!1},h=[po(d)];return d.build&&h.push(ao(d)),h}function ao(o){let t={};return{name:"vite-plugin-mock-dev-server-generator",enforce:"post",apply:"build",configResolved(e){t=e,e.logger.warn("")},async buildEnd(e){e||t.command==="build"&&await Ce(this,t,o)}}}function po(o){let t={};return{name:"vite-plugin-mock-dev-server",enforce:"pre",apply:"serve",config(e){var n;let r=co(o.wsPrefix);if(r.length===0||!((n=e.server)!=null&&n.proxy)||Object.keys(e.server.proxy).length===0)return;let s={};Object.keys(e.server.proxy).forEach(i=>{r.includes(i)||(s[i]=e.server.proxy[i])}),e.server.proxy=s},configResolved(e){t=e,e.logger.warn("")},configureServer({middlewares:e,config:r,httpServer:s,ws:n}){de(r,o,s,n).forEach(c=>e.use(c))},configurePreviewServer({middlewares:e,httpServer:r}){de(t,o,r).forEach(n=>e.use(n))}}}import{isArray as lo}from"@pengzhanbo/utils";function pn(o){return o}function ln(o){return e=>(lo(e)?e=e.map(r=>o(r)||r):e=o(e)||e,e)}import{deepClone as Ve,deepEqual as uo,isFunction as mo}from"@pengzhanbo/utils";var fe=new Map,ge=new WeakMap,fo=70,ke=class{value;#e;#t;constructor(t){this.value=t,this.#e=Ve(t),this.#t=Date.now()}hotUpdate(t){Date.now()-this.#t<fo||uo(t,this.#e)||(this.value=t,this.#e=Ve(t),this.#t=Date.now())}};function fn(o,t){fe.has(o)||fe.set(o,new ke(t));let e=fe.get(o);if(e.hotUpdate(t),ge.has(e))return ge.get(e);let r=[()=>e.value,s=>{mo(s)&&(s=s(e.value)??e.value),e.value=s}];return Object.defineProperty(r,"value",{get(){return e.value},set(s){e.value=s}}),ge.set(e,r),r}var yn=Qe;export{Fe as baseMiddleware,ln as createDefineMock,yn as default,pn as defineMock,fn as defineMockData,Qe as mockDevServerPlugin,Ge as mockWebSocket,Be as transformMockData};
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "vite-plugin-mock-dev-server",
|
|
3
|
-
"version": "1.3.
|
|
3
|
+
"version": "1.3.2",
|
|
4
4
|
"keywords": [
|
|
5
5
|
"vite",
|
|
6
6
|
"plugin",
|
|
@@ -44,11 +44,11 @@
|
|
|
44
44
|
"cookies": "^0.8.0",
|
|
45
45
|
"cors": "^2.8.5",
|
|
46
46
|
"debug": "^4.3.4",
|
|
47
|
-
"esbuild": "^0.
|
|
47
|
+
"esbuild": "^0.19.2",
|
|
48
48
|
"fast-glob": "^3.3.1",
|
|
49
49
|
"formidable": "2.1.1",
|
|
50
50
|
"http-status": "^1.6.2",
|
|
51
|
-
"is-core-module": "^2.
|
|
51
|
+
"is-core-module": "^2.13.0",
|
|
52
52
|
"json5": "^2.2.3",
|
|
53
53
|
"mime-types": "^2.1.35",
|
|
54
54
|
"path-to-regexp": "^6.2.1",
|
|
@@ -56,8 +56,8 @@
|
|
|
56
56
|
"ws": "^8.13.0"
|
|
57
57
|
},
|
|
58
58
|
"devDependencies": {
|
|
59
|
-
"@pengzhanbo/eslint-config": "^0.4.
|
|
60
|
-
"@pengzhanbo/prettier-config": "^0.4.
|
|
59
|
+
"@pengzhanbo/eslint-config": "^0.4.2",
|
|
60
|
+
"@pengzhanbo/prettier-config": "^0.4.2",
|
|
61
61
|
"@types/co-body": "^6.1.0",
|
|
62
62
|
"@types/cookies": "^0.7.7",
|
|
63
63
|
"@types/cors": "^2.8.13",
|
|
@@ -67,15 +67,15 @@
|
|
|
67
67
|
"@types/mime-types": "^2.1.1",
|
|
68
68
|
"@types/node": "^20.4.3",
|
|
69
69
|
"@types/ws": "^8.5.5",
|
|
70
|
-
"bumpp": "^9.
|
|
70
|
+
"bumpp": "^9.2.0",
|
|
71
71
|
"conventional-changelog-cli": "^3.0.0",
|
|
72
|
-
"eslint": "^8.
|
|
72
|
+
"eslint": "^8.48.0",
|
|
73
73
|
"mockjs": "^1.1.0",
|
|
74
|
-
"prettier": "^3.0.
|
|
75
|
-
"tsup": "^7.
|
|
76
|
-
"typescript": "^5.
|
|
77
|
-
"vite": "^4.4.
|
|
78
|
-
"vitepress": "1.0.0-
|
|
74
|
+
"prettier": "^3.0.2",
|
|
75
|
+
"tsup": "^7.2.0",
|
|
76
|
+
"typescript": "^5.2.2",
|
|
77
|
+
"vite": "^4.4.9",
|
|
78
|
+
"vitepress": "^1.0.0-rc.4"
|
|
79
79
|
},
|
|
80
80
|
"peerDependencies": {
|
|
81
81
|
"vite": ">=3.0.0"
|