eslint-plugin-reliability 3.1.10 → 3.1.11

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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "eslint-plugin-reliability",
3
- "version": "3.1.10",
3
+ "version": "3.1.11",
4
4
  "description": "ESLint plugin for runtime reliability — enforces error handling, network timeouts, null checks, and safe type narrowing.",
5
5
  "type": "commonjs",
6
6
  "main": "./src/index.js",
@@ -50,7 +50,7 @@
50
50
  "node": ">=18.0.0"
51
51
  },
52
52
  "dependencies": {
53
- "@interlace/eslint-devkit": "^1.8.0"
53
+ "@interlace/eslint-devkit": "^1.10.0"
54
54
  },
55
55
  "repository": {
56
56
  "type": "git",
package/src/index.js CHANGED
@@ -1,44 +1 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.configs = exports.plugin = exports.rules = void 0;
4
- exports.rules = {
5
- get 'no-unhandled-promise'() { return require("./rules/error-handling/no-unhandled-promise").noUnhandledPromise; },
6
- get 'no-silent-errors'() { return require("./rules/error-handling/no-silent-errors").noSilentErrors; },
7
- get 'no-missing-error-context'() { return require("./rules/error-handling/no-missing-error-context").noMissingErrorContext; },
8
- get 'error-message'() { return require("./rules/error-handling/error-message").errorMessage; },
9
- get 'no-missing-null-checks'() { return require("./rules/reliability/no-missing-null-checks").noMissingNullChecks; },
10
- get 'no-unsafe-type-narrowing'() { return require("./rules/reliability/no-unsafe-type-narrowing").noUnsafeTypeNarrowing; },
11
- get 'require-network-timeout'() { return require("./rules/reliability/require-network-timeout").requireNetworkTimeout; },
12
- get 'no-await-in-loop'() { return require("./rules/reliability/no-await-in-loop").noAwaitInLoop; },
13
- get 'no-jsdoc-terminator-in-example'() { return require("./rules/reliability/no-jsdoc-terminator-in-example").noJsdocTerminatorInExample; },
14
- get 'error-handling/no-unhandled-promise'() { return require("./rules/error-handling/no-unhandled-promise").noUnhandledPromise; },
15
- get 'error-handling/no-silent-errors'() { return require("./rules/error-handling/no-silent-errors").noSilentErrors; },
16
- get 'error-handling/no-missing-error-context'() { return require("./rules/error-handling/no-missing-error-context").noMissingErrorContext; },
17
- get 'error-handling/error-message'() { return require("./rules/error-handling/error-message").errorMessage; },
18
- get 'reliability/no-missing-null-checks'() { return require("./rules/reliability/no-missing-null-checks").noMissingNullChecks; },
19
- get 'reliability/no-unsafe-type-narrowing'() { return require("./rules/reliability/no-unsafe-type-narrowing").noUnsafeTypeNarrowing; },
20
- get 'reliability/require-network-timeout'() { return require("./rules/reliability/require-network-timeout").requireNetworkTimeout; },
21
- get 'reliability/no-await-in-loop'() { return require("./rules/reliability/no-await-in-loop").noAwaitInLoop; },
22
- get 'reliability/no-jsdoc-terminator-in-example'() { return require("./rules/reliability/no-jsdoc-terminator-in-example").noJsdocTerminatorInExample; },
23
-
24
- };
25
- exports.plugin = {
26
- meta: {
27
- name: 'eslint-plugin-reliability',
28
- version: '3.1.10',
29
- },
30
- rules: exports.rules,
31
- };
32
- exports.configs = {
33
- recommended: {
34
- plugins: {
35
- reliability: exports.plugin,
36
- },
37
- rules: {
38
- 'reliability/no-silent-errors': 'error',
39
- 'reliability/no-missing-null-checks': 'warn',
40
- 'reliability/require-network-timeout': 'error',
41
- },
42
- },
43
- };
44
- exports.default = exports.plugin;
1
+ "use strict";Object.defineProperty(exports,"__esModule",{value:true});exports.configs=exports.plugin=exports.rules=void 0;exports.rules={get"no-unhandled-promise"(){return require("./rules/error-handling/no-unhandled-promise").noUnhandledPromise},get"no-silent-errors"(){return require("./rules/error-handling/no-silent-errors").noSilentErrors},get"no-missing-error-context"(){return require("./rules/error-handling/no-missing-error-context").noMissingErrorContext},get"error-message"(){return require("./rules/error-handling/error-message").errorMessage},get"no-missing-null-checks"(){return require("./rules/reliability/no-missing-null-checks").noMissingNullChecks},get"no-unsafe-type-narrowing"(){return require("./rules/reliability/no-unsafe-type-narrowing").noUnsafeTypeNarrowing},get"require-network-timeout"(){return require("./rules/reliability/require-network-timeout").requireNetworkTimeout},get"no-await-in-loop"(){return require("./rules/reliability/no-await-in-loop").noAwaitInLoop},get"no-jsdoc-terminator-in-example"(){return require("./rules/reliability/no-jsdoc-terminator-in-example").noJsdocTerminatorInExample},get"error-handling/no-unhandled-promise"(){return require("./rules/error-handling/no-unhandled-promise").noUnhandledPromise},get"error-handling/no-silent-errors"(){return require("./rules/error-handling/no-silent-errors").noSilentErrors},get"error-handling/no-missing-error-context"(){return require("./rules/error-handling/no-missing-error-context").noMissingErrorContext},get"error-handling/error-message"(){return require("./rules/error-handling/error-message").errorMessage},get"reliability/no-missing-null-checks"(){return require("./rules/reliability/no-missing-null-checks").noMissingNullChecks},get"reliability/no-unsafe-type-narrowing"(){return require("./rules/reliability/no-unsafe-type-narrowing").noUnsafeTypeNarrowing},get"reliability/require-network-timeout"(){return require("./rules/reliability/require-network-timeout").requireNetworkTimeout},get"reliability/no-await-in-loop"(){return require("./rules/reliability/no-await-in-loop").noAwaitInLoop},get"reliability/no-jsdoc-terminator-in-example"(){return require("./rules/reliability/no-jsdoc-terminator-in-example").noJsdocTerminatorInExample}};exports.plugin={meta:{name:"eslint-plugin-reliability",version:"3.1.11"},rules:exports.rules};exports.configs={recommended:{plugins:{reliability:exports.plugin},rules:{"reliability/no-silent-errors":"error","reliability/no-missing-null-checks":"warn","reliability/require-network-timeout":"error"}}};exports.default=exports.plugin;
@@ -1,6 +1 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.eslintPluginReliability = eslintPluginReliability;
4
- function eslintPluginReliability() {
5
- return 'eslint-plugin-reliability';
6
- }
1
+ "use strict";Object.defineProperty(exports,"__esModule",{value:true});exports.eslintPluginReliability=eslintPluginReliability;function eslintPluginReliability(){return"eslint-plugin-reliability"}
package/src/oxlint.js CHANGED
@@ -1,3 +1 @@
1
- "use strict";
2
- const index_1 = require("./index");
3
- module.exports = index_1.plugin;
1
+ "use strict";const index_1=require("./index");module.exports=index_1.plugin;
@@ -1,131 +1 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.errorMessage = void 0;
4
- const eslint_devkit_1 = require("@interlace/eslint-devkit");
5
- const eslint_devkit_2 = require("@interlace/eslint-devkit");
6
- exports.errorMessage = (0, eslint_devkit_1.createRule)({
7
- name: 'error-message',
8
- meta: {
9
- type: 'problem',
10
- docs: {
11
- url: 'https://github.com/ofri-peretz/eslint/blob/main/packages/eslint-plugin-reliability/docs/rules/error-message.md',
12
- description: 'Enforce providing a message when creating built-in Error objects for better debugging',
13
- },
14
- hasSuggestions: true,
15
- messages: {
16
- missingErrorMessage: (0, eslint_devkit_2.formatLLMMessage)({
17
- icon: eslint_devkit_2.MessageIcons.INFO,
18
- issueName: 'Missing Error Message',
19
- description: 'Error constructor called without message parameter',
20
- severity: 'HIGH',
21
- fix: 'Add descriptive error message: new Error("description")',
22
- documentationLink: 'https://github.com/sindresorhus/eslint-plugin-unicorn/blob/main/docs/rules/error-message.md',
23
- }),
24
- addErrorMessage: (0, eslint_devkit_2.formatLLMMessage)({
25
- icon: eslint_devkit_2.MessageIcons.WARNING,
26
- issueName: 'Add Error Message',
27
- description: 'Add descriptive error message to constructor',
28
- severity: 'HIGH',
29
- fix: 'Add descriptive error message: new Error("description")',
30
- documentationLink: 'https://github.com/sindresorhus/eslint-plugin-unicorn/blob/main/docs/rules/error-message.md',
31
- }),
32
- },
33
- schema: [
34
- {
35
- type: 'object',
36
- properties: {
37
- allowEmptyCatch: {
38
- type: 'boolean',
39
- default: false,
40
- },
41
- },
42
- additionalProperties: false,
43
- },
44
- ],
45
- },
46
- defaultOptions: [{ allowEmptyCatch: false }],
47
- create(context) {
48
- const [options] = context.options;
49
- const { allowEmptyCatch = false } = options || {};
50
- const errorConstructors = new Set([
51
- 'Error',
52
- 'TypeError',
53
- 'ReferenceError',
54
- 'SyntaxError',
55
- 'RangeError',
56
- 'EvalError',
57
- 'URIError',
58
- ]);
59
- function isErrorConstructor(name) {
60
- return errorConstructors.has(name);
61
- }
62
- function hasMessageArgument(node) {
63
- if (!node.arguments || node.arguments.length === 0) {
64
- return false;
65
- }
66
- const firstArg = node.arguments[0];
67
- if (firstArg.type === 'Literal') {
68
- return (typeof firstArg.value === 'string' && firstArg.value.trim().length > 0);
69
- }
70
- return true;
71
- }
72
- function isInCatchClause(node) {
73
- let current = node;
74
- while (current) {
75
- if (current.type === 'CatchClause') {
76
- return true;
77
- }
78
- current = current.parent;
79
- }
80
- return false;
81
- }
82
- function checkErrorCreation(node) {
83
- let constructorName = null;
84
- if (node.type === 'NewExpression') {
85
- if (node.callee.type === 'Identifier') {
86
- constructorName = node.callee.name;
87
- }
88
- }
89
- else if (node.type === 'CallExpression') {
90
- if (node.callee.type === 'Identifier') {
91
- constructorName = node.callee.name;
92
- }
93
- }
94
- if (!constructorName || !isErrorConstructor(constructorName)) {
95
- return;
96
- }
97
- if (allowEmptyCatch && isInCatchClause(node)) {
98
- return;
99
- }
100
- if (!hasMessageArgument(node)) {
101
- context.report({
102
- node,
103
- messageId: 'missingErrorMessage',
104
- data: {
105
- constructor: constructorName,
106
- },
107
- suggest: [
108
- {
109
- messageId: 'addErrorMessage',
110
- data: { constructor: constructorName },
111
- fix(fixer) {
112
- if (node.arguments.length === 0) {
113
- const parenStart = node.callee.range[1];
114
- const parenEnd = node.range[1];
115
- return fixer.replaceTextRange([parenStart, parenEnd], '("Error message")');
116
- }
117
- else {
118
- return fixer.replaceText(node.arguments[0], '"Error message"');
119
- }
120
- },
121
- },
122
- ],
123
- });
124
- }
125
- }
126
- return {
127
- NewExpression: checkErrorCreation,
128
- CallExpression: checkErrorCreation,
129
- };
130
- },
131
- });
1
+ "use strict";Object.defineProperty(exports,"__esModule",{value:true});exports.errorMessage=void 0;const eslint_devkit_1=require("@interlace/eslint-devkit");const eslint_devkit_2=require("@interlace/eslint-devkit");exports.errorMessage=(0,eslint_devkit_1.createRule)({name:"error-message",meta:{type:"problem",docs:{url:"https://github.com/ofri-peretz/eslint/blob/main/packages/eslint-plugin-reliability/docs/rules/error-message.md",description:"Enforce providing a message when creating built-in Error objects for better debugging"},hasSuggestions:true,messages:{missingErrorMessage:(0,eslint_devkit_2.formatLLMMessage)({icon:eslint_devkit_2.MessageIcons.INFO,issueName:"Missing Error Message",description:"Error constructor called without message parameter",severity:"HIGH",fix:'Add descriptive error message: new Error("description")',documentationLink:"https://github.com/sindresorhus/eslint-plugin-unicorn/blob/main/docs/rules/error-message.md"}),addErrorMessage:(0,eslint_devkit_2.formatLLMMessage)({icon:eslint_devkit_2.MessageIcons.WARNING,issueName:"Add Error Message",description:"Add descriptive error message to constructor",severity:"HIGH",fix:'Add descriptive error message: new Error("description")',documentationLink:"https://github.com/sindresorhus/eslint-plugin-unicorn/blob/main/docs/rules/error-message.md"})},schema:[{type:"object",properties:{allowEmptyCatch:{type:"boolean",default:false}},additionalProperties:false}]},defaultOptions:[{allowEmptyCatch:false}],create(context){const[options]=context.options;const{allowEmptyCatch=false}=options||{};const errorConstructors=new Set(["Error","TypeError","ReferenceError","SyntaxError","RangeError","EvalError","URIError"]);function isErrorConstructor(name){return errorConstructors.has(name)}function hasMessageArgument(node){if(!node.arguments||node.arguments.length===0){return false}const firstArg=node.arguments[0];if(firstArg.type==="Literal"){return typeof firstArg.value==="string"&&firstArg.value.trim().length>0}return true}function isInCatchClause(node){let current=node;while(current){if(current.type==="CatchClause"){return true}current=current.parent}return false}function checkErrorCreation(node){let constructorName=null;if(node.type==="NewExpression"){if(node.callee.type==="Identifier"){constructorName=node.callee.name}}else if(node.type==="CallExpression"){if(node.callee.type==="Identifier"){constructorName=node.callee.name}}if(!constructorName||!isErrorConstructor(constructorName)){return}if(allowEmptyCatch&&isInCatchClause(node)){return}if(!hasMessageArgument(node)){context.report({node,messageId:"missingErrorMessage",data:{constructor:constructorName},suggest:[{messageId:"addErrorMessage",data:{constructor:constructorName},fix(fixer){if(node.arguments.length===0){const parenStart=node.callee.range[1];const parenEnd=node.range[1];return fixer.replaceTextRange([parenStart,parenEnd],'("Error message")')}else{return fixer.replaceText(node.arguments[0],'"Error message"')}}}]})}}return{NewExpression:checkErrorCreation,CallExpression:checkErrorCreation}}});
@@ -1,180 +1 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.noMissingErrorContext = void 0;
4
- const eslint_devkit_1 = require("@interlace/eslint-devkit");
5
- const eslint_devkit_2 = require("@interlace/eslint-devkit");
6
- function hasErrorMessage(node) {
7
- if (!node.argument) {
8
- return false;
9
- }
10
- if (node.argument.type === 'Identifier' &&
11
- node.argument.name !== 'undefined' &&
12
- node.argument.name !== 'NaN' &&
13
- node.argument.name !== 'Infinity') {
14
- return true;
15
- }
16
- if (node.argument.type === 'NewExpression' &&
17
- node.argument.callee.type === 'Identifier' &&
18
- (node.argument.callee.name === 'Error' ||
19
- node.argument.callee.name.endsWith('Error'))) {
20
- if (node.argument.arguments.length > 0) {
21
- const firstArg = node.argument.arguments[0];
22
- if (firstArg.type === 'Literal' && typeof firstArg.value === 'string') {
23
- return firstArg.value.length > 0;
24
- }
25
- if (firstArg.type === 'TemplateLiteral') {
26
- return true;
27
- }
28
- if (node.argument.callee.name !== 'Error' &&
29
- node.argument.callee.name.endsWith('Error')) {
30
- return true;
31
- }
32
- }
33
- }
34
- if (node.argument.type === 'Literal' &&
35
- typeof node.argument.value === 'string') {
36
- return node.argument.value.length > 0;
37
- }
38
- if (node.argument.type === 'TemplateLiteral') {
39
- return true;
40
- }
41
- return false;
42
- }
43
- function hasErrorStack(node) {
44
- if (!node.argument) {
45
- return false;
46
- }
47
- if (node.argument.type === 'Identifier' &&
48
- node.argument.name !== 'undefined' &&
49
- node.argument.name !== 'NaN' &&
50
- node.argument.name !== 'Infinity') {
51
- return true;
52
- }
53
- if (node.argument.type === 'NewExpression' &&
54
- node.argument.callee.type === 'Identifier') {
55
- const calleeName = node.argument.callee.name;
56
- if (calleeName === 'Error' || calleeName.endsWith('Error')) {
57
- return true;
58
- }
59
- }
60
- return false;
61
- }
62
- exports.noMissingErrorContext = (0, eslint_devkit_2.createRule)({
63
- name: 'no-missing-error-context',
64
- meta: {
65
- type: 'suggestion',
66
- docs: {
67
- url: 'https://github.com/ofri-peretz/eslint/blob/main/packages/eslint-plugin-reliability/docs/rules/no-missing-error-context.md',
68
- description: 'Detects thrown errors without context',
69
- },
70
- hasSuggestions: true,
71
- messages: {
72
- missingErrorContext: (0, eslint_devkit_1.formatLLMMessage)({
73
- icon: eslint_devkit_1.MessageIcons.WARNING,
74
- issueName: 'Missing error context',
75
- description: 'Thrown error missing {{missing}}',
76
- severity: 'MEDIUM',
77
- fix: 'Add error message and use Error class for stack trace',
78
- documentationLink: 'https://rules.sonarsource.com/javascript/RSPEC-1128/',
79
- }),
80
- addErrorMessage: (0, eslint_devkit_1.formatLLMMessage)({
81
- icon: eslint_devkit_1.MessageIcons.INFO,
82
- issueName: 'Add Error Message',
83
- description: 'Add descriptive error message',
84
- severity: 'LOW',
85
- fix: 'throw new Error("descriptive message")',
86
- documentationLink: 'https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Error',
87
- }),
88
- addErrorStack: (0, eslint_devkit_1.formatLLMMessage)({
89
- icon: eslint_devkit_1.MessageIcons.INFO,
90
- issueName: 'Use Error Class',
91
- description: 'Use Error class for stack trace',
92
- severity: 'LOW',
93
- fix: 'throw new Error(message) instead of throw message',
94
- documentationLink: 'https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Error',
95
- }),
96
- useErrorClass: (0, eslint_devkit_1.formatLLMMessage)({
97
- icon: eslint_devkit_1.MessageIcons.INFO,
98
- issueName: 'Use Specific Error',
99
- description: 'Use specific error class',
100
- severity: 'LOW',
101
- fix: 'throw new TypeError("message") or throw new RangeError("message")',
102
- documentationLink: 'https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/TypeError',
103
- }),
104
- },
105
- schema: [
106
- {
107
- type: 'object',
108
- properties: {
109
- requireMessage: {
110
- type: 'boolean',
111
- default: true,
112
- description: 'Require error message',
113
- },
114
- requireStackTrace: {
115
- type: 'boolean',
116
- default: false,
117
- description: 'Require stack trace',
118
- },
119
- ignoreInTests: {
120
- type: 'boolean',
121
- default: true,
122
- description: 'Ignore in test files',
123
- },
124
- },
125
- additionalProperties: false,
126
- },
127
- ],
128
- },
129
- defaultOptions: [
130
- {
131
- requireMessage: true,
132
- requireStackTrace: false,
133
- ignoreInTests: true,
134
- },
135
- ],
136
- create(context, [options = {}]) {
137
- const { requireMessage = true, requireStackTrace = false, ignoreInTests = true, } = options || {};
138
- const filename = context.filename;
139
- const isTestFile = ignoreInTests && /\.(test|spec)\.(ts|tsx|js|jsx)$/.test(filename);
140
- if (isTestFile) {
141
- return {};
142
- }
143
- function checkThrowStatement(node) {
144
- const missing = [];
145
- if (requireMessage && !hasErrorMessage(node)) {
146
- missing.push('message');
147
- }
148
- if (requireStackTrace && !hasErrorStack(node)) {
149
- missing.push('stack trace');
150
- }
151
- if (missing.length === 0) {
152
- return;
153
- }
154
- context.report({
155
- node,
156
- messageId: 'missingErrorContext',
157
- data: {
158
- missing: missing.join(' and '),
159
- },
160
- suggest: [
161
- {
162
- messageId: 'addErrorMessage',
163
- fix: () => null,
164
- },
165
- {
166
- messageId: 'addErrorStack',
167
- fix: () => null,
168
- },
169
- {
170
- messageId: 'useErrorClass',
171
- fix: () => null,
172
- },
173
- ],
174
- });
175
- }
176
- return {
177
- ThrowStatement: checkThrowStatement,
178
- };
179
- },
180
- });
1
+ "use strict";Object.defineProperty(exports,"__esModule",{value:true});exports.noMissingErrorContext=void 0;const eslint_devkit_1=require("@interlace/eslint-devkit");const eslint_devkit_2=require("@interlace/eslint-devkit");function hasErrorMessage(node){if(!node.argument){return false}if(node.argument.type==="Identifier"&&node.argument.name!=="undefined"&&node.argument.name!=="NaN"&&node.argument.name!=="Infinity"){return true}if(node.argument.type==="NewExpression"&&node.argument.callee.type==="Identifier"&&(node.argument.callee.name==="Error"||node.argument.callee.name.endsWith("Error"))){if(node.argument.arguments.length>0){const firstArg=node.argument.arguments[0];if(firstArg.type==="Literal"&&typeof firstArg.value==="string"){return firstArg.value.length>0}if(firstArg.type==="TemplateLiteral"){return true}if(node.argument.callee.name!=="Error"&&node.argument.callee.name.endsWith("Error")){return true}}}if(node.argument.type==="Literal"&&typeof node.argument.value==="string"){return node.argument.value.length>0}if(node.argument.type==="TemplateLiteral"){return true}return false}function hasErrorStack(node){if(!node.argument){return false}if(node.argument.type==="Identifier"&&node.argument.name!=="undefined"&&node.argument.name!=="NaN"&&node.argument.name!=="Infinity"){return true}if(node.argument.type==="NewExpression"&&node.argument.callee.type==="Identifier"){const calleeName=node.argument.callee.name;if(calleeName==="Error"||calleeName.endsWith("Error")){return true}}return false}exports.noMissingErrorContext=(0,eslint_devkit_2.createRule)({name:"no-missing-error-context",meta:{type:"suggestion",docs:{url:"https://github.com/ofri-peretz/eslint/blob/main/packages/eslint-plugin-reliability/docs/rules/no-missing-error-context.md",description:"Detects thrown errors without context"},hasSuggestions:true,messages:{missingErrorContext:(0,eslint_devkit_1.formatLLMMessage)({icon:eslint_devkit_1.MessageIcons.WARNING,issueName:"Missing error context",description:"Thrown error missing {{missing}}",severity:"MEDIUM",fix:"Add error message and use Error class for stack trace",documentationLink:"https://rules.sonarsource.com/javascript/RSPEC-1128/"}),addErrorMessage:(0,eslint_devkit_1.formatLLMMessage)({icon:eslint_devkit_1.MessageIcons.INFO,issueName:"Add Error Message",description:"Add descriptive error message",severity:"LOW",fix:'throw new Error("descriptive message")',documentationLink:"https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Error"}),addErrorStack:(0,eslint_devkit_1.formatLLMMessage)({icon:eslint_devkit_1.MessageIcons.INFO,issueName:"Use Error Class",description:"Use Error class for stack trace",severity:"LOW",fix:"throw new Error(message) instead of throw message",documentationLink:"https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Error"}),useErrorClass:(0,eslint_devkit_1.formatLLMMessage)({icon:eslint_devkit_1.MessageIcons.INFO,issueName:"Use Specific Error",description:"Use specific error class",severity:"LOW",fix:'throw new TypeError("message") or throw new RangeError("message")',documentationLink:"https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/TypeError"})},schema:[{type:"object",properties:{requireMessage:{type:"boolean",default:true,description:"Require error message"},requireStackTrace:{type:"boolean",default:false,description:"Require stack trace"},ignoreInTests:{type:"boolean",default:true,description:"Ignore in test files"}},additionalProperties:false}]},defaultOptions:[{requireMessage:true,requireStackTrace:false,ignoreInTests:true}],create(context,[options={}]){const{requireMessage=true,requireStackTrace=false,ignoreInTests=true}=options||{};const filename=context.filename;const isTestFile=ignoreInTests&&/\.(test|spec)\.(ts|tsx|js|jsx)$/.test(filename);if(isTestFile){return{}}function checkThrowStatement(node){const missing=[];if(requireMessage&&!hasErrorMessage(node)){missing.push("message")}if(requireStackTrace&&!hasErrorStack(node)){missing.push("stack trace")}if(missing.length===0){return}context.report({node,messageId:"missingErrorContext",data:{missing:missing.join(" and ")},suggest:[{messageId:"addErrorMessage",fix:()=>null},{messageId:"addErrorStack",fix:()=>null},{messageId:"useErrorClass",fix:()=>null}]})}return{ThrowStatement:checkThrowStatement}}});
@@ -1,157 +1 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.noSilentErrors = void 0;
4
- const eslint_devkit_1 = require("@interlace/eslint-devkit");
5
- const eslint_devkit_2 = require("@interlace/eslint-devkit");
6
- function isEmptyCatchBlock(catchClause) {
7
- const body = catchClause.body;
8
- if (!body || body.type !== 'BlockStatement') {
9
- return true;
10
- }
11
- const statements = body.body;
12
- if (statements.length === 0) {
13
- return true;
14
- }
15
- const nonEmptyStatements = statements.filter((stmt) => stmt.type !== 'EmptyStatement');
16
- return nonEmptyStatements.length === 0;
17
- }
18
- function hasExplanatoryComment(catchClause, sourceCode) {
19
- const comments = sourceCode.getAllComments();
20
- const catchStart = catchClause.loc?.start;
21
- if (!catchStart || !comments.length) {
22
- return false;
23
- }
24
- const explanatoryPatterns = [
25
- /intentional/i,
26
- /expected/i,
27
- /ignore/i,
28
- /silent/i,
29
- /noop/i,
30
- /no-op/i,
31
- /by design/i,
32
- /known issue/i,
33
- /legacy/i,
34
- /third.?party/i,
35
- /framework/i,
36
- /library/i,
37
- /not implemented/i,
38
- /todo/i,
39
- /fixme/i,
40
- ];
41
- for (const comment of comments) {
42
- if (comment.loc && catchStart.line - comment.loc.end.line <= 2) {
43
- const commentText = comment.value.toLowerCase();
44
- if (explanatoryPatterns.some((pattern) => pattern.test(commentText))) {
45
- return true;
46
- }
47
- }
48
- }
49
- return false;
50
- }
51
- exports.noSilentErrors = (0, eslint_devkit_2.createRule)({
52
- name: 'no-silent-errors',
53
- meta: {
54
- type: 'problem',
55
- docs: {
56
- url: 'https://github.com/ofri-peretz/eslint/blob/main/packages/eslint-plugin-reliability/docs/rules/no-silent-errors.md',
57
- description: 'Detects empty catch blocks',
58
- },
59
- hasSuggestions: true,
60
- messages: {
61
- silentError: (0, eslint_devkit_1.formatLLMMessage)({
62
- icon: eslint_devkit_1.MessageIcons.WARNING,
63
- issueName: 'Silent error',
64
- description: 'Empty catch block detected - errors are silently ignored',
65
- severity: 'MEDIUM',
66
- fix: 'Add error logging or handling in catch block',
67
- documentationLink: 'https://rules.sonarsource.com/javascript/RSPEC-1186/',
68
- }),
69
- addErrorLogging: (0, eslint_devkit_1.formatLLMMessage)({
70
- icon: eslint_devkit_1.MessageIcons.INFO,
71
- issueName: 'Add Error Logging',
72
- description: 'Add error logging to catch block',
73
- severity: 'LOW',
74
- fix: 'catch (error) { console.error(error); }',
75
- documentationLink: 'https://rules.sonarsource.com/javascript/RSPEC-1186/',
76
- }),
77
- addErrorHandling: (0, eslint_devkit_1.formatLLMMessage)({
78
- icon: eslint_devkit_1.MessageIcons.INFO,
79
- issueName: 'Add Error Handling',
80
- description: 'Add error handling to catch block',
81
- severity: 'LOW',
82
- fix: 'catch (error) { handleError(error); }',
83
- documentationLink: 'https://rules.sonarsource.com/javascript/RSPEC-1186/',
84
- }),
85
- rethrowError: (0, eslint_devkit_1.formatLLMMessage)({
86
- icon: eslint_devkit_1.MessageIcons.INFO,
87
- issueName: 'Rethrow Error',
88
- description: 'Rethrow error if needed',
89
- severity: 'LOW',
90
- fix: 'catch (error) { throw new CustomError(error); }',
91
- documentationLink: 'https://rules.sonarsource.com/javascript/RSPEC-1186/',
92
- }),
93
- },
94
- schema: [
95
- {
96
- type: 'object',
97
- properties: {
98
- allowWithComment: {
99
- type: 'boolean',
100
- default: false,
101
- description: 'Allow empty catch if comment explains why',
102
- },
103
- ignoreInTests: {
104
- type: 'boolean',
105
- default: true,
106
- description: 'Ignore in test files',
107
- },
108
- },
109
- additionalProperties: false,
110
- },
111
- ],
112
- },
113
- defaultOptions: [
114
- {
115
- allowWithComment: false,
116
- ignoreInTests: true,
117
- },
118
- ],
119
- create(context, [options = {}]) {
120
- const { allowWithComment = false, ignoreInTests = true } = options || {};
121
- const filename = context.filename;
122
- const isTestFile = ignoreInTests && /\.(test|spec)\.(ts|tsx|js|jsx)$/.test(filename);
123
- if (isTestFile) {
124
- return {};
125
- }
126
- const sourceCode = context.sourceCode;
127
- function checkCatchClause(node) {
128
- if (!isEmptyCatchBlock(node)) {
129
- return;
130
- }
131
- if (allowWithComment && hasExplanatoryComment(node, sourceCode)) {
132
- return;
133
- }
134
- context.report({
135
- node,
136
- messageId: 'silentError',
137
- suggest: [
138
- {
139
- messageId: 'addErrorLogging',
140
- fix: () => null,
141
- },
142
- {
143
- messageId: 'addErrorHandling',
144
- fix: () => null,
145
- },
146
- {
147
- messageId: 'rethrowError',
148
- fix: () => null,
149
- },
150
- ],
151
- });
152
- }
153
- return {
154
- CatchClause: checkCatchClause,
155
- };
156
- },
157
- });
1
+ "use strict";Object.defineProperty(exports,"__esModule",{value:true});exports.noSilentErrors=void 0;const eslint_devkit_1=require("@interlace/eslint-devkit");const eslint_devkit_2=require("@interlace/eslint-devkit");function isEmptyCatchBlock(catchClause){const body=catchClause.body;if(!body||body.type!=="BlockStatement"){return true}const statements=body.body;if(statements.length===0){return true}const nonEmptyStatements=statements.filter(stmt=>stmt.type!=="EmptyStatement");return nonEmptyStatements.length===0}function hasExplanatoryComment(catchClause,sourceCode){const comments=sourceCode.getAllComments();const catchStart=catchClause.loc?.start;if(!catchStart||!comments.length){return false}const explanatoryPatterns=[/intentional/i,/expected/i,/ignore/i,/silent/i,/noop/i,/no-op/i,/by design/i,/known issue/i,/legacy/i,/third.?party/i,/framework/i,/library/i,/not implemented/i,/todo/i,/fixme/i];for(const comment of comments){if(comment.loc&&catchStart.line-comment.loc.end.line<=2){const commentText=comment.value.toLowerCase();if(explanatoryPatterns.some(pattern=>pattern.test(commentText))){return true}}}return false}exports.noSilentErrors=(0,eslint_devkit_2.createRule)({name:"no-silent-errors",meta:{type:"problem",docs:{url:"https://github.com/ofri-peretz/eslint/blob/main/packages/eslint-plugin-reliability/docs/rules/no-silent-errors.md",description:"Detects empty catch blocks"},hasSuggestions:true,messages:{silentError:(0,eslint_devkit_1.formatLLMMessage)({icon:eslint_devkit_1.MessageIcons.WARNING,issueName:"Silent error",description:"Empty catch block detected - errors are silently ignored",severity:"MEDIUM",fix:"Add error logging or handling in catch block",documentationLink:"https://rules.sonarsource.com/javascript/RSPEC-1186/"}),addErrorLogging:(0,eslint_devkit_1.formatLLMMessage)({icon:eslint_devkit_1.MessageIcons.INFO,issueName:"Add Error Logging",description:"Add error logging to catch block",severity:"LOW",fix:"catch (error) { console.error(error); }",documentationLink:"https://rules.sonarsource.com/javascript/RSPEC-1186/"}),addErrorHandling:(0,eslint_devkit_1.formatLLMMessage)({icon:eslint_devkit_1.MessageIcons.INFO,issueName:"Add Error Handling",description:"Add error handling to catch block",severity:"LOW",fix:"catch (error) { handleError(error); }",documentationLink:"https://rules.sonarsource.com/javascript/RSPEC-1186/"}),rethrowError:(0,eslint_devkit_1.formatLLMMessage)({icon:eslint_devkit_1.MessageIcons.INFO,issueName:"Rethrow Error",description:"Rethrow error if needed",severity:"LOW",fix:"catch (error) { throw new CustomError(error); }",documentationLink:"https://rules.sonarsource.com/javascript/RSPEC-1186/"})},schema:[{type:"object",properties:{allowWithComment:{type:"boolean",default:false,description:"Allow empty catch if comment explains why"},ignoreInTests:{type:"boolean",default:true,description:"Ignore in test files"}},additionalProperties:false}]},defaultOptions:[{allowWithComment:false,ignoreInTests:true}],create(context,[options={}]){const{allowWithComment=false,ignoreInTests=true}=options||{};const filename=context.filename;const isTestFile=ignoreInTests&&/\.(test|spec)\.(ts|tsx|js|jsx)$/.test(filename);if(isTestFile){return{}}const sourceCode=context.sourceCode;function checkCatchClause(node){if(!isEmptyCatchBlock(node)){return}if(allowWithComment&&hasExplanatoryComment(node,sourceCode)){return}context.report({node,messageId:"silentError",suggest:[{messageId:"addErrorLogging",fix:()=>null},{messageId:"addErrorHandling",fix:()=>null},{messageId:"rethrowError",fix:()=>null}]})}return{CatchClause:checkCatchClause}}});