@abaplint/core
Version:
abaplint - Core API
134 lines (133 loc) • 5.88 kB
JavaScript
;
Object.defineProperty(exports, "__esModule", { value: true });
exports.SelectSingleFullKey = exports.SelectSingleFullKeyConf = void 0;
const _abap_object_1 = require("../objects/_abap_object");
const _basic_rule_config_1 = require("./_basic_rule_config");
const edit_helper_1 = require("../edit_helper");
const _irule_1 = require("./_irule");
const issue_1 = require("../issue");
const syntax_1 = require("../abap/5_syntax/syntax");
const Expressions = require("../abap/2_statements/expressions");
const Statements = require("../abap/2_statements/statements");
const _statement_1 = require("../abap/2_statements/statements/_statement");
class SelectSingleFullKeyConf extends _basic_rule_config_1.BasicRuleConfig {
constructor() {
super(...arguments);
this.allowPseudo = true;
}
}
exports.SelectSingleFullKeyConf = SelectSingleFullKeyConf;
class SelectSingleFullKey {
constructor() {
this.conf = new SelectSingleFullKeyConf();
}
getMetadata() {
return {
key: "select_single_full_key",
title: "Detect SELECT SINGLE which are possibily not unique",
shortDescription: `Detect SELECT SINGLE which are possibily not unique`,
extendedInformation: `Table definitions must be known, ie. inside the errorNamespace
If the statement contains a JOIN it is not checked`,
pseudoComment: "EC CI_NOORDER",
tags: [_irule_1.RuleTag.Quickfix],
};
}
initialize(reg) {
this.reg = reg;
return this;
}
getConfig() {
if (this.conf === undefined) {
this.conf = {
allowPseudo: true,
};
}
if (this.conf.allowPseudo === undefined) {
this.conf.allowPseudo = true;
}
return this.conf;
}
setConfig(conf) {
this.conf = conf;
}
buildFix(file, statement) {
return {
description: `Add "#EC CI_NOORDER`,
edit: edit_helper_1.EditHelper.insertAt(file, statement.getLastToken().getStart(), ` "#EC CI_NOORDER`),
};
}
run(obj) {
var _a, _b;
if (!(obj instanceof _abap_object_1.ABAPObject)) {
return [];
}
const syntax = new syntax_1.SyntaxLogic(this.reg, obj).run();
if (syntax.issues.length > 0) {
return [];
}
const issues = [];
const message = "SELECT SINGLE possibily not unique";
for (const file of obj.getABAPFiles()) {
const statements = file.getStatements();
for (let i = 0; i < statements.length; i++) {
const s = statements[i];
if (!(s.get() instanceof Statements.Select)) {
continue;
}
else if (s.findFirstExpression(Expressions.SQLJoin)) {
continue;
}
else if (s.findTokenSequencePosition("SELECT", "SINGLE") === undefined) {
continue;
}
const databaseTable = s.findFirstExpression(Expressions.DatabaseTable);
if (databaseTable === undefined) {
continue;
}
const next = statements[i + 1];
if ((next === null || next === void 0 ? void 0 : next.get()) instanceof _statement_1.Comment
&& next.concatTokens().includes(this.getMetadata().pseudoComment + "")) {
if (this.getConfig().allowPseudo !== true) {
issues.push(issue_1.Issue.atStatement(file, s, "Pseudo comment not allowed", this.getMetadata().key, this.getConfig().severity));
}
continue;
}
const tabl = this.findReference(databaseTable.getFirstToken().getStart(), syntax.spaghetti, file);
const table = this.reg.getObject("TABL", tabl);
if (table === undefined) {
continue;
}
const keys = table.listKeys(this.reg);
const cond = s.findFirstExpression(Expressions.SQLCond);
const set = new Set();
for (const key of keys) {
if (key === "MANDT") {
// todo, it should check for the correct type instead
continue;
}
set.add(key);
}
for (const compare of (cond === null || cond === void 0 ? void 0 : cond.findAllExpressionsRecursive(Expressions.SQLCompare)) || []) {
if (compare.getChildren().length === 3) {
const fname = (_a = compare.findDirectExpression(Expressions.SQLFieldName)) === null || _a === void 0 ? void 0 : _a.concatTokens().toUpperCase();
const operator = (_b = compare.findDirectExpression(Expressions.SQLCompareOperator)) === null || _b === void 0 ? void 0 : _b.concatTokens().toUpperCase();
if (fname && (operator === "=" || operator === "EQ")) {
set.delete(fname);
}
}
}
if (set.size > 0) {
const fix = this.buildFix(file, s);
issues.push(issue_1.Issue.atStatement(file, s, message, this.getMetadata().key, this.getConfig().severity, undefined, [fix]));
}
}
}
return issues;
}
findReference(position, spaghetti, file) {
const scope = spaghetti.lookupPosition(position, file.getFilename());
return scope === null || scope === void 0 ? void 0 : scope.findTableReference(position);
}
}
exports.SelectSingleFullKey = SelectSingleFullKey;
//# sourceMappingURL=select_single_full_key.js.map