@webpieces/dev-config 0.2.94 → 0.2.97
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/config/eslint/base.mjs +1 -1
- package/executors.json +6 -91
- package/package.json +6 -19
- package/{executors → src/executors}/help/executor.d.ts +4 -2
- package/src/executors/help/executor.js.map +1 -0
- package/{executors → src/executors}/validate-eslint-sync/executor.d.ts +3 -2
- package/src/executors/validate-eslint-sync/executor.js.map +1 -0
- package/{executors → src/executors}/validate-versions-locked/executor.js +5 -3
- package/src/executors/validate-versions-locked/executor.js.map +1 -0
- package/src/generators/init/generator.js.map +1 -1
- package/src/index.d.ts +1 -1
- package/src/index.js +1 -1
- package/src/index.js.map +1 -1
- package/src/plugin.d.ts +86 -0
- package/{plugin.js → src/plugin.js} +31 -15
- package/src/plugin.js.map +1 -0
- package/src/toError.d.ts +5 -0
- package/src/toError.js +37 -0
- package/src/toError.js.map +1 -0
- package/templates/eslint.webpieces.config.mjs +1 -1
- package/templates/webpieces.exceptions.md +15 -15
- package/architecture/executors/diff-utils.d.ts +0 -24
- package/architecture/executors/diff-utils.js +0 -119
- package/architecture/executors/diff-utils.js.map +0 -1
- package/architecture/executors/diff-utils.ts +0 -127
- package/architecture/executors/generate/executor.d.ts +0 -16
- package/architecture/executors/generate/executor.js +0 -44
- package/architecture/executors/generate/executor.js.map +0 -1
- package/architecture/executors/generate/executor.ts +0 -59
- package/architecture/executors/generate/schema.json +0 -14
- package/architecture/executors/validate-architecture-unchanged/executor.d.ts +0 -17
- package/architecture/executors/validate-architecture-unchanged/executor.js +0 -229
- package/architecture/executors/validate-architecture-unchanged/executor.js.map +0 -1
- package/architecture/executors/validate-architecture-unchanged/executor.ts +0 -251
- package/architecture/executors/validate-architecture-unchanged/schema.json +0 -14
- package/architecture/executors/validate-code/executor.d.ts +0 -78
- package/architecture/executors/validate-code/executor.js +0 -243
- package/architecture/executors/validate-code/executor.js.map +0 -1
- package/architecture/executors/validate-code/executor.ts +0 -406
- package/architecture/executors/validate-code/schema.json +0 -227
- package/architecture/executors/validate-dtos/executor.d.ts +0 -42
- package/architecture/executors/validate-dtos/executor.js +0 -561
- package/architecture/executors/validate-dtos/executor.js.map +0 -1
- package/architecture/executors/validate-dtos/executor.ts +0 -689
- package/architecture/executors/validate-dtos/schema.json +0 -33
- package/architecture/executors/validate-modified-files/executor.d.ts +0 -25
- package/architecture/executors/validate-modified-files/executor.js +0 -501
- package/architecture/executors/validate-modified-files/executor.js.map +0 -1
- package/architecture/executors/validate-modified-files/executor.ts +0 -571
- package/architecture/executors/validate-modified-files/schema.json +0 -25
- package/architecture/executors/validate-modified-methods/executor.d.ts +0 -31
- package/architecture/executors/validate-modified-methods/executor.js +0 -694
- package/architecture/executors/validate-modified-methods/executor.js.map +0 -1
- package/architecture/executors/validate-modified-methods/executor.ts +0 -797
- package/architecture/executors/validate-modified-methods/schema.json +0 -25
- package/architecture/executors/validate-new-methods/executor.d.ts +0 -28
- package/architecture/executors/validate-new-methods/executor.js +0 -513
- package/architecture/executors/validate-new-methods/executor.js.map +0 -1
- package/architecture/executors/validate-new-methods/executor.ts +0 -584
- package/architecture/executors/validate-new-methods/schema.json +0 -25
- package/architecture/executors/validate-no-any-unknown/executor.d.ts +0 -42
- package/architecture/executors/validate-no-any-unknown/executor.js +0 -462
- package/architecture/executors/validate-no-any-unknown/executor.js.map +0 -1
- package/architecture/executors/validate-no-any-unknown/executor.ts +0 -540
- package/architecture/executors/validate-no-any-unknown/schema.json +0 -24
- package/architecture/executors/validate-no-architecture-cycles/executor.d.ts +0 -16
- package/architecture/executors/validate-no-architecture-cycles/executor.js +0 -48
- package/architecture/executors/validate-no-architecture-cycles/executor.js.map +0 -1
- package/architecture/executors/validate-no-architecture-cycles/executor.ts +0 -60
- package/architecture/executors/validate-no-architecture-cycles/schema.json +0 -8
- package/architecture/executors/validate-no-destructure/executor.d.ts +0 -52
- package/architecture/executors/validate-no-destructure/executor.js +0 -491
- package/architecture/executors/validate-no-destructure/executor.js.map +0 -1
- package/architecture/executors/validate-no-destructure/executor.ts +0 -578
- package/architecture/executors/validate-no-destructure/schema.json +0 -24
- package/architecture/executors/validate-no-direct-api-resolver/executor.d.ts +0 -47
- package/architecture/executors/validate-no-direct-api-resolver/executor.js +0 -566
- package/architecture/executors/validate-no-direct-api-resolver/executor.js.map +0 -1
- package/architecture/executors/validate-no-direct-api-resolver/executor.ts +0 -666
- package/architecture/executors/validate-no-direct-api-resolver/schema.json +0 -29
- package/architecture/executors/validate-no-inline-types/executor.d.ts +0 -91
- package/architecture/executors/validate-no-inline-types/executor.js +0 -669
- package/architecture/executors/validate-no-inline-types/executor.js.map +0 -1
- package/architecture/executors/validate-no-inline-types/executor.ts +0 -775
- package/architecture/executors/validate-no-inline-types/schema.json +0 -24
- package/architecture/executors/validate-no-skiplevel-deps/executor.d.ts +0 -19
- package/architecture/executors/validate-no-skiplevel-deps/executor.js +0 -227
- package/architecture/executors/validate-no-skiplevel-deps/executor.js.map +0 -1
- package/architecture/executors/validate-no-skiplevel-deps/executor.ts +0 -267
- package/architecture/executors/validate-no-skiplevel-deps/schema.json +0 -8
- package/architecture/executors/validate-packagejson/executor.d.ts +0 -16
- package/architecture/executors/validate-packagejson/executor.js +0 -57
- package/architecture/executors/validate-packagejson/executor.js.map +0 -1
- package/architecture/executors/validate-packagejson/executor.ts +0 -74
- package/architecture/executors/validate-packagejson/schema.json +0 -8
- package/architecture/executors/validate-prisma-converters/executor.d.ts +0 -60
- package/architecture/executors/validate-prisma-converters/executor.js +0 -634
- package/architecture/executors/validate-prisma-converters/executor.js.map +0 -1
- package/architecture/executors/validate-prisma-converters/executor.ts +0 -822
- package/architecture/executors/validate-prisma-converters/schema.json +0 -38
- package/architecture/executors/validate-return-types/executor.d.ts +0 -29
- package/architecture/executors/validate-return-types/executor.js +0 -439
- package/architecture/executors/validate-return-types/executor.js.map +0 -1
- package/architecture/executors/validate-return-types/executor.ts +0 -524
- package/architecture/executors/validate-return-types/schema.json +0 -24
- package/architecture/executors/visualize/executor.d.ts +0 -17
- package/architecture/executors/visualize/executor.js +0 -49
- package/architecture/executors/visualize/executor.js.map +0 -1
- package/architecture/executors/visualize/executor.ts +0 -63
- package/architecture/executors/visualize/schema.json +0 -14
- package/architecture/index.d.ts +0 -19
- package/architecture/index.js +0 -23
- package/architecture/index.js.map +0 -1
- package/architecture/index.ts +0 -20
- package/architecture/lib/graph-comparator.d.ts +0 -39
- package/architecture/lib/graph-comparator.js +0 -100
- package/architecture/lib/graph-comparator.js.map +0 -1
- package/architecture/lib/graph-comparator.ts +0 -141
- package/architecture/lib/graph-generator.d.ts +0 -19
- package/architecture/lib/graph-generator.js +0 -84
- package/architecture/lib/graph-generator.js.map +0 -1
- package/architecture/lib/graph-generator.ts +0 -97
- package/architecture/lib/graph-loader.d.ts +0 -31
- package/architecture/lib/graph-loader.js +0 -98
- package/architecture/lib/graph-loader.js.map +0 -1
- package/architecture/lib/graph-loader.ts +0 -116
- package/architecture/lib/graph-sorter.d.ts +0 -37
- package/architecture/lib/graph-sorter.js +0 -110
- package/architecture/lib/graph-sorter.js.map +0 -1
- package/architecture/lib/graph-sorter.ts +0 -137
- package/architecture/lib/graph-visualizer.d.ts +0 -29
- package/architecture/lib/graph-visualizer.js +0 -217
- package/architecture/lib/graph-visualizer.js.map +0 -1
- package/architecture/lib/graph-visualizer.ts +0 -231
- package/architecture/lib/package-validator.d.ts +0 -38
- package/architecture/lib/package-validator.js +0 -126
- package/architecture/lib/package-validator.js.map +0 -1
- package/architecture/lib/package-validator.ts +0 -170
- package/eslint-plugin/__tests__/catch-error-pattern.test.ts +0 -359
- package/eslint-plugin/__tests__/max-file-lines.test.ts +0 -207
- package/eslint-plugin/__tests__/max-method-lines.test.ts +0 -258
- package/eslint-plugin/__tests__/no-unmanaged-exceptions.test.ts +0 -359
- package/eslint-plugin/index.d.ts +0 -23
- package/eslint-plugin/index.js +0 -30
- package/eslint-plugin/index.js.map +0 -1
- package/eslint-plugin/index.ts +0 -29
- package/eslint-plugin/rules/catch-error-pattern.d.ts +0 -11
- package/eslint-plugin/rules/catch-error-pattern.js +0 -196
- package/eslint-plugin/rules/catch-error-pattern.js.map +0 -1
- package/eslint-plugin/rules/catch-error-pattern.ts +0 -281
- package/eslint-plugin/rules/enforce-architecture.d.ts +0 -15
- package/eslint-plugin/rules/enforce-architecture.js +0 -476
- package/eslint-plugin/rules/enforce-architecture.js.map +0 -1
- package/eslint-plugin/rules/enforce-architecture.ts +0 -543
- package/eslint-plugin/rules/max-file-lines.d.ts +0 -12
- package/eslint-plugin/rules/max-file-lines.js +0 -257
- package/eslint-plugin/rules/max-file-lines.js.map +0 -1
- package/eslint-plugin/rules/max-file-lines.ts +0 -272
- package/eslint-plugin/rules/max-method-lines.d.ts +0 -12
- package/eslint-plugin/rules/max-method-lines.js +0 -240
- package/eslint-plugin/rules/max-method-lines.js.map +0 -1
- package/eslint-plugin/rules/max-method-lines.ts +0 -287
- package/eslint-plugin/rules/no-unmanaged-exceptions.d.ts +0 -22
- package/eslint-plugin/rules/no-unmanaged-exceptions.js +0 -160
- package/eslint-plugin/rules/no-unmanaged-exceptions.js.map +0 -1
- package/eslint-plugin/rules/no-unmanaged-exceptions.ts +0 -179
- package/executors/help/executor.js.map +0 -1
- package/executors/help/executor.ts +0 -61
- package/executors/validate-eslint-sync/executor.js.map +0 -1
- package/executors/validate-eslint-sync/executor.ts +0 -83
- package/executors/validate-versions-locked/executor.js.map +0 -1
- package/executors/validate-versions-locked/executor.ts +0 -367
- package/plugin/README.md +0 -243
- package/plugin/index.d.ts +0 -4
- package/plugin/index.js +0 -8
- package/plugin/index.js.map +0 -1
- package/plugin/index.ts +0 -4
- /package/{executors → src/executors}/help/executor.js +0 -0
- /package/{executors → src/executors}/help/schema.json +0 -0
- /package/{executors → src/executors}/validate-eslint-sync/executor.js +0 -0
- /package/{executors → src/executors}/validate-eslint-sync/schema.json +0 -0
- /package/{executors → src/executors}/validate-versions-locked/executor.d.ts +0 -0
- /package/{executors → src/executors}/validate-versions-locked/schema.json +0 -0
|
@@ -1,359 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Tests for no-unmanaged-exceptions ESLint rule
|
|
3
|
-
*
|
|
4
|
-
* Validates that try-catch blocks are:
|
|
5
|
-
* - Auto-allowed in test files (.test.ts, .spec.ts, __tests__/)
|
|
6
|
-
* - Allowed with eslint-disable comment
|
|
7
|
-
* - Disallowed in production code without approval
|
|
8
|
-
*/
|
|
9
|
-
|
|
10
|
-
import { RuleTester } from 'eslint';
|
|
11
|
-
import rule from '../rules/no-unmanaged-exceptions';
|
|
12
|
-
|
|
13
|
-
const tsParser = require('@typescript-eslint/parser');
|
|
14
|
-
|
|
15
|
-
const ruleTester = new RuleTester({
|
|
16
|
-
languageOptions: {
|
|
17
|
-
parser: tsParser,
|
|
18
|
-
parserOptions: {
|
|
19
|
-
ecmaVersion: 2020,
|
|
20
|
-
sourceType: 'module',
|
|
21
|
-
},
|
|
22
|
-
},
|
|
23
|
-
});
|
|
24
|
-
|
|
25
|
-
ruleTester.run('no-unmanaged-exceptions', rule, {
|
|
26
|
-
valid: [
|
|
27
|
-
// ============================================
|
|
28
|
-
// Test files - auto-allowed
|
|
29
|
-
// ============================================
|
|
30
|
-
{
|
|
31
|
-
code: `
|
|
32
|
-
try {
|
|
33
|
-
await operation();
|
|
34
|
-
} catch (err: any) {
|
|
35
|
-
const error = toError(err);
|
|
36
|
-
expect(error).toBeDefined();
|
|
37
|
-
}
|
|
38
|
-
`,
|
|
39
|
-
filename: 'SaveController.test.ts',
|
|
40
|
-
},
|
|
41
|
-
{
|
|
42
|
-
code: `
|
|
43
|
-
try {
|
|
44
|
-
await controller.save(request);
|
|
45
|
-
fail('Should have thrown');
|
|
46
|
-
} catch (err: any) {
|
|
47
|
-
const error = toError(err);
|
|
48
|
-
expect(error.message).toContain('Invalid');
|
|
49
|
-
}
|
|
50
|
-
`,
|
|
51
|
-
filename: 'packages/http/http-server/src/SaveController.test.ts',
|
|
52
|
-
},
|
|
53
|
-
|
|
54
|
-
// Spec files - auto-allowed
|
|
55
|
-
{
|
|
56
|
-
code: `
|
|
57
|
-
try {
|
|
58
|
-
await operation();
|
|
59
|
-
} catch (err: any) {
|
|
60
|
-
const error = toError(err);
|
|
61
|
-
}
|
|
62
|
-
`,
|
|
63
|
-
filename: 'userService.spec.ts',
|
|
64
|
-
},
|
|
65
|
-
{
|
|
66
|
-
code: `
|
|
67
|
-
it('should throw error', async () => {
|
|
68
|
-
try {
|
|
69
|
-
await service.process();
|
|
70
|
-
fail();
|
|
71
|
-
} catch (err: any) {
|
|
72
|
-
const error = toError(err);
|
|
73
|
-
expect(error).toBeDefined();
|
|
74
|
-
}
|
|
75
|
-
});
|
|
76
|
-
`,
|
|
77
|
-
filename: 'packages/services/user/userService.spec.ts',
|
|
78
|
-
},
|
|
79
|
-
|
|
80
|
-
// __tests__ directory - auto-allowed (need full path)
|
|
81
|
-
{
|
|
82
|
-
code: `
|
|
83
|
-
try {
|
|
84
|
-
await operation();
|
|
85
|
-
} catch (err: any) {
|
|
86
|
-
const error = toError(err);
|
|
87
|
-
}
|
|
88
|
-
`,
|
|
89
|
-
filename: '/project/__tests__/integration.ts',
|
|
90
|
-
},
|
|
91
|
-
{
|
|
92
|
-
code: `
|
|
93
|
-
try {
|
|
94
|
-
await runIntegrationTest();
|
|
95
|
-
} catch (err: any) {
|
|
96
|
-
const error = toError(err);
|
|
97
|
-
console.error(error);
|
|
98
|
-
}
|
|
99
|
-
`,
|
|
100
|
-
filename: '/project/packages/http/__tests__/server-integration.ts',
|
|
101
|
-
},
|
|
102
|
-
{
|
|
103
|
-
code: `
|
|
104
|
-
try {
|
|
105
|
-
const result = performAction();
|
|
106
|
-
} catch (err: any) {
|
|
107
|
-
const error = toError(err);
|
|
108
|
-
}
|
|
109
|
-
`,
|
|
110
|
-
filename: '/project/src/__tests__/helpers/testUtils.ts',
|
|
111
|
-
},
|
|
112
|
-
|
|
113
|
-
// ============================================
|
|
114
|
-
// Code without try-catch (preferred pattern)
|
|
115
|
-
// ============================================
|
|
116
|
-
{
|
|
117
|
-
code: `
|
|
118
|
-
async function processOrder(order: Order): Promise<void> {
|
|
119
|
-
await validateOrder(order);
|
|
120
|
-
await saveToDatabase(order);
|
|
121
|
-
}
|
|
122
|
-
`,
|
|
123
|
-
filename: 'OrderService.ts',
|
|
124
|
-
},
|
|
125
|
-
{
|
|
126
|
-
code: `
|
|
127
|
-
export class SaveController {
|
|
128
|
-
async save(request: SaveRequest): Promise<SaveResponse> {
|
|
129
|
-
const result = await this.service.save(request);
|
|
130
|
-
return result;
|
|
131
|
-
}
|
|
132
|
-
}
|
|
133
|
-
`,
|
|
134
|
-
filename: 'packages/http/http-server/src/SaveController.ts',
|
|
135
|
-
},
|
|
136
|
-
|
|
137
|
-
// ============================================
|
|
138
|
-
// Nested functions without try-catch
|
|
139
|
-
// ============================================
|
|
140
|
-
{
|
|
141
|
-
code: `
|
|
142
|
-
function outer() {
|
|
143
|
-
function inner() {
|
|
144
|
-
return doSomething();
|
|
145
|
-
}
|
|
146
|
-
return inner();
|
|
147
|
-
}
|
|
148
|
-
`,
|
|
149
|
-
filename: 'Utils.ts',
|
|
150
|
-
},
|
|
151
|
-
],
|
|
152
|
-
|
|
153
|
-
invalid: [
|
|
154
|
-
// ============================================
|
|
155
|
-
// Controllers without approval
|
|
156
|
-
// ============================================
|
|
157
|
-
{
|
|
158
|
-
code: `
|
|
159
|
-
try {
|
|
160
|
-
await operation();
|
|
161
|
-
} catch (err: any) {
|
|
162
|
-
const error = toError(err);
|
|
163
|
-
}
|
|
164
|
-
`,
|
|
165
|
-
filename: 'SaveController.ts',
|
|
166
|
-
errors: [{ messageId: 'noUnmanagedExceptions' }],
|
|
167
|
-
},
|
|
168
|
-
{
|
|
169
|
-
code: `
|
|
170
|
-
export class SaveController {
|
|
171
|
-
async save(request: SaveRequest): Promise<SaveResponse> {
|
|
172
|
-
try {
|
|
173
|
-
const result = await this.service.save(request);
|
|
174
|
-
return result;
|
|
175
|
-
} catch (err: any) {
|
|
176
|
-
const error = toError(err);
|
|
177
|
-
throw error;
|
|
178
|
-
}
|
|
179
|
-
}
|
|
180
|
-
}
|
|
181
|
-
`,
|
|
182
|
-
filename: 'packages/http/http-server/src/SaveController.ts',
|
|
183
|
-
errors: [{ messageId: 'noUnmanagedExceptions' }],
|
|
184
|
-
},
|
|
185
|
-
|
|
186
|
-
// ============================================
|
|
187
|
-
// Services without approval
|
|
188
|
-
// ============================================
|
|
189
|
-
{
|
|
190
|
-
code: `
|
|
191
|
-
try {
|
|
192
|
-
await this.database.query(sql);
|
|
193
|
-
} catch (err: any) {
|
|
194
|
-
const error = toError(err);
|
|
195
|
-
}
|
|
196
|
-
`,
|
|
197
|
-
filename: 'UserService.ts',
|
|
198
|
-
errors: [{ messageId: 'noUnmanagedExceptions' }],
|
|
199
|
-
},
|
|
200
|
-
{
|
|
201
|
-
code: `
|
|
202
|
-
export class UserService {
|
|
203
|
-
async getUserById(id: string): Promise<User> {
|
|
204
|
-
try {
|
|
205
|
-
const user = await this.db.findOne({ id });
|
|
206
|
-
return user;
|
|
207
|
-
} catch (err: any) {
|
|
208
|
-
const error = toError(err);
|
|
209
|
-
console.error('Failed to fetch user:', error);
|
|
210
|
-
return null;
|
|
211
|
-
}
|
|
212
|
-
}
|
|
213
|
-
}
|
|
214
|
-
`,
|
|
215
|
-
filename: 'packages/services/user/UserService.ts',
|
|
216
|
-
errors: [{ messageId: 'noUnmanagedExceptions' }],
|
|
217
|
-
},
|
|
218
|
-
|
|
219
|
-
// ============================================
|
|
220
|
-
// Filters without approval
|
|
221
|
-
// ============================================
|
|
222
|
-
{
|
|
223
|
-
code: `
|
|
224
|
-
try {
|
|
225
|
-
return JSON.parse(body);
|
|
226
|
-
} catch (err: any) {
|
|
227
|
-
const error = toError(err);
|
|
228
|
-
}
|
|
229
|
-
`,
|
|
230
|
-
filename: 'JsonFilter.ts',
|
|
231
|
-
errors: [{ messageId: 'noUnmanagedExceptions' }],
|
|
232
|
-
},
|
|
233
|
-
{
|
|
234
|
-
code: `
|
|
235
|
-
export class LogFilter implements Filter {
|
|
236
|
-
async filter(meta: MethodMeta, next: NextFilter): Promise<Action> {
|
|
237
|
-
try {
|
|
238
|
-
return await next.execute();
|
|
239
|
-
} catch (err: any) {
|
|
240
|
-
const error = toError(err);
|
|
241
|
-
console.error('Filter error:', error);
|
|
242
|
-
throw error;
|
|
243
|
-
}
|
|
244
|
-
}
|
|
245
|
-
}
|
|
246
|
-
`,
|
|
247
|
-
filename: 'packages/http/http-server/src/filters/LogFilter.ts',
|
|
248
|
-
errors: [{ messageId: 'noUnmanagedExceptions' }],
|
|
249
|
-
},
|
|
250
|
-
|
|
251
|
-
// ============================================
|
|
252
|
-
// Utility functions without approval
|
|
253
|
-
// ============================================
|
|
254
|
-
{
|
|
255
|
-
code: `
|
|
256
|
-
async function fetchData(url: string): Promise<Data> {
|
|
257
|
-
try {
|
|
258
|
-
const response = await fetch(url);
|
|
259
|
-
return await response.json();
|
|
260
|
-
} catch (err: any) {
|
|
261
|
-
const error = toError(err);
|
|
262
|
-
throw new Error(\`Fetch failed: \${error.message}\`);
|
|
263
|
-
}
|
|
264
|
-
}
|
|
265
|
-
`,
|
|
266
|
-
filename: 'packages/core/core-util/src/httpUtils.ts',
|
|
267
|
-
errors: [{ messageId: 'noUnmanagedExceptions' }],
|
|
268
|
-
},
|
|
269
|
-
|
|
270
|
-
// ============================================
|
|
271
|
-
// Multiple try-catch blocks in one file
|
|
272
|
-
// ============================================
|
|
273
|
-
{
|
|
274
|
-
code: `
|
|
275
|
-
async function operation1() {
|
|
276
|
-
try {
|
|
277
|
-
await doSomething();
|
|
278
|
-
} catch (err: any) {
|
|
279
|
-
const error = toError(err);
|
|
280
|
-
}
|
|
281
|
-
}
|
|
282
|
-
|
|
283
|
-
async function operation2() {
|
|
284
|
-
try {
|
|
285
|
-
await doSomethingElse();
|
|
286
|
-
} catch (err: any) {
|
|
287
|
-
const error = toError(err);
|
|
288
|
-
}
|
|
289
|
-
}
|
|
290
|
-
`,
|
|
291
|
-
filename: 'MultipleOperations.ts',
|
|
292
|
-
errors: [
|
|
293
|
-
{ messageId: 'noUnmanagedExceptions' },
|
|
294
|
-
{ messageId: 'noUnmanagedExceptions' },
|
|
295
|
-
],
|
|
296
|
-
},
|
|
297
|
-
|
|
298
|
-
// ============================================
|
|
299
|
-
// Nested try-catch blocks
|
|
300
|
-
// ============================================
|
|
301
|
-
{
|
|
302
|
-
code: `
|
|
303
|
-
try {
|
|
304
|
-
try {
|
|
305
|
-
await operation();
|
|
306
|
-
} catch (err2: any) {
|
|
307
|
-
const error2 = toError(err2);
|
|
308
|
-
}
|
|
309
|
-
} catch (err: any) {
|
|
310
|
-
const error = toError(err);
|
|
311
|
-
}
|
|
312
|
-
`,
|
|
313
|
-
filename: 'NestedOperations.ts',
|
|
314
|
-
errors: [
|
|
315
|
-
{ messageId: 'noUnmanagedExceptions' },
|
|
316
|
-
{ messageId: 'noUnmanagedExceptions' },
|
|
317
|
-
],
|
|
318
|
-
},
|
|
319
|
-
|
|
320
|
-
// ============================================
|
|
321
|
-
// Try-catch in arrow functions
|
|
322
|
-
// ============================================
|
|
323
|
-
{
|
|
324
|
-
code: `
|
|
325
|
-
const handler = async () => {
|
|
326
|
-
try {
|
|
327
|
-
await doSomething();
|
|
328
|
-
} catch (err: any) {
|
|
329
|
-
const error = toError(err);
|
|
330
|
-
}
|
|
331
|
-
};
|
|
332
|
-
`,
|
|
333
|
-
filename: 'Handlers.ts',
|
|
334
|
-
errors: [{ messageId: 'noUnmanagedExceptions' }],
|
|
335
|
-
},
|
|
336
|
-
|
|
337
|
-
// ============================================
|
|
338
|
-
// Try-catch in class methods
|
|
339
|
-
// ============================================
|
|
340
|
-
{
|
|
341
|
-
code: `
|
|
342
|
-
export class DataProcessor {
|
|
343
|
-
process(data: Data): Result {
|
|
344
|
-
try {
|
|
345
|
-
return this.performProcessing(data);
|
|
346
|
-
} catch (err: any) {
|
|
347
|
-
const error = toError(err);
|
|
348
|
-
return null;
|
|
349
|
-
}
|
|
350
|
-
}
|
|
351
|
-
}
|
|
352
|
-
`,
|
|
353
|
-
filename: 'packages/processors/DataProcessor.ts',
|
|
354
|
-
errors: [{ messageId: 'noUnmanagedExceptions' }],
|
|
355
|
-
},
|
|
356
|
-
],
|
|
357
|
-
});
|
|
358
|
-
|
|
359
|
-
console.log('All no-unmanaged-exceptions tests passed!');
|
package/eslint-plugin/index.d.ts
DELETED
|
@@ -1,23 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* ESLint plugin for WebPieces
|
|
3
|
-
* Provides rules for enforcing WebPieces code patterns
|
|
4
|
-
*
|
|
5
|
-
* This plugin is automatically included in @webpieces/dev-config
|
|
6
|
-
*
|
|
7
|
-
* Available rules:
|
|
8
|
-
* - catch-error-pattern: Enforce toError() usage in catch blocks (HOW to handle)
|
|
9
|
-
* - no-unmanaged-exceptions: Discourage try-catch outside tests (WHERE to handle)
|
|
10
|
-
* - max-method-lines: Enforce maximum method length (default: 70 lines)
|
|
11
|
-
* - max-file-lines: Enforce maximum file length (default: 700 lines)
|
|
12
|
-
* - enforce-architecture: Enforce architecture dependency boundaries
|
|
13
|
-
*/
|
|
14
|
-
declare const _default: {
|
|
15
|
-
rules: {
|
|
16
|
-
'catch-error-pattern': import("eslint").Rule.RuleModule;
|
|
17
|
-
'no-unmanaged-exceptions': import("eslint").Rule.RuleModule;
|
|
18
|
-
'max-method-lines': import("eslint").Rule.RuleModule;
|
|
19
|
-
'max-file-lines': import("eslint").Rule.RuleModule;
|
|
20
|
-
'enforce-architecture': import("eslint").Rule.RuleModule;
|
|
21
|
-
};
|
|
22
|
-
};
|
|
23
|
-
export = _default;
|
package/eslint-plugin/index.js
DELETED
|
@@ -1,30 +0,0 @@
|
|
|
1
|
-
"use strict";
|
|
2
|
-
/**
|
|
3
|
-
* ESLint plugin for WebPieces
|
|
4
|
-
* Provides rules for enforcing WebPieces code patterns
|
|
5
|
-
*
|
|
6
|
-
* This plugin is automatically included in @webpieces/dev-config
|
|
7
|
-
*
|
|
8
|
-
* Available rules:
|
|
9
|
-
* - catch-error-pattern: Enforce toError() usage in catch blocks (HOW to handle)
|
|
10
|
-
* - no-unmanaged-exceptions: Discourage try-catch outside tests (WHERE to handle)
|
|
11
|
-
* - max-method-lines: Enforce maximum method length (default: 70 lines)
|
|
12
|
-
* - max-file-lines: Enforce maximum file length (default: 700 lines)
|
|
13
|
-
* - enforce-architecture: Enforce architecture dependency boundaries
|
|
14
|
-
*/
|
|
15
|
-
const tslib_1 = require("tslib");
|
|
16
|
-
const catch_error_pattern_1 = tslib_1.__importDefault(require("./rules/catch-error-pattern"));
|
|
17
|
-
const no_unmanaged_exceptions_1 = tslib_1.__importDefault(require("./rules/no-unmanaged-exceptions"));
|
|
18
|
-
const max_method_lines_1 = tslib_1.__importDefault(require("./rules/max-method-lines"));
|
|
19
|
-
const max_file_lines_1 = tslib_1.__importDefault(require("./rules/max-file-lines"));
|
|
20
|
-
const enforce_architecture_1 = tslib_1.__importDefault(require("./rules/enforce-architecture"));
|
|
21
|
-
module.exports = {
|
|
22
|
-
rules: {
|
|
23
|
-
'catch-error-pattern': catch_error_pattern_1.default,
|
|
24
|
-
'no-unmanaged-exceptions': no_unmanaged_exceptions_1.default,
|
|
25
|
-
'max-method-lines': max_method_lines_1.default,
|
|
26
|
-
'max-file-lines': max_file_lines_1.default,
|
|
27
|
-
'enforce-architecture': enforce_architecture_1.default,
|
|
28
|
-
},
|
|
29
|
-
};
|
|
30
|
-
//# sourceMappingURL=index.js.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../../../packages/tooling/dev-config/eslint-plugin/index.ts"],"names":[],"mappings":";AAAA;;;;;;;;;;;;GAYG;;AAEH,8FAA4D;AAC5D,sGAAoE;AACpE,wFAAsD;AACtD,oFAAkD;AAClD,gGAA+D;AAE/D,iBAAS;IACL,KAAK,EAAE;QACH,qBAAqB,EAAE,6BAAiB;QACxC,yBAAyB,EAAE,iCAAqB;QAChD,kBAAkB,EAAE,0BAAc;QAClC,gBAAgB,EAAE,wBAAY;QAC9B,sBAAsB,EAAE,8BAAmB;KAC9C;CACJ,CAAC","sourcesContent":["/**\n * ESLint plugin for WebPieces\n * Provides rules for enforcing WebPieces code patterns\n *\n * This plugin is automatically included in @webpieces/dev-config\n *\n * Available rules:\n * - catch-error-pattern: Enforce toError() usage in catch blocks (HOW to handle)\n * - no-unmanaged-exceptions: Discourage try-catch outside tests (WHERE to handle)\n * - max-method-lines: Enforce maximum method length (default: 70 lines)\n * - max-file-lines: Enforce maximum file length (default: 700 lines)\n * - enforce-architecture: Enforce architecture dependency boundaries\n */\n\nimport catchErrorPattern from './rules/catch-error-pattern';\nimport noUnmanagedExceptions from './rules/no-unmanaged-exceptions';\nimport maxMethodLines from './rules/max-method-lines';\nimport maxFileLines from './rules/max-file-lines';\nimport enforceArchitecture from './rules/enforce-architecture';\n\nexport = {\n rules: {\n 'catch-error-pattern': catchErrorPattern,\n 'no-unmanaged-exceptions': noUnmanagedExceptions,\n 'max-method-lines': maxMethodLines,\n 'max-file-lines': maxFileLines,\n 'enforce-architecture': enforceArchitecture,\n },\n};\n"]}
|
package/eslint-plugin/index.ts
DELETED
|
@@ -1,29 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* ESLint plugin for WebPieces
|
|
3
|
-
* Provides rules for enforcing WebPieces code patterns
|
|
4
|
-
*
|
|
5
|
-
* This plugin is automatically included in @webpieces/dev-config
|
|
6
|
-
*
|
|
7
|
-
* Available rules:
|
|
8
|
-
* - catch-error-pattern: Enforce toError() usage in catch blocks (HOW to handle)
|
|
9
|
-
* - no-unmanaged-exceptions: Discourage try-catch outside tests (WHERE to handle)
|
|
10
|
-
* - max-method-lines: Enforce maximum method length (default: 70 lines)
|
|
11
|
-
* - max-file-lines: Enforce maximum file length (default: 700 lines)
|
|
12
|
-
* - enforce-architecture: Enforce architecture dependency boundaries
|
|
13
|
-
*/
|
|
14
|
-
|
|
15
|
-
import catchErrorPattern from './rules/catch-error-pattern';
|
|
16
|
-
import noUnmanagedExceptions from './rules/no-unmanaged-exceptions';
|
|
17
|
-
import maxMethodLines from './rules/max-method-lines';
|
|
18
|
-
import maxFileLines from './rules/max-file-lines';
|
|
19
|
-
import enforceArchitecture from './rules/enforce-architecture';
|
|
20
|
-
|
|
21
|
-
export = {
|
|
22
|
-
rules: {
|
|
23
|
-
'catch-error-pattern': catchErrorPattern,
|
|
24
|
-
'no-unmanaged-exceptions': noUnmanagedExceptions,
|
|
25
|
-
'max-method-lines': maxMethodLines,
|
|
26
|
-
'max-file-lines': maxFileLines,
|
|
27
|
-
'enforce-architecture': enforceArchitecture,
|
|
28
|
-
},
|
|
29
|
-
};
|
|
@@ -1,11 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* ESLint rule to enforce standardized catch block error handling patterns
|
|
3
|
-
*
|
|
4
|
-
* Enforces three approved patterns:
|
|
5
|
-
* 1. Standard: catch (err: any) { const error = toError(err); }
|
|
6
|
-
* 2. Ignored: catch (err: any) { //const error = toError(err); }
|
|
7
|
-
* 3. Nested: catch (err2: any) { const error2 = toError(err2); }
|
|
8
|
-
*/
|
|
9
|
-
import type { Rule } from 'eslint';
|
|
10
|
-
declare const rule: Rule.RuleModule;
|
|
11
|
-
export = rule;
|
|
@@ -1,196 +0,0 @@
|
|
|
1
|
-
"use strict";
|
|
2
|
-
/**
|
|
3
|
-
* ESLint rule to enforce standardized catch block error handling patterns
|
|
4
|
-
*
|
|
5
|
-
* Enforces three approved patterns:
|
|
6
|
-
* 1. Standard: catch (err: any) { const error = toError(err); }
|
|
7
|
-
* 2. Ignored: catch (err: any) { //const error = toError(err); }
|
|
8
|
-
* 3. Nested: catch (err2: any) { const error2 = toError(err2); }
|
|
9
|
-
*/
|
|
10
|
-
const rule = {
|
|
11
|
-
meta: {
|
|
12
|
-
type: 'problem',
|
|
13
|
-
docs: {
|
|
14
|
-
description: 'Enforce standardized catch block error handling patterns',
|
|
15
|
-
category: 'Best Practices',
|
|
16
|
-
recommended: true,
|
|
17
|
-
url: 'https://github.com/deanhiller/webpieces-ts/blob/main/claude.patterns.md#error-handling-pattern',
|
|
18
|
-
},
|
|
19
|
-
messages: {
|
|
20
|
-
missingToError: 'Catch block must call toError({{param}}) as first statement or comment it out to explicitly ignore errors',
|
|
21
|
-
wrongVariableName: 'Error variable must be named "{{expected}}", got "{{actual}}"',
|
|
22
|
-
missingTypeAnnotation: 'Catch parameter must be typed as "any": catch ({{param}}: any)',
|
|
23
|
-
wrongParameterName: 'Catch parameter must be named "err" (or "err2", "err3" for nested catches), got "{{actual}}"',
|
|
24
|
-
toErrorNotFirst: 'toError({{param}}) must be the first statement in the catch block',
|
|
25
|
-
},
|
|
26
|
-
fixable: undefined,
|
|
27
|
-
schema: [],
|
|
28
|
-
},
|
|
29
|
-
create(context) {
|
|
30
|
-
// Track nesting depth for err, err2, err3, etc.
|
|
31
|
-
const catchStack = [];
|
|
32
|
-
return {
|
|
33
|
-
CatchClause(node) {
|
|
34
|
-
const catchNode = node;
|
|
35
|
-
// Calculate depth (1-based: first catch is depth 1)
|
|
36
|
-
const depth = catchStack.length + 1;
|
|
37
|
-
catchStack.push(catchNode);
|
|
38
|
-
// Build expected names based on depth
|
|
39
|
-
const suffix = depth === 1 ? '' : String(depth);
|
|
40
|
-
const expectedParamName = 'err' + suffix;
|
|
41
|
-
const expectedVarName = 'error' + suffix;
|
|
42
|
-
// Get the catch parameter
|
|
43
|
-
const param = catchNode.param;
|
|
44
|
-
if (!param) {
|
|
45
|
-
// No parameter - unusual but technically valid (though not our pattern)
|
|
46
|
-
context.report({
|
|
47
|
-
node: catchNode,
|
|
48
|
-
messageId: 'missingTypeAnnotation',
|
|
49
|
-
data: { param: expectedParamName },
|
|
50
|
-
});
|
|
51
|
-
return;
|
|
52
|
-
}
|
|
53
|
-
// Track the actual parameter name for validation (may differ from expected)
|
|
54
|
-
const actualParamName = param.type === 'Identifier' ? param.name : expectedParamName;
|
|
55
|
-
// RULE 1: Parameter must be named correctly (err, err2, err3, etc.)
|
|
56
|
-
if (param.type === 'Identifier' && param.name !== expectedParamName) {
|
|
57
|
-
context.report({
|
|
58
|
-
node: param,
|
|
59
|
-
messageId: 'wrongParameterName',
|
|
60
|
-
data: {
|
|
61
|
-
actual: param.name,
|
|
62
|
-
},
|
|
63
|
-
});
|
|
64
|
-
}
|
|
65
|
-
// RULE 2: Must have type annotation ": any"
|
|
66
|
-
if (!param.typeAnnotation ||
|
|
67
|
-
!param.typeAnnotation.typeAnnotation ||
|
|
68
|
-
param.typeAnnotation.typeAnnotation.type !== 'TSAnyKeyword') {
|
|
69
|
-
context.report({
|
|
70
|
-
node: param,
|
|
71
|
-
messageId: 'missingTypeAnnotation',
|
|
72
|
-
data: {
|
|
73
|
-
param: param.name || expectedParamName,
|
|
74
|
-
},
|
|
75
|
-
});
|
|
76
|
-
}
|
|
77
|
-
// RULE 3: Check first statement in catch block
|
|
78
|
-
const body = catchNode.body.body;
|
|
79
|
-
const sourceCode = context.sourceCode || context.getSourceCode();
|
|
80
|
-
// IMPORTANT: Check for commented ignore pattern FIRST (before checking if body is empty)
|
|
81
|
-
// This allows Pattern 2 (empty catch with only comment) to be valid
|
|
82
|
-
// Look for: //const error = toError(err);
|
|
83
|
-
const catchBlockStart = catchNode.body.range[0];
|
|
84
|
-
const catchBlockEnd = catchNode.body.range[1];
|
|
85
|
-
const catchBlockText = sourceCode.text.substring(catchBlockStart, catchBlockEnd);
|
|
86
|
-
const ignorePattern = new RegExp(`//\\s*const\\s+${expectedVarName}\\s*=\\s*toError\\(${actualParamName}\\)`);
|
|
87
|
-
if (ignorePattern.test(catchBlockText)) {
|
|
88
|
-
// Pattern 2: Explicitly ignored - valid!
|
|
89
|
-
return;
|
|
90
|
-
}
|
|
91
|
-
// Now check if body is empty (after checking for commented pattern)
|
|
92
|
-
if (body.length === 0) {
|
|
93
|
-
// Empty catch block without comment - not allowed
|
|
94
|
-
context.report({
|
|
95
|
-
node: catchNode.body,
|
|
96
|
-
messageId: 'missingToError',
|
|
97
|
-
data: {
|
|
98
|
-
param: expectedParamName,
|
|
99
|
-
},
|
|
100
|
-
});
|
|
101
|
-
return;
|
|
102
|
-
}
|
|
103
|
-
const firstStatement = body[0];
|
|
104
|
-
// Check if first statement is: const error = toError(err)
|
|
105
|
-
if (firstStatement.type !== 'VariableDeclaration') {
|
|
106
|
-
context.report({
|
|
107
|
-
node: firstStatement,
|
|
108
|
-
messageId: 'missingToError',
|
|
109
|
-
data: {
|
|
110
|
-
param: expectedParamName,
|
|
111
|
-
},
|
|
112
|
-
});
|
|
113
|
-
return;
|
|
114
|
-
}
|
|
115
|
-
const varDecl = firstStatement;
|
|
116
|
-
const declaration = varDecl.declarations[0];
|
|
117
|
-
if (!declaration) {
|
|
118
|
-
context.report({
|
|
119
|
-
node: firstStatement,
|
|
120
|
-
messageId: 'missingToError',
|
|
121
|
-
data: {
|
|
122
|
-
param: expectedParamName,
|
|
123
|
-
},
|
|
124
|
-
});
|
|
125
|
-
return;
|
|
126
|
-
}
|
|
127
|
-
// Check variable name
|
|
128
|
-
if (declaration.id.type !== 'Identifier' ||
|
|
129
|
-
declaration.id.name !== expectedVarName) {
|
|
130
|
-
context.report({
|
|
131
|
-
node: declaration.id,
|
|
132
|
-
messageId: 'wrongVariableName',
|
|
133
|
-
data: {
|
|
134
|
-
expected: expectedVarName,
|
|
135
|
-
actual: declaration.id.name || 'unknown',
|
|
136
|
-
},
|
|
137
|
-
});
|
|
138
|
-
return;
|
|
139
|
-
}
|
|
140
|
-
// Check initialization: toError(err)
|
|
141
|
-
if (!declaration.init) {
|
|
142
|
-
context.report({
|
|
143
|
-
node: declaration,
|
|
144
|
-
messageId: 'missingToError',
|
|
145
|
-
data: {
|
|
146
|
-
param: expectedParamName,
|
|
147
|
-
},
|
|
148
|
-
});
|
|
149
|
-
return;
|
|
150
|
-
}
|
|
151
|
-
if (declaration.init.type !== 'CallExpression') {
|
|
152
|
-
context.report({
|
|
153
|
-
node: declaration.init,
|
|
154
|
-
messageId: 'missingToError',
|
|
155
|
-
data: {
|
|
156
|
-
param: expectedParamName,
|
|
157
|
-
},
|
|
158
|
-
});
|
|
159
|
-
return;
|
|
160
|
-
}
|
|
161
|
-
const callExpr = declaration.init;
|
|
162
|
-
const callee = callExpr.callee;
|
|
163
|
-
if (callee.type !== 'Identifier' || callee.name !== 'toError') {
|
|
164
|
-
context.report({
|
|
165
|
-
node: callee,
|
|
166
|
-
messageId: 'missingToError',
|
|
167
|
-
data: {
|
|
168
|
-
param: expectedParamName,
|
|
169
|
-
},
|
|
170
|
-
});
|
|
171
|
-
return;
|
|
172
|
-
}
|
|
173
|
-
// Check argument: must be the catch parameter (use actual param name)
|
|
174
|
-
const args = callExpr.arguments;
|
|
175
|
-
if (args.length !== 1 ||
|
|
176
|
-
args[0].type !== 'Identifier' ||
|
|
177
|
-
args[0].name !== actualParamName) {
|
|
178
|
-
context.report({
|
|
179
|
-
node: callExpr,
|
|
180
|
-
messageId: 'missingToError',
|
|
181
|
-
data: {
|
|
182
|
-
param: actualParamName,
|
|
183
|
-
},
|
|
184
|
-
});
|
|
185
|
-
return;
|
|
186
|
-
}
|
|
187
|
-
// All checks passed! ✅
|
|
188
|
-
},
|
|
189
|
-
'CatchClause:exit'() {
|
|
190
|
-
catchStack.pop();
|
|
191
|
-
},
|
|
192
|
-
};
|
|
193
|
-
},
|
|
194
|
-
};
|
|
195
|
-
module.exports = rule;
|
|
196
|
-
//# sourceMappingURL=catch-error-pattern.js.map
|