@longzai-intelligence-workflow/core 0.0.1 → 0.0.5
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/.turbo/turbo-build.log +5 -0
- package/.turbo/turbo-lint.log +1305 -0
- package/.turbo/turbo-typecheck.log +12 -0
- package/CHANGELOG.md +24 -1
- package/coverage/.lcov.info.09bb1f2a9aba2380.tmp +169 -0
- package/coverage/.lcov.info.0e095d78ac9192b0.tmp +329 -0
- package/coverage/.lcov.info.53a7ebfa7c8664ce.tmp +12 -0
- package/coverage/.lcov.info.6ea86c7cbc796fe0.tmp +12 -0
- package/coverage/.lcov.info.8f2985e5b3ad22cc.tmp +329 -0
- package/coverage/.lcov.info.a6ce2b7c3df2438b.tmp +228 -0
- package/coverage/.lcov.info.cc45f2f81aa7e02f.tmp +12 -0
- package/coverage/.lcov.info.cd0e8c028b2d5097.tmp +329 -0
- package/coverage/.lcov.info.dae76ebcf998e663.tmp +12 -0
- package/coverage/.lcov.info.e3bdb201eb5ce330.tmp +170 -0
- package/coverage/.lcov.info.e54e42fa06f69854.tmp +12 -0
- package/coverage/.lcov.info.f3e7537ac7b81e07.tmp +12 -0
- package/coverage/.lcov.info.fbb8af17757faa2d.tmp +329 -0
- package/coverage/lcov.info +208 -48
- package/dist/index.d.ts +3 -29
- package/dist/index.js +3 -3
- package/docs/overview.md +1 -1
- package/package.json +2 -1
- package/src/__tests__/unit/constants.test.ts +75 -30
- package/src/__tests__/unit/utils.test.ts +110 -38
- package/src/__tests__/work-item-rules.test.ts +18 -5
- package/src/index.ts +19 -5
- package/src/ports/action-executor.port.ts +2 -1
- package/src/ports/feed-event.port.ts +1 -1
- package/src/ports/index.ts +1 -0
- package/src/schemas/action-executor.schema.ts +2 -1
- package/src/schemas/definition.schema.ts +1 -1
- package/src/schemas/feed-event-trigger.schema.ts +1 -1
- package/src/schemas/index.ts +7 -0
- package/src/schemas/instance.schema.ts +1 -1
- package/src/schemas/monitoring.schema.ts +1 -1
- package/src/schemas/trigger.schema.ts +1 -1
- package/src/schemas/workflow-doc.schema.ts +4 -2
- package/src/types/action-executor.ts +1 -1
- package/src/types/feed-event-trigger.ts +1 -1
- package/src/types/index.ts +5 -0
- package/src/utils/dag.utils.ts +14 -93
- package/src/utils/index.ts +4 -2
- package/src/utils/work-item-rules.utils.ts +28 -7
- package/tsconfig/.cache/build.tsbuildinfo +1 -1
- package/tsconfig/.cache/node.tsbuildinfo +1 -1
- package/tsconfig/.cache/test.tsbuildinfo +1 -1
- package/tsconfig/node.json +1 -1
- package/tsconfig.json +9 -1
|
@@ -0,0 +1,1305 @@
|
|
|
1
|
+
$ oxlint src && oxfmt --check src
|
|
2
|
+
|
|
3
|
+
! @longzai-intelligence-oxlint/zod-plugin(prefer-zod-namespace): 请使用命名空间导入 zod(import * as z from "zod")代替命名导入。
|
|
4
|
+
,-[src/schemas/instance.schema.ts:1:10]
|
|
5
|
+
1 | import { z } from 'zod';
|
|
6
|
+
: ^
|
|
7
|
+
2 |
|
|
8
|
+
`----
|
|
9
|
+
|
|
10
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(padding-line-between-statements): export 语句之间需要空行
|
|
11
|
+
,-[src/utils/index.ts:18:1]
|
|
12
|
+
17 | export * from './declaration-frontmatter.utils';
|
|
13
|
+
18 | export * from './work-item-rules.utils';
|
|
14
|
+
: ^
|
|
15
|
+
19 | export * from './dag.utils';
|
|
16
|
+
`----
|
|
17
|
+
|
|
18
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(padding-line-between-statements): export 语句之间需要空行
|
|
19
|
+
,-[src/utils/index.ts:19:1]
|
|
20
|
+
18 | export * from './work-item-rules.utils';
|
|
21
|
+
19 | export * from './dag.utils';
|
|
22
|
+
: ^
|
|
23
|
+
`----
|
|
24
|
+
|
|
25
|
+
x @longzai-intelligence-oxlint/code-style-plugin(no-inline-type-definition): 函数 "getPagination" 的返回值使用了内联对象类型定义。请将其提取为具名的 type。
|
|
26
|
+
,-[src/utils/index.ts:3:8]
|
|
27
|
+
2 |
|
|
28
|
+
3 | ,-> export function getPagination(page?: number, pageSize?: number): { offset: number; limit: number } {
|
|
29
|
+
4 | | const limit = Math.min(pageSize ?? DEFAULT_PAGE_SIZE, MAX_PAGE_SIZE);
|
|
30
|
+
5 | | const offset = (Math.max(page ?? 1, 1) - 1) * limit;
|
|
31
|
+
6 | | return { offset, limit };
|
|
32
|
+
7 | `-> }
|
|
33
|
+
8 |
|
|
34
|
+
`----
|
|
35
|
+
|
|
36
|
+
x @longzai-intelligence-oxlint/file-naming-plugin(require-type-suffix): 文件 "feed-event-trigger.ts" 缺少类型后缀。除特殊文件外,所有文件应使用 xxx.yyy.ts 格式明确表达用途。建议: .utils.ts, .config.ts, .constants.ts
|
|
37
|
+
,-[src/types/feed-event-trigger.ts:8:1]
|
|
38
|
+
7 |
|
|
39
|
+
8 | ,-> import type {
|
|
40
|
+
9 | | feedEventFilterSchema,
|
|
41
|
+
10 | | feedEventNameSchema,
|
|
42
|
+
11 | | feedEventPayloadSchema,
|
|
43
|
+
12 | | feedEventTriggerSchema,
|
|
44
|
+
13 | | } from '@/schemas';
|
|
45
|
+
14 | | import type { z } from 'zod';
|
|
46
|
+
15 | |
|
|
47
|
+
16 | | /**
|
|
48
|
+
17 | | * feed 事件名称类型
|
|
49
|
+
18 | | */
|
|
50
|
+
19 | | export type FeedEventName = z.infer<typeof feedEventNameSchema>;
|
|
51
|
+
20 | |
|
|
52
|
+
21 | | /**
|
|
53
|
+
22 | | * feed 事件过滤条件类型
|
|
54
|
+
23 | | */
|
|
55
|
+
24 | | export type FeedEventFilter = z.infer<typeof feedEventFilterSchema>;
|
|
56
|
+
25 | |
|
|
57
|
+
26 | | /**
|
|
58
|
+
27 | | * feed 事件触发器配置类型
|
|
59
|
+
28 | | *
|
|
60
|
+
29 | | * 工作流 trigger.type 为 'feed.event' 时的配置结构。
|
|
61
|
+
30 | | */
|
|
62
|
+
31 | | export type FeedEventTrigger = z.infer<typeof feedEventTriggerSchema>;
|
|
63
|
+
32 | |
|
|
64
|
+
33 | | /**
|
|
65
|
+
34 | | * feed 事件 payload 类型
|
|
66
|
+
35 | | *
|
|
67
|
+
36 | | * feed 项目在事件触发时传递给工作流上下文的事件数据。
|
|
68
|
+
37 | | */
|
|
69
|
+
38 | `-> export type FeedEventPayload = z.infer<typeof feedEventPayloadSchema>;
|
|
70
|
+
`----
|
|
71
|
+
|
|
72
|
+
! @longzai-intelligence-oxlint/zod-plugin(prefer-zod-namespace): 请使用命名空间导入 zod(import * as z from "zod")代替命名导入。
|
|
73
|
+
,-[src/types/feed-event-trigger.ts:14:15]
|
|
74
|
+
13 | } from '@/schemas';
|
|
75
|
+
14 | import type { z } from 'zod';
|
|
76
|
+
: ^
|
|
77
|
+
15 |
|
|
78
|
+
`----
|
|
79
|
+
|
|
80
|
+
! @longzai-intelligence-oxlint/zod-plugin(prefer-zod-namespace): 请使用命名空间导入 zod(import * as z from "zod")代替命名导入。
|
|
81
|
+
,-[src/schemas/definition.schema.ts:1:10]
|
|
82
|
+
1 | import { z } from 'zod';
|
|
83
|
+
: ^
|
|
84
|
+
2 |
|
|
85
|
+
`----
|
|
86
|
+
|
|
87
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(padding-line-between-statements): export 语句之间需要空行
|
|
88
|
+
,-[src/index.ts:10:1]
|
|
89
|
+
9 | // 常量导出
|
|
90
|
+
10 | export * from './constants/index';
|
|
91
|
+
: ^
|
|
92
|
+
11 | // 工具函数导出
|
|
93
|
+
`----
|
|
94
|
+
|
|
95
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(padding-line-between-statements): export 语句之间需要空行
|
|
96
|
+
,-[src/index.ts:12:1]
|
|
97
|
+
11 | // 工具函数导出
|
|
98
|
+
12 | export * from './utils/index';
|
|
99
|
+
: ^
|
|
100
|
+
13 | // zod schema 导出
|
|
101
|
+
`----
|
|
102
|
+
|
|
103
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(padding-line-between-statements): export 语句之间需要空行
|
|
104
|
+
,-[src/index.ts:14:1]
|
|
105
|
+
13 | // zod schema 导出
|
|
106
|
+
14 | export * from './schemas/index';
|
|
107
|
+
: ^
|
|
108
|
+
15 | // 端口契约导出(C1 合规,零框架依赖)
|
|
109
|
+
`----
|
|
110
|
+
|
|
111
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(padding-line-between-statements): export 语句之间需要空行
|
|
112
|
+
,-[src/index.ts:16:1]
|
|
113
|
+
15 | // 端口契约导出(C1 合规,零框架依赖)
|
|
114
|
+
16 | export * from './ports/index';
|
|
115
|
+
: ^
|
|
116
|
+
`----
|
|
117
|
+
|
|
118
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
119
|
+
,-[src/index.ts:7:1]
|
|
120
|
+
6 | */
|
|
121
|
+
7 | // 类型导出
|
|
122
|
+
: ^^^^^^^^^^^
|
|
123
|
+
8 | export * from './types/index';
|
|
124
|
+
`----
|
|
125
|
+
|
|
126
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
127
|
+
,-[src/index.ts:9:1]
|
|
128
|
+
8 | export * from './types/index';
|
|
129
|
+
9 | // 常量导出
|
|
130
|
+
: ^^^^^^^^^^^
|
|
131
|
+
10 | export * from './constants/index';
|
|
132
|
+
`----
|
|
133
|
+
|
|
134
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
135
|
+
,-[src/index.ts:11:1]
|
|
136
|
+
10 | export * from './constants/index';
|
|
137
|
+
11 | // 工具函数导出
|
|
138
|
+
: ^^^^^^^^^^^^^^^
|
|
139
|
+
12 | export * from './utils/index';
|
|
140
|
+
`----
|
|
141
|
+
|
|
142
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
143
|
+
,-[src/index.ts:13:1]
|
|
144
|
+
12 | export * from './utils/index';
|
|
145
|
+
13 | // zod schema 导出
|
|
146
|
+
: ^^^^^^^^^^^^^^^^^^
|
|
147
|
+
14 | export * from './schemas/index';
|
|
148
|
+
`----
|
|
149
|
+
|
|
150
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
151
|
+
,-[src/index.ts:15:1]
|
|
152
|
+
14 | export * from './schemas/index';
|
|
153
|
+
15 | // 端口契约导出(C1 合规,零框架依赖)
|
|
154
|
+
: ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
|
155
|
+
16 | export * from './ports/index';
|
|
156
|
+
`----
|
|
157
|
+
|
|
158
|
+
! @longzai-intelligence-oxlint/zod-plugin(prefer-zod-namespace): 请使用命名空间导入 zod(import * as z from "zod")代替命名导入。
|
|
159
|
+
,-[src/schemas/monitoring.schema.ts:1:10]
|
|
160
|
+
1 | import { z } from 'zod';
|
|
161
|
+
: ^
|
|
162
|
+
2 |
|
|
163
|
+
`----
|
|
164
|
+
|
|
165
|
+
! @longzai-intelligence-oxlint/zod-plugin(prefer-zod-namespace): 请使用命名空间导入 zod(import * as z from "zod")代替命名导入。
|
|
166
|
+
,-[src/schemas/feed-event-trigger.schema.ts:13:10]
|
|
167
|
+
12 |
|
|
168
|
+
13 | import { z } from 'zod';
|
|
169
|
+
: ^
|
|
170
|
+
14 |
|
|
171
|
+
`----
|
|
172
|
+
|
|
173
|
+
! @longzai-intelligence-oxlint/zod-plugin(prefer-zod-namespace): 请使用命名空间导入 zod(import * as z from "zod")代替命名导入。
|
|
174
|
+
,-[src/schemas/action-executor.schema.ts:16:10]
|
|
175
|
+
15 |
|
|
176
|
+
16 | import { z } from 'zod';
|
|
177
|
+
: ^
|
|
178
|
+
17 |
|
|
179
|
+
`----
|
|
180
|
+
|
|
181
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(padding-line-between-statements): export 语句之间需要空行
|
|
182
|
+
,-[src/types/index.ts:2:1]
|
|
183
|
+
1 | export * from './definition';
|
|
184
|
+
2 | export * from './instance';
|
|
185
|
+
: ^
|
|
186
|
+
3 | export * from './trigger';
|
|
187
|
+
`----
|
|
188
|
+
|
|
189
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(padding-line-between-statements): export 语句之间需要空行
|
|
190
|
+
,-[src/types/index.ts:3:1]
|
|
191
|
+
2 | export * from './instance';
|
|
192
|
+
3 | export * from './trigger';
|
|
193
|
+
: ^
|
|
194
|
+
4 | export * from './monitoring';
|
|
195
|
+
`----
|
|
196
|
+
|
|
197
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(padding-line-between-statements): export 语句之间需要空行
|
|
198
|
+
,-[src/types/index.ts:4:1]
|
|
199
|
+
3 | export * from './trigger';
|
|
200
|
+
4 | export * from './monitoring';
|
|
201
|
+
: ^
|
|
202
|
+
5 | export * from './feed-event-trigger';
|
|
203
|
+
`----
|
|
204
|
+
|
|
205
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(padding-line-between-statements): export 语句之间需要空行
|
|
206
|
+
,-[src/types/index.ts:5:1]
|
|
207
|
+
4 | export * from './monitoring';
|
|
208
|
+
5 | export * from './feed-event-trigger';
|
|
209
|
+
: ^
|
|
210
|
+
6 | export * from './action-executor';
|
|
211
|
+
`----
|
|
212
|
+
|
|
213
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(padding-line-between-statements): export 语句之间需要空行
|
|
214
|
+
,-[src/types/index.ts:6:1]
|
|
215
|
+
5 | export * from './feed-event-trigger';
|
|
216
|
+
6 | export * from './action-executor';
|
|
217
|
+
: ^
|
|
218
|
+
`----
|
|
219
|
+
|
|
220
|
+
! @longzai-intelligence-oxlint/zod-plugin(prefer-zod-namespace): 请使用命名空间导入 zod(import * as z from "zod")代替命名导入。
|
|
221
|
+
,-[src/schemas/trigger.schema.ts:1:10]
|
|
222
|
+
1 | import { z } from 'zod';
|
|
223
|
+
: ^
|
|
224
|
+
2 |
|
|
225
|
+
`----
|
|
226
|
+
|
|
227
|
+
x @longzai-intelligence-oxlint/file-naming-plugin(require-type-suffix): 文件 "action-executor.ts" 缺少类型后缀。除特殊文件外,所有文件应使用 xxx.yyy.ts 格式明确表达用途。建议: .utils.ts, .config.ts, .constants.ts
|
|
228
|
+
,-[src/types/action-executor.ts:8:1]
|
|
229
|
+
7 |
|
|
230
|
+
8 | ,-> import type {
|
|
231
|
+
9 | | actionContextSchema,
|
|
232
|
+
10 | | actionResultSchema,
|
|
233
|
+
11 | | actionSchema,
|
|
234
|
+
12 | | actionTypeSchema,
|
|
235
|
+
13 | | feedApplyTagsActionSchema,
|
|
236
|
+
14 | | feedSummarizeActionSchema,
|
|
237
|
+
15 | | llmCompleteActionSchema,
|
|
238
|
+
16 | | webhookSendActionSchema,
|
|
239
|
+
17 | | } from '@/schemas';
|
|
240
|
+
18 | | import type { z } from 'zod';
|
|
241
|
+
19 | |
|
|
242
|
+
20 | | /**
|
|
243
|
+
21 | | * action 类型枚举
|
|
244
|
+
22 | | */
|
|
245
|
+
23 | | export type ActionType = z.infer<typeof actionTypeSchema>;
|
|
246
|
+
24 | |
|
|
247
|
+
25 | | /**
|
|
248
|
+
26 | | * feed.applyTags action 输入类型
|
|
249
|
+
27 | | */
|
|
250
|
+
28 | | export type FeedApplyTagsAction = z.infer<typeof feedApplyTagsActionSchema>;
|
|
251
|
+
29 | |
|
|
252
|
+
30 | | /**
|
|
253
|
+
31 | | * feed.summarize action 输入类型
|
|
254
|
+
32 | | */
|
|
255
|
+
33 | | export type FeedSummarizeAction = z.infer<typeof feedSummarizeActionSchema>;
|
|
256
|
+
34 | |
|
|
257
|
+
35 | | /**
|
|
258
|
+
36 | | * llm.complete action 输入类型
|
|
259
|
+
37 | | */
|
|
260
|
+
38 | | export type LlmCompleteAction = z.infer<typeof llmCompleteActionSchema>;
|
|
261
|
+
39 | |
|
|
262
|
+
40 | | /**
|
|
263
|
+
41 | | * webhook.send action 输入类型
|
|
264
|
+
42 | | */
|
|
265
|
+
43 | | export type WebhookSendAction = z.infer<typeof webhookSendActionSchema>;
|
|
266
|
+
44 | |
|
|
267
|
+
45 | | /**
|
|
268
|
+
46 | | * action 联合类型
|
|
269
|
+
47 | | *
|
|
270
|
+
48 | | * 所有内置 action 的联合类型,按 type 字段区分。
|
|
271
|
+
49 | | */
|
|
272
|
+
50 | | export type Action = z.infer<typeof actionSchema>;
|
|
273
|
+
51 | |
|
|
274
|
+
52 | | /**
|
|
275
|
+
53 | | * action 执行上下文类型
|
|
276
|
+
54 | | *
|
|
277
|
+
55 | | * 工作流引擎在执行 action 节点时传入的上下文信息。
|
|
278
|
+
56 | | */
|
|
279
|
+
57 | | export type ActionContext = z.infer<typeof actionContextSchema>;
|
|
280
|
+
58 | |
|
|
281
|
+
59 | | /**
|
|
282
|
+
60 | | * action 执行结果类型
|
|
283
|
+
61 | | *
|
|
284
|
+
62 | | * action handler 执行完成后返回的结果。
|
|
285
|
+
63 | | */
|
|
286
|
+
64 | `-> export type ActionResult = z.infer<typeof actionResultSchema>;
|
|
287
|
+
`----
|
|
288
|
+
|
|
289
|
+
! @longzai-intelligence-oxlint/zod-plugin(prefer-zod-namespace): 请使用命名空间导入 zod(import * as z from "zod")代替命名导入。
|
|
290
|
+
,-[src/types/action-executor.ts:18:15]
|
|
291
|
+
17 | } from '@/schemas';
|
|
292
|
+
18 | import type { z } from 'zod';
|
|
293
|
+
: ^
|
|
294
|
+
19 |
|
|
295
|
+
`----
|
|
296
|
+
|
|
297
|
+
x @longzai-intelligence-oxlint/file-naming-plugin(require-type-suffix): 文件 "monitoring.ts" 缺少类型后缀。除特殊文件外,所有文件应使用 xxx.yyy.ts 格式明确表达用途。建议: .utils.ts, .config.ts, .constants.ts
|
|
298
|
+
,-[src/types/monitoring.ts:1:1]
|
|
299
|
+
1 | ,-> export type AuditLogDTO = {
|
|
300
|
+
2 | | id: string;
|
|
301
|
+
3 | | instanceId: string;
|
|
302
|
+
4 | | nodeId: string | null;
|
|
303
|
+
5 | | action: string;
|
|
304
|
+
6 | | fromStatus: string | null;
|
|
305
|
+
7 | | toStatus: string;
|
|
306
|
+
8 | | operator: string | null;
|
|
307
|
+
9 | | detail: Record<string, unknown>;
|
|
308
|
+
10 | | createdAt: string;
|
|
309
|
+
11 | | };
|
|
310
|
+
12 | |
|
|
311
|
+
13 | | export type AlertDTO = {
|
|
312
|
+
14 | | id: string;
|
|
313
|
+
15 | | definitionId: string;
|
|
314
|
+
16 | | type: AlertTypeDTO;
|
|
315
|
+
17 | | threshold: number;
|
|
316
|
+
18 | | notifyConfig: Record<string, unknown>;
|
|
317
|
+
19 | | enabled: boolean;
|
|
318
|
+
20 | | lastTriggeredAt: string | null;
|
|
319
|
+
21 | | createdAt: string;
|
|
320
|
+
22 | | updatedAt: string;
|
|
321
|
+
23 | | };
|
|
322
|
+
24 | |
|
|
323
|
+
25 | | export type AlertTypeDTO = 'timeout' | 'failure_rate' | 'slow_execution';
|
|
324
|
+
26 | |
|
|
325
|
+
27 | | export type PerformanceMetricDTO = {
|
|
326
|
+
28 | | id: string;
|
|
327
|
+
29 | | definitionId: string;
|
|
328
|
+
30 | | metricType: MetricTypeDTO;
|
|
329
|
+
31 | | value: number;
|
|
330
|
+
32 | | period: string;
|
|
331
|
+
33 | | calculatedAt: string;
|
|
332
|
+
34 | | };
|
|
333
|
+
35 | |
|
|
334
|
+
36 | | export type MetricTypeDTO =
|
|
335
|
+
37 | | | 'avg_duration'
|
|
336
|
+
38 | | | 'success_rate'
|
|
337
|
+
39 | | | 'failure_rate'
|
|
338
|
+
40 | | | 'timeout_rate'
|
|
339
|
+
41 | | | 'instance_count';
|
|
340
|
+
42 | |
|
|
341
|
+
43 | | export type MonitoringDashboardDTO = {
|
|
342
|
+
44 | | runningInstances: number;
|
|
343
|
+
45 | | successRate: number;
|
|
344
|
+
46 | | avgDuration: number;
|
|
345
|
+
47 | | failureAlerts: number;
|
|
346
|
+
48 | | trend: TrendPointDTO[];
|
|
347
|
+
49 | | };
|
|
348
|
+
50 | |
|
|
349
|
+
51 | | export type TrendPointDTO = {
|
|
350
|
+
52 | | date: string;
|
|
351
|
+
53 | | value: number;
|
|
352
|
+
54 | `-> };
|
|
353
|
+
`----
|
|
354
|
+
|
|
355
|
+
x @longzai-intelligence-oxlint/tsdoc-plugin(require-returns): 缺少 @returns 文档
|
|
356
|
+
,-[src/utils/work-item-rules.utils.ts:138:1]
|
|
357
|
+
137 | */
|
|
358
|
+
138 | ,-> function isSettled(status: WorkItemStatus): boolean {
|
|
359
|
+
139 | | return status === 'done' || status === 'dropped';
|
|
360
|
+
140 | `-> }
|
|
361
|
+
141 |
|
|
362
|
+
`----
|
|
363
|
+
|
|
364
|
+
x @longzai-intelligence-oxlint/tsdoc-plugin(require-returns): 缺少 @returns 文档
|
|
365
|
+
,-[src/utils/work-item-rules.utils.ts:149:8]
|
|
366
|
+
148 | */
|
|
367
|
+
149 | ,-> export function deriveWorkflowView(
|
|
368
|
+
150 | | items: readonly WorkflowItem[],
|
|
369
|
+
151 | | edges: readonly WorkflowEdge[],
|
|
370
|
+
152 | | gates: readonly WorkflowGate[],
|
|
371
|
+
153 | | ): WorkflowView {
|
|
372
|
+
154 | | /**
|
|
373
|
+
155 | | * 已闭环工作项 id 集合
|
|
374
|
+
156 | | */
|
|
375
|
+
157 | | const settled = new Set(items.filter((item) => isSettled(item.status)).map((item) => item.id));
|
|
376
|
+
158 | |
|
|
377
|
+
159 | | /**
|
|
378
|
+
160 | | * 各工作项挂靠的未批准门(ruling.status 非 approved 即阻塞)
|
|
379
|
+
161 | | */
|
|
380
|
+
162 | | const unapprovedGateAt = new Set(gates.filter((gate) => gate.ruling.status !== 'approved' && gate.at !== 'workflow').map((gate) => gate.at));
|
|
381
|
+
163 | |
|
|
382
|
+
164 | | /**
|
|
383
|
+
165 | | * 工作项视图累积
|
|
384
|
+
166 | | */
|
|
385
|
+
167 | | const views: WorkItemView[] = items.map((item) => {
|
|
386
|
+
168 | | /**
|
|
387
|
+
169 | | * 依赖满足判定(DAG 基础能力域机件,闭环定义由本域注入)
|
|
388
|
+
170 | | */
|
|
389
|
+
171 | | const depsMet = dependenciesMet(item.id, edges, settled);
|
|
390
|
+
172 | |
|
|
391
|
+
173 | | return {
|
|
392
|
+
174 | | id: item.id,
|
|
393
|
+
175 | | status: item.status,
|
|
394
|
+
176 | | depsMet,
|
|
395
|
+
177 | | blockedOnPrerequisite: item.status === 'todo' && !depsMet,
|
|
396
|
+
178 | | canStart: item.status === 'todo' && depsMet && !unapprovedGateAt.has(item.id),
|
|
397
|
+
179 | | };
|
|
398
|
+
180 | | });
|
|
399
|
+
181 | |
|
|
400
|
+
182 | | /**
|
|
401
|
+
183 | | * 未决裁定视图累积(pending 与 escalated)
|
|
402
|
+
184 | | */
|
|
403
|
+
185 | | const pendingRulings: PendingRulingView[] = gates
|
|
404
|
+
186 | | .filter((gate) => gate.ruling.status === 'pending' || gate.ruling.status === 'escalated')
|
|
405
|
+
187 | | .map((gate) => ({
|
|
406
|
+
188 | | key: `${gate.at}:${gate.kind}`,
|
|
407
|
+
189 | | at: gate.at,
|
|
408
|
+
190 | | kind: gate.kind,
|
|
409
|
+
191 | | note: gate.note,
|
|
410
|
+
192 | | rulingStatus: gate.ruling.status as 'pending' | 'escalated',
|
|
411
|
+
193 | | }));
|
|
412
|
+
194 | |
|
|
413
|
+
195 | | return { items: views, pendingRulings };
|
|
414
|
+
196 | `-> }
|
|
415
|
+
`----
|
|
416
|
+
|
|
417
|
+
x @longzai-intelligence-oxlint/typescript-eslint-plugin(consistent-type-assertions): 禁止使用 as 类型断言,请使用类型守卫或 Zod 进行类型验证
|
|
418
|
+
,-[src/utils/work-item-rules.utils.ts:192:21]
|
|
419
|
+
191 | note: gate.note,
|
|
420
|
+
192 | rulingStatus: gate.ruling.status as 'pending' | 'escalated',
|
|
421
|
+
: ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
|
422
|
+
193 | }));
|
|
423
|
+
`----
|
|
424
|
+
|
|
425
|
+
x @longzai-intelligence-oxlint/file-naming-plugin(require-type-suffix): 文件 "workflow.ts" 缺少类型后缀。除特殊文件外,所有文件应使用 xxx.yyy.ts 格式明确表达用途。建议: .utils.ts, .config.ts, .constants.ts
|
|
426
|
+
,-[src/constants/workflow.ts:4:1]
|
|
427
|
+
3 | */
|
|
428
|
+
4 | ,-> export const NODE_TYPES = [
|
|
429
|
+
5 | | 'StartEvent',
|
|
430
|
+
6 | | 'EndEvent',
|
|
431
|
+
7 | | 'UserTask',
|
|
432
|
+
8 | | 'ServiceTask',
|
|
433
|
+
9 | | 'ExclusiveGateway',
|
|
434
|
+
10 | | 'ParallelGateway',
|
|
435
|
+
11 | | 'InclusiveGateway',
|
|
436
|
+
12 | | 'SubProcess',
|
|
437
|
+
13 | | 'TimerEvent',
|
|
438
|
+
14 | | 'ErrorEvent',
|
|
439
|
+
15 | | 'SignalEvent',
|
|
440
|
+
16 | | ] as const;
|
|
441
|
+
17 | |
|
|
442
|
+
18 | | /**
|
|
443
|
+
19 | | * 工作流实例状态枚举
|
|
444
|
+
20 | | */
|
|
445
|
+
21 | | export const INSTANCE_STATUSES = [
|
|
446
|
+
22 | | 'pending',
|
|
447
|
+
23 | | 'running',
|
|
448
|
+
24 | | 'paused',
|
|
449
|
+
25 | | 'completed',
|
|
450
|
+
26 | | 'cancelled',
|
|
451
|
+
27 | | 'failed',
|
|
452
|
+
28 | | ] as const;
|
|
453
|
+
29 | |
|
|
454
|
+
30 | | /**
|
|
455
|
+
31 | | * 节点执行状态枚举
|
|
456
|
+
32 | | */
|
|
457
|
+
33 | | export const NODE_EXECUTION_STATUSES = [
|
|
458
|
+
34 | | 'pending',
|
|
459
|
+
35 | | 'running',
|
|
460
|
+
36 | | 'completed',
|
|
461
|
+
37 | | 'failed',
|
|
462
|
+
38 | | 'skipped',
|
|
463
|
+
39 | | ] as const;
|
|
464
|
+
40 | |
|
|
465
|
+
41 | | /**
|
|
466
|
+
42 | | * 触发器类型枚举
|
|
467
|
+
43 | | */
|
|
468
|
+
44 | | export const TRIGGER_TYPES = ['timer', 'webhook', 'event', 'feed.event'] as const;
|
|
469
|
+
45 | |
|
|
470
|
+
46 | | /**
|
|
471
|
+
47 | | * feed 事件名称枚举(W-2,Phase 2)
|
|
472
|
+
48 | | *
|
|
473
|
+
49 | | * 用于 feed.event 触发器订阅 feed 项目暴露的事件总线。
|
|
474
|
+
50 | | */
|
|
475
|
+
51 | | export const FEED_EVENT_NAMES = [
|
|
476
|
+
52 | | /**
|
|
477
|
+
53 | | * 新条目入库事件
|
|
478
|
+
54 | | */
|
|
479
|
+
55 | | 'item.ingested',
|
|
480
|
+
56 | |
|
|
481
|
+
57 | | /**
|
|
482
|
+
58 | | * 信息源抓取完成事件
|
|
483
|
+
59 | | */
|
|
484
|
+
60 | | 'source.fetched',
|
|
485
|
+
61 | |
|
|
486
|
+
62 | | /**
|
|
487
|
+
63 | | * 条目过滤事件
|
|
488
|
+
64 | | */
|
|
489
|
+
65 | | 'item.filtered',
|
|
490
|
+
66 | |
|
|
491
|
+
67 | | /**
|
|
492
|
+
68 | | * 行业识别事件
|
|
493
|
+
69 | | */
|
|
494
|
+
70 | | 'industry.detected',
|
|
495
|
+
71 | | ] as const;
|
|
496
|
+
72 | |
|
|
497
|
+
73 | | /**
|
|
498
|
+
74 | | * 告警类型枚举
|
|
499
|
+
75 | | */
|
|
500
|
+
76 | | export const ALERT_TYPES = ['timeout', 'failure_rate', 'slow_execution'] as const;
|
|
501
|
+
77 | |
|
|
502
|
+
78 | | /**
|
|
503
|
+
79 | | * 工作流内置 action 类型枚举(W-3,Phase 2)
|
|
504
|
+
80 | | *
|
|
505
|
+
81 | | * - feed.applyTags:调用 feed F-2 applyTags 为条目打标签
|
|
506
|
+
82 | | * - feed.summarize:调用 feed F-3 summarize 生成摘要
|
|
507
|
+
83 | | * - llm.complete:调用 agent LlmCompletePort 完成文本
|
|
508
|
+
84 | | * - webhook.send:调用 webhook 项目发送 webhook
|
|
509
|
+
85 | | *
|
|
510
|
+
86 | | * D-08 决策:不暴露 DSL 编辑 UI,action 通过自然语言编译的 DSL 执行。
|
|
511
|
+
87 | | */
|
|
512
|
+
88 | | export const ACTION_TYPES = [
|
|
513
|
+
89 | | 'feed.applyTags',
|
|
514
|
+
90 | | 'feed.summarize',
|
|
515
|
+
91 | | 'llm.complete',
|
|
516
|
+
92 | | 'webhook.send',
|
|
517
|
+
93 | | ] as const;
|
|
518
|
+
94 | |
|
|
519
|
+
95 | | /**
|
|
520
|
+
96 | | * 监控指标类型枚举
|
|
521
|
+
97 | | */
|
|
522
|
+
98 | | export const METRIC_TYPES = [
|
|
523
|
+
99 | | 'avg_duration',
|
|
524
|
+
100 | | 'success_rate',
|
|
525
|
+
101 | | 'failure_rate',
|
|
526
|
+
102 | | 'timeout_rate',
|
|
527
|
+
103 | | 'instance_count',
|
|
528
|
+
104 | | ] as const;
|
|
529
|
+
105 | |
|
|
530
|
+
106 | | /**
|
|
531
|
+
107 | | * 分页查询默认每页条数
|
|
532
|
+
108 | | */
|
|
533
|
+
109 | | export const DEFAULT_PAGE_SIZE = 20;
|
|
534
|
+
110 | |
|
|
535
|
+
111 | | /**
|
|
536
|
+
112 | | * 分页查询每页最大条数上限
|
|
537
|
+
113 | | */
|
|
538
|
+
114 | `-> export const MAX_PAGE_SIZE = 100;
|
|
539
|
+
`----
|
|
540
|
+
|
|
541
|
+
x @longzai-intelligence-oxlint/file-naming-plugin(require-type-suffix): 文件 "instance.ts" 缺少类型后缀。除特殊文件外,所有文件应使用 xxx.yyy.ts 格式明确表达用途。建议: .utils.ts, .config.ts, .constants.ts
|
|
542
|
+
,-[src/types/instance.ts:1:1]
|
|
543
|
+
1 | ,-> export type InstanceDTO = {
|
|
544
|
+
2 | | id: string;
|
|
545
|
+
3 | | definitionId: string;
|
|
546
|
+
4 | | definitionVersion: number;
|
|
547
|
+
5 | | status: InstanceStatusDTO;
|
|
548
|
+
6 | | currentState: string;
|
|
549
|
+
7 | | previousState: string | null;
|
|
550
|
+
8 | | currentNodeId: string | null;
|
|
551
|
+
9 | | variables: Record<string, unknown>;
|
|
552
|
+
10 | | startedAt: string | null;
|
|
553
|
+
11 | | completedAt: string | null;
|
|
554
|
+
12 | | createdAt: string;
|
|
555
|
+
13 | | updatedAt: string;
|
|
556
|
+
14 | | };
|
|
557
|
+
15 | |
|
|
558
|
+
16 | | export type InstanceStatusDTO =
|
|
559
|
+
17 | | | 'pending'
|
|
560
|
+
18 | | | 'running'
|
|
561
|
+
19 | | | 'paused'
|
|
562
|
+
20 | | | 'completed'
|
|
563
|
+
21 | | | 'cancelled'
|
|
564
|
+
22 | | | 'failed';
|
|
565
|
+
23 | |
|
|
566
|
+
24 | | export type NodeExecutionDTO = {
|
|
567
|
+
25 | | id: string;
|
|
568
|
+
26 | | instanceId: string;
|
|
569
|
+
27 | | nodeId: string;
|
|
570
|
+
28 | | nodeName: string;
|
|
571
|
+
29 | | nodeType: string;
|
|
572
|
+
30 | | status: NodeExecutionStatusDTO;
|
|
573
|
+
31 | | startedAt: string | null;
|
|
574
|
+
32 | | completedAt: string | null;
|
|
575
|
+
33 | | error: string | null;
|
|
576
|
+
34 | | createdAt: string;
|
|
577
|
+
35 | | };
|
|
578
|
+
36 | |
|
|
579
|
+
37 | | export type NodeExecutionStatusDTO = 'pending' | 'running' | 'completed' | 'failed' | 'skipped';
|
|
580
|
+
38 | |
|
|
581
|
+
39 | | export type CreateInstanceInput = {
|
|
582
|
+
40 | | definitionId: string;
|
|
583
|
+
41 | | input?: Record<string, unknown>;
|
|
584
|
+
42 | | };
|
|
585
|
+
43 | |
|
|
586
|
+
44 | | export type InstanceQueryParams = {
|
|
587
|
+
45 | | status?: InstanceStatusDTO;
|
|
588
|
+
46 | | definitionId?: string;
|
|
589
|
+
47 | | page?: number;
|
|
590
|
+
48 | | pageSize?: number;
|
|
591
|
+
49 | `-> };
|
|
592
|
+
`----
|
|
593
|
+
|
|
594
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(padding-line-between-statements): export 语句之间需要空行
|
|
595
|
+
,-[src/ports/index.ts:9:1]
|
|
596
|
+
8 | export * from './feed-event.port';
|
|
597
|
+
9 | export * from './action-executor.port';
|
|
598
|
+
: ^
|
|
599
|
+
`----
|
|
600
|
+
|
|
601
|
+
x @longzai-intelligence-oxlint/file-naming-plugin(require-type-suffix): 文件 "trigger.ts" 缺少类型后缀。除特殊文件外,所有文件应使用 xxx.yyy.ts 格式明确表达用途。建议: .utils.ts, .config.ts, .constants.ts
|
|
602
|
+
,-[src/types/trigger.ts:4:1]
|
|
603
|
+
3 | */
|
|
604
|
+
4 | ,-> export type TriggerDTO = {
|
|
605
|
+
5 | | id: string;
|
|
606
|
+
6 | | definitionId: string;
|
|
607
|
+
7 | | name: string;
|
|
608
|
+
8 | | type: TriggerTypeDTO;
|
|
609
|
+
9 | | config: Record<string, unknown>;
|
|
610
|
+
10 | | enabled: boolean;
|
|
611
|
+
11 | | lastTriggeredAt: string | null;
|
|
612
|
+
12 | | createdAt: string;
|
|
613
|
+
13 | | updatedAt: string;
|
|
614
|
+
14 | | };
|
|
615
|
+
15 | |
|
|
616
|
+
16 | | /**
|
|
617
|
+
17 | | * 触发器类型枚举
|
|
618
|
+
18 | | *
|
|
619
|
+
19 | | * - timer:定时触发
|
|
620
|
+
20 | | * - webhook:Webhook 触发
|
|
621
|
+
21 | | * - event:通用事件触发
|
|
622
|
+
22 | | * - feed.event:feed 事件触发(W-2,Phase 2)
|
|
623
|
+
23 | | */
|
|
624
|
+
24 | | export type TriggerTypeDTO = 'timer' | 'webhook' | 'event' | 'feed.event';
|
|
625
|
+
25 | |
|
|
626
|
+
26 | | /**
|
|
627
|
+
27 | | * 创建触发器的入参
|
|
628
|
+
28 | | */
|
|
629
|
+
29 | | export type CreateTriggerInput = {
|
|
630
|
+
30 | | definitionId: string;
|
|
631
|
+
31 | | name: string;
|
|
632
|
+
32 | | type: TriggerTypeDTO;
|
|
633
|
+
33 | | config: Record<string, unknown>;
|
|
634
|
+
34 | | };
|
|
635
|
+
35 | |
|
|
636
|
+
36 | | /**
|
|
637
|
+
37 | | * 更新触发器的入参
|
|
638
|
+
38 | | */
|
|
639
|
+
39 | `-> export type UpdateTriggerInput = Partial<CreateTriggerInput>;
|
|
640
|
+
`----
|
|
641
|
+
|
|
642
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
643
|
+
,-[src/__tests__/unit/utils.test.ts:8:5]
|
|
644
|
+
7 | it('默认参数返回 offset=0, limit=DEFAULT_PAGE_SIZE', () => {
|
|
645
|
+
8 | // Arrange & Act
|
|
646
|
+
: ^^^^^^^^^^^^^^^^
|
|
647
|
+
9 | const result = getPagination();
|
|
648
|
+
`----
|
|
649
|
+
|
|
650
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
651
|
+
,-[src/__tests__/unit/utils.test.ts:11:5]
|
|
652
|
+
10 |
|
|
653
|
+
11 | // Assert
|
|
654
|
+
: ^^^^^^^^^
|
|
655
|
+
12 | expect(result.offset).toBe(0);
|
|
656
|
+
`----
|
|
657
|
+
|
|
658
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
659
|
+
,-[src/__tests__/unit/utils.test.ts:17:5]
|
|
660
|
+
16 | it('page=2, pageSize=10 返回 offset=10, limit=10', () => {
|
|
661
|
+
17 | // Arrange & Act
|
|
662
|
+
: ^^^^^^^^^^^^^^^^
|
|
663
|
+
18 | const result = getPagination(2, 10);
|
|
664
|
+
`----
|
|
665
|
+
|
|
666
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
667
|
+
,-[src/__tests__/unit/utils.test.ts:20:5]
|
|
668
|
+
19 |
|
|
669
|
+
20 | // Assert
|
|
670
|
+
: ^^^^^^^^^
|
|
671
|
+
21 | expect(result.offset).toBe(10);
|
|
672
|
+
`----
|
|
673
|
+
|
|
674
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
675
|
+
,-[src/__tests__/unit/utils.test.ts:26:5]
|
|
676
|
+
25 | it('pageSize 超过 MAX_PAGE_SIZE 时限制为 MAX_PAGE_SIZE', () => {
|
|
677
|
+
26 | // Arrange
|
|
678
|
+
: ^^^^^^^^^^
|
|
679
|
+
27 | const oversizedPageSize = MAX_PAGE_SIZE + 50;
|
|
680
|
+
`----
|
|
681
|
+
|
|
682
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
683
|
+
,-[src/__tests__/unit/utils.test.ts:29:5]
|
|
684
|
+
28 |
|
|
685
|
+
29 | // Act
|
|
686
|
+
: ^^^^^^
|
|
687
|
+
30 | const result = getPagination(1, oversizedPageSize);
|
|
688
|
+
`----
|
|
689
|
+
|
|
690
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
691
|
+
,-[src/__tests__/unit/utils.test.ts:32:5]
|
|
692
|
+
31 |
|
|
693
|
+
32 | // Assert
|
|
694
|
+
: ^^^^^^^^^
|
|
695
|
+
33 | expect(result.limit).toBe(MAX_PAGE_SIZE);
|
|
696
|
+
`----
|
|
697
|
+
|
|
698
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
699
|
+
,-[src/__tests__/unit/utils.test.ts:37:5]
|
|
700
|
+
36 | it('page=0 时默认为 page=1', () => {
|
|
701
|
+
37 | // Arrange & Act
|
|
702
|
+
: ^^^^^^^^^^^^^^^^
|
|
703
|
+
38 | const result = getPagination(0, 10);
|
|
704
|
+
`----
|
|
705
|
+
|
|
706
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
707
|
+
,-[src/__tests__/unit/utils.test.ts:40:5]
|
|
708
|
+
39 |
|
|
709
|
+
40 | // Assert
|
|
710
|
+
: ^^^^^^^^^
|
|
711
|
+
41 | expect(result.offset).toBe(0);
|
|
712
|
+
`----
|
|
713
|
+
|
|
714
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
715
|
+
,-[src/__tests__/unit/utils.test.ts:46:5]
|
|
716
|
+
45 | it('page 为负数时默认为 page=1', () => {
|
|
717
|
+
46 | // Arrange & Act
|
|
718
|
+
: ^^^^^^^^^^^^^^^^
|
|
719
|
+
47 | const result = getPagination(-1, 10);
|
|
720
|
+
`----
|
|
721
|
+
|
|
722
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
723
|
+
,-[src/__tests__/unit/utils.test.ts:49:5]
|
|
724
|
+
48 |
|
|
725
|
+
49 | // Assert
|
|
726
|
+
: ^^^^^^^^^
|
|
727
|
+
50 | expect(result.offset).toBe(0);
|
|
728
|
+
`----
|
|
729
|
+
|
|
730
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
731
|
+
,-[src/__tests__/unit/utils.test.ts:54:5]
|
|
732
|
+
53 | it('仅传入 page 时 pageSize 使用默认值', () => {
|
|
733
|
+
54 | // Arrange & Act
|
|
734
|
+
: ^^^^^^^^^^^^^^^^
|
|
735
|
+
55 | const result = getPagination(3);
|
|
736
|
+
`----
|
|
737
|
+
|
|
738
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
739
|
+
,-[src/__tests__/unit/utils.test.ts:57:5]
|
|
740
|
+
56 |
|
|
741
|
+
57 | // Assert
|
|
742
|
+
: ^^^^^^^^^
|
|
743
|
+
58 | expect(result.offset).toBe((3 - 1) * DEFAULT_PAGE_SIZE);
|
|
744
|
+
`----
|
|
745
|
+
|
|
746
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
747
|
+
,-[src/__tests__/unit/utils.test.ts:63:5]
|
|
748
|
+
62 | it('仅传入 pageSize 时 page 默认为 1', () => {
|
|
749
|
+
63 | // Arrange & Act
|
|
750
|
+
: ^^^^^^^^^^^^^^^^
|
|
751
|
+
64 | const result = getPagination(undefined, 15);
|
|
752
|
+
`----
|
|
753
|
+
|
|
754
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
755
|
+
,-[src/__tests__/unit/utils.test.ts:66:5]
|
|
756
|
+
65 |
|
|
757
|
+
66 | // Assert
|
|
758
|
+
: ^^^^^^^^^
|
|
759
|
+
67 | expect(result.offset).toBe(0);
|
|
760
|
+
`----
|
|
761
|
+
|
|
762
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
763
|
+
,-[src/__tests__/unit/utils.test.ts:74:5]
|
|
764
|
+
73 | it('正确计算总页数', () => {
|
|
765
|
+
74 | // Arrange
|
|
766
|
+
: ^^^^^^^^^^
|
|
767
|
+
75 | const total = 45;
|
|
768
|
+
`----
|
|
769
|
+
|
|
770
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
771
|
+
,-[src/__tests__/unit/utils.test.ts:78:5]
|
|
772
|
+
77 |
|
|
773
|
+
78 | // Act
|
|
774
|
+
: ^^^^^^
|
|
775
|
+
79 | const result = getTotalPages(total, pageSize);
|
|
776
|
+
`----
|
|
777
|
+
|
|
778
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
779
|
+
,-[src/__tests__/unit/utils.test.ts:81:5]
|
|
780
|
+
80 |
|
|
781
|
+
81 | // Assert
|
|
782
|
+
: ^^^^^^^^^
|
|
783
|
+
82 | expect(result).toBe(5);
|
|
784
|
+
`----
|
|
785
|
+
|
|
786
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
787
|
+
,-[src/__tests__/unit/utils.test.ts:86:5]
|
|
788
|
+
85 | it('总数恰好整除时返回精确页数', () => {
|
|
789
|
+
86 | // Arrange
|
|
790
|
+
: ^^^^^^^^^^
|
|
791
|
+
87 | const total = 40;
|
|
792
|
+
`----
|
|
793
|
+
|
|
794
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
795
|
+
,-[src/__tests__/unit/utils.test.ts:90:5]
|
|
796
|
+
89 |
|
|
797
|
+
90 | // Act
|
|
798
|
+
: ^^^^^^
|
|
799
|
+
91 | const result = getTotalPages(total, pageSize);
|
|
800
|
+
`----
|
|
801
|
+
|
|
802
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
803
|
+
,-[src/__tests__/unit/utils.test.ts:93:5]
|
|
804
|
+
92 |
|
|
805
|
+
93 | // Assert
|
|
806
|
+
: ^^^^^^^^^
|
|
807
|
+
94 | expect(result).toBe(4);
|
|
808
|
+
`----
|
|
809
|
+
|
|
810
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
811
|
+
,-[src/__tests__/unit/utils.test.ts:98:5]
|
|
812
|
+
97 | it('总数为 0 时返回 0', () => {
|
|
813
|
+
98 | // Arrange
|
|
814
|
+
: ^^^^^^^^^^
|
|
815
|
+
99 | const total = 0;
|
|
816
|
+
`----
|
|
817
|
+
|
|
818
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
819
|
+
,-[src/__tests__/unit/utils.test.ts:102:5]
|
|
820
|
+
101 |
|
|
821
|
+
102 | // Act
|
|
822
|
+
: ^^^^^^
|
|
823
|
+
103 | const result = getTotalPages(total, pageSize);
|
|
824
|
+
`----
|
|
825
|
+
|
|
826
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
827
|
+
,-[src/__tests__/unit/utils.test.ts:105:5]
|
|
828
|
+
104 |
|
|
829
|
+
105 | // Assert
|
|
830
|
+
: ^^^^^^^^^
|
|
831
|
+
106 | expect(result).toBe(0);
|
|
832
|
+
`----
|
|
833
|
+
|
|
834
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
835
|
+
,-[src/__tests__/unit/utils.test.ts:110:5]
|
|
836
|
+
109 | it('总数为 1 时返回 1', () => {
|
|
837
|
+
110 | // Arrange
|
|
838
|
+
: ^^^^^^^^^^
|
|
839
|
+
111 | const total = 1;
|
|
840
|
+
`----
|
|
841
|
+
|
|
842
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
843
|
+
,-[src/__tests__/unit/utils.test.ts:114:5]
|
|
844
|
+
113 |
|
|
845
|
+
114 | // Act
|
|
846
|
+
: ^^^^^^
|
|
847
|
+
115 | const result = getTotalPages(total, pageSize);
|
|
848
|
+
`----
|
|
849
|
+
|
|
850
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
851
|
+
,-[src/__tests__/unit/utils.test.ts:117:5]
|
|
852
|
+
116 |
|
|
853
|
+
117 | // Assert
|
|
854
|
+
: ^^^^^^^^^
|
|
855
|
+
118 | expect(result).toBe(1);
|
|
856
|
+
`----
|
|
857
|
+
|
|
858
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
859
|
+
,-[src/__tests__/unit/utils.test.ts:124:5]
|
|
860
|
+
123 | it('将 Date 对象转换为 ISO 字符串', () => {
|
|
861
|
+
124 | // Arrange
|
|
862
|
+
: ^^^^^^^^^^
|
|
863
|
+
125 | const date = new Date('2025-01-15T10:30:00.000Z');
|
|
864
|
+
`----
|
|
865
|
+
|
|
866
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
867
|
+
,-[src/__tests__/unit/utils.test.ts:127:5]
|
|
868
|
+
126 |
|
|
869
|
+
127 | // Act
|
|
870
|
+
: ^^^^^^
|
|
871
|
+
128 | const result = formatDate(date);
|
|
872
|
+
`----
|
|
873
|
+
|
|
874
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
875
|
+
,-[src/__tests__/unit/utils.test.ts:130:5]
|
|
876
|
+
129 |
|
|
877
|
+
130 | // Assert
|
|
878
|
+
: ^^^^^^^^^
|
|
879
|
+
131 | expect(result).toBe('2025-01-15T10:30:00.000Z');
|
|
880
|
+
`----
|
|
881
|
+
|
|
882
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
883
|
+
,-[src/__tests__/unit/utils.test.ts:135:5]
|
|
884
|
+
134 | it('将日期字符串转换为 ISO 字符串', () => {
|
|
885
|
+
135 | // Arrange
|
|
886
|
+
: ^^^^^^^^^^
|
|
887
|
+
136 | const dateStr = '2025-06-01';
|
|
888
|
+
`----
|
|
889
|
+
|
|
890
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
891
|
+
,-[src/__tests__/unit/utils.test.ts:138:5]
|
|
892
|
+
137 |
|
|
893
|
+
138 | // Act
|
|
894
|
+
: ^^^^^^
|
|
895
|
+
139 | const result = formatDate(dateStr);
|
|
896
|
+
`----
|
|
897
|
+
|
|
898
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
899
|
+
,-[src/__tests__/unit/utils.test.ts:141:5]
|
|
900
|
+
140 |
|
|
901
|
+
141 | // Assert
|
|
902
|
+
: ^^^^^^^^^
|
|
903
|
+
142 | expect(result).toContain('2025-06-01');
|
|
904
|
+
`----
|
|
905
|
+
|
|
906
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
907
|
+
,-[src/__tests__/unit/utils.test.ts:147:5]
|
|
908
|
+
146 | it('返回值为有效的 ISO 格式', () => {
|
|
909
|
+
147 | // Arrange
|
|
910
|
+
: ^^^^^^^^^^
|
|
911
|
+
148 | const date = new Date();
|
|
912
|
+
`----
|
|
913
|
+
|
|
914
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
915
|
+
,-[src/__tests__/unit/utils.test.ts:150:5]
|
|
916
|
+
149 |
|
|
917
|
+
150 | // Act
|
|
918
|
+
: ^^^^^^
|
|
919
|
+
151 | const result = formatDate(date);
|
|
920
|
+
`----
|
|
921
|
+
|
|
922
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
923
|
+
,-[src/__tests__/unit/utils.test.ts:153:5]
|
|
924
|
+
152 |
|
|
925
|
+
153 | // Assert
|
|
926
|
+
: ^^^^^^^^^
|
|
927
|
+
154 | expect(new Date(result).toISOString()).toBe(result);
|
|
928
|
+
`----
|
|
929
|
+
|
|
930
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
931
|
+
,-[src/__tests__/unit/constants.test.ts:16:5]
|
|
932
|
+
15 | it('默认分页大小为 20', () => {
|
|
933
|
+
16 | // Arrange & Act & Assert
|
|
934
|
+
: ^^^^^^^^^^^^^^^^^^^^^^^^^
|
|
935
|
+
17 | expect(DEFAULT_PAGE_SIZE).toBe(20);
|
|
936
|
+
`----
|
|
937
|
+
|
|
938
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
939
|
+
,-[src/__tests__/unit/constants.test.ts:23:5]
|
|
940
|
+
22 | it('最大分页大小为 100', () => {
|
|
941
|
+
23 | // Arrange & Act & Assert
|
|
942
|
+
: ^^^^^^^^^^^^^^^^^^^^^^^^^
|
|
943
|
+
24 | expect(MAX_PAGE_SIZE).toBe(100);
|
|
944
|
+
`----
|
|
945
|
+
|
|
946
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
947
|
+
,-[src/__tests__/unit/constants.test.ts:30:5]
|
|
948
|
+
29 | it('包含预期的节点类型', () => {
|
|
949
|
+
30 | // Arrange
|
|
950
|
+
: ^^^^^^^^^^
|
|
951
|
+
31 | const expectedTypes = [
|
|
952
|
+
`----
|
|
953
|
+
|
|
954
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
955
|
+
,-[src/__tests__/unit/constants.test.ts:45:5]
|
|
956
|
+
44 |
|
|
957
|
+
45 | // Act & Assert
|
|
958
|
+
: ^^^^^^^^^^^^^^^
|
|
959
|
+
46 | expect(NODE_TYPES).toEqual(expectedTypes);
|
|
960
|
+
`----
|
|
961
|
+
|
|
962
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
963
|
+
,-[src/__tests__/unit/constants.test.ts:50:5]
|
|
964
|
+
49 | it('包含 StartEvent', () => {
|
|
965
|
+
50 | // Arrange & Act & Assert
|
|
966
|
+
: ^^^^^^^^^^^^^^^^^^^^^^^^^
|
|
967
|
+
51 | expect(NODE_TYPES).toContain('StartEvent');
|
|
968
|
+
`----
|
|
969
|
+
|
|
970
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
971
|
+
,-[src/__tests__/unit/constants.test.ts:55:5]
|
|
972
|
+
54 | it('包含 EndEvent', () => {
|
|
973
|
+
55 | // Arrange & Act & Assert
|
|
974
|
+
: ^^^^^^^^^^^^^^^^^^^^^^^^^
|
|
975
|
+
56 | expect(NODE_TYPES).toContain('EndEvent');
|
|
976
|
+
`----
|
|
977
|
+
|
|
978
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
979
|
+
,-[src/__tests__/unit/constants.test.ts:60:5]
|
|
980
|
+
59 | it('为只读数组', () => {
|
|
981
|
+
60 | // Arrange & Act & Assert
|
|
982
|
+
: ^^^^^^^^^^^^^^^^^^^^^^^^^
|
|
983
|
+
61 | expect(Array.isArray(NODE_TYPES)).toBe(true);
|
|
984
|
+
`----
|
|
985
|
+
|
|
986
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
987
|
+
,-[src/__tests__/unit/constants.test.ts:67:5]
|
|
988
|
+
66 | it('包含预期的实例状态', () => {
|
|
989
|
+
67 | // Arrange
|
|
990
|
+
: ^^^^^^^^^^
|
|
991
|
+
68 | const expectedStatuses = ['pending', 'running', 'paused', 'completed', 'cancelled', 'failed'];
|
|
992
|
+
`----
|
|
993
|
+
|
|
994
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
995
|
+
,-[src/__tests__/unit/constants.test.ts:70:5]
|
|
996
|
+
69 |
|
|
997
|
+
70 | // Act & Assert
|
|
998
|
+
: ^^^^^^^^^^^^^^^
|
|
999
|
+
71 | expect(INSTANCE_STATUSES).toEqual(expectedStatuses);
|
|
1000
|
+
`----
|
|
1001
|
+
|
|
1002
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
1003
|
+
,-[src/__tests__/unit/constants.test.ts:75:5]
|
|
1004
|
+
74 | it('包含 pending 状态', () => {
|
|
1005
|
+
75 | // Arrange & Act & Assert
|
|
1006
|
+
: ^^^^^^^^^^^^^^^^^^^^^^^^^
|
|
1007
|
+
76 | expect(INSTANCE_STATUSES).toContain('pending');
|
|
1008
|
+
`----
|
|
1009
|
+
|
|
1010
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
1011
|
+
,-[src/__tests__/unit/constants.test.ts:80:5]
|
|
1012
|
+
79 | it('包含 failed 状态', () => {
|
|
1013
|
+
80 | // Arrange & Act & Assert
|
|
1014
|
+
: ^^^^^^^^^^^^^^^^^^^^^^^^^
|
|
1015
|
+
81 | expect(INSTANCE_STATUSES).toContain('failed');
|
|
1016
|
+
`----
|
|
1017
|
+
|
|
1018
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
1019
|
+
,-[src/__tests__/unit/constants.test.ts:87:5]
|
|
1020
|
+
86 | it('包含预期的节点执行状态', () => {
|
|
1021
|
+
87 | // Arrange
|
|
1022
|
+
: ^^^^^^^^^^
|
|
1023
|
+
88 | const expectedStatuses = ['pending', 'running', 'completed', 'failed', 'skipped'];
|
|
1024
|
+
`----
|
|
1025
|
+
|
|
1026
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
1027
|
+
,-[src/__tests__/unit/constants.test.ts:90:5]
|
|
1028
|
+
89 |
|
|
1029
|
+
90 | // Act & Assert
|
|
1030
|
+
: ^^^^^^^^^^^^^^^
|
|
1031
|
+
91 | expect(NODE_EXECUTION_STATUSES).toEqual(expectedStatuses);
|
|
1032
|
+
`----
|
|
1033
|
+
|
|
1034
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
1035
|
+
,-[src/__tests__/unit/constants.test.ts:97:5]
|
|
1036
|
+
96 | it('包含预期的触发器类型', () => {
|
|
1037
|
+
97 | // Arrange
|
|
1038
|
+
: ^^^^^^^^^^
|
|
1039
|
+
98 | const expectedTypes = ['timer', 'webhook', 'event'];
|
|
1040
|
+
`----
|
|
1041
|
+
|
|
1042
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
1043
|
+
,-[src/__tests__/unit/constants.test.ts:100:5]
|
|
1044
|
+
99 |
|
|
1045
|
+
100 | // Act & Assert
|
|
1046
|
+
: ^^^^^^^^^^^^^^^
|
|
1047
|
+
101 | expect(TRIGGER_TYPES).toEqual(expectedTypes);
|
|
1048
|
+
`----
|
|
1049
|
+
|
|
1050
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
1051
|
+
,-[src/__tests__/unit/constants.test.ts:107:5]
|
|
1052
|
+
106 | it('包含预期的告警类型', () => {
|
|
1053
|
+
107 | // Arrange
|
|
1054
|
+
: ^^^^^^^^^^
|
|
1055
|
+
108 | const expectedTypes = ['timeout', 'failure_rate', 'slow_execution'];
|
|
1056
|
+
`----
|
|
1057
|
+
|
|
1058
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
1059
|
+
,-[src/__tests__/unit/constants.test.ts:110:5]
|
|
1060
|
+
109 |
|
|
1061
|
+
110 | // Act & Assert
|
|
1062
|
+
: ^^^^^^^^^^^^^^^
|
|
1063
|
+
111 | expect(ALERT_TYPES).toEqual(expectedTypes);
|
|
1064
|
+
`----
|
|
1065
|
+
|
|
1066
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
1067
|
+
,-[src/__tests__/unit/constants.test.ts:117:5]
|
|
1068
|
+
116 | it('包含预期的指标类型', () => {
|
|
1069
|
+
117 | // Arrange
|
|
1070
|
+
: ^^^^^^^^^^
|
|
1071
|
+
118 | const expectedTypes = [
|
|
1072
|
+
`----
|
|
1073
|
+
|
|
1074
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(multiline-comment-style): 禁止双斜杠注释,只允许多行块注释
|
|
1075
|
+
,-[src/__tests__/unit/constants.test.ts:126:5]
|
|
1076
|
+
125 |
|
|
1077
|
+
126 | // Act & Assert
|
|
1078
|
+
: ^^^^^^^^^^^^^^^
|
|
1079
|
+
127 | expect(METRIC_TYPES).toEqual(expectedTypes);
|
|
1080
|
+
`----
|
|
1081
|
+
|
|
1082
|
+
x @longzai-intelligence-oxlint/file-naming-plugin(require-type-suffix): 文件 "setup.ts" 缺少类型后缀。除特殊文件外,所有文件应使用 xxx.yyy.ts 格式明确表达用途。建议: .utils.ts, .config.ts, .constants.ts
|
|
1083
|
+
,-[src/__tests__/helpers/setup.ts:1:1]
|
|
1084
|
+
1 | ,-> import { afterAll, afterEach, beforeAll } from 'bun:test';
|
|
1085
|
+
2 | |
|
|
1086
|
+
3 | | process.env.NODE_ENV ??= 'test';
|
|
1087
|
+
4 | |
|
|
1088
|
+
5 | | beforeAll(() => {});
|
|
1089
|
+
6 | |
|
|
1090
|
+
7 | | afterAll(() => {});
|
|
1091
|
+
8 | |
|
|
1092
|
+
9 | `-> afterEach(() => {});
|
|
1093
|
+
`----
|
|
1094
|
+
|
|
1095
|
+
x @longzai-intelligence-oxlint/architecture-library-plugin(test-file-matches-source): 测试文件 "work-item-rules.test.ts" 未找到匹配的源文件。测试文件应集中放置在 __tests__/ 目录下(可按 unit/integration/e2e 或 bun/vitest 分子目录组织),文件名与源文件名或目录名保持一致,例如 src/user.service.ts -> src/__tests__/user.service.test.ts、src/bridge/ -> src/__tests__/bridge.test.ts。同一源文件拆分多
|
|
1096
|
+
| 个测试时,用点号分隔拆分标识(如 src/comment.orm-repository.ts -> src/__tests__/comment.orm-repository.query.test.ts,而非 comment.orm-repository-query.test.ts)
|
|
1097
|
+
,-[src/__tests__/work-item-rules.test.ts:4:1]
|
|
1098
|
+
3 | */
|
|
1099
|
+
4 | ,-> import { describe, expect, test } from 'bun:test';
|
|
1100
|
+
5 | |
|
|
1101
|
+
6 | | import { parseGateLine, parseItemLine, type WorkflowEdge, type WorkflowGate, type WorkflowItem } from '@/schemas/workflow-doc.schema';
|
|
1102
|
+
7 | | import { checkStatusTransition, deriveWorkflowView } from '@/utils/work-item-rules.utils';
|
|
1103
|
+
8 | |
|
|
1104
|
+
9 | | describe('声明方言四段制解析', () => {
|
|
1105
|
+
10 | | test('工作项行:状态段执法', () => {
|
|
1106
|
+
11 | | expect(parseItemLine('t-011 | 生成器补全 | ref:demo/docs/tasks/a.md | todo')).toEqual({
|
|
1107
|
+
12 | | id: 't-011',
|
|
1108
|
+
13 | | title: '生成器补全',
|
|
1109
|
+
14 | | ref: 'ref:demo/docs/tasks/a.md',
|
|
1110
|
+
15 | | status: 'todo',
|
|
1111
|
+
16 | | });
|
|
1112
|
+
17 | | expect(parseItemLine('t-011 | 生成器补全 | ref:demo/docs/tasks/a.md')).toBeNull();
|
|
1113
|
+
18 | | expect(parseItemLine('t-011 | 生成器补全 | ref:demo/docs/tasks/a.md | invalid')).toBeNull();
|
|
1114
|
+
19 | | });
|
|
1115
|
+
20 | |
|
|
1116
|
+
21 | | test('裁定门行:裁定段四形态执法', () => {
|
|
1117
|
+
22 | | expect(parseGateLine('t-013 | ruling | 载体指示待裁 | pending')?.ruling).toEqual({ status: 'pending' });
|
|
1118
|
+
23 | | expect(parseGateLine('workflow | ruling | TE 悬置 | pending')?.at).toBe('workflow');
|
|
1119
|
+
24 | | expect(parseGateLine('t-013 | ruling | 载体指示待裁 | approved:user:decisions/019.md')?.ruling).toEqual({
|
|
1120
|
+
25 | | status: 'approved',
|
|
1121
|
+
26 | | decidedBy: 'user',
|
|
1122
|
+
27 | | evidence: 'decisions/019.md',
|
|
1123
|
+
28 | | });
|
|
1124
|
+
29 | | expect(parseGateLine('t-013 | ruling | 载体指示待裁 | rejected:user')?.ruling).toEqual({
|
|
1125
|
+
30 | | status: 'rejected',
|
|
1126
|
+
31 | | decidedBy: 'user',
|
|
1127
|
+
32 | | });
|
|
1128
|
+
33 | | expect(parseGateLine('t-013 | ruling | 载体指示待裁 | approved')).toBeNull();
|
|
1129
|
+
34 | | });
|
|
1130
|
+
35 | | });
|
|
1131
|
+
36 | |
|
|
1132
|
+
37 | | describe('状态转移表执法', () => {
|
|
1133
|
+
38 | | test('合法/非法转移判定', () => {
|
|
1134
|
+
39 | | expect(checkStatusTransition('todo', 'doing')).toBeNull();
|
|
1135
|
+
40 | | expect(checkStatusTransition('doing', 'blocked')).toBeNull();
|
|
1136
|
+
41 | | expect(checkStatusTransition('done', 'todo')).toBeNull();
|
|
1137
|
+
42 | | const error = checkStatusTransition('todo', 'done');
|
|
1138
|
+
43 | | expect(error?.code).toBe('INVALID_TRANSITION');
|
|
1139
|
+
44 | | expect(error?.message).toContain('todo → done');
|
|
1140
|
+
45 | | });
|
|
1141
|
+
46 | | });
|
|
1142
|
+
47 | |
|
|
1143
|
+
48 | | describe('视图派生(依赖门控与未决裁定)', () => {
|
|
1144
|
+
49 | | /**
|
|
1145
|
+
50 | | * 拓扑:a -> b(b 挂门);c 独立;workflow 级门一枚
|
|
1146
|
+
51 | | */
|
|
1147
|
+
52 | | const items: readonly WorkflowItem[] = [
|
|
1148
|
+
53 | | { id: 'a', title: '甲', ref: 'ref:demo/a.md', status: 'todo' },
|
|
1149
|
+
54 | | { id: 'b', title: '乙', ref: 'ref:demo/b.md', status: 'todo' },
|
|
1150
|
+
55 | | { id: 'c', title: '丙', ref: 'task:demo/c-item', status: 'doing' },
|
|
1151
|
+
56 | | ];
|
|
1152
|
+
57 | | const edges: readonly WorkflowEdge[] = [{ from: 'a', to: 'b' }];
|
|
1153
|
+
58 | | const gates: readonly WorkflowGate[] = [
|
|
1154
|
+
59 | | { at: 'b', kind: 'ruling', note: '乙项须裁定', ruling: { status: 'pending' } },
|
|
1155
|
+
60 | | { at: 'workflow', kind: 'ruling', note: '工作流级悬置', ruling: { status: 'pending' } },
|
|
1156
|
+
61 | | ];
|
|
1157
|
+
62 | |
|
|
1158
|
+
63 | | test('依赖未满足派生阻塞;门未批不可启动;未决裁定含工作流级', () => {
|
|
1159
|
+
64 | | const view = deriveWorkflowView(items, edges, gates);
|
|
1160
|
+
65 | | const byId = new Map(view.items.map((entry) => [entry.id, entry]));
|
|
1161
|
+
66 | |
|
|
1162
|
+
67 | | expect(byId.get('a')?.canStart).toBe(true);
|
|
1163
|
+
68 | | expect(byId.get('b')?.blockedOnPrerequisite).toBe(true);
|
|
1164
|
+
69 | | expect(byId.get('b')?.canStart).toBe(false);
|
|
1165
|
+
70 | | expect(byId.get('c')?.canStart).toBe(false);
|
|
1166
|
+
71 | | expect(view.pendingRulings.map((ruling) => ruling.key)).toEqual(['b:ruling', 'workflow:ruling']);
|
|
1167
|
+
72 | | });
|
|
1168
|
+
73 | |
|
|
1169
|
+
74 | | test('前置闭环解除阻塞;门批准解除门控;escalated 仍属未决', () => {
|
|
1170
|
+
75 | | const settledItems: readonly WorkflowItem[] = [
|
|
1171
|
+
76 | | { id: 'a', title: '甲', ref: 'ref:demo/a.md', status: 'done' },
|
|
1172
|
+
77 | | { id: 'b', title: '乙', ref: 'ref:demo/b.md', status: 'todo' },
|
|
1173
|
+
78 | | ];
|
|
1174
|
+
79 | | const approvedGates: readonly WorkflowGate[] = [
|
|
1175
|
+
80 | | { at: 'b', kind: 'ruling', note: '已裁', ruling: { status: 'approved', decidedBy: 'user' } },
|
|
1176
|
+
81 | | { at: 'workflow', kind: 'ruling', note: '升级待裁', ruling: { status: 'escalated' } },
|
|
1177
|
+
82 | | ];
|
|
1178
|
+
83 | | const view = deriveWorkflowView(settledItems, edges, approvedGates);
|
|
1179
|
+
84 | | const byId = new Map(view.items.map((entry) => [entry.id, entry]));
|
|
1180
|
+
85 | |
|
|
1181
|
+
86 | | expect(byId.get('b')?.blockedOnPrerequisite).toBe(false);
|
|
1182
|
+
87 | | expect(byId.get('b')?.canStart).toBe(true);
|
|
1183
|
+
88 | | expect(view.pendingRulings.map((ruling) => ruling.rulingStatus)).toEqual(['escalated']);
|
|
1184
|
+
89 | | });
|
|
1185
|
+
90 | `-> });
|
|
1186
|
+
`----
|
|
1187
|
+
|
|
1188
|
+
x @longzai-intelligence-oxlint/file-naming-plugin(require-type-suffix): 文件 "definition.ts" 缺少类型后缀。除特殊文件外,所有文件应使用 xxx.yyy.ts 格式明确表达用途。建议: .utils.ts, .config.ts, .constants.ts
|
|
1189
|
+
,-[src/types/definition.ts:1:1]
|
|
1190
|
+
1 | ,-> export type DefinitionDTO = {
|
|
1191
|
+
2 | | id: string;
|
|
1192
|
+
3 | | name: string;
|
|
1193
|
+
4 | | description: string | null;
|
|
1194
|
+
5 | | version: number;
|
|
1195
|
+
6 | | nodes: WorkflowNodeDTO[];
|
|
1196
|
+
7 | | edges: WorkflowEdgeDTO[];
|
|
1197
|
+
8 | | initialState: string;
|
|
1198
|
+
9 | | states: string[];
|
|
1199
|
+
10 | | publishedAt: string | null;
|
|
1200
|
+
11 | | createdAt: string;
|
|
1201
|
+
12 | | updatedAt: string;
|
|
1202
|
+
13 | | };
|
|
1203
|
+
14 | |
|
|
1204
|
+
15 | | export type WorkflowNodeDTO = {
|
|
1205
|
+
16 | | nodeId: string;
|
|
1206
|
+
17 | | name: string;
|
|
1207
|
+
18 | | type: string;
|
|
1208
|
+
19 | | properties: Record<string, unknown>;
|
|
1209
|
+
20 | | position: { x: number; y: number };
|
|
1210
|
+
21 | | };
|
|
1211
|
+
22 | |
|
|
1212
|
+
23 | | export type WorkflowEdgeDTO = {
|
|
1213
|
+
24 | | edgeId: string;
|
|
1214
|
+
25 | | sourceNodeId: string;
|
|
1215
|
+
26 | | targetNodeId: string;
|
|
1216
|
+
27 | | condition?: string;
|
|
1217
|
+
28 | | label?: string;
|
|
1218
|
+
29 | | };
|
|
1219
|
+
30 | |
|
|
1220
|
+
31 | | export type CreateDefinitionInput = {
|
|
1221
|
+
32 | | name: string;
|
|
1222
|
+
33 | | description?: string;
|
|
1223
|
+
34 | | nodes: WorkflowNodeDTO[];
|
|
1224
|
+
35 | | edges: WorkflowEdgeDTO[];
|
|
1225
|
+
36 | | initialState: string;
|
|
1226
|
+
37 | | states: string[];
|
|
1227
|
+
38 | | transitions: StateTransitionDTO[];
|
|
1228
|
+
39 | | };
|
|
1229
|
+
40 | |
|
|
1230
|
+
41 | | export type StateTransitionDTO = {
|
|
1231
|
+
42 | | from: string;
|
|
1232
|
+
43 | | to: string;
|
|
1233
|
+
44 | | event: string;
|
|
1234
|
+
45 | | guard?: string;
|
|
1235
|
+
46 | | action?: string;
|
|
1236
|
+
47 | | };
|
|
1237
|
+
48 | |
|
|
1238
|
+
49 | `-> export type UpdateDefinitionInput = Partial<CreateDefinitionInput>;
|
|
1239
|
+
`----
|
|
1240
|
+
|
|
1241
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(padding-line-between-statements): export 语句之间需要空行
|
|
1242
|
+
,-[src/schemas/index.ts:2:1]
|
|
1243
|
+
1 | export * from './definition.schema';
|
|
1244
|
+
2 | export * from './workflow-doc.schema';
|
|
1245
|
+
: ^
|
|
1246
|
+
3 | export * from './instance.schema';
|
|
1247
|
+
`----
|
|
1248
|
+
|
|
1249
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(padding-line-between-statements): export 语句之间需要空行
|
|
1250
|
+
,-[src/schemas/index.ts:3:1]
|
|
1251
|
+
2 | export * from './workflow-doc.schema';
|
|
1252
|
+
3 | export * from './instance.schema';
|
|
1253
|
+
: ^
|
|
1254
|
+
4 | export * from './trigger.schema';
|
|
1255
|
+
`----
|
|
1256
|
+
|
|
1257
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(padding-line-between-statements): export 语句之间需要空行
|
|
1258
|
+
,-[src/schemas/index.ts:4:1]
|
|
1259
|
+
3 | export * from './instance.schema';
|
|
1260
|
+
4 | export * from './trigger.schema';
|
|
1261
|
+
: ^
|
|
1262
|
+
5 | export * from './monitoring.schema';
|
|
1263
|
+
`----
|
|
1264
|
+
|
|
1265
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(padding-line-between-statements): export 语句之间需要空行
|
|
1266
|
+
,-[src/schemas/index.ts:5:1]
|
|
1267
|
+
4 | export * from './trigger.schema';
|
|
1268
|
+
5 | export * from './monitoring.schema';
|
|
1269
|
+
: ^
|
|
1270
|
+
6 | export * from './feed-event-trigger.schema';
|
|
1271
|
+
`----
|
|
1272
|
+
|
|
1273
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(padding-line-between-statements): export 语句之间需要空行
|
|
1274
|
+
,-[src/schemas/index.ts:6:1]
|
|
1275
|
+
5 | export * from './monitoring.schema';
|
|
1276
|
+
6 | export * from './feed-event-trigger.schema';
|
|
1277
|
+
: ^
|
|
1278
|
+
7 | export * from './action-executor.schema';
|
|
1279
|
+
`----
|
|
1280
|
+
|
|
1281
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(padding-line-between-statements): export 语句之间需要空行
|
|
1282
|
+
,-[src/schemas/index.ts:7:1]
|
|
1283
|
+
6 | export * from './feed-event-trigger.schema';
|
|
1284
|
+
7 | export * from './action-executor.schema';
|
|
1285
|
+
: ^
|
|
1286
|
+
8 | export * from './workflow-doc.schema';
|
|
1287
|
+
`----
|
|
1288
|
+
|
|
1289
|
+
x @longzai-intelligence-oxlint/stylistic-plugin(padding-line-between-statements): export 语句之间需要空行
|
|
1290
|
+
,-[src/schemas/index.ts:8:1]
|
|
1291
|
+
7 | export * from './action-executor.schema';
|
|
1292
|
+
8 | export * from './workflow-doc.schema';
|
|
1293
|
+
: ^
|
|
1294
|
+
`----
|
|
1295
|
+
|
|
1296
|
+
x @longzai-intelligence-oxlint/file-naming-plugin(require-type-suffix): 文件 "api.ts" 缺少类型后缀。除特殊文件外,所有文件应使用 xxx.yyy.ts 格式明确表达用途。建议: .utils.ts, .config.ts, .constants.ts
|
|
1297
|
+
,-[src/types/api.ts:10:1]
|
|
1298
|
+
9 | */
|
|
1299
|
+
10 | export {};
|
|
1300
|
+
: ^^^^^^^^^^^
|
|
1301
|
+
`----
|
|
1302
|
+
|
|
1303
|
+
Found 8 warnings and 93 errors.
|
|
1304
|
+
Finished in 938ms on 31 files with 199 rules using 10 threads.
|
|
1305
|
+
error: script "lint" exited with code 1
|