UNPKG

@abaplint/core

Version:
134 lines (133 loc) 5.88 kB
"use strict"; 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