@eagleoutice/flowr 2.9.2 → 2.9.4
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/README.md +18 -18
- package/cli/flowr.js +4 -2
- package/control-flow/basic-cfg-guided-visitor.js +10 -4
- package/control-flow/cfg-dead-code.js +6 -3
- package/control-flow/control-flow-graph.js +3 -2
- package/control-flow/simple-visitor.d.ts +2 -1
- package/control-flow/simple-visitor.js +6 -7
- package/core/print/slice-diff-ansi.js +3 -3
- package/dataflow/environments/built-in.d.ts +10 -1
- package/dataflow/environments/environment.js +12 -7
- package/dataflow/eval/resolve/alias-tracking.d.ts +8 -8
- package/dataflow/eval/resolve/alias-tracking.js +33 -34
- package/dataflow/eval/resolve/resolve.d.ts +7 -41
- package/dataflow/eval/resolve/resolve.js +24 -54
- package/dataflow/extractor.js +2 -2
- package/dataflow/fn/higher-order-function.d.ts +2 -1
- package/dataflow/fn/higher-order-function.js +5 -4
- package/dataflow/graph/graph.js +7 -12
- package/dataflow/internal/process/functions/call/argument/make-argument.js +1 -2
- package/dataflow/internal/process/functions/call/built-in/built-in-register-hook.js +2 -2
- package/dataflow/internal/process/functions/call/built-in/built-in-replacement.js +2 -2
- package/dataflow/internal/process/functions/call/built-in/built-in-s-seven-new-generic.js +2 -2
- package/dataflow/internal/process/functions/call/built-in/built-in-s-three-dispatch.js +1 -1
- package/documentation/doc-util/doc-search.js +2 -2
- package/linter/linter-executor.js +1 -2
- package/linter/linter-format.d.ts +37 -11
- package/linter/linter-format.js +59 -16
- package/linter/linter-rules.d.ts +8 -23
- package/linter/rules/absolute-path.d.ts +2 -2
- package/linter/rules/absolute-path.js +6 -7
- package/linter/rules/dataframe-access-validation.d.ts +1 -1
- package/linter/rules/dataframe-access-validation.js +3 -4
- package/linter/rules/dead-code.d.ts +2 -2
- package/linter/rules/dead-code.js +5 -6
- package/linter/rules/deprecated-functions.d.ts +4 -7
- package/linter/rules/file-path-validity.d.ts +2 -2
- package/linter/rules/file-path-validity.js +9 -6
- package/linter/rules/function-finder-util.d.ts +8 -11
- package/linter/rules/function-finder-util.js +21 -12
- package/linter/rules/naming-convention.d.ts +4 -11
- package/linter/rules/naming-convention.js +10 -10
- package/linter/rules/network-functions.d.ts +5 -8
- package/linter/rules/network-functions.js +14 -1
- package/linter/rules/seeded-randomness.d.ts +3 -3
- package/linter/rules/seeded-randomness.js +5 -5
- package/linter/rules/unused-definition.d.ts +2 -2
- package/linter/rules/unused-definition.js +13 -14
- package/linter/rules/useless-loop.d.ts +3 -3
- package/linter/rules/useless-loop.js +4 -4
- package/package.json +1 -1
- package/project/plugins/file-plugins/files/flowr-namespace-file.js +2 -2
- package/queries/catalog/does-call-query/does-call-query-format.js +2 -2
- package/queries/catalog/inspect-exceptions-query/inspect-exception-query-format.js +5 -4
- package/queries/catalog/inspect-higher-order-query/inspect-higher-order-query-executor.js +6 -1
- package/queries/catalog/inspect-higher-order-query/inspect-higher-order-query-format.d.ts +1 -1
- package/queries/catalog/inspect-higher-order-query/inspect-higher-order-query-format.js +5 -4
- package/queries/catalog/inspect-recursion-query/inspect-recursion-query-format.js +4 -3
- package/queries/catalog/linter-query/linter-query-format.d.ts +1 -1
- package/queries/catalog/linter-query/linter-query-format.js +13 -9
- package/queries/query.d.ts +1 -1
- package/r-bridge/lang-4.x/ast/parser/main/normalize-meta.d.ts +1 -1
- package/r-bridge/lang-4.x/ast/parser/main/normalize-meta.js +2 -2
- package/r-bridge/lang-4.x/tree-sitter/tree-sitter-normalize.js +1 -1
- package/r-bridge/roxygen2/roxygen-parse.js +1 -1
- package/statistics/features/supported/defined-functions/defined-functions.d.ts +1 -1
- package/statistics/features/supported/defined-functions/defined-functions.js +4 -4
- package/statistics/features/supported/used-functions/used-functions.js +3 -3
- package/statistics/features/supported/variables/variables.js +4 -4
- package/util/mermaid/dfg.d.ts +0 -5
- package/util/mermaid/dfg.js +2 -19
- package/util/range.d.ts +137 -54
- package/util/range.js +249 -88
- package/util/version.js +1 -1
package/linter/linter-format.js
CHANGED
|
@@ -1,27 +1,70 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.LintingPrettyPrintContext = exports.LintingRuleCertainty = exports.LintingResultCertainty = void 0;
|
|
4
|
-
|
|
5
|
-
exports.isLintingResultsSuccess = isLintingResultsSuccess;
|
|
3
|
+
exports.LintingPrettyPrintContext = exports.LintingRuleCertainty = exports.LintingResultCertainty = exports.LintingResults = void 0;
|
|
4
|
+
const assert_1 = require("../util/assert");
|
|
6
5
|
/**
|
|
7
|
-
*
|
|
8
|
-
* @see {@link isLintingResultsSuccess}
|
|
6
|
+
* Helper functions for working with {@link LintingResults}.
|
|
9
7
|
*/
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
8
|
+
exports.LintingResults = {
|
|
9
|
+
/**
|
|
10
|
+
* Checks whether the given linting results represent an error.
|
|
11
|
+
* @see {@link LintingResultsError}
|
|
12
|
+
* @see {@link LintingResults.isSuccess}
|
|
13
|
+
*/
|
|
14
|
+
isError(o) {
|
|
15
|
+
return 'error' in o;
|
|
16
|
+
},
|
|
17
|
+
/**
|
|
18
|
+
* Checks whether the given linting results represent a successful execution.
|
|
19
|
+
* @see {@link LintingResultsSuccess}
|
|
20
|
+
* @see {@link LintingResults.isError}
|
|
21
|
+
* @see {@link LintingResults.unpackSuccess}
|
|
22
|
+
*/
|
|
23
|
+
isSuccess(o) {
|
|
24
|
+
return 'results' in o;
|
|
25
|
+
},
|
|
26
|
+
/**
|
|
27
|
+
* Unpacks the given linting results, throwing an error if they represent an error.
|
|
28
|
+
*/
|
|
29
|
+
unpackSuccess(o) {
|
|
30
|
+
if (exports.LintingResults.isSuccess(o)) {
|
|
31
|
+
return o;
|
|
32
|
+
}
|
|
33
|
+
throw new Error(exports.LintingResults.stringifyError(o));
|
|
34
|
+
},
|
|
35
|
+
/**
|
|
36
|
+
* Gets all involved node IDs from the given linting results.
|
|
37
|
+
* If the results represent an error, an empty set is returned.
|
|
38
|
+
*/
|
|
39
|
+
allInvolvedIds(res) {
|
|
40
|
+
if (!res || exports.LintingResults.isError(res)) {
|
|
41
|
+
return new Set();
|
|
42
|
+
}
|
|
43
|
+
return new Set(res.results.flatMap(r => r.involvedId).filter(assert_1.isNotUndefined));
|
|
44
|
+
},
|
|
45
|
+
/**
|
|
46
|
+
* Stringifies the error contained in the given linting results error.
|
|
47
|
+
*/
|
|
48
|
+
stringifyError({ error }) {
|
|
49
|
+
if (error instanceof Error) {
|
|
50
|
+
return error.message;
|
|
51
|
+
}
|
|
52
|
+
if (typeof error === 'string') {
|
|
53
|
+
return error;
|
|
54
|
+
}
|
|
55
|
+
try {
|
|
56
|
+
return JSON.stringify(error);
|
|
57
|
+
}
|
|
58
|
+
catch {
|
|
59
|
+
return String(error);
|
|
60
|
+
}
|
|
61
|
+
}
|
|
62
|
+
};
|
|
20
63
|
var LintingResultCertainty;
|
|
21
64
|
(function (LintingResultCertainty) {
|
|
22
65
|
/**
|
|
23
66
|
* The linting rule cannot say for sure whether the result is correct or not.
|
|
24
|
-
* This linting certainty should be used for linting results whose calculations are based on estimations involving unknown side
|
|
67
|
+
* This linting certainty should be used for linting results whose calculations are based on estimations involving unknown side effects, reflection, etc.
|
|
25
68
|
*/
|
|
26
69
|
LintingResultCertainty["Uncertain"] = "uncertain";
|
|
27
70
|
/**
|
package/linter/linter-rules.d.ts
CHANGED
|
@@ -6,13 +6,10 @@ import type { LintingRule } from './linter-format';
|
|
|
6
6
|
export declare const LintingRules: {
|
|
7
7
|
readonly 'deprecated-functions': {
|
|
8
8
|
readonly createSearch: (config: import("./rules/function-finder-util").FunctionsToDetectConfig) => import("../search/flowr-search-builder").FlowrSearchBuilder<"all", ["filter", "with", "filter"], import("../r-bridge/lang-4.x/ast/model/processing/decorate").ParentInformation, Promise<import("../search/flowr-search").FlowrSearchElements<import("../r-bridge/lang-4.x/ast/model/processing/decorate").ParentInformation, [] | import("../search/flowr-search").FlowrSearchElement<import("../r-bridge/lang-4.x/ast/model/processing/decorate").ParentInformation>[]>>>;
|
|
9
|
-
readonly processSearchResult: <T extends import("../search/flowr-search").FlowrSearchElement<import("../r-bridge/lang-4.x/ast/model/processing/decorate").ParentInformation>[]>(elements: import("../search/flowr-search").FlowrSearchElements<import("../r-bridge/lang-4.x/ast/model/processing/decorate").ParentInformation, T>, _config: unknown, _data: unknown, refineSearch?: (elements: T) => T
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
function: import("../dataflow/environments/identifier").BrandedIdentifier;
|
|
14
|
-
range: import("../util/range").SourceRange;
|
|
15
|
-
}[];
|
|
9
|
+
readonly processSearchResult: <T extends import("../search/flowr-search").FlowrSearchElement<import("../r-bridge/lang-4.x/ast/model/processing/decorate").ParentInformation>[]>(elements: import("../search/flowr-search").FlowrSearchElements<import("../r-bridge/lang-4.x/ast/model/processing/decorate").ParentInformation, T>, _config: unknown, _data: unknown, refineSearch?: (elements: T) => (T[number] & {
|
|
10
|
+
certainty?: import("./linter-format").LintingResultCertainty;
|
|
11
|
+
})[]) => {
|
|
12
|
+
results: import("./rules/function-finder-util").FunctionsResult[];
|
|
16
13
|
'.meta': import("./rules/function-finder-util").FunctionsMetadata;
|
|
17
14
|
};
|
|
18
15
|
readonly prettyPrint: {
|
|
@@ -68,7 +65,7 @@ export declare const LintingRules: {
|
|
|
68
65
|
involvedId: import("../r-bridge/lang-4.x/ast/model/processing/node-id").NodeId;
|
|
69
66
|
certainty: import("./linter-format").LintingResultCertainty;
|
|
70
67
|
function: import("../dataflow/environments/identifier").BrandedIdentifier;
|
|
71
|
-
|
|
68
|
+
loc: [startLine: number, startColumn: number, endLine: number, endColumn: number, f?: string | undefined];
|
|
72
69
|
}[];
|
|
73
70
|
'.meta': import("./rules/seeded-randomness").SeededRandomnessMeta;
|
|
74
71
|
};
|
|
@@ -157,14 +154,7 @@ export declare const LintingRules: {
|
|
|
157
154
|
cfg: import("../control-flow/control-flow-graph").ControlFlowInformation;
|
|
158
155
|
analyzer: import("../project/flowr-analyzer").ReadonlyFlowrAnalysisProvider;
|
|
159
156
|
}) => {
|
|
160
|
-
results:
|
|
161
|
-
involvedId: import("../r-bridge/lang-4.x/ast/model/processing/node-id").NodeId;
|
|
162
|
-
quickFix: import("./linter-format").LintQuickFixReplacement[] | undefined;
|
|
163
|
-
certainty: import("./linter-format").LintingResultCertainty;
|
|
164
|
-
detectedCasing: import("./rules/naming-convention").CasingConvention;
|
|
165
|
-
name: string;
|
|
166
|
-
range: import("../util/range").SourceRange;
|
|
167
|
-
}[];
|
|
157
|
+
results: import("./rules/naming-convention").NamingConventionResult[];
|
|
168
158
|
'.meta': {
|
|
169
159
|
numMatches: number;
|
|
170
160
|
numBreak: number;
|
|
@@ -193,12 +183,7 @@ export declare const LintingRules: {
|
|
|
193
183
|
cfg: import("../control-flow/control-flow-graph").ControlFlowInformation;
|
|
194
184
|
analyzer: import("../project/flowr-analyzer").ReadonlyFlowrAnalysisProvider;
|
|
195
185
|
}) => {
|
|
196
|
-
results:
|
|
197
|
-
certainty: import("./linter-format").LintingResultCertainty;
|
|
198
|
-
involvedId: import("../r-bridge/lang-4.x/ast/model/processing/node-id").NodeId;
|
|
199
|
-
function: import("../dataflow/environments/identifier").BrandedIdentifier;
|
|
200
|
-
range: import("../util/range").SourceRange;
|
|
201
|
-
}[];
|
|
186
|
+
results: import("./rules/function-finder-util").FunctionsResult[];
|
|
202
187
|
'.meta': import("./rules/function-finder-util").FunctionsMetadata;
|
|
203
188
|
};
|
|
204
189
|
readonly prettyPrint: {
|
|
@@ -275,7 +260,7 @@ export declare const LintingRules: {
|
|
|
275
260
|
results: {
|
|
276
261
|
certainty: import("./linter-format").LintingResultCertainty.Certain;
|
|
277
262
|
name: string;
|
|
278
|
-
|
|
263
|
+
loc: [startLine: number, startColumn: number, endLine: number, endColumn: number, f?: string | undefined];
|
|
279
264
|
involvedId: import("../r-bridge/lang-4.x/ast/model/processing/node-id").NodeId;
|
|
280
265
|
}[];
|
|
281
266
|
'.meta': {
|
|
@@ -1,11 +1,11 @@
|
|
|
1
1
|
import { type LintingResult, LintingRuleCertainty } from '../linter-format';
|
|
2
2
|
import { type MergeableRecord } from '../../util/objects';
|
|
3
|
-
import {
|
|
3
|
+
import { SourceLocation } from '../../util/range';
|
|
4
4
|
import { LintingRuleTag } from '../linter-tags';
|
|
5
5
|
import type { FunctionInfo } from '../../queries/catalog/dependencies-query/function-info/function-info';
|
|
6
6
|
export interface AbsoluteFilePathResult extends LintingResult {
|
|
7
7
|
filePath: string;
|
|
8
|
-
|
|
8
|
+
loc: SourceLocation;
|
|
9
9
|
}
|
|
10
10
|
type SupportedWd = '@script' | '@home' | string;
|
|
11
11
|
export interface AbsoluteFilePathConfig extends MergeableRecord {
|
|
@@ -8,7 +8,6 @@ const linter_format_1 = require("../linter-format");
|
|
|
8
8
|
const objects_1 = require("../../util/objects");
|
|
9
9
|
const flowr_search_builder_1 = require("../../search/flowr-search-builder");
|
|
10
10
|
const range_1 = require("../../util/range");
|
|
11
|
-
const dfg_1 = require("../../util/mermaid/dfg");
|
|
12
11
|
const linter_tags_1 = require("../linter-tags");
|
|
13
12
|
const type_1 = require("../../r-bridge/lang-4.x/ast/model/type");
|
|
14
13
|
const strings_1 = require("../../util/text/strings");
|
|
@@ -42,7 +41,7 @@ function buildQuickFix(str, filePath, wd) {
|
|
|
42
41
|
}
|
|
43
42
|
return [{
|
|
44
43
|
type: 'replace',
|
|
45
|
-
|
|
44
|
+
loc: range_1.SourceLocation.fromNode(str) ?? range_1.SourceLocation.invalid(),
|
|
46
45
|
description: `Replace with a relative path to \`${filePath}\``,
|
|
47
46
|
replacement: str.content.quotes + '.' + path_1.default.sep + path_1.default.relative(wd, filePath) + str.content.quotes
|
|
48
47
|
}];
|
|
@@ -108,7 +107,7 @@ exports.ABSOLUTE_PATH = {
|
|
|
108
107
|
return [{
|
|
109
108
|
certainty: linter_format_1.LintingResultCertainty.Uncertain,
|
|
110
109
|
filePath: node.content.str,
|
|
111
|
-
|
|
110
|
+
loc: range_1.SourceLocation.fromNode(node) ?? range_1.SourceLocation.invalid(),
|
|
112
111
|
quickFix: buildQuickFix(node, node.content.str, wd)
|
|
113
112
|
}];
|
|
114
113
|
}
|
|
@@ -123,7 +122,7 @@ exports.ABSOLUTE_PATH = {
|
|
|
123
122
|
return {
|
|
124
123
|
certainty: linter_format_1.LintingResultCertainty.Certain,
|
|
125
124
|
filePath: r.value,
|
|
126
|
-
|
|
125
|
+
loc: elem ? range_1.SourceLocation.fromNode(elem) ?? range_1.SourceLocation.invalid() : range_1.SourceLocation.invalid(),
|
|
127
126
|
quickFix: buildQuickFix(elem, r.value, wd)
|
|
128
127
|
};
|
|
129
128
|
});
|
|
@@ -144,7 +143,7 @@ exports.ABSOLUTE_PATH = {
|
|
|
144
143
|
return strings.filter(s => (0, strings_1.isAbsolutePath)(s, regex)).map(str => ({
|
|
145
144
|
certainty: linter_format_1.LintingResultCertainty.Uncertain,
|
|
146
145
|
filePath: str,
|
|
147
|
-
|
|
146
|
+
loc: range_1.SourceLocation.fromNode(element.node) ?? range_1.SourceLocation.invalid(),
|
|
148
147
|
quickFix: undefined
|
|
149
148
|
}));
|
|
150
149
|
}
|
|
@@ -158,8 +157,8 @@ exports.ABSOLUTE_PATH = {
|
|
|
158
157
|
};
|
|
159
158
|
},
|
|
160
159
|
prettyPrint: {
|
|
161
|
-
[linter_format_1.LintingPrettyPrintContext.Query]: result => `Path \`${result.filePath}\` at ${
|
|
162
|
-
[linter_format_1.LintingPrettyPrintContext.Full]: result => `Path \`${result.filePath}\` at ${
|
|
160
|
+
[linter_format_1.LintingPrettyPrintContext.Query]: result => `Path \`${result.filePath}\` at ${range_1.SourceLocation.format(result.loc)}`,
|
|
161
|
+
[linter_format_1.LintingPrettyPrintContext.Full]: result => `Path \`${result.filePath}\` at ${range_1.SourceLocation.format(result.loc)} is absolute`
|
|
163
162
|
},
|
|
164
163
|
info: {
|
|
165
164
|
name: 'Absolute Paths',
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import type { ParentInformation } from '../../r-bridge/lang-4.x/ast/model/processing/decorate';
|
|
2
2
|
import type { FlowrSearchElements } from '../../search/flowr-search';
|
|
3
3
|
import { type MergeableRecord } from '../../util/objects';
|
|
4
|
-
import {
|
|
4
|
+
import { SourceRange } from '../../util/range';
|
|
5
5
|
import { LintingRuleCertainty, type LintingResult } from '../linter-format';
|
|
6
6
|
import { LintingRuleTag } from '../linter-tags';
|
|
7
7
|
export interface DataFrameAccessValidationResult extends LintingResult {
|
|
@@ -9,7 +9,6 @@ const type_1 = require("../../r-bridge/lang-4.x/ast/model/type");
|
|
|
9
9
|
const flowr_search_builder_1 = require("../../search/flowr-search-builder");
|
|
10
10
|
const search_enrichers_1 = require("../../search/search-executor/search-enrichers");
|
|
11
11
|
const logic_1 = require("../../util/logic");
|
|
12
|
-
const dfg_1 = require("../../util/mermaid/dfg");
|
|
13
12
|
const range_1 = require("../../util/range");
|
|
14
13
|
const linter_format_1 = require("../linter-format");
|
|
15
14
|
const linter_tags_1 = require("../linter-tags");
|
|
@@ -69,7 +68,7 @@ exports.DATA_FRAME_ACCESS_VALIDATION = {
|
|
|
69
68
|
involvedId: node?.info.id,
|
|
70
69
|
access: node?.lexeme ?? '???',
|
|
71
70
|
...(operand?.type === type_1.RType.Symbol ? { operand: identifier_1.Identifier.getName(operand.content) } : {}),
|
|
72
|
-
range:
|
|
71
|
+
range: range_1.SourceRange.fromNode(node) ?? range_1.SourceRange.invalid(),
|
|
73
72
|
certainty: linter_format_1.LintingResultCertainty.Certain
|
|
74
73
|
}));
|
|
75
74
|
return { results, '.meta': metadata };
|
|
@@ -77,10 +76,10 @@ exports.DATA_FRAME_ACCESS_VALIDATION = {
|
|
|
77
76
|
prettyPrint: {
|
|
78
77
|
[linter_format_1.LintingPrettyPrintContext.Query]: result => `Access of ${result.type} ` +
|
|
79
78
|
(typeof result.accessed === 'string' ? `"${result.accessed}"` : result.accessed) + ' ' +
|
|
80
|
-
(result.operand !== undefined ? `of \`${result.operand}\`` : `at \`${result.access}\``) + ` at ${
|
|
79
|
+
(result.operand !== undefined ? `of \`${result.operand}\`` : `at \`${result.access}\``) + ` at ${range_1.SourceRange.format(result.range)}`,
|
|
81
80
|
[linter_format_1.LintingPrettyPrintContext.Full]: result => `Accessed ${result.type} ` +
|
|
82
81
|
(typeof result.accessed === 'string' ? `"${result.accessed}"` : result.accessed) + ' does not exist ' +
|
|
83
|
-
(result.operand !== undefined ? `in \`${result.operand}\`` : `at \`${result.access}\``) + ` at ${
|
|
82
|
+
(result.operand !== undefined ? `in \`${result.operand}\`` : `at \`${result.access}\``) + ` at ${range_1.SourceRange.format(result.range)}`
|
|
84
83
|
},
|
|
85
84
|
info: {
|
|
86
85
|
name: 'Dataframe Access Validation',
|
|
@@ -1,10 +1,10 @@
|
|
|
1
1
|
import { type LintingResult, LintingRuleCertainty } from '../linter-format';
|
|
2
|
-
import {
|
|
2
|
+
import { SourceLocation } from '../../util/range';
|
|
3
3
|
import type { MergeableRecord } from '../../util/objects';
|
|
4
4
|
import { LintingRuleTag } from '../linter-tags';
|
|
5
5
|
import { type CfgSimplificationPassName } from '../../control-flow/cfg-simplification';
|
|
6
6
|
export interface DeadCodeResult extends LintingResult {
|
|
7
|
-
readonly
|
|
7
|
+
readonly loc: SourceLocation;
|
|
8
8
|
}
|
|
9
9
|
export interface DeadCodeConfig extends MergeableRecord {
|
|
10
10
|
/**
|
|
@@ -4,7 +4,6 @@ exports.DEAD_CODE = void 0;
|
|
|
4
4
|
const linter_format_1 = require("../linter-format");
|
|
5
5
|
const range_1 = require("../../util/range");
|
|
6
6
|
const flowr_search_builder_1 = require("../../search/flowr-search-builder");
|
|
7
|
-
const dfg_1 = require("../../util/mermaid/dfg");
|
|
8
7
|
const linter_tags_1 = require("../linter-tags");
|
|
9
8
|
const search_enrichers_1 = require("../../search/search-executor/search-enrichers");
|
|
10
9
|
const assert_1 = require("../../util/assert");
|
|
@@ -28,15 +27,15 @@ exports.DEAD_CODE = {
|
|
|
28
27
|
.map(element => ({
|
|
29
28
|
certainty: linter_format_1.LintingResultCertainty.Certain,
|
|
30
29
|
involvedId: element.node.info.id,
|
|
31
|
-
|
|
30
|
+
loc: range_1.SourceLocation.fromNode(element.node)
|
|
32
31
|
}))
|
|
33
|
-
.filter(element => (0, assert_1.isNotUndefined)(element.
|
|
32
|
+
.filter(element => (0, assert_1.isNotUndefined)(element.loc))),
|
|
34
33
|
'.meta': meta
|
|
35
34
|
};
|
|
36
35
|
},
|
|
37
36
|
prettyPrint: {
|
|
38
|
-
[linter_format_1.LintingPrettyPrintContext.Query]: result => `Code at ${
|
|
39
|
-
[linter_format_1.LintingPrettyPrintContext.Full]: result => `Code at ${
|
|
37
|
+
[linter_format_1.LintingPrettyPrintContext.Query]: result => `Code at ${range_1.SourceLocation.format(result.loc)}`,
|
|
38
|
+
[linter_format_1.LintingPrettyPrintContext.Full]: result => `Code at ${range_1.SourceLocation.format(result.loc)} can never be executed`,
|
|
40
39
|
},
|
|
41
40
|
info: {
|
|
42
41
|
name: 'Dead Code',
|
|
@@ -50,7 +49,7 @@ exports.DEAD_CODE = {
|
|
|
50
49
|
function combineResults(results) {
|
|
51
50
|
for (let i = results.length - 1; i >= 0; i--) {
|
|
52
51
|
const result = results[i];
|
|
53
|
-
const other = results.find(other => result !== other &&
|
|
52
|
+
const other = results.find(other => result !== other && range_1.SourceLocation.isSubsetOf(result.loc, other.loc));
|
|
54
53
|
if (other !== undefined) {
|
|
55
54
|
if (!Array.isArray(other.involvedId)) {
|
|
56
55
|
other.involvedId = other.involvedId !== undefined ? [other.involvedId] : [];
|
|
@@ -3,13 +3,10 @@ import { LintingRuleTag } from '../linter-tags';
|
|
|
3
3
|
import { type FunctionsMetadata, type FunctionsResult, type FunctionsToDetectConfig } from './function-finder-util';
|
|
4
4
|
export declare const DEPRECATED_FUNCTIONS: {
|
|
5
5
|
readonly createSearch: (config: FunctionsToDetectConfig) => import("../../search/flowr-search-builder").FlowrSearchBuilder<"all", ["filter", "with", "filter"], import("../../r-bridge/lang-4.x/ast/model/processing/decorate").ParentInformation, Promise<import("../../search/flowr-search").FlowrSearchElements<import("../../r-bridge/lang-4.x/ast/model/processing/decorate").ParentInformation, [] | import("../../search/flowr-search").FlowrSearchElement<import("../../r-bridge/lang-4.x/ast/model/processing/decorate").ParentInformation>[]>>>;
|
|
6
|
-
readonly processSearchResult: <T extends import("../../search/flowr-search").FlowrSearchElement<import("../../r-bridge/lang-4.x/ast/model/processing/decorate").ParentInformation>[]>(elements: import("../../search/flowr-search").FlowrSearchElements<import("../../r-bridge/lang-4.x/ast/model/processing/decorate").ParentInformation, T>, _config: unknown, _data: unknown, refineSearch?: (elements: T) => T
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
function: import("../../dataflow/environments/identifier").BrandedIdentifier;
|
|
11
|
-
range: import("../../util/range").SourceRange;
|
|
12
|
-
}[];
|
|
6
|
+
readonly processSearchResult: <T extends import("../../search/flowr-search").FlowrSearchElement<import("../../r-bridge/lang-4.x/ast/model/processing/decorate").ParentInformation>[]>(elements: import("../../search/flowr-search").FlowrSearchElements<import("../../r-bridge/lang-4.x/ast/model/processing/decorate").ParentInformation, T>, _config: unknown, _data: unknown, refineSearch?: (elements: T) => (T[number] & {
|
|
7
|
+
certainty?: import("../linter-format").LintingResultCertainty;
|
|
8
|
+
})[]) => {
|
|
9
|
+
results: FunctionsResult[];
|
|
13
10
|
'.meta': FunctionsMetadata;
|
|
14
11
|
};
|
|
15
12
|
readonly prettyPrint: {
|
|
@@ -1,11 +1,11 @@
|
|
|
1
1
|
import { type LintingResult, LintingRuleCertainty } from '../linter-format';
|
|
2
2
|
import type { MergeableRecord } from '../../util/objects';
|
|
3
|
-
import
|
|
3
|
+
import { SourceLocation } from '../../util/range';
|
|
4
4
|
import type { FunctionInfo } from '../../queries/catalog/dependencies-query/function-info/function-info';
|
|
5
5
|
import { LintingRuleTag } from '../linter-tags';
|
|
6
6
|
export interface FilePathValidityResult extends LintingResult {
|
|
7
7
|
filePath: string;
|
|
8
|
-
|
|
8
|
+
loc: SourceLocation;
|
|
9
9
|
}
|
|
10
10
|
export interface FilePathValidityConfig extends MergeableRecord {
|
|
11
11
|
/**
|
|
@@ -3,7 +3,7 @@ Object.defineProperty(exports, "__esModule", { value: true });
|
|
|
3
3
|
exports.FILE_PATH_VALIDITY = void 0;
|
|
4
4
|
const linter_format_1 = require("../linter-format");
|
|
5
5
|
const flowr_search_builder_1 = require("../../search/flowr-search-builder");
|
|
6
|
-
const
|
|
6
|
+
const range_1 = require("../../util/range");
|
|
7
7
|
const dependencies_query_format_1 = require("../../queries/catalog/dependencies-query/dependencies-query-format");
|
|
8
8
|
const built_in_source_1 = require("../../dataflow/internal/process/functions/call/built-in/built-in-source");
|
|
9
9
|
const logic_1 = require("../../util/logic");
|
|
@@ -33,14 +33,17 @@ exports.FILE_PATH_VALIDITY = {
|
|
|
33
33
|
return [];
|
|
34
34
|
}
|
|
35
35
|
metadata.totalReads++;
|
|
36
|
-
const
|
|
36
|
+
const loc = range_1.SourceLocation.fromNode(element.node);
|
|
37
|
+
if (!loc) {
|
|
38
|
+
return [];
|
|
39
|
+
}
|
|
37
40
|
// check if we can't parse the file path statically
|
|
38
41
|
if (matchingRead.value === dependencies_query_format_1.Unknown) {
|
|
39
42
|
metadata.totalUnknown++;
|
|
40
43
|
if (config.includeUnknown) {
|
|
41
44
|
return [{
|
|
42
45
|
involvedId: matchingRead.nodeId,
|
|
43
|
-
|
|
46
|
+
loc,
|
|
44
47
|
filePath: dependencies_query_format_1.Unknown,
|
|
45
48
|
certainty: linter_format_1.LintingResultCertainty.Uncertain
|
|
46
49
|
}];
|
|
@@ -67,7 +70,7 @@ exports.FILE_PATH_VALIDITY = {
|
|
|
67
70
|
}
|
|
68
71
|
return [{
|
|
69
72
|
involvedId: matchingRead.nodeId,
|
|
70
|
-
|
|
73
|
+
loc,
|
|
71
74
|
filePath: matchingRead.value,
|
|
72
75
|
certainty: writesBefore && writesBefore.length && writesBefore.every(w => w === logic_1.Ternary.Maybe) ? linter_format_1.LintingResultCertainty.Uncertain : linter_format_1.LintingResultCertainty.Certain
|
|
73
76
|
}];
|
|
@@ -88,8 +91,8 @@ exports.FILE_PATH_VALIDITY = {
|
|
|
88
91
|
}
|
|
89
92
|
},
|
|
90
93
|
prettyPrint: {
|
|
91
|
-
[linter_format_1.LintingPrettyPrintContext.Query]: result => `Path \`${result.filePath}\` at ${
|
|
92
|
-
[linter_format_1.LintingPrettyPrintContext.Full]: result => `Path \`${result.filePath}\` at ${
|
|
94
|
+
[linter_format_1.LintingPrettyPrintContext.Query]: result => `Path \`${result.filePath}\` at ${range_1.SourceLocation.format(result.loc)}`,
|
|
95
|
+
[linter_format_1.LintingPrettyPrintContext.Full]: result => `Path \`${result.filePath}\` at ${range_1.SourceLocation.format(result.loc)} does not point to a valid file`
|
|
93
96
|
}
|
|
94
97
|
};
|
|
95
98
|
function samePath(a, b, ignoreCapitalization) {
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import
|
|
1
|
+
import { SourceLocation } from '../../util/range';
|
|
2
2
|
import { type LintingResult, LintingResultCertainty } from '../linter-format';
|
|
3
3
|
import type { FlowrSearchElement, FlowrSearchElements } from '../../search/flowr-search';
|
|
4
4
|
import type { NormalizedAst, ParentInformation } from '../../r-bridge/lang-4.x/ast/model/processing/decorate';
|
|
@@ -6,10 +6,10 @@ import type { MergeableRecord } from '../../util/objects';
|
|
|
6
6
|
import type { DataflowInformation } from '../../dataflow/info';
|
|
7
7
|
import type { FunctionInfo } from '../../queries/catalog/dependencies-query/function-info/function-info';
|
|
8
8
|
import type { ReadonlyFlowrAnalysisProvider } from '../../project/flowr-analyzer';
|
|
9
|
-
import
|
|
9
|
+
import { Ternary } from '../../util/logic';
|
|
10
10
|
export interface FunctionsResult extends LintingResult {
|
|
11
11
|
function: string;
|
|
12
|
-
|
|
12
|
+
loc: SourceLocation;
|
|
13
13
|
}
|
|
14
14
|
export interface FunctionsMetadata extends MergeableRecord {
|
|
15
15
|
totalCalls: number;
|
|
@@ -26,13 +26,10 @@ export interface FunctionsToDetectConfig extends MergeableRecord {
|
|
|
26
26
|
*/
|
|
27
27
|
export declare const functionFinderUtil: {
|
|
28
28
|
createSearch: (functions: readonly string[]) => import("../../search/flowr-search-builder").FlowrSearchBuilder<"all", ["filter", "with", "filter"], ParentInformation, Promise<FlowrSearchElements<ParentInformation, [] | FlowrSearchElement<ParentInformation>[]>>>;
|
|
29
|
-
processSearchResult: <T extends FlowrSearchElement<ParentInformation>[]>(elements: FlowrSearchElements<ParentInformation, T>, _config: unknown, _data: unknown, refineSearch?: (elements: T) => T
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
function: BrandedIdentifier;
|
|
34
|
-
range: SourceRange;
|
|
35
|
-
}[];
|
|
29
|
+
processSearchResult: <T extends FlowrSearchElement<ParentInformation>[]>(elements: FlowrSearchElements<ParentInformation, T>, _config: unknown, _data: unknown, refineSearch?: (elements: T) => (T[number] & {
|
|
30
|
+
certainty?: LintingResultCertainty;
|
|
31
|
+
})[]) => {
|
|
32
|
+
results: FunctionsResult[];
|
|
36
33
|
'.meta': FunctionsMetadata;
|
|
37
34
|
};
|
|
38
35
|
prettyPrint: (functionType: string) => {
|
|
@@ -43,5 +40,5 @@ export declare const functionFinderUtil: {
|
|
|
43
40
|
normalize: NormalizedAst;
|
|
44
41
|
dataflow: DataflowInformation;
|
|
45
42
|
analyzer: ReadonlyFlowrAnalysisProvider;
|
|
46
|
-
}, requireValue: RegExp | string | undefined):
|
|
43
|
+
}, requireValue: RegExp | string | undefined): Ternary;
|
|
47
44
|
};
|
|
@@ -4,12 +4,13 @@ exports.functionFinderUtil = void 0;
|
|
|
4
4
|
const flowr_search_builder_1 = require("../../search/flowr-search-builder");
|
|
5
5
|
const flowr_search_filters_1 = require("../../search/flowr-search-filters");
|
|
6
6
|
const search_enrichers_1 = require("../../search/search-executor/search-enrichers");
|
|
7
|
+
const range_1 = require("../../util/range");
|
|
7
8
|
const linter_format_1 = require("../linter-format");
|
|
8
|
-
const dfg_1 = require("../../util/mermaid/dfg");
|
|
9
9
|
const assert_1 = require("../../util/assert");
|
|
10
10
|
const resolve_argument_1 = require("../../dataflow/eval/resolve/resolve-argument");
|
|
11
11
|
const vertex_1 = require("../../dataflow/graph/vertex");
|
|
12
12
|
const dependencies_query_format_1 = require("../../queries/catalog/dependencies-query/dependencies-query-format");
|
|
13
|
+
const logic_1 = require("../../util/logic");
|
|
13
14
|
/**
|
|
14
15
|
* This helper object collects utility functions used to create linting rules that search for specific functions.
|
|
15
16
|
*/
|
|
@@ -37,42 +38,50 @@ exports.functionFinderUtil = {
|
|
|
37
38
|
metadata.totalFunctionDefinitions++;
|
|
38
39
|
return {
|
|
39
40
|
node: element.node,
|
|
40
|
-
|
|
41
|
-
target: target
|
|
41
|
+
loc: range_1.SourceLocation.fromNode(element.node),
|
|
42
|
+
target: target,
|
|
43
|
+
certainty: element.certainty
|
|
42
44
|
};
|
|
43
45
|
});
|
|
44
46
|
});
|
|
45
47
|
return {
|
|
46
48
|
results: results.map(element => ({
|
|
47
|
-
certainty: linter_format_1.LintingResultCertainty.Certain,
|
|
49
|
+
certainty: element.certainty ?? linter_format_1.LintingResultCertainty.Certain,
|
|
48
50
|
involvedId: element.node.info.id,
|
|
49
51
|
function: element.target,
|
|
50
|
-
|
|
51
|
-
})),
|
|
52
|
+
loc: element.loc
|
|
53
|
+
})).filter(e => (0, assert_1.isNotUndefined)(e.loc)),
|
|
52
54
|
'.meta': metadata
|
|
53
55
|
};
|
|
54
56
|
},
|
|
55
57
|
prettyPrint: (functionType) => {
|
|
56
58
|
return {
|
|
57
|
-
[linter_format_1.LintingPrettyPrintContext.Query]: (result) => `Function \`${result.function}\` at ${
|
|
58
|
-
[linter_format_1.LintingPrettyPrintContext.Full]: (result) => `Function \`${result.function}\` called at ${
|
|
59
|
+
[linter_format_1.LintingPrettyPrintContext.Query]: (result) => `Function \`${result.function}\` at ${range_1.SourceLocation.format(result.loc)}`,
|
|
60
|
+
[linter_format_1.LintingPrettyPrintContext.Full]: (result) => `Function \`${result.function}\` called at ${range_1.SourceLocation.format(result.loc)} is related to ${functionType}`
|
|
59
61
|
};
|
|
60
62
|
},
|
|
61
63
|
requireArgumentValue(element, pool, data, requireValue) {
|
|
62
64
|
const info = pool.find(f => f.name === element.node.lexeme);
|
|
63
65
|
/* if we have no additional info, we assume they always access the network */
|
|
64
66
|
if (info === undefined) {
|
|
65
|
-
return
|
|
67
|
+
return logic_1.Ternary.Always;
|
|
66
68
|
}
|
|
67
69
|
const vert = data.dataflow.graph.getVertex(element.node.info.id);
|
|
68
70
|
if ((0, vertex_1.isFunctionCallVertex)(vert)) {
|
|
69
71
|
const args = (0, resolve_argument_1.getArgumentStringValue)(data.analyzer.flowrConfig.solver.variables, data.dataflow.graph, vert, info.argIdx, info.argName, info.resolveValue, data.analyzer.inspectContext());
|
|
70
72
|
// we obtain all values, at least one of them has to trigger for the request
|
|
71
73
|
const argValues = args ? args.values().flatMap(v => [...v]).filter(assert_1.isNotUndefined).toArray() : [];
|
|
72
|
-
|
|
73
|
-
|
|
74
|
+
if (argValues.length === 0) {
|
|
75
|
+
return logic_1.Ternary.Maybe;
|
|
76
|
+
}
|
|
77
|
+
else if (argValues.some(v => requireValue instanceof RegExp ? requireValue.test(v) : v === requireValue)) {
|
|
78
|
+
return logic_1.Ternary.Always;
|
|
79
|
+
}
|
|
80
|
+
else if (argValues.some(v => v === dependencies_query_format_1.Unknown)) {
|
|
81
|
+
return logic_1.Ternary.Maybe;
|
|
82
|
+
}
|
|
74
83
|
}
|
|
75
|
-
return
|
|
84
|
+
return logic_1.Ternary.Never;
|
|
76
85
|
}
|
|
77
86
|
};
|
|
78
87
|
//# sourceMappingURL=function-finder-util.js.map
|
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
import type { DataflowGraph } from '../../dataflow/graph/graph';
|
|
2
2
|
import type { NodeId } from '../../r-bridge/lang-4.x/ast/model/processing/node-id';
|
|
3
3
|
import type { MergeableRecord } from '../../util/objects';
|
|
4
|
-
import
|
|
5
|
-
import { type LintingResult, type LintQuickFixReplacement,
|
|
4
|
+
import { SourceLocation } from '../../util/range';
|
|
5
|
+
import { type LintingResult, type LintQuickFixReplacement, LintingRuleCertainty } from '../linter-format';
|
|
6
6
|
import { LintingRuleTag } from '../linter-tags';
|
|
7
7
|
export declare enum CasingConvention {
|
|
8
8
|
CamelCase = "camelCase",
|
|
@@ -16,7 +16,7 @@ export declare enum CasingConvention {
|
|
|
16
16
|
export interface NamingConventionResult extends LintingResult {
|
|
17
17
|
name: string;
|
|
18
18
|
detectedCasing: CasingConvention;
|
|
19
|
-
|
|
19
|
+
loc: SourceLocation;
|
|
20
20
|
}
|
|
21
21
|
/**
|
|
22
22
|
* It is planned to have a config like ESLint
|
|
@@ -66,14 +66,7 @@ export declare const NAMING_CONVENTION: {
|
|
|
66
66
|
cfg: import("../../control-flow/control-flow-graph").ControlFlowInformation;
|
|
67
67
|
analyzer: import("../../project/flowr-analyzer").ReadonlyFlowrAnalysisProvider;
|
|
68
68
|
}) => {
|
|
69
|
-
results:
|
|
70
|
-
involvedId: NodeId;
|
|
71
|
-
quickFix: LintQuickFixReplacement[] | undefined;
|
|
72
|
-
certainty: LintingResultCertainty;
|
|
73
|
-
detectedCasing: CasingConvention;
|
|
74
|
-
name: string;
|
|
75
|
-
range: SourceRange;
|
|
76
|
-
}[];
|
|
69
|
+
results: NamingConventionResult[];
|
|
77
70
|
'.meta': {
|
|
78
71
|
numMatches: number;
|
|
79
72
|
numBreak: number;
|
|
@@ -10,7 +10,7 @@ const vertex_1 = require("../../dataflow/graph/vertex");
|
|
|
10
10
|
const dfg_get_symbol_refs_1 = require("../../dataflow/origin/dfg-get-symbol-refs");
|
|
11
11
|
const flowr_search_builder_1 = require("../../search/flowr-search-builder");
|
|
12
12
|
const assert_1 = require("../../util/assert");
|
|
13
|
-
const
|
|
13
|
+
const range_1 = require("../../util/range");
|
|
14
14
|
const linter_format_1 = require("../linter-format");
|
|
15
15
|
const linter_tags_1 = require("../linter-tags");
|
|
16
16
|
var CasingConvention;
|
|
@@ -136,21 +136,21 @@ function createNamingConventionQuickFixes(graph, nodeId, replacement, conv) {
|
|
|
136
136
|
if (node === undefined) {
|
|
137
137
|
continue;
|
|
138
138
|
}
|
|
139
|
-
const
|
|
140
|
-
if (
|
|
139
|
+
const loc = range_1.SourceLocation.fromNode(node);
|
|
140
|
+
if (loc) {
|
|
141
141
|
// In case of a function call we only need to include the name, not the '()'
|
|
142
|
-
|
|
142
|
+
loc[3] = loc[1] + node.lexeme.length - 1;
|
|
143
143
|
result.push({
|
|
144
144
|
type: 'replace',
|
|
145
145
|
replacement: replacement,
|
|
146
146
|
description: `Rename to match naming convention ${conv}`,
|
|
147
|
-
|
|
147
|
+
loc: loc
|
|
148
148
|
});
|
|
149
149
|
}
|
|
150
150
|
}
|
|
151
151
|
return result.length === 0 ?
|
|
152
152
|
undefined : // We sort so that when applied in order the fixes will start from the end of the line to avoid conflicts
|
|
153
|
-
result.sort((a, b) =>
|
|
153
|
+
result.sort((a, b) => range_1.SourceLocation.compare(b.loc, a.loc));
|
|
154
154
|
}
|
|
155
155
|
exports.NAMING_CONVENTION = {
|
|
156
156
|
createSearch: (_config) => flowr_search_builder_1.Q.all().filter(vertex_1.VertexType.VariableDefinition),
|
|
@@ -160,9 +160,9 @@ exports.NAMING_CONVENTION = {
|
|
|
160
160
|
certainty: linter_format_1.LintingResultCertainty.Certain,
|
|
161
161
|
detectedCasing: detectCasing(m.node.lexeme, config.ignorePrefix),
|
|
162
162
|
name: m.node.lexeme,
|
|
163
|
-
|
|
163
|
+
loc: range_1.SourceLocation.fromNode(m.node),
|
|
164
164
|
id: m.node.info.id
|
|
165
|
-
}));
|
|
165
|
+
})).filter(e => (0, assert_1.isNotUndefined)(e.loc));
|
|
166
166
|
const casing = config.caseing === 'auto' ? getMostUsedCasing(symbols) : config.caseing;
|
|
167
167
|
const results = symbols
|
|
168
168
|
.filter(m => (m.detectedCasing !== casing) && (!config.ignoreNonAlpha || containsAlpha(m.name)))
|
|
@@ -183,8 +183,8 @@ exports.NAMING_CONVENTION = {
|
|
|
183
183
|
};
|
|
184
184
|
},
|
|
185
185
|
prettyPrint: {
|
|
186
|
-
[linter_format_1.LintingPrettyPrintContext.Query]: result => `Identifier '${result.name}' at ${
|
|
187
|
-
[linter_format_1.LintingPrettyPrintContext.Full]: result => `Identifier '${result.name}' at ${
|
|
186
|
+
[linter_format_1.LintingPrettyPrintContext.Query]: result => `Identifier '${result.name}' at ${range_1.SourceLocation.format(result.loc)} (${result.detectedCasing})`,
|
|
187
|
+
[linter_format_1.LintingPrettyPrintContext.Full]: result => `Identifier '${result.name}' at ${range_1.SourceLocation.format(result.loc)} follows wrong convention: ${result.detectedCasing}`
|
|
188
188
|
},
|
|
189
189
|
info: {
|
|
190
190
|
name: 'Naming Convention',
|