@cdklabs/eslint-plugin 1.3.5 → 1.4.0

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/lib/index.d.ts CHANGED
@@ -10,4 +10,5 @@ export declare const rules: {
10
10
  'no-throw-default-error': any;
11
11
  'promiseall-no-unbounded-parallelism': any;
12
12
  'no-this-in-static': any;
13
+ 'no-evaluating-typeguard': any;
13
14
  };
package/lib/index.js CHANGED
@@ -14,5 +14,6 @@ exports.rules = {
14
14
  'no-throw-default-error': require('./rules/no-throw-default-error'),
15
15
  'promiseall-no-unbounded-parallelism': require('./rules/promiseall-no-unbounded-parallelism'),
16
16
  'no-this-in-static': require('./rules/no-this-in-static'),
17
+ 'no-evaluating-typeguard': require('./rules/no-evaluating-typeguard'),
17
18
  };
18
- //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiaW5kZXguanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi9zcmMvaW5kZXgudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IjtBQUFBLDBEQUEwRDs7O0FBRTdDLFFBQUEsSUFBSSxHQUFHO0lBQ2xCLElBQUksRUFBRSxPQUFPLENBQUMsaUJBQWlCLENBQUMsQ0FBQyxJQUFJO0lBQ3JDLE9BQU8sRUFBRSxPQUFPLENBQUMsaUJBQWlCLENBQUMsQ0FBQyxPQUFPO0NBQzVDLENBQUM7QUFFVyxRQUFBLEtBQUssR0FBRztJQUNuQixtQkFBbUIsRUFBRSxPQUFPLENBQUMsMkJBQTJCLENBQUM7SUFDekQscUJBQXFCLEVBQUUsT0FBTyxDQUFDLDZCQUE2QixDQUFDO0lBQzdELHNCQUFzQixFQUFFLE9BQU8sQ0FBQyw4QkFBOEIsQ0FBQztJQUMvRCxpQkFBaUIsRUFBRSxPQUFPLENBQUMseUJBQXlCLENBQUM7SUFDckQsd0JBQXdCLEVBQUUsT0FBTyxDQUFDLGdDQUFnQyxDQUFDO0lBQ25FLHFDQUFxQyxFQUFFLE9BQU8sQ0FBQyw2Q0FBNkMsQ0FBQztJQUM3RixtQkFBbUIsRUFBRSxPQUFPLENBQUMsMkJBQTJCLENBQUM7Q0FDMUQsQ0FBQyIsInNvdXJjZXNDb250ZW50IjpbIi8qIGVzbGludC1kaXNhYmxlIEB0eXBlc2NyaXB0LWVzbGludC9uby1yZXF1aXJlLWltcG9ydHMgKi9cblxuZXhwb3J0IGNvbnN0IG1ldGEgPSB7XG4gIG5hbWU6IHJlcXVpcmUoJy4uL3BhY2thZ2UuanNvbicpLm5hbWUsXG4gIHZlcnNpb246IHJlcXVpcmUoJy4uL3BhY2thZ2UuanNvbicpLnZlcnNpb24sXG59O1xuXG5leHBvcnQgY29uc3QgcnVsZXMgPSB7XG4gICduby1jb3JlLWNvbnN0cnVjdCc6IHJlcXVpcmUoJy4vcnVsZXMvbm8tY29yZS1jb25zdHJ1Y3QnKSxcbiAgJ2ludmFsaWQtY2ZuLWltcG9ydHMnOiByZXF1aXJlKCcuL3J1bGVzL2ludmFsaWQtY2ZuLWltcG9ydHMnKSxcbiAgJ25vLWxpdGVyYWwtcGFydGl0aW9uJzogcmVxdWlyZSgnLi9ydWxlcy9uby1saXRlcmFsLXBhcnRpdGlvbicpLFxuICAnbm8taW52YWxpZC1wYXRoJzogcmVxdWlyZSgnLi9ydWxlcy9uby1pbnZhbGlkLXBhdGgnKSxcbiAgJ25vLXRocm93LWRlZmF1bHQtZXJyb3InOiByZXF1aXJlKCcuL3J1bGVzL25vLXRocm93LWRlZmF1bHQtZXJyb3InKSxcbiAgJ3Byb21pc2VhbGwtbm8tdW5ib3VuZGVkLXBhcmFsbGVsaXNtJzogcmVxdWlyZSgnLi9ydWxlcy9wcm9taXNlYWxsLW5vLXVuYm91bmRlZC1wYXJhbGxlbGlzbScpLFxuICAnbm8tdGhpcy1pbi1zdGF0aWMnOiByZXF1aXJlKCcuL3J1bGVzL25vLXRoaXMtaW4tc3RhdGljJyksXG59O1xuIl19
19
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiaW5kZXguanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi9zcmMvaW5kZXgudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IjtBQUFBLDBEQUEwRDs7O0FBRTdDLFFBQUEsSUFBSSxHQUFHO0lBQ2xCLElBQUksRUFBRSxPQUFPLENBQUMsaUJBQWlCLENBQUMsQ0FBQyxJQUFJO0lBQ3JDLE9BQU8sRUFBRSxPQUFPLENBQUMsaUJBQWlCLENBQUMsQ0FBQyxPQUFPO0NBQzVDLENBQUM7QUFFVyxRQUFBLEtBQUssR0FBRztJQUNuQixtQkFBbUIsRUFBRSxPQUFPLENBQUMsMkJBQTJCLENBQUM7SUFDekQscUJBQXFCLEVBQUUsT0FBTyxDQUFDLDZCQUE2QixDQUFDO0lBQzdELHNCQUFzQixFQUFFLE9BQU8sQ0FBQyw4QkFBOEIsQ0FBQztJQUMvRCxpQkFBaUIsRUFBRSxPQUFPLENBQUMseUJBQXlCLENBQUM7SUFDckQsd0JBQXdCLEVBQUUsT0FBTyxDQUFDLGdDQUFnQyxDQUFDO0lBQ25FLHFDQUFxQyxFQUFFLE9BQU8sQ0FBQyw2Q0FBNkMsQ0FBQztJQUM3RixtQkFBbUIsRUFBRSxPQUFPLENBQUMsMkJBQTJCLENBQUM7SUFDekQseUJBQXlCLEVBQUUsT0FBTyxDQUFDLGlDQUFpQyxDQUFDO0NBQ3RFLENBQUMiLCJzb3VyY2VzQ29udGVudCI6WyIvKiBlc2xpbnQtZGlzYWJsZSBAdHlwZXNjcmlwdC1lc2xpbnQvbm8tcmVxdWlyZS1pbXBvcnRzICovXG5cbmV4cG9ydCBjb25zdCBtZXRhID0ge1xuICBuYW1lOiByZXF1aXJlKCcuLi9wYWNrYWdlLmpzb24nKS5uYW1lLFxuICB2ZXJzaW9uOiByZXF1aXJlKCcuLi9wYWNrYWdlLmpzb24nKS52ZXJzaW9uLFxufTtcblxuZXhwb3J0IGNvbnN0IHJ1bGVzID0ge1xuICAnbm8tY29yZS1jb25zdHJ1Y3QnOiByZXF1aXJlKCcuL3J1bGVzL25vLWNvcmUtY29uc3RydWN0JyksXG4gICdpbnZhbGlkLWNmbi1pbXBvcnRzJzogcmVxdWlyZSgnLi9ydWxlcy9pbnZhbGlkLWNmbi1pbXBvcnRzJyksXG4gICduby1saXRlcmFsLXBhcnRpdGlvbic6IHJlcXVpcmUoJy4vcnVsZXMvbm8tbGl0ZXJhbC1wYXJ0aXRpb24nKSxcbiAgJ25vLWludmFsaWQtcGF0aCc6IHJlcXVpcmUoJy4vcnVsZXMvbm8taW52YWxpZC1wYXRoJyksXG4gICduby10aHJvdy1kZWZhdWx0LWVycm9yJzogcmVxdWlyZSgnLi9ydWxlcy9uby10aHJvdy1kZWZhdWx0LWVycm9yJyksXG4gICdwcm9taXNlYWxsLW5vLXVuYm91bmRlZC1wYXJhbGxlbGlzbSc6IHJlcXVpcmUoJy4vcnVsZXMvcHJvbWlzZWFsbC1uby11bmJvdW5kZWQtcGFyYWxsZWxpc20nKSxcbiAgJ25vLXRoaXMtaW4tc3RhdGljJzogcmVxdWlyZSgnLi9ydWxlcy9uby10aGlzLWluLXN0YXRpYycpLFxuICAnbm8tZXZhbHVhdGluZy10eXBlZ3VhcmQnOiByZXF1aXJlKCcuL3J1bGVzL25vLWV2YWx1YXRpbmctdHlwZWd1YXJkJyksXG59O1xuIl19
@@ -0,0 +1,4 @@
1
+ import { Rule } from 'eslint';
2
+ export declare const meta: Rule.RuleMetaData;
3
+ export declare const defaultOptions: {};
4
+ export declare function create(context: Rule.RuleContext): Rule.RuleListener;
@@ -0,0 +1,134 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.defaultOptions = exports.meta = void 0;
4
+ exports.create = create;
5
+ const utils_1 = require("@typescript-eslint/utils");
6
+ const eslint_utils_1 = require("@typescript-eslint/utils/eslint-utils");
7
+ exports.meta = {
8
+ messages: {
9
+ avoidAccess: "{{ memberAccess }}: this will evaluate '{{ prop }}', which might throw if it's a getter. Prefer using `'{{ prop }}' in {{ obj }}` (don't forget to check for object-ness of {{ obj }} if necessary!)",
10
+ },
11
+ };
12
+ exports.defaultOptions = {};
13
+ function create(context) {
14
+ const services = (0, eslint_utils_1.getParserServices)(context);
15
+ const functionStack = [];
16
+ // const classDeclarations: Map<string, ClassDeclaration> = new Map();
17
+ /**
18
+ * Whether this function is a type predicate
19
+ *
20
+ * ```
21
+ * function isSomething(x: unknown): x is Something { ... }
22
+ * ```
23
+ */
24
+ function isUserDefinedTypeGuard(node) {
25
+ if (node.params.length !== 1 || node.params[0].type !== utils_1.AST_NODE_TYPES.Identifier) {
26
+ return false;
27
+ }
28
+ return node.returnType?.typeAnnotation.type === utils_1.AST_NODE_TYPES.TSTypePredicate;
29
+ }
30
+ /**
31
+ * Whether this looks like a type coercion function
32
+ *
33
+ * ```
34
+ * function toSomething(x: SomeType): SomeSubType { ... }
35
+ * ```
36
+ */
37
+ function isTypeCoercionFunction(node) {
38
+ const typeChecker = services.program.getTypeChecker();
39
+ const functionType = services.getTypeAtLocation(node);
40
+ const argumentType = typeChecker.getTypeOfSymbol(functionType.getCallSignatures()[0].getParameters()[0]);
41
+ const returnType = functionType.getCallSignatures()[0].getReturnType();
42
+ // If the return type is assignable to the input type, then this looks like
43
+ // a downcast which probably means it's a type coerction function.
44
+ return typeChecker.isTypeAssignableTo(returnType, argumentType);
45
+ }
46
+ // eslint-disable-next-line @stylistic/max-len
47
+ function maybeInteresting(node) {
48
+ if (node.params.length !== 1 || node.params[0].type !== utils_1.AST_NODE_TYPES.Identifier) {
49
+ return undefined;
50
+ }
51
+ if (isUserDefinedTypeGuard(node) || isTypeCoercionFunction(node)) {
52
+ return {
53
+ argumentName: node.params[0].name,
54
+ };
55
+ }
56
+ return undefined;
57
+ }
58
+ /**
59
+ * Enter a function and see if it's interesting
60
+ */
61
+ function enterFunction(node) {
62
+ functionStack.push(maybeInteresting(node));
63
+ }
64
+ function exitFunction() {
65
+ functionStack.pop();
66
+ }
67
+ function currentInteresting() {
68
+ return functionStack.length > 0 ? functionStack[functionStack.length - 1] : undefined;
69
+ }
70
+ function onlyInInterestingFunction(fn) {
71
+ return ((...args) => {
72
+ if (currentInteresting()) {
73
+ return fn(...args);
74
+ }
75
+ return undefined;
76
+ });
77
+ }
78
+ /**
79
+ * For member expressions in interesting functions
80
+ *
81
+ * - If their LHS refers to the only function argument; AND
82
+ * - If their parent is a `typeof` node; OR
83
+ * - The member expression is part of a boolean expression; OR
84
+ * - The member expression is in a bang-bang operator (!!); OR
85
+ * - The expression is by itself in an `if` or `return` or `?:` ternary
86
+ *
87
+ * Then that is a potential problem because it will evaluate a member
88
+ * that we potentially only wanted to test for presence.
89
+ */
90
+ function memberExpression(node) {
91
+ const current = currentInteresting();
92
+ // Only property access on the primary argument
93
+ if ((node.object.type !== utils_1.AST_NODE_TYPES.Identifier) || node.object.name !== current.argumentName) {
94
+ return;
95
+ }
96
+ let dangerous = false;
97
+ if (node.parent.type === utils_1.AST_NODE_TYPES.UnaryExpression && node.parent.operator === 'typeof') {
98
+ dangerous = true;
99
+ }
100
+ if (node.parent.type === utils_1.AST_NODE_TYPES.UnaryExpression
101
+ && node.parent.operator === '!'
102
+ && node.parent.parent.type === utils_1.AST_NODE_TYPES.UnaryExpression
103
+ && node.parent.parent.operator === '!') {
104
+ dangerous = true;
105
+ }
106
+ if (node.parent.type === utils_1.AST_NODE_TYPES.LogicalExpression) {
107
+ dangerous = true;
108
+ }
109
+ if ([utils_1.AST_NODE_TYPES.ReturnStatement, utils_1.AST_NODE_TYPES.IfStatement, utils_1.AST_NODE_TYPES.ConditionalExpression].includes(node.parent.type)) {
110
+ dangerous = true;
111
+ }
112
+ if (dangerous) {
113
+ const eslintNode = node;
114
+ context.report({
115
+ node: eslintNode,
116
+ messageId: 'avoidAccess',
117
+ loc: eslintNode.loc ?? { line: 0, column: 0 },
118
+ data: {
119
+ memberAccess: context.sourceCode.getText(eslintNode),
120
+ obj: current.argumentName,
121
+ prop: node.property.name,
122
+ },
123
+ });
124
+ }
125
+ }
126
+ return {
127
+ 'FunctionDeclaration': enterFunction,
128
+ 'FunctionExpression': enterFunction,
129
+ 'FunctionDeclaration:exit': exitFunction,
130
+ 'FunctionExpression:exit': exitFunction,
131
+ 'MemberExpression': onlyInInterestingFunction(memberExpression),
132
+ };
133
+ }
134
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoibm8tZXZhbHVhdGluZy10eXBlZ3VhcmQuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi9zcmMvcnVsZXMvbm8tZXZhbHVhdGluZy10eXBlZ3VhcmQudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6Ijs7O0FBb0JBLHdCQW1JQztBQXZKRCxvREFBb0U7QUFFcEUsd0VBQTBFO0FBSzdELFFBQUEsSUFBSSxHQUFzQjtJQUNyQyxRQUFRLEVBQUU7UUFDUixXQUFXLEVBQUUsc01BQXNNO0tBQ3BOO0NBQ0YsQ0FBQztBQUVXLFFBQUEsY0FBYyxHQUFHLEVBQUUsQ0FBQztBQU9qQyxTQUFnQixNQUFNLENBQUMsT0FBeUI7SUFDOUMsTUFBTSxRQUFRLEdBQUcsSUFBQSxnQ0FBaUIsRUFBQyxPQUFjLENBQUMsQ0FBQztJQUVuRCxNQUFNLGFBQWEsR0FBMkMsRUFBRSxDQUFDO0lBQ2pFLHVFQUF1RTtJQUV2RTs7Ozs7O09BTUc7SUFDSCxTQUFTLHNCQUFzQixDQUFDLElBQWdFO1FBQzlGLElBQUksSUFBSSxDQUFDLE1BQU0sQ0FBQyxNQUFNLEtBQUssQ0FBQyxJQUFJLElBQUksQ0FBQyxNQUFNLENBQUMsQ0FBQyxDQUFDLENBQUMsSUFBSSxLQUFLLHNCQUFjLENBQUMsVUFBVSxFQUFFLENBQUM7WUFBQyxPQUFPLEtBQUssQ0FBQztRQUFDLENBQUM7UUFDcEcsT0FBTyxJQUFJLENBQUMsVUFBVSxFQUFFLGNBQWMsQ0FBQyxJQUFJLEtBQUssc0JBQWMsQ0FBQyxlQUFlLENBQUM7SUFDakYsQ0FBQztJQUVEOzs7Ozs7T0FNRztJQUNILFNBQVMsc0JBQXNCLENBQUMsSUFBZ0U7UUFDOUYsTUFBTSxXQUFXLEdBQUcsUUFBUSxDQUFDLE9BQU8sQ0FBQyxjQUFjLEVBQUUsQ0FBQztRQUV0RCxNQUFNLFlBQVksR0FBRyxRQUFRLENBQUMsaUJBQWlCLENBQUMsSUFBSSxDQUFDLENBQUM7UUFDdEQsTUFBTSxZQUFZLEdBQUcsV0FBVyxDQUFDLGVBQWUsQ0FBQyxZQUFZ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WVBFUywgVFNFU1RyZWUgfSBmcm9tICdAdHlwZXNjcmlwdC1lc2xpbnQvdXRpbHMnO1xuXG5pbXBvcnQgeyBnZXRQYXJzZXJTZXJ2aWNlcyB9IGZyb20gJ0B0eXBlc2NyaXB0LWVzbGludC91dGlscy9lc2xpbnQtdXRpbHMnO1xuaW1wb3J0IHsgUnVsZSB9IGZyb20gJ2VzbGludCc7XG5pbXBvcnQgdHlwZSB7IE1lbWJlckV4cHJlc3Npb24gfSBmcm9tICdlc3RyZWUnO1xuaW1wb3J0IE5vZGVQYXJlbnRFeHRlbnNpb24gPSBSdWxlLk5vZGVQYXJlbnRFeHRlbnNpb247XG5cbmV4cG9ydCBjb25zdCBtZXRhOiBSdWxlLlJ1bGVNZXRhRGF0YSA9IHtcbiAgbWVzc2FnZXM6IHtcbiAgICBhdm9pZEFjY2VzczogXCJ7eyBtZW1iZXJBY2Nlc3MgfX06IHRoaXMgd2lsbCBldmFsdWF0ZSAne3sgcHJvcCB9fScsIHdoaWNoIG1pZ2h0IHRocm93IGlmIGl0J3MgYSBnZXR0ZXIuIFByZWZlciB1c2luZyBgJ3t7IHByb3AgfX0nIGluIHt7IG9iaiB9fWAgKGRvbid0IGZvcmdldCB0byBjaGVjayBmb3Igb2JqZWN0LW5lc3Mgb2Yge3sgb2JqIH19IGlmIG5lY2Vzc2FyeSEpXCIsXG4gIH0sXG59O1xuXG5leHBvcnQgY29uc3QgZGVmYXVsdE9wdGlvbnMgPSB7fTtcblxuXG5pbnRlcmZhY2UgSW50ZXJlc3RpbmdGdW5jdGlvbiB7XG4gIHJlYWRvbmx5IGFyZ3VtZW50TmFtZTogc3RyaW5nO1xufVxuXG5leHBvcnQgZnVuY3Rpb24gY3JlYXRlKGNvbnRleHQ6IFJ1bGUuUnVsZUNvbnRleHQpOiBSdWxlLlJ1bGVMaXN0ZW5lciB7XG4gIGNvbnN0IHNlcnZpY2VzID0gZ2V0UGFyc2VyU2VydmljZXMoY29udGV4dCBhcyBhbnkpO1xuXG4gIGNvbnN0IGZ1bmN0aW9uU3RhY2s6IEFycmF5PEludGVyZXN0aW5nRnVuY3Rpb24gfCB1bmRlZmluZWQ+ID0gW107XG4gIC8vICBjb25zdCBjbGFzc0RlY2xhcmF0aW9uczogTWFwPHN0cmluZywgQ2xhc3NEZWNsYXJhdGlvbj4gPSBuZXcgTWFwKCk7XG5cbiAgLyoqXG4gICAqIFdoZXRoZXIgdGhpcyBmdW5jdGlvbiBpcyBhIHR5cGUgcHJlZGljYXRlXG4gICAqXG4gICAqIGBgYFxuICAgKiBmdW5jdGlvbiBpc1NvbWV0aGluZyh4OiB1bmtub3duKTogeCBpcyBTb21ldGhpbmcgeyAuLi4gfVxuICAgKiBgYGBcbiAgICovXG4gIGZ1bmN0aW9uIGlzVXNlckRlZmluZWRUeXBlR3VhcmQobm9kZTogVFNFU1RyZWUuRnVuY3Rpb25EZWNsYXJhdGlvbiB8IFRTRVNUcmVlLkZ1bmN0aW9uRXhwcmVzc2lvbikge1xuICAgIGlmIChub2RlLnBhcmFtcy5sZW5ndGggIT09IDEgfHwgbm9kZS5wYXJhbXNbMF0udHlwZSAhPT0gQVNUX05PREVfVFlQRVMuSWRlbnRpZmllcikgeyByZXR1cm4gZmFsc2U7IH1cbiAgICByZXR1cm4gbm9kZS5yZXR1cm5UeXBlPy50eXBlQW5ub3RhdGlvbi50eXBlID09PSBBU1RfTk9ERV9UWVBFUy5UU1R5cGVQcmVkaWNhdGU7XG4gIH1cblxuICAvKipcbiAgICogV2hldGhlciB0aGlzIGxvb2tzIGxpa2UgYSB0eXBlIGNvZXJjaW9uIGZ1bmN0aW9uXG4gICAqXG4gICAqIGBgYFxuICAgKiBmdW5jdGlvbiB0b1NvbWV0aGluZyh4OiBTb21lVHlwZSk6IFNvbWVTdWJUeXBlIHsgLi4uIH1cbiAgICogYGBgXG4gICAqL1xuICBmdW5jdGlvbiBpc1R5cGVDb2VyY2lvbkZ1bmN0aW9uKG5vZGU6IFRTRVNUcmVlLkZ1bmN0aW9uRGVjbGFyYXRpb24gfCBUU0VTVHJlZS5GdW5jdGlvbkV4cHJlc3Npb24pIHtcbiAgICBjb25zdCB0eXBlQ2hlY2tlciA9IHNlcnZpY2VzLnByb2dyYW0uZ2V0VHlwZUNoZWNrZXIoKTtcblxuICAgIGNvbnN0IGZ1bmN0aW9uVHlwZSA9IHNlcnZpY2VzLmdldFR5cGVBdExvY2F0aW9uKG5vZGUpO1xuICAgIGNvbnN0IGFyZ3VtZW50VHlwZSA9IHR5cGVDaGVja2VyLmdldFR5cGVPZlN5bWJvbChmdW5jdGlvblR5cGUuZ2V0Q2FsbFNpZ25hdHVyZXMoKVswXS5nZXRQYXJhbWV0ZXJzKClbMF0pO1xuICAgIGNvbnN0IHJldHVyblR5cGUgPSBmdW5jdGlvblR5cGUuZ2V0Q2FsbFNpZ25hdHVyZXMoKVswXS5nZXRSZXR1cm5UeXBlKCk7XG5cbiAgICAvLyBJZiB0aGUgcmV0dXJuIHR5cGUgaXMgYXNzaWduYWJsZSB0byB0aGUgaW5wdXQgdHlwZSwgdGhlbiB0aGlzIGxvb2tzIGxpa2VcbiAgICAvLyBhIGRvd25jYXN0IHdoaWNoIHByb2JhYmx5IG1lYW5zIGl0J3MgYSB0eXBlIGNvZXJjdGlvbiBmdW5jdGlvbi5cbiAgICByZXR1cm4gdHlwZUNoZWNrZXIuaXNUeXBlQXNzaWduYWJsZVRvKHJldHVyblR5cGUsIGFyZ3VtZW50VHlwZSk7XG4gIH1cblxuICAvLyBlc2xpbnQtZGlzYWJsZS1uZXh0LWxpbmUgQHN0eWxpc3RpYy9tYXgtbGVuXG4gIGZ1bmN0aW9uIG1heWJlSW50ZXJlc3Rpbmcobm9kZTogVFNFU1RyZWUuRnVuY3Rpb25EZWNsYXJhdGlvbiB8IFRTRVNUcmVlLkZ1bmN0aW9uRXhwcmVzc2lvbik6IEludGVyZXN0aW5nRnVuY3Rpb24gfCB1bmRlZmluZWQge1xuICAgIGlmIChub2RlLnBhcmFtcy5sZW5ndGggIT09IDEgfHwgbm9kZS5wYXJhbXNbMF0udHlwZSAhPT0gQVNUX05PREVfVFlQRVMuSWRlbnRpZmllcikgeyByZXR1cm4gdW5kZWZpbmVkOyB9XG4gICAgaWYgKGlzVXNlckRlZmluZWRUeXBlR3VhcmQobm9kZSkgfHwgaXNUeXBlQ29lcmNpb25GdW5jdGlvbihub2RlKSkge1xuICAgICAgcmV0dXJuIHtcbiAgICAgICAgYXJndW1lbnROYW1lOiAobm9kZS5wYXJhbXNbMF0gYXMgVFNFU1RyZWUuSWRlbnRpZmllcikubmFtZSxcbiAgICAgIH07XG4gICAgfVxuICAgIHJldHVybiB1bmRlZmluZWQ7XG4gIH1cblxuICAvKipcbiAgICogRW50ZXIgYSBmdW5jdGlvbiBhbmQgc2VlIGlmIGl0J3MgaW50ZXJlc3RpbmdcbiAgICovXG4gIGZ1bmN0aW9uIGVudGVyRnVuY3Rpb24obm9kZTogKFRTRVNUcmVlLkZ1bmN0aW9uRGVjbGFyYXRpb24gfCBUU0VTVHJlZS5GdW5jdGlvbkV4cHJlc3Npb24pICYgTm9kZVBhcmVudEV4dGVuc2lvbikge1xuICAgIGZ1bmN0aW9uU3RhY2sucHVzaChtYXliZUludGVyZXN0aW5nKG5vZGUpKTtcbiAgfVxuXG4gIGZ1bmN0aW9uIGV4aXRGdW5jdGlvbigpIHtcbiAgICBmdW5jdGlvblN0YWNrLnBvcCgpO1xuICB9XG5cbiAgZnVuY3Rpb24gY3VycmVudEludGVyZXN0aW5nKCk6IEludGVyZXN0aW5nRnVuY3Rpb24gfCB1bmRlZmluZWQge1xuICAgIHJldHVybiBmdW5jdGlvblN0YWNrLmxlbmd0aCA+IDAgPyBmdW5jdGlvblN0YWNrW2Z1bmN0aW9uU3RhY2subGVuZ3RoIC0gMV0gOiB1bmRlZmluZWQ7XG4gIH1cblxuICBmdW5jdGlvbiBvbmx5SW5JbnRlcmVzdGluZ0Z1bmN0aW9uPEEgZXh0ZW5kcyBGdW5jdGlvbj4oZm46IEEpOiBBIHtcbiAgICByZXR1cm4gKCguLi5hcmdzOiBhbnlbXSkgPT4ge1xuICAgICAgaWYgKGN1cnJlbnRJbnRlcmVzdGluZygpKSB7XG4gICAgICAgIHJldHVybiBmbiguLi5hcmdzKTtcbiAgICAgIH1cbiAgICAgIHJldHVybiB1bmRlZmluZWQ7XG4gICAgfSkgYXMgYW55O1xuICB9XG5cbiAgLyoqXG4gICAqIEZvciBtZW1iZXIgZXhwcmVzc2lvbnMgaW4gaW50ZXJlc3RpbmcgZnVuY3Rpb25zXG4gICAqXG4gICAqIC0gSWYgdGhlaXIgTEhTIHJlZmVycyB0byB0aGUgb25seSBmdW5jdGlvbiBhcmd1bWVudDsgQU5EXG4gICAqICAgLSBJZiB0aGVpciBwYXJlbnQgaXMgYSBgdHlwZW9mYCBub2RlOyBPUlxuICAgKiAgIC0gVGhlIG1lbWJlciBleHByZXNzaW9uIGlzIHBhcnQgb2YgYSBib29sZWFuIGV4cHJlc3Npb247IE9SXG4gICAqICAgLSBUaGUgbWVtYmVyIGV4cHJlc3Npb24gaXMgaW4gYSBiYW5nLWJhbmcgb3BlcmF0b3IgKCEhKTsgT1JcbiAgICogICAtIFRoZSBleHByZXNzaW9uIGlzIGJ5IGl0c2VsZiBpbiBhbiBgaWZgIG9yIGByZXR1cm5gIG9yIGA/OmAgdGVybmFyeVxuICAgKlxuICAgKiBUaGVuIHRoYXQgaXMgYSBwb3RlbnRpYWwgcHJvYmxlbSBiZWNhdXNlIGl0IHdpbGwgZXZhbHVhdGUgYSBtZW1iZXJcbiAgICogdGhhdCB3ZSBwb3RlbnRpYWxseSBvbmx5IHdhbnRlZCB0byB0ZXN0IGZvciBwcmVzZW5jZS5cbiAgICovXG4gIGZ1bmN0aW9uIG1lbWJlckV4cHJlc3Npb24obm9kZTogVFNFU1RyZWUuTWVtYmVyRXhwcmVzc2lvbikge1xuICAgIGNvbnN0IGN1cnJlbnQgPSBjdXJyZW50SW50ZXJlc3RpbmcoKSE7XG5cbiAgICAvLyBPbmx5IHByb3BlcnR5IGFjY2VzcyBvbiB0aGUgcHJpbWFyeSBhcmd1bWVudFxuICAgIGlmICgobm9kZS5vYmplY3QudHlwZSAhPT0gQVNUX05PREVfVFlQRVMuSWRlbnRpZmllcikgfHwgKG5vZGUub2JqZWN0IGFzIFRTRVNUcmVlLklkZW50aWZpZXIpLm5hbWUgIT09IGN1cnJlbnQuYXJndW1lbnROYW1lKSB7XG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgbGV0IGRhbmdlcm91cyA9IGZhbHNlO1xuICAgIGlmIChub2RlLnBhcmVudC50eXBlID09PSBBU1RfTk9ERV9UWVBFUy5VbmFyeUV4cHJlc3Npb24gJiYgbm9kZS5wYXJlbnQub3BlcmF0b3IgPT09ICd0eXBlb2YnKSB7XG4gICAgICBkYW5nZXJvdXMgPSB0cnVlO1xuICAgIH1cbiAgICBpZiAobm9kZS5wYXJlbnQudHlwZSA9PT0gQVNUX05PREVfVFlQRVMuVW5hcnlFeHByZXNzaW9uXG4gICAgICAmJiBub2RlLnBhcmVudC5vcGVyYXRvciA9PT0gJyEnXG4gICAgICAmJiBub2RlLnBhcmVudC5wYXJlbnQudHlwZSA9PT0gQVNUX05PREVfVFlQRVMuVW5hcnlFeHByZXNzaW9uXG4gICAgICAmJiBub2RlLnBhcmVudC5wYXJlbnQub3BlcmF0b3IgPT09ICchJykge1xuICAgICAgZGFuZ2Vyb3VzID0gdHJ1ZTtcbiAgICB9XG4gICAgaWYgKG5vZGUucGFyZW50LnR5cGUgPT09IEFTVF9OT0RFX1RZUEVTLkxvZ2ljYWxFeHByZXNzaW9uKSB7XG4gICAgICBkYW5nZXJvdXMgPSB0cnVlO1xuICAgIH1cbiAgICBpZiAoW0FTVF9OT0RFX1RZUEVTLlJldHVyblN0YXRlbWVudCwgQVNUX05PREVfVFlQRVMuSWZTdGF0ZW1lbnQsIEFTVF9OT0RFX1RZUEVTLkNvbmRpdGlvbmFsRXhwcmVzc2lvbl0uaW5jbHVkZXMobm9kZS5wYXJlbnQudHlwZSkpIHtcbiAgICAgIGRhbmdlcm91cyA9IHRydWU7XG4gICAgfVxuXG4gICAgaWYgKGRhbmdlcm91cykge1xuICAgICAgY29uc3QgZXNsaW50Tm9kZSA9IG5vZGUgYXMgTWVtYmVyRXhwcmVzc2lvbjtcbiAgICAgIGNvbnRleHQucmVwb3J0KHtcbiAgICAgICAgbm9kZTogZXNsaW50Tm9kZSxcbiAgICAgICAgbWVzc2FnZUlkOiAnYXZvaWRBY2Nlc3MnLFxuICAgICAgICBsb2M6IGVzbGludE5vZGUubG9jID8/IHsgbGluZTogMCwgY29sdW1uOiAwIH0sXG4gICAgICAgIGRhdGE6IHtcbiAgICAgICAgICBtZW1iZXJBY2Nlc3M6IGNvbnRleHQuc291cmNlQ29kZS5nZXRUZXh0KGVzbGludE5vZGUpLFxuICAgICAgICAgIG9iajogY3VycmVudC5hcmd1bWVudE5hbWUsXG4gICAgICAgICAgcHJvcDogKG5vZGUucHJvcGVydHkgYXMgVFNFU1RyZWUuUHJpdmF0ZUlkZW50aWZpZXIgfCBUU0VTVHJlZS5JZGVudGlmaWVyKS5uYW1lLFxuICAgICAgICB9LFxuICAgICAgfSk7XG4gICAgfVxuICB9XG5cbiAgcmV0dXJuIHtcbiAgICAnRnVuY3Rpb25EZWNsYXJhdGlvbic6IGVudGVyRnVuY3Rpb24gYXMgYW55LFxuICAgICdGdW5jdGlvbkV4cHJlc3Npb24nOiBlbnRlckZ1bmN0aW9uIGFzIGFueSxcbiAgICAnRnVuY3Rpb25EZWNsYXJhdGlvbjpleGl0JzogZXhpdEZ1bmN0aW9uLFxuICAgICdGdW5jdGlvbkV4cHJlc3Npb246ZXhpdCc6IGV4aXRGdW5jdGlvbixcbiAgICAnTWVtYmVyRXhwcmVzc2lvbic6IG9ubHlJbkludGVyZXN0aW5nRnVuY3Rpb24obWVtYmVyRXhwcmVzc2lvbikgYXMgYW55LFxuICB9O1xufVxuIl19
package/package.json CHANGED
@@ -42,7 +42,8 @@
42
42
  "@types/node": "^18",
43
43
  "@typescript-eslint/eslint-plugin": "^8",
44
44
  "@typescript-eslint/parser": "^8",
45
- "cdklabs-projen-project-types": "^0.3.1",
45
+ "@typescript-eslint/rule-tester": "^8.52.0",
46
+ "cdklabs-projen-project-types": "^0.3.7",
46
47
  "commit-and-tag-version": "^12",
47
48
  "constructs": "^10.0.0",
48
49
  "eslint": "^8",
@@ -50,17 +51,18 @@
50
51
  "eslint-plugin-import": "^2.32.0",
51
52
  "jest": "^29.7.0",
52
53
  "jest-junit": "^16",
53
- "projen": "^0.92.9",
54
- "ts-jest": "^29.4.1",
54
+ "projen": "^0.98.4",
55
+ "ts-jest": "^29.4.6",
55
56
  "ts-node": "^10.9.2",
56
- "typescript": "^5.9.2"
57
+ "typescript": "^5.9.3"
57
58
  },
58
59
  "peerDependencies": {
59
60
  "@typescript-eslint/parser": "^7.18.0",
60
61
  "eslint": ">=6 <9"
61
62
  },
62
63
  "dependencies": {
63
- "fs-extra": "^11.3.2"
64
+ "@typescript-eslint/utils": "^8.52.0",
65
+ "fs-extra": "^11.3.3"
64
66
  },
65
67
  "engines": {
66
68
  "node": ">= 18.12.0"
@@ -70,7 +72,7 @@
70
72
  "publishConfig": {
71
73
  "access": "public"
72
74
  },
73
- "version": "1.3.5",
75
+ "version": "1.4.0",
74
76
  "jest": {
75
77
  "coverageProvider": "v8",
76
78
  "testMatch": [