@dangao/bun-server 1.8.0 → 1.8.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/docs/api.md +194 -81
- package/docs/extensions.md +53 -0
- package/docs/guide.md +243 -1
- package/docs/microservice-config-center.md +73 -74
- package/docs/microservice-nacos.md +89 -90
- package/docs/microservice-service-registry.md +85 -86
- package/docs/microservice.md +142 -137
- package/docs/request-lifecycle.md +45 -4
- package/docs/symbol-interface-pattern.md +106 -106
- package/docs/zh/api.md +458 -18
- package/docs/zh/extensions.md +53 -0
- package/docs/zh/guide.md +251 -4
- package/docs/zh/microservice-config-center.md +258 -0
- package/docs/zh/microservice-nacos.md +346 -0
- package/docs/zh/microservice-service-registry.md +306 -0
- package/docs/zh/microservice.md +680 -0
- package/docs/zh/request-lifecycle.md +43 -5
- package/package.json +1 -1
- package/tests/auth/auth-decorators.test.ts +241 -0
- package/tests/auth/oauth2-service.test.ts +318 -0
- package/tests/cache/cache-decorators-extended.test.ts +272 -0
- package/tests/cache/cache-interceptors.test.ts +534 -0
- package/tests/cache/cache-service-proxy.test.ts +246 -0
- package/tests/cache/memory-cache-store.test.ts +155 -0
- package/tests/cache/redis-cache-store.test.ts +199 -0
- package/tests/config/config-center-integration.test.ts +334 -0
- package/tests/config/config-module-extended.test.ts +165 -0
- package/tests/controller/param-binder.test.ts +333 -0
- package/tests/error/error-handler.test.ts +166 -57
- package/tests/error/i18n-extended.test.ts +105 -0
- package/tests/events/event-listener-scanner.test.ts +114 -0
- package/tests/events/event-module.test.ts +133 -302
- package/tests/extensions/logger-module.test.ts +158 -0
- package/tests/files/file-storage.test.ts +136 -0
- package/tests/interceptor/base-interceptor.test.ts +605 -0
- package/tests/interceptor/builtin/cache-interceptor.test.ts +233 -86
- package/tests/interceptor/builtin/log-interceptor.test.ts +469 -0
- package/tests/interceptor/builtin/permission-interceptor.test.ts +219 -120
- package/tests/interceptor/interceptor-chain.test.ts +241 -189
- package/tests/interceptor/interceptor-metadata.test.ts +221 -0
- package/tests/microservice/circuit-breaker.test.ts +221 -0
- package/tests/microservice/service-client-decorators.test.ts +86 -0
- package/tests/microservice/service-client-interceptors.test.ts +274 -0
- package/tests/microservice/service-registry-decorators.test.ts +147 -0
- package/tests/microservice/tracer.test.ts +213 -0
- package/tests/microservice/tracing-collectors.test.ts +168 -0
- package/tests/middleware/builtin/middleware-builtin-extended.test.ts +237 -0
- package/tests/middleware/builtin/rate-limit.test.ts +257 -0
- package/tests/middleware/middleware-decorators.test.ts +222 -0
- package/tests/middleware/middleware-pipeline.test.ts +160 -0
- package/tests/queue/queue-decorators.test.ts +139 -0
- package/tests/queue/queue-service.test.ts +191 -0
- package/tests/request/body-parser-extended.test.ts +291 -0
- package/tests/request/request-wrapper.test.ts +319 -0
- package/tests/router/router-decorators.test.ts +260 -0
- package/tests/router/router-extended.test.ts +298 -0
- package/tests/security/guards/reflector.test.ts +188 -0
- package/tests/security/security-filter.test.ts +182 -0
- package/tests/security/security-module-extended.test.ts +133 -0
- package/tests/session/memory-session-store.test.ts +172 -0
- package/tests/session/session-decorators.test.ts +163 -0
- package/tests/swagger/ui.test.ts +212 -0
package/docs/zh/guide.md
CHANGED
|
@@ -25,6 +25,50 @@ app.listen();
|
|
|
25
25
|
> Tip: 默认端口为 3000,可通过 `app.listen(customPort)` 或
|
|
26
26
|
> `new Application({ port })` 调整。
|
|
27
27
|
|
|
28
|
+
### 使用 BunServer(底层 API)
|
|
29
|
+
|
|
30
|
+
对于高级用例,您可以直接使用 `BunServer`:
|
|
31
|
+
|
|
32
|
+
```ts
|
|
33
|
+
import { BunServer } from "@dangao/bun-server";
|
|
34
|
+
|
|
35
|
+
const server = new BunServer({
|
|
36
|
+
port: 3000,
|
|
37
|
+
fetch: async (request) => {
|
|
38
|
+
// 自定义请求处理
|
|
39
|
+
return new Response("Hello World");
|
|
40
|
+
},
|
|
41
|
+
});
|
|
42
|
+
|
|
43
|
+
server.listen();
|
|
44
|
+
```
|
|
45
|
+
|
|
46
|
+
### 在服务中访问请求上下文
|
|
47
|
+
|
|
48
|
+
使用 `ContextService` 在服务中访问当前请求上下文:
|
|
49
|
+
|
|
50
|
+
```ts
|
|
51
|
+
import {
|
|
52
|
+
ContextService,
|
|
53
|
+
CONTEXT_SERVICE_TOKEN,
|
|
54
|
+
Inject,
|
|
55
|
+
Injectable,
|
|
56
|
+
} from "@dangao/bun-server";
|
|
57
|
+
|
|
58
|
+
@Injectable()
|
|
59
|
+
class UserService {
|
|
60
|
+
public constructor(
|
|
61
|
+
@Inject(CONTEXT_SERVICE_TOKEN) private readonly contextService: ContextService,
|
|
62
|
+
) {}
|
|
63
|
+
|
|
64
|
+
public getCurrentUser() {
|
|
65
|
+
const ctx = this.contextService.getContext();
|
|
66
|
+
const userId = ctx.getHeader("x-user-id");
|
|
67
|
+
return { userId };
|
|
68
|
+
}
|
|
69
|
+
}
|
|
70
|
+
```
|
|
71
|
+
|
|
28
72
|
## 2. 注册控制器与依赖
|
|
29
73
|
|
|
30
74
|
```ts
|
|
@@ -71,14 +115,81 @@ app.registerController(UserController);
|
|
|
71
115
|
app.listen();
|
|
72
116
|
```
|
|
73
117
|
|
|
118
|
+
### 高级参数绑定
|
|
119
|
+
|
|
120
|
+
Bun Server 支持高级参数绑定装饰器:
|
|
121
|
+
|
|
122
|
+
```ts
|
|
123
|
+
import {
|
|
124
|
+
Body,
|
|
125
|
+
Context,
|
|
126
|
+
Controller,
|
|
127
|
+
GET,
|
|
128
|
+
Header,
|
|
129
|
+
HeaderMap,
|
|
130
|
+
Param,
|
|
131
|
+
Query,
|
|
132
|
+
QueryMap,
|
|
133
|
+
} from "@dangao/bun-server";
|
|
134
|
+
|
|
135
|
+
@Controller("/api/users")
|
|
136
|
+
class UserController {
|
|
137
|
+
// 获取单个查询参数
|
|
138
|
+
@GET("/search")
|
|
139
|
+
public search(@Query("q") query: string) {
|
|
140
|
+
return { query };
|
|
141
|
+
}
|
|
142
|
+
|
|
143
|
+
// 获取所有查询参数作为对象
|
|
144
|
+
@GET("/filter")
|
|
145
|
+
public filter(@QueryMap() params: Record<string, string>) {
|
|
146
|
+
return { filters: params };
|
|
147
|
+
}
|
|
148
|
+
|
|
149
|
+
// 获取单个请求头
|
|
150
|
+
@GET("/profile")
|
|
151
|
+
public getProfile(@Header("authorization") token: string) {
|
|
152
|
+
return { token };
|
|
153
|
+
}
|
|
154
|
+
|
|
155
|
+
// 获取所有请求头作为对象
|
|
156
|
+
@GET("/headers")
|
|
157
|
+
public getHeaders(@HeaderMap() headers: Record<string, string>) {
|
|
158
|
+
return { headers };
|
|
159
|
+
}
|
|
160
|
+
|
|
161
|
+
// 获取完整的上下文对象
|
|
162
|
+
@GET("/context")
|
|
163
|
+
public getContext(@Context() ctx: Context) {
|
|
164
|
+
return {
|
|
165
|
+
method: ctx.getMethod(),
|
|
166
|
+
path: ctx.getPath(),
|
|
167
|
+
query: ctx.getQuery(),
|
|
168
|
+
};
|
|
169
|
+
}
|
|
170
|
+
}
|
|
171
|
+
```
|
|
172
|
+
|
|
74
173
|
## 3. 使用中间件
|
|
75
174
|
|
|
76
175
|
```ts
|
|
77
|
-
import {
|
|
176
|
+
import {
|
|
177
|
+
createCorsMiddleware,
|
|
178
|
+
createLoggerMiddleware,
|
|
179
|
+
createRateLimitMiddleware,
|
|
180
|
+
} from "@dangao/bun-server";
|
|
78
181
|
|
|
79
182
|
const app = new Application();
|
|
80
183
|
app.use(createLoggerMiddleware({ prefix: "[Example]" }));
|
|
81
184
|
app.use(createCorsMiddleware({ origin: "*" }));
|
|
185
|
+
|
|
186
|
+
// 限流中间件
|
|
187
|
+
app.use(
|
|
188
|
+
createRateLimitMiddleware({
|
|
189
|
+
windowMs: 60000, // 1 分钟
|
|
190
|
+
max: 100, // 每个窗口 100 个请求
|
|
191
|
+
}),
|
|
192
|
+
);
|
|
82
193
|
```
|
|
83
194
|
|
|
84
195
|
`@UseMiddleware()` 可作用于单个控制器或方法:
|
|
@@ -99,6 +210,29 @@ const auth = async (ctx, next) => {
|
|
|
99
210
|
class SecureController { ... }
|
|
100
211
|
```
|
|
101
212
|
|
|
213
|
+
### 限流装饰器
|
|
214
|
+
|
|
215
|
+
您也可以在控制器或方法上使用 `@RateLimit()` 装饰器:
|
|
216
|
+
|
|
217
|
+
```ts
|
|
218
|
+
import { Controller, GET, RateLimit } from "@dangao/bun-server";
|
|
219
|
+
|
|
220
|
+
@Controller("/api")
|
|
221
|
+
@RateLimit({ windowMs: 60000, max: 10 }) // 应用于所有方法
|
|
222
|
+
class ApiController {
|
|
223
|
+
@GET("/public")
|
|
224
|
+
public publicEndpoint() {
|
|
225
|
+
return { message: "Public" };
|
|
226
|
+
}
|
|
227
|
+
|
|
228
|
+
@GET("/limited")
|
|
229
|
+
@RateLimit({ windowMs: 60000, max: 5 }) // 覆盖控制器限制
|
|
230
|
+
public limitedEndpoint() {
|
|
231
|
+
return { message: "Limited" };
|
|
232
|
+
}
|
|
233
|
+
}
|
|
234
|
+
```
|
|
235
|
+
|
|
102
236
|
## 4. 参数验证
|
|
103
237
|
|
|
104
238
|
```ts
|
|
@@ -140,15 +274,34 @@ app.listen();
|
|
|
140
274
|
import {
|
|
141
275
|
createFileUploadMiddleware,
|
|
142
276
|
createStaticFileMiddleware,
|
|
277
|
+
FileStorage,
|
|
278
|
+
Inject,
|
|
279
|
+
Injectable,
|
|
143
280
|
} from "@dangao/bun-server";
|
|
144
281
|
|
|
145
282
|
const app = new Application({ port: 3000 });
|
|
146
283
|
|
|
147
|
-
//
|
|
284
|
+
// 文件上传
|
|
148
285
|
app.use(createFileUploadMiddleware({ maxSize: 5 * 1024 * 1024 }));
|
|
149
286
|
|
|
150
|
-
//
|
|
287
|
+
// 静态文件
|
|
151
288
|
app.use(createStaticFileMiddleware({ root: "./public", prefix: "/assets" }));
|
|
289
|
+
|
|
290
|
+
// 使用 FileStorage 服务
|
|
291
|
+
@Injectable()
|
|
292
|
+
class FileService {
|
|
293
|
+
public constructor(
|
|
294
|
+
@Inject(FileStorage) private readonly fileStorage: FileStorage,
|
|
295
|
+
) {}
|
|
296
|
+
|
|
297
|
+
public async saveFile(file: File): Promise<string> {
|
|
298
|
+
const path = await this.fileStorage.save(file, {
|
|
299
|
+
directory: "./uploads",
|
|
300
|
+
filename: `file-${Date.now()}`,
|
|
301
|
+
});
|
|
302
|
+
return path;
|
|
303
|
+
}
|
|
304
|
+
}
|
|
152
305
|
```
|
|
153
306
|
|
|
154
307
|
上传后的文件可在 `context.body.files` 中读取;静态资源请求会自动设置
|
|
@@ -665,7 +818,101 @@ class AppService {
|
|
|
665
818
|
}
|
|
666
819
|
```
|
|
667
820
|
|
|
668
|
-
## 12.
|
|
821
|
+
## 12. 微服务支持
|
|
822
|
+
|
|
823
|
+
Bun Server 提供了完整的微服务架构支持,包括配置中心、服务注册与发现、服务调用、服务治理和可观测性等功能。
|
|
824
|
+
|
|
825
|
+
### 配置中心
|
|
826
|
+
|
|
827
|
+
```ts
|
|
828
|
+
import {
|
|
829
|
+
ConfigCenterModule,
|
|
830
|
+
CONFIG_CENTER_TOKEN,
|
|
831
|
+
Inject,
|
|
832
|
+
Injectable,
|
|
833
|
+
} from "@dangao/bun-server";
|
|
834
|
+
import type { ConfigCenter } from "@dangao/bun-server";
|
|
835
|
+
|
|
836
|
+
ConfigCenterModule.forRoot({
|
|
837
|
+
provider: "nacos",
|
|
838
|
+
nacos: {
|
|
839
|
+
client: {
|
|
840
|
+
serverList: ["http://localhost:8848"],
|
|
841
|
+
namespace: "public",
|
|
842
|
+
},
|
|
843
|
+
},
|
|
844
|
+
});
|
|
845
|
+
|
|
846
|
+
@Injectable()
|
|
847
|
+
class ConfigService {
|
|
848
|
+
public constructor(
|
|
849
|
+
@Inject(CONFIG_CENTER_TOKEN) private readonly configCenter: ConfigCenter,
|
|
850
|
+
) {}
|
|
851
|
+
|
|
852
|
+
public async getConfig() {
|
|
853
|
+
const config = await this.configCenter.getConfig(
|
|
854
|
+
"my-config",
|
|
855
|
+
"DEFAULT_GROUP",
|
|
856
|
+
);
|
|
857
|
+
return JSON.parse(config.content);
|
|
858
|
+
}
|
|
859
|
+
}
|
|
860
|
+
```
|
|
861
|
+
|
|
862
|
+
### 服务注册中心
|
|
863
|
+
|
|
864
|
+
```ts
|
|
865
|
+
import {
|
|
866
|
+
RegisterService,
|
|
867
|
+
ServiceRegistryModule,
|
|
868
|
+
} from "@dangao/bun-server";
|
|
869
|
+
|
|
870
|
+
ServiceRegistryModule.forRoot({
|
|
871
|
+
provider: "nacos",
|
|
872
|
+
nacos: {
|
|
873
|
+
client: {
|
|
874
|
+
serverList: ["http://localhost:8848"],
|
|
875
|
+
},
|
|
876
|
+
},
|
|
877
|
+
});
|
|
878
|
+
|
|
879
|
+
@Injectable()
|
|
880
|
+
class MyService {
|
|
881
|
+
@RegisterService({
|
|
882
|
+
serviceName: "my-service",
|
|
883
|
+
ip: "127.0.0.1",
|
|
884
|
+
port: 3000,
|
|
885
|
+
})
|
|
886
|
+
public start() {
|
|
887
|
+
// 服务已注册
|
|
888
|
+
}
|
|
889
|
+
}
|
|
890
|
+
```
|
|
891
|
+
|
|
892
|
+
### 服务客户端
|
|
893
|
+
|
|
894
|
+
```ts
|
|
895
|
+
import {
|
|
896
|
+
ServiceClient,
|
|
897
|
+
ServiceCall,
|
|
898
|
+
Injectable,
|
|
899
|
+
} from "@dangao/bun-server";
|
|
900
|
+
|
|
901
|
+
@Injectable()
|
|
902
|
+
class OrderService {
|
|
903
|
+
@ServiceClient("user-service")
|
|
904
|
+
private readonly userClient!: ServiceClient;
|
|
905
|
+
|
|
906
|
+
@ServiceCall("GET", "/users/:id")
|
|
907
|
+
public async getUser(id: string) {
|
|
908
|
+
return await this.userClient.call("GET", `/users/${id}`);
|
|
909
|
+
}
|
|
910
|
+
}
|
|
911
|
+
```
|
|
912
|
+
|
|
913
|
+
详细文档请参阅 [微服务架构](./microservice.md)。
|
|
914
|
+
|
|
915
|
+
## 13. 测试建议
|
|
669
916
|
|
|
670
917
|
- 使用 `tests/utils/test-port.ts` 获取自增端口,避免本地冲突。
|
|
671
918
|
- 在 `afterEach` 钩子中调用 `RouteRegistry.getInstance().clear()` 和
|
|
@@ -0,0 +1,258 @@
|
|
|
1
|
+
# 配置中心使用指南
|
|
2
|
+
|
|
3
|
+
本文档介绍如何使用 Bun Server Framework 的配置中心功能。
|
|
4
|
+
|
|
5
|
+
## 目录
|
|
6
|
+
|
|
7
|
+
- [概述](#概述)
|
|
8
|
+
- [快速开始](#快速开始)
|
|
9
|
+
- [基本使用](#基本使用)
|
|
10
|
+
- [配置热更新](#配置热更新)
|
|
11
|
+
- [ConfigModule 集成](#configmodule-集成)
|
|
12
|
+
- [装饰器使用](#装饰器使用)
|
|
13
|
+
- [最佳实践](#最佳实践)
|
|
14
|
+
|
|
15
|
+
## 概述
|
|
16
|
+
|
|
17
|
+
配置中心提供了集中式配置管理能力,支持:
|
|
18
|
+
|
|
19
|
+
- **动态配置**:从配置中心获取配置,支持配置热更新
|
|
20
|
+
- **多环境支持**:通过命名空间和分组管理不同环境的配置
|
|
21
|
+
- **配置优先级**:配置中心配置 > 环境变量 > 默认配置
|
|
22
|
+
- **配置监听**:监听配置变更,自动刷新应用配置
|
|
23
|
+
|
|
24
|
+
## 快速开始
|
|
25
|
+
|
|
26
|
+
### 1. 注册配置中心模块
|
|
27
|
+
|
|
28
|
+
```typescript
|
|
29
|
+
import { Application } from '@dangao/bun-server';
|
|
30
|
+
import { ConfigCenterModule } from '@dangao/bun-server';
|
|
31
|
+
|
|
32
|
+
const app = new Application();
|
|
33
|
+
|
|
34
|
+
app.registerModule(
|
|
35
|
+
ConfigCenterModule.forRoot({
|
|
36
|
+
provider: 'nacos',
|
|
37
|
+
nacos: {
|
|
38
|
+
client: {
|
|
39
|
+
serverList: ['http://localhost:8848'],
|
|
40
|
+
namespaceId: 'public',
|
|
41
|
+
username: 'nacos',
|
|
42
|
+
password: 'nacos',
|
|
43
|
+
},
|
|
44
|
+
watchInterval: 3000, // 配置轮询间隔(毫秒)
|
|
45
|
+
},
|
|
46
|
+
}),
|
|
47
|
+
);
|
|
48
|
+
```
|
|
49
|
+
|
|
50
|
+
### 2. 使用配置中心
|
|
51
|
+
|
|
52
|
+
```typescript
|
|
53
|
+
import {
|
|
54
|
+
CONFIG_CENTER_TOKEN,
|
|
55
|
+
type ConfigCenter,
|
|
56
|
+
} from '@dangao/bun-server';
|
|
57
|
+
import { Inject, Injectable } from '@dangao/bun-server';
|
|
58
|
+
|
|
59
|
+
@Injectable()
|
|
60
|
+
class MyService {
|
|
61
|
+
public constructor(
|
|
62
|
+
@Inject(CONFIG_CENTER_TOKEN) private readonly configCenter: ConfigCenter,
|
|
63
|
+
) {}
|
|
64
|
+
|
|
65
|
+
public async getConfig() {
|
|
66
|
+
const result = await this.configCenter.getConfig(
|
|
67
|
+
'my-config',
|
|
68
|
+
'DEFAULT_GROUP',
|
|
69
|
+
);
|
|
70
|
+
return JSON.parse(result.content);
|
|
71
|
+
}
|
|
72
|
+
}
|
|
73
|
+
```
|
|
74
|
+
|
|
75
|
+
## 基本使用
|
|
76
|
+
|
|
77
|
+
### 获取配置
|
|
78
|
+
|
|
79
|
+
```typescript
|
|
80
|
+
// 基本用法
|
|
81
|
+
const config = await configCenter.getConfig('my-config', 'DEFAULT_GROUP');
|
|
82
|
+
|
|
83
|
+
// 指定命名空间
|
|
84
|
+
const config = await configCenter.getConfig(
|
|
85
|
+
'my-config',
|
|
86
|
+
'DEFAULT_GROUP',
|
|
87
|
+
'production',
|
|
88
|
+
);
|
|
89
|
+
```
|
|
90
|
+
|
|
91
|
+
### 配置结果
|
|
92
|
+
|
|
93
|
+
`getConfig` 返回 `ConfigResult` 对象:
|
|
94
|
+
|
|
95
|
+
```typescript
|
|
96
|
+
interface ConfigResult {
|
|
97
|
+
content: string; // 配置内容
|
|
98
|
+
md5: string; // 配置 MD5(用于判断是否变更)
|
|
99
|
+
lastModified: number; // 最后修改时间(时间戳)
|
|
100
|
+
contentType: string; // 内容类型
|
|
101
|
+
}
|
|
102
|
+
```
|
|
103
|
+
|
|
104
|
+
### 监听配置变更
|
|
105
|
+
|
|
106
|
+
```typescript
|
|
107
|
+
const unsubscribe = configCenter.watchConfig(
|
|
108
|
+
'my-config',
|
|
109
|
+
'DEFAULT_GROUP',
|
|
110
|
+
(newConfig) => {
|
|
111
|
+
console.log('Config updated:', newConfig.content);
|
|
112
|
+
// 更新应用配置
|
|
113
|
+
updateAppConfig(JSON.parse(newConfig.content));
|
|
114
|
+
},
|
|
115
|
+
);
|
|
116
|
+
|
|
117
|
+
// 取消监听
|
|
118
|
+
unsubscribe();
|
|
119
|
+
```
|
|
120
|
+
|
|
121
|
+
## 配置热更新
|
|
122
|
+
|
|
123
|
+
配置中心支持配置热更新,通过轮询机制检测配置变更:
|
|
124
|
+
|
|
125
|
+
```typescript
|
|
126
|
+
ConfigCenterModule.forRoot({
|
|
127
|
+
provider: 'nacos',
|
|
128
|
+
nacos: {
|
|
129
|
+
watchInterval: 3000, // 每 3 秒检查一次配置变更
|
|
130
|
+
},
|
|
131
|
+
});
|
|
132
|
+
|
|
133
|
+
// 监听配置变更
|
|
134
|
+
configCenter.watchConfig('my-config', 'DEFAULT_GROUP', (newConfig) => {
|
|
135
|
+
// 配置变更时自动调用
|
|
136
|
+
console.log('Config hot updated:', newConfig.content);
|
|
137
|
+
});
|
|
138
|
+
```
|
|
139
|
+
|
|
140
|
+
## ConfigModule 集成
|
|
141
|
+
|
|
142
|
+
ConfigModule 支持与配置中心深度集成,配置变更会自动刷新 ConfigService:
|
|
143
|
+
|
|
144
|
+
```typescript
|
|
145
|
+
import { ConfigModule } from '@dangao/bun-server';
|
|
146
|
+
|
|
147
|
+
ConfigModule.forRoot({
|
|
148
|
+
defaultConfig: {
|
|
149
|
+
app: {
|
|
150
|
+
name: 'MyApp',
|
|
151
|
+
port: 3000,
|
|
152
|
+
},
|
|
153
|
+
},
|
|
154
|
+
configCenter: {
|
|
155
|
+
enabled: true,
|
|
156
|
+
configs: new Map([
|
|
157
|
+
['app.name', { dataId: 'app-name', groupName: 'DEFAULT_GROUP' }],
|
|
158
|
+
['app.port', { dataId: 'app-port', groupName: 'DEFAULT_GROUP' }],
|
|
159
|
+
]),
|
|
160
|
+
configCenterPriority: true, // 配置中心配置优先级最高
|
|
161
|
+
},
|
|
162
|
+
});
|
|
163
|
+
|
|
164
|
+
// 使用 ConfigService
|
|
165
|
+
import { CONFIG_SERVICE_TOKEN, ConfigService } from '@dangao/bun-server';
|
|
166
|
+
|
|
167
|
+
@Injectable()
|
|
168
|
+
class MyService {
|
|
169
|
+
public constructor(
|
|
170
|
+
@Inject(CONFIG_SERVICE_TOKEN) private readonly config: ConfigService,
|
|
171
|
+
) {}
|
|
172
|
+
|
|
173
|
+
public getAppName() {
|
|
174
|
+
// 自动从配置中心获取,配置变更时自动更新
|
|
175
|
+
return this.config.get<string>('app.name');
|
|
176
|
+
}
|
|
177
|
+
}
|
|
178
|
+
```
|
|
179
|
+
|
|
180
|
+
### 配置优先级
|
|
181
|
+
|
|
182
|
+
- `configCenterPriority: true`(默认):配置中心 > 环境变量 > 默认配置
|
|
183
|
+
- `configCenterPriority: false`:默认配置 > 环境变量 > 配置中心
|
|
184
|
+
|
|
185
|
+
## 装饰器使用
|
|
186
|
+
|
|
187
|
+
### @ConfigCenterValue
|
|
188
|
+
|
|
189
|
+
自动注入配置值:
|
|
190
|
+
|
|
191
|
+
```typescript
|
|
192
|
+
import { ConfigCenterValue, Injectable } from '@dangao/bun-server';
|
|
193
|
+
|
|
194
|
+
@Injectable()
|
|
195
|
+
class MyService {
|
|
196
|
+
@ConfigCenterValue('app-name', 'DEFAULT_GROUP', {
|
|
197
|
+
defaultValue: 'MyApp',
|
|
198
|
+
watch: true, // 监听配置变更
|
|
199
|
+
})
|
|
200
|
+
public appName: string = '';
|
|
201
|
+
|
|
202
|
+
public getAppName() {
|
|
203
|
+
return this.appName; // 自动从配置中心获取
|
|
204
|
+
}
|
|
205
|
+
}
|
|
206
|
+
```
|
|
207
|
+
|
|
208
|
+
### @NacosValue
|
|
209
|
+
|
|
210
|
+
Nacos 特定的配置值注入(便捷别名):
|
|
211
|
+
|
|
212
|
+
```typescript
|
|
213
|
+
import { NacosValue, Injectable } from '@dangao/bun-server';
|
|
214
|
+
|
|
215
|
+
@Injectable()
|
|
216
|
+
class MyService {
|
|
217
|
+
@NacosValue('app-name', 'DEFAULT_GROUP', {
|
|
218
|
+
defaultValue: 'MyApp',
|
|
219
|
+
})
|
|
220
|
+
public appName: string = '';
|
|
221
|
+
}
|
|
222
|
+
```
|
|
223
|
+
|
|
224
|
+
## 最佳实践
|
|
225
|
+
|
|
226
|
+
### 1. 配置组织
|
|
227
|
+
|
|
228
|
+
- **命名空间**:用于区分不同环境(dev、test、prod)
|
|
229
|
+
- **分组**:用于逻辑分组(DEFAULT_GROUP、DATABASE_GROUP 等)
|
|
230
|
+
- **DataId**:配置的唯一标识
|
|
231
|
+
|
|
232
|
+
### 2. 配置格式
|
|
233
|
+
|
|
234
|
+
- 推荐使用 JSON 格式存储配置
|
|
235
|
+
- 支持纯文本配置(如 properties、yaml 等)
|
|
236
|
+
|
|
237
|
+
### 3. 配置监听
|
|
238
|
+
|
|
239
|
+
- 为关键配置启用监听(`watch: true`)
|
|
240
|
+
- 配置变更时及时更新应用状态
|
|
241
|
+
- 避免频繁的配置变更
|
|
242
|
+
|
|
243
|
+
### 4. 错误处理
|
|
244
|
+
|
|
245
|
+
- 配置获取失败时使用默认值
|
|
246
|
+
- 记录配置获取错误日志
|
|
247
|
+
- 实现配置降级策略
|
|
248
|
+
|
|
249
|
+
### 5. 性能优化
|
|
250
|
+
|
|
251
|
+
- 合理设置 `watchInterval`(建议 3-10 秒)
|
|
252
|
+
- 使用配置缓存减少 API 调用
|
|
253
|
+
- 批量获取配置(如果支持)
|
|
254
|
+
|
|
255
|
+
## 示例
|
|
256
|
+
|
|
257
|
+
完整示例请参考 `examples/microservice-app.ts`。
|
|
258
|
+
|