@tsslint/config 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/index.d.ts +1 -0
- package/index.js +3 -0
- package/lib/ignore.d.ts +2 -0
- package/lib/ignore.js +186 -0
- package/lib/ignorePlugin.d.ts +2 -0
- package/lib/ignorePlugin.js +186 -0
- package/lib/plugins/ignore.d.ts +2 -0
- package/lib/plugins/ignore.js +206 -0
- package/package.json +3 -3
package/index.d.ts
CHANGED
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
export * from '@tsslint/types';
|
|
2
|
+
export { create as createIgnorePlugin } from './lib/plugins/ignore.js';
|
|
2
3
|
import type { Config, Plugin, Rule } from '@tsslint/types';
|
|
3
4
|
export declare function defineRule(rule: Rule): Rule;
|
|
4
5
|
export declare function definePlugin(plugin: Plugin): Plugin;
|
package/index.js
CHANGED
|
@@ -14,10 +14,13 @@ var __exportStar = (this && this.__exportStar) || function(m, exports) {
|
|
|
14
14
|
for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
|
|
15
15
|
};
|
|
16
16
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
17
|
+
exports.createIgnorePlugin = void 0;
|
|
17
18
|
exports.defineRule = defineRule;
|
|
18
19
|
exports.definePlugin = definePlugin;
|
|
19
20
|
exports.defineConfig = defineConfig;
|
|
20
21
|
__exportStar(require("@tsslint/types"), exports);
|
|
22
|
+
var ignore_js_1 = require("./lib/plugins/ignore.js");
|
|
23
|
+
Object.defineProperty(exports, "createIgnorePlugin", { enumerable: true, get: function () { return ignore_js_1.create; } });
|
|
21
24
|
function defineRule(rule) {
|
|
22
25
|
return rule;
|
|
23
26
|
}
|
package/lib/ignore.d.ts
ADDED
package/lib/ignore.js
ADDED
|
@@ -0,0 +1,186 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.create = create;
|
|
4
|
+
function create(cmd, reportsUnusedComments) {
|
|
5
|
+
return ({ typescript: ts, languageService }) => {
|
|
6
|
+
const reg = new RegExp(`//\\s*${cmd}\\b[ \\t]*(?<ruleId>\\S*)\\b`, 'g');
|
|
7
|
+
const completeReg1 = /^\s*\/\/(\s*)([\S]*)?$/;
|
|
8
|
+
const completeReg2 = new RegExp(`//\\s*${cmd}\\b[ \\t]*(\\S*)?$`);
|
|
9
|
+
const reportedRulesOfFile = new Map();
|
|
10
|
+
const { getCompletionsAtPosition } = languageService;
|
|
11
|
+
languageService.getCompletionsAtPosition = (fileName, position, ...rest) => {
|
|
12
|
+
let result = getCompletionsAtPosition(fileName, position, ...rest);
|
|
13
|
+
const sourceFile = languageService.getProgram()?.getSourceFile(fileName);
|
|
14
|
+
if (!sourceFile) {
|
|
15
|
+
return result;
|
|
16
|
+
}
|
|
17
|
+
const reportedRules = reportedRulesOfFile.get(fileName);
|
|
18
|
+
const line = sourceFile.getLineAndCharacterOfPosition(position).line;
|
|
19
|
+
const lineStart = sourceFile.getPositionOfLineAndCharacter(line, 0);
|
|
20
|
+
const prefix = sourceFile.text.slice(lineStart, position);
|
|
21
|
+
const matchCmd = completeReg1
|
|
22
|
+
? prefix.match(completeReg1)
|
|
23
|
+
: undefined;
|
|
24
|
+
if (matchCmd) {
|
|
25
|
+
const nextLineRules = reportedRules?.filter(([, reportedLine]) => reportedLine === line + 1) ?? [];
|
|
26
|
+
const item = {
|
|
27
|
+
name: cmd,
|
|
28
|
+
insertText: matchCmd[1].length ? cmd : ` ${cmd}`,
|
|
29
|
+
kind: ts.ScriptElementKind.keyword,
|
|
30
|
+
sortText: 'a',
|
|
31
|
+
replacementSpan: matchCmd[2]
|
|
32
|
+
? {
|
|
33
|
+
start: position - matchCmd[2].length,
|
|
34
|
+
length: matchCmd[2].length,
|
|
35
|
+
}
|
|
36
|
+
: undefined,
|
|
37
|
+
labelDetails: {
|
|
38
|
+
description: nextLineRules.length >= 2
|
|
39
|
+
? `Ignore ${nextLineRules.length} issues in next line`
|
|
40
|
+
: nextLineRules.length
|
|
41
|
+
? 'Ignore 1 issue in next line'
|
|
42
|
+
: undefined,
|
|
43
|
+
}
|
|
44
|
+
};
|
|
45
|
+
if (result) {
|
|
46
|
+
result.entries.push(item);
|
|
47
|
+
}
|
|
48
|
+
else {
|
|
49
|
+
result = {
|
|
50
|
+
isGlobalCompletion: false,
|
|
51
|
+
isMemberCompletion: false,
|
|
52
|
+
isNewIdentifierLocation: false,
|
|
53
|
+
entries: [item],
|
|
54
|
+
};
|
|
55
|
+
}
|
|
56
|
+
}
|
|
57
|
+
else if (reportedRules?.length) {
|
|
58
|
+
const matchRule = completeReg2
|
|
59
|
+
? prefix.match(completeReg2)
|
|
60
|
+
: undefined;
|
|
61
|
+
if (matchRule) {
|
|
62
|
+
const visited = new Set();
|
|
63
|
+
for (const [ruleId] of reportedRules) {
|
|
64
|
+
if (visited.has(ruleId)) {
|
|
65
|
+
continue;
|
|
66
|
+
}
|
|
67
|
+
visited.add(ruleId);
|
|
68
|
+
const reportedLines = reportedRules
|
|
69
|
+
.filter(([r]) => r === ruleId)
|
|
70
|
+
.map(([, l]) => l + 1);
|
|
71
|
+
const item = {
|
|
72
|
+
name: ruleId,
|
|
73
|
+
kind: ts.ScriptElementKind.keyword,
|
|
74
|
+
sortText: ruleId,
|
|
75
|
+
replacementSpan: matchRule[1]
|
|
76
|
+
? {
|
|
77
|
+
start: position - matchRule[1].length,
|
|
78
|
+
length: matchRule[1].length,
|
|
79
|
+
}
|
|
80
|
+
: undefined,
|
|
81
|
+
labelDetails: {
|
|
82
|
+
description: `Reported in line${reportedLines.length >= 2 ? 's' : ''} ${reportedLines.join(', ')}`,
|
|
83
|
+
},
|
|
84
|
+
};
|
|
85
|
+
if (result) {
|
|
86
|
+
result.entries.push(item);
|
|
87
|
+
}
|
|
88
|
+
else {
|
|
89
|
+
result = {
|
|
90
|
+
isGlobalCompletion: false,
|
|
91
|
+
isMemberCompletion: false,
|
|
92
|
+
isNewIdentifierLocation: false,
|
|
93
|
+
entries: [item],
|
|
94
|
+
};
|
|
95
|
+
}
|
|
96
|
+
}
|
|
97
|
+
}
|
|
98
|
+
}
|
|
99
|
+
return result;
|
|
100
|
+
};
|
|
101
|
+
return {
|
|
102
|
+
resolveDiagnostics(sourceFile, results) {
|
|
103
|
+
if (!reportsUnusedComments &&
|
|
104
|
+
!results.some(error => error.source === 'tsslint')) {
|
|
105
|
+
return results;
|
|
106
|
+
}
|
|
107
|
+
const disabledLines = new Map();
|
|
108
|
+
const disabledLinesByRules = new Map();
|
|
109
|
+
for (const comment of sourceFile.text.matchAll(reg)) {
|
|
110
|
+
const line = sourceFile.getLineAndCharacterOfPosition(comment.index).line + 1;
|
|
111
|
+
const ruleId = comment.groups?.ruleId;
|
|
112
|
+
if (ruleId) {
|
|
113
|
+
if (!disabledLinesByRules.has(ruleId)) {
|
|
114
|
+
disabledLinesByRules.set(ruleId, new Map());
|
|
115
|
+
}
|
|
116
|
+
disabledLinesByRules.get(ruleId).set(line, {
|
|
117
|
+
start: comment.index,
|
|
118
|
+
end: comment.index + comment[0].length,
|
|
119
|
+
});
|
|
120
|
+
}
|
|
121
|
+
else {
|
|
122
|
+
disabledLines.set(line, {
|
|
123
|
+
start: comment.index,
|
|
124
|
+
end: comment.index + comment[0].length,
|
|
125
|
+
});
|
|
126
|
+
}
|
|
127
|
+
}
|
|
128
|
+
let reportedRules = reportedRulesOfFile.get(sourceFile.fileName);
|
|
129
|
+
if (!reportedRules) {
|
|
130
|
+
reportedRules = [];
|
|
131
|
+
reportedRulesOfFile.set(sourceFile.fileName, reportedRules);
|
|
132
|
+
}
|
|
133
|
+
reportedRules.length = 0;
|
|
134
|
+
results = results.filter(error => {
|
|
135
|
+
if (error.source !== 'tsslint') {
|
|
136
|
+
return true;
|
|
137
|
+
}
|
|
138
|
+
const line = sourceFile.getLineAndCharacterOfPosition(error.start).line;
|
|
139
|
+
reportedRules.push([error.code, line]);
|
|
140
|
+
if (disabledLines.has(line)) {
|
|
141
|
+
disabledLines.get(line).used = true;
|
|
142
|
+
return false;
|
|
143
|
+
}
|
|
144
|
+
const disabledLinesByRule = disabledLinesByRules.get(error.code);
|
|
145
|
+
if (disabledLinesByRule?.has(line)) {
|
|
146
|
+
disabledLinesByRule.get(line).used = true;
|
|
147
|
+
return false;
|
|
148
|
+
}
|
|
149
|
+
return true;
|
|
150
|
+
});
|
|
151
|
+
if (reportsUnusedComments) {
|
|
152
|
+
for (const state of disabledLines.values()) {
|
|
153
|
+
if (!state.used) {
|
|
154
|
+
results.push({
|
|
155
|
+
file: sourceFile,
|
|
156
|
+
start: state.start,
|
|
157
|
+
length: state.end - state.start,
|
|
158
|
+
code: 'tsslint:unused-ignore-comment',
|
|
159
|
+
messageText: `Unused ${cmd} comment.`,
|
|
160
|
+
source: 'tsslint',
|
|
161
|
+
category: 1,
|
|
162
|
+
});
|
|
163
|
+
}
|
|
164
|
+
}
|
|
165
|
+
for (const disabledLinesByRule of disabledLinesByRules.values()) {
|
|
166
|
+
for (const state of disabledLinesByRule.values()) {
|
|
167
|
+
if (!state.used) {
|
|
168
|
+
results.push({
|
|
169
|
+
file: sourceFile,
|
|
170
|
+
start: state.start,
|
|
171
|
+
length: state.end - state.start,
|
|
172
|
+
code: 'tsslint:unused-ignore-comment',
|
|
173
|
+
messageText: `Unused ${cmd} comment.`,
|
|
174
|
+
source: 'tsslint',
|
|
175
|
+
category: 1,
|
|
176
|
+
});
|
|
177
|
+
}
|
|
178
|
+
}
|
|
179
|
+
}
|
|
180
|
+
}
|
|
181
|
+
return results;
|
|
182
|
+
},
|
|
183
|
+
};
|
|
184
|
+
};
|
|
185
|
+
}
|
|
186
|
+
//# sourceMappingURL=ignore.js.map
|
|
@@ -0,0 +1,186 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.create = create;
|
|
4
|
+
function create(cmd, reportsUnusedComments) {
|
|
5
|
+
return ({ typescript: ts, languageService }) => {
|
|
6
|
+
const reg = new RegExp(`//\\s*${cmd}\\b[ \\t]*(?<ruleId>\\S*)\\b`, 'g');
|
|
7
|
+
const completeReg1 = /^\s*\/\/(\s*)([\S]*)?$/;
|
|
8
|
+
const completeReg2 = new RegExp(`//\\s*${cmd}\\b[ \\t]*(\\S*)?$`);
|
|
9
|
+
const reportedRulesOfFile = new Map();
|
|
10
|
+
const { getCompletionsAtPosition } = languageService;
|
|
11
|
+
languageService.getCompletionsAtPosition = (fileName, position, ...rest) => {
|
|
12
|
+
let result = getCompletionsAtPosition(fileName, position, ...rest);
|
|
13
|
+
const sourceFile = languageService.getProgram()?.getSourceFile(fileName);
|
|
14
|
+
if (!sourceFile) {
|
|
15
|
+
return result;
|
|
16
|
+
}
|
|
17
|
+
const reportedRules = reportedRulesOfFile.get(fileName);
|
|
18
|
+
const line = sourceFile.getLineAndCharacterOfPosition(position).line;
|
|
19
|
+
const lineStart = sourceFile.getPositionOfLineAndCharacter(line, 0);
|
|
20
|
+
const prefix = sourceFile.text.slice(lineStart, position);
|
|
21
|
+
const matchCmd = completeReg1
|
|
22
|
+
? prefix.match(completeReg1)
|
|
23
|
+
: undefined;
|
|
24
|
+
if (matchCmd) {
|
|
25
|
+
const nextLineRules = reportedRules?.filter(([, reportedLine]) => reportedLine === line + 1) ?? [];
|
|
26
|
+
const item = {
|
|
27
|
+
name: cmd,
|
|
28
|
+
insertText: matchCmd[1].length ? cmd : ` ${cmd}`,
|
|
29
|
+
kind: ts.ScriptElementKind.keyword,
|
|
30
|
+
sortText: 'a',
|
|
31
|
+
replacementSpan: matchCmd[2]
|
|
32
|
+
? {
|
|
33
|
+
start: position - matchCmd[2].length,
|
|
34
|
+
length: matchCmd[2].length,
|
|
35
|
+
}
|
|
36
|
+
: undefined,
|
|
37
|
+
labelDetails: {
|
|
38
|
+
description: nextLineRules.length >= 2
|
|
39
|
+
? `Ignore ${nextLineRules.length} issues in next line`
|
|
40
|
+
: nextLineRules.length
|
|
41
|
+
? 'Ignore 1 issue in next line'
|
|
42
|
+
: undefined,
|
|
43
|
+
}
|
|
44
|
+
};
|
|
45
|
+
if (result) {
|
|
46
|
+
result.entries.push(item);
|
|
47
|
+
}
|
|
48
|
+
else {
|
|
49
|
+
result = {
|
|
50
|
+
isGlobalCompletion: false,
|
|
51
|
+
isMemberCompletion: false,
|
|
52
|
+
isNewIdentifierLocation: false,
|
|
53
|
+
entries: [item],
|
|
54
|
+
};
|
|
55
|
+
}
|
|
56
|
+
}
|
|
57
|
+
else if (reportedRules?.length) {
|
|
58
|
+
const matchRule = completeReg2
|
|
59
|
+
? prefix.match(completeReg2)
|
|
60
|
+
: undefined;
|
|
61
|
+
if (matchRule) {
|
|
62
|
+
const visited = new Set();
|
|
63
|
+
for (const [ruleId] of reportedRules) {
|
|
64
|
+
if (visited.has(ruleId)) {
|
|
65
|
+
continue;
|
|
66
|
+
}
|
|
67
|
+
visited.add(ruleId);
|
|
68
|
+
const reportedLines = reportedRules
|
|
69
|
+
.filter(([r]) => r === ruleId)
|
|
70
|
+
.map(([, l]) => l + 1);
|
|
71
|
+
const item = {
|
|
72
|
+
name: ruleId,
|
|
73
|
+
kind: ts.ScriptElementKind.keyword,
|
|
74
|
+
sortText: ruleId,
|
|
75
|
+
replacementSpan: matchRule[1]
|
|
76
|
+
? {
|
|
77
|
+
start: position - matchRule[1].length,
|
|
78
|
+
length: matchRule[1].length,
|
|
79
|
+
}
|
|
80
|
+
: undefined,
|
|
81
|
+
labelDetails: {
|
|
82
|
+
description: `Reported in line${reportedLines.length >= 2 ? 's' : ''} ${reportedLines.join(', ')}`,
|
|
83
|
+
},
|
|
84
|
+
};
|
|
85
|
+
if (result) {
|
|
86
|
+
result.entries.push(item);
|
|
87
|
+
}
|
|
88
|
+
else {
|
|
89
|
+
result = {
|
|
90
|
+
isGlobalCompletion: false,
|
|
91
|
+
isMemberCompletion: false,
|
|
92
|
+
isNewIdentifierLocation: false,
|
|
93
|
+
entries: [item],
|
|
94
|
+
};
|
|
95
|
+
}
|
|
96
|
+
}
|
|
97
|
+
}
|
|
98
|
+
}
|
|
99
|
+
return result;
|
|
100
|
+
};
|
|
101
|
+
return {
|
|
102
|
+
resolveDiagnostics(sourceFile, results) {
|
|
103
|
+
if (!reportsUnusedComments &&
|
|
104
|
+
!results.some(error => error.source === 'tsslint')) {
|
|
105
|
+
return results;
|
|
106
|
+
}
|
|
107
|
+
const disabledLines = new Map();
|
|
108
|
+
const disabledLinesByRules = new Map();
|
|
109
|
+
for (const comment of sourceFile.text.matchAll(reg)) {
|
|
110
|
+
const line = sourceFile.getLineAndCharacterOfPosition(comment.index).line + 1;
|
|
111
|
+
const ruleId = comment.groups?.ruleId;
|
|
112
|
+
if (ruleId) {
|
|
113
|
+
if (!disabledLinesByRules.has(ruleId)) {
|
|
114
|
+
disabledLinesByRules.set(ruleId, new Map());
|
|
115
|
+
}
|
|
116
|
+
disabledLinesByRules.get(ruleId).set(line, {
|
|
117
|
+
start: comment.index,
|
|
118
|
+
end: comment.index + comment[0].length,
|
|
119
|
+
});
|
|
120
|
+
}
|
|
121
|
+
else {
|
|
122
|
+
disabledLines.set(line, {
|
|
123
|
+
start: comment.index,
|
|
124
|
+
end: comment.index + comment[0].length,
|
|
125
|
+
});
|
|
126
|
+
}
|
|
127
|
+
}
|
|
128
|
+
let reportedRules = reportedRulesOfFile.get(sourceFile.fileName);
|
|
129
|
+
if (!reportedRules) {
|
|
130
|
+
reportedRules = [];
|
|
131
|
+
reportedRulesOfFile.set(sourceFile.fileName, reportedRules);
|
|
132
|
+
}
|
|
133
|
+
reportedRules.length = 0;
|
|
134
|
+
results = results.filter(error => {
|
|
135
|
+
if (error.source !== 'tsslint') {
|
|
136
|
+
return true;
|
|
137
|
+
}
|
|
138
|
+
const line = sourceFile.getLineAndCharacterOfPosition(error.start).line;
|
|
139
|
+
reportedRules.push([error.code, line]);
|
|
140
|
+
if (disabledLines.has(line)) {
|
|
141
|
+
disabledLines.get(line).used = true;
|
|
142
|
+
return false;
|
|
143
|
+
}
|
|
144
|
+
const disabledLinesByRule = disabledLinesByRules.get(error.code);
|
|
145
|
+
if (disabledLinesByRule?.has(line)) {
|
|
146
|
+
disabledLinesByRule.get(line).used = true;
|
|
147
|
+
return false;
|
|
148
|
+
}
|
|
149
|
+
return true;
|
|
150
|
+
});
|
|
151
|
+
if (reportsUnusedComments) {
|
|
152
|
+
for (const state of disabledLines.values()) {
|
|
153
|
+
if (!state.used) {
|
|
154
|
+
results.push({
|
|
155
|
+
file: sourceFile,
|
|
156
|
+
start: state.start,
|
|
157
|
+
length: state.end - state.start,
|
|
158
|
+
code: 'tsslint:unused-ignore-comment',
|
|
159
|
+
messageText: `Unused ${cmd} comment.`,
|
|
160
|
+
source: 'tsslint',
|
|
161
|
+
category: 1,
|
|
162
|
+
});
|
|
163
|
+
}
|
|
164
|
+
}
|
|
165
|
+
for (const disabledLinesByRule of disabledLinesByRules.values()) {
|
|
166
|
+
for (const state of disabledLinesByRule.values()) {
|
|
167
|
+
if (!state.used) {
|
|
168
|
+
results.push({
|
|
169
|
+
file: sourceFile,
|
|
170
|
+
start: state.start,
|
|
171
|
+
length: state.end - state.start,
|
|
172
|
+
code: 'tsslint:unused-ignore-comment',
|
|
173
|
+
messageText: `Unused ${cmd} comment.`,
|
|
174
|
+
source: 'tsslint',
|
|
175
|
+
category: 1,
|
|
176
|
+
});
|
|
177
|
+
}
|
|
178
|
+
}
|
|
179
|
+
}
|
|
180
|
+
}
|
|
181
|
+
return results;
|
|
182
|
+
},
|
|
183
|
+
};
|
|
184
|
+
};
|
|
185
|
+
}
|
|
186
|
+
//# sourceMappingURL=ignorePlugin.js.map
|
|
@@ -0,0 +1,206 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.create = create;
|
|
4
|
+
function create(cmd, reportsUnusedComments, reg = new RegExp(`//\\s*${cmd}\\b[ \\t]*(?<ruleId>\\S*)\\b`, 'g'), completeReg1 = /^\s*\/\/(\s*)([\S]*)?$/, completeReg2 = new RegExp(`//\\s*${cmd}\\b[ \\t]*(\\S*)?$`)) {
|
|
5
|
+
return ({ typescript: ts, languageService }) => {
|
|
6
|
+
const reportedRulesOfFile = new Map();
|
|
7
|
+
const { getCompletionsAtPosition } = languageService;
|
|
8
|
+
languageService.getCompletionsAtPosition = (fileName, position, ...rest) => {
|
|
9
|
+
let result = getCompletionsAtPosition(fileName, position, ...rest);
|
|
10
|
+
const sourceFile = languageService.getProgram()?.getSourceFile(fileName);
|
|
11
|
+
if (!sourceFile) {
|
|
12
|
+
return result;
|
|
13
|
+
}
|
|
14
|
+
const reportedRules = reportedRulesOfFile.get(fileName);
|
|
15
|
+
const line = sourceFile.getLineAndCharacterOfPosition(position).line;
|
|
16
|
+
const lineStart = sourceFile.getPositionOfLineAndCharacter(line, 0);
|
|
17
|
+
const prefix = sourceFile.text.slice(lineStart, position);
|
|
18
|
+
const matchCmd = completeReg1
|
|
19
|
+
? prefix.match(completeReg1)
|
|
20
|
+
: undefined;
|
|
21
|
+
if (matchCmd) {
|
|
22
|
+
const nextLineRules = reportedRules?.filter(([, reportedLine]) => reportedLine === line + 1) ?? [];
|
|
23
|
+
const item = {
|
|
24
|
+
name: cmd,
|
|
25
|
+
insertText: matchCmd[1].length ? cmd : ` ${cmd}`,
|
|
26
|
+
kind: ts.ScriptElementKind.keyword,
|
|
27
|
+
sortText: 'a',
|
|
28
|
+
replacementSpan: matchCmd[2]
|
|
29
|
+
? {
|
|
30
|
+
start: position - matchCmd[2].length,
|
|
31
|
+
length: matchCmd[2].length,
|
|
32
|
+
}
|
|
33
|
+
: undefined,
|
|
34
|
+
labelDetails: {
|
|
35
|
+
description: nextLineRules.length >= 2
|
|
36
|
+
? `Ignore ${nextLineRules.length} issues in next line`
|
|
37
|
+
: nextLineRules.length
|
|
38
|
+
? 'Ignore 1 issue in next line'
|
|
39
|
+
: undefined,
|
|
40
|
+
}
|
|
41
|
+
};
|
|
42
|
+
if (result) {
|
|
43
|
+
result.entries.push(item);
|
|
44
|
+
}
|
|
45
|
+
else {
|
|
46
|
+
result = {
|
|
47
|
+
isGlobalCompletion: false,
|
|
48
|
+
isMemberCompletion: false,
|
|
49
|
+
isNewIdentifierLocation: false,
|
|
50
|
+
entries: [item],
|
|
51
|
+
};
|
|
52
|
+
}
|
|
53
|
+
}
|
|
54
|
+
else if (reportedRules?.length) {
|
|
55
|
+
const matchRule = completeReg2
|
|
56
|
+
? prefix.match(completeReg2)
|
|
57
|
+
: undefined;
|
|
58
|
+
if (matchRule) {
|
|
59
|
+
const visited = new Set();
|
|
60
|
+
for (const [ruleId] of reportedRules) {
|
|
61
|
+
if (visited.has(ruleId)) {
|
|
62
|
+
continue;
|
|
63
|
+
}
|
|
64
|
+
visited.add(ruleId);
|
|
65
|
+
const reportedLines = reportedRules
|
|
66
|
+
.filter(([r]) => r === ruleId)
|
|
67
|
+
.map(([, l]) => l + 1);
|
|
68
|
+
const item = {
|
|
69
|
+
name: ruleId,
|
|
70
|
+
kind: ts.ScriptElementKind.keyword,
|
|
71
|
+
sortText: ruleId,
|
|
72
|
+
replacementSpan: matchRule[1]
|
|
73
|
+
? {
|
|
74
|
+
start: position - matchRule[1].length,
|
|
75
|
+
length: matchRule[1].length,
|
|
76
|
+
}
|
|
77
|
+
: undefined,
|
|
78
|
+
labelDetails: {
|
|
79
|
+
description: `Reported in line${reportedLines.length >= 2 ? 's' : ''} ${reportedLines.join(', ')}`,
|
|
80
|
+
},
|
|
81
|
+
};
|
|
82
|
+
if (result) {
|
|
83
|
+
result.entries.push(item);
|
|
84
|
+
}
|
|
85
|
+
else {
|
|
86
|
+
result = {
|
|
87
|
+
isGlobalCompletion: false,
|
|
88
|
+
isMemberCompletion: false,
|
|
89
|
+
isNewIdentifierLocation: false,
|
|
90
|
+
entries: [item],
|
|
91
|
+
};
|
|
92
|
+
}
|
|
93
|
+
}
|
|
94
|
+
}
|
|
95
|
+
}
|
|
96
|
+
return result;
|
|
97
|
+
};
|
|
98
|
+
return {
|
|
99
|
+
resolveDiagnostics(sourceFile, results) {
|
|
100
|
+
if (!reportsUnusedComments &&
|
|
101
|
+
!results.some(error => error.source === 'tsslint')) {
|
|
102
|
+
return results;
|
|
103
|
+
}
|
|
104
|
+
const disabledLines = new Map();
|
|
105
|
+
const disabledLinesByRules = new Map();
|
|
106
|
+
for (const comment of sourceFile.text.matchAll(reg)) {
|
|
107
|
+
const line = sourceFile.getLineAndCharacterOfPosition(comment.index).line + 1;
|
|
108
|
+
const ruleId = comment.groups?.ruleId;
|
|
109
|
+
if (ruleId) {
|
|
110
|
+
if (!disabledLinesByRules.has(ruleId)) {
|
|
111
|
+
disabledLinesByRules.set(ruleId, new Map());
|
|
112
|
+
}
|
|
113
|
+
disabledLinesByRules.get(ruleId).set(line, {
|
|
114
|
+
start: comment.index,
|
|
115
|
+
end: comment.index + comment[0].length,
|
|
116
|
+
});
|
|
117
|
+
}
|
|
118
|
+
else {
|
|
119
|
+
disabledLines.set(line, {
|
|
120
|
+
start: comment.index,
|
|
121
|
+
end: comment.index + comment[0].length,
|
|
122
|
+
});
|
|
123
|
+
}
|
|
124
|
+
}
|
|
125
|
+
let reportedRules = reportedRulesOfFile.get(sourceFile.fileName);
|
|
126
|
+
if (!reportedRules) {
|
|
127
|
+
reportedRules = [];
|
|
128
|
+
reportedRulesOfFile.set(sourceFile.fileName, reportedRules);
|
|
129
|
+
}
|
|
130
|
+
reportedRules.length = 0;
|
|
131
|
+
results = results.filter(error => {
|
|
132
|
+
if (error.source !== 'tsslint') {
|
|
133
|
+
return true;
|
|
134
|
+
}
|
|
135
|
+
const line = sourceFile.getLineAndCharacterOfPosition(error.start).line;
|
|
136
|
+
reportedRules.push([error.code, line]);
|
|
137
|
+
if (disabledLines.has(line)) {
|
|
138
|
+
disabledLines.get(line).used = true;
|
|
139
|
+
return false;
|
|
140
|
+
}
|
|
141
|
+
const disabledLinesByRule = disabledLinesByRules.get(error.code);
|
|
142
|
+
if (disabledLinesByRule?.has(line)) {
|
|
143
|
+
disabledLinesByRule.get(line).used = true;
|
|
144
|
+
return false;
|
|
145
|
+
}
|
|
146
|
+
return true;
|
|
147
|
+
});
|
|
148
|
+
if (reportsUnusedComments) {
|
|
149
|
+
for (const state of disabledLines.values()) {
|
|
150
|
+
if (!state.used) {
|
|
151
|
+
results.push({
|
|
152
|
+
file: sourceFile,
|
|
153
|
+
start: state.start,
|
|
154
|
+
length: state.end - state.start,
|
|
155
|
+
code: 'tsslint:unused-ignore-comment',
|
|
156
|
+
messageText: `Unused ${cmd} comment.`,
|
|
157
|
+
source: 'tsslint',
|
|
158
|
+
category: 1,
|
|
159
|
+
});
|
|
160
|
+
}
|
|
161
|
+
}
|
|
162
|
+
for (const disabledLinesByRule of disabledLinesByRules.values()) {
|
|
163
|
+
for (const state of disabledLinesByRule.values()) {
|
|
164
|
+
if (!state.used) {
|
|
165
|
+
results.push({
|
|
166
|
+
file: sourceFile,
|
|
167
|
+
start: state.start,
|
|
168
|
+
length: state.end - state.start,
|
|
169
|
+
code: 'tsslint:unused-ignore-comment',
|
|
170
|
+
messageText: `Unused ${cmd} comment.`,
|
|
171
|
+
source: 'tsslint',
|
|
172
|
+
category: 1,
|
|
173
|
+
});
|
|
174
|
+
}
|
|
175
|
+
}
|
|
176
|
+
}
|
|
177
|
+
}
|
|
178
|
+
return results;
|
|
179
|
+
},
|
|
180
|
+
resolveCodeFixes(sourceFile, diagnostic, codeFixes) {
|
|
181
|
+
if (diagnostic.source !== 'tsslint' || diagnostic.start === undefined) {
|
|
182
|
+
return codeFixes;
|
|
183
|
+
}
|
|
184
|
+
const line = sourceFile.getLineAndCharacterOfPosition(diagnostic.start).line;
|
|
185
|
+
codeFixes.push({
|
|
186
|
+
fixName: cmd,
|
|
187
|
+
description: `Ignore with ${cmd}`,
|
|
188
|
+
changes: [
|
|
189
|
+
{
|
|
190
|
+
fileName: sourceFile.fileName,
|
|
191
|
+
textChanges: [{
|
|
192
|
+
newText: `// ${cmd} ${diagnostic.code}\n`,
|
|
193
|
+
span: {
|
|
194
|
+
start: sourceFile.getPositionOfLineAndCharacter(line, 0),
|
|
195
|
+
length: 0,
|
|
196
|
+
},
|
|
197
|
+
}],
|
|
198
|
+
},
|
|
199
|
+
],
|
|
200
|
+
});
|
|
201
|
+
return codeFixes;
|
|
202
|
+
},
|
|
203
|
+
};
|
|
204
|
+
};
|
|
205
|
+
}
|
|
206
|
+
//# sourceMappingURL=ignore.js.map
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@tsslint/config",
|
|
3
|
-
"version": "1.
|
|
3
|
+
"version": "1.4.0",
|
|
4
4
|
"license": "MIT",
|
|
5
5
|
"files": [
|
|
6
6
|
"**/*.js",
|
|
@@ -12,7 +12,7 @@
|
|
|
12
12
|
"directory": "packages/config"
|
|
13
13
|
},
|
|
14
14
|
"dependencies": {
|
|
15
|
-
"@tsslint/types": "1.
|
|
15
|
+
"@tsslint/types": "1.4.0"
|
|
16
16
|
},
|
|
17
|
-
"gitHead": "
|
|
17
|
+
"gitHead": "9a3f7ce55f079eaaedfb61af9b72d8ba736f0123"
|
|
18
18
|
}
|