@abaplint/cli 2.115.2 → 2.115.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/build/cli.js +116 -22
- package/package.json +2 -2
package/build/cli.js
CHANGED
|
@@ -11974,7 +11974,7 @@ const combi_1 = __webpack_require__(/*! ../combi */ "./node_modules/@abaplint/co
|
|
|
11974
11974
|
const expressions_1 = __webpack_require__(/*! ../expressions */ "./node_modules/@abaplint/core/build/src/abap/2_statements/expressions/index.js");
|
|
11975
11975
|
class DataBegin {
|
|
11976
11976
|
getMatcher() {
|
|
11977
|
-
const occurs = (0, combi_1.seq)("OCCURS", expressions_1.Integer);
|
|
11977
|
+
const occurs = (0, combi_1.seq)("OCCURS", (0, combi_1.altPrio)(expressions_1.Integer, expressions_1.FieldChain));
|
|
11978
11978
|
const common = (0, combi_1.seq)("COMMON PART", (0, combi_1.optPrio)(expressions_1.DefinitionName));
|
|
11979
11979
|
const structure = (0, combi_1.seq)("BEGIN OF", (0, combi_1.altPrio)(common, (0, combi_1.seq)(expressions_1.DefinitionName, (0, combi_1.optPrio)("READ-ONLY"), (0, combi_1.optPrio)(occurs))));
|
|
11980
11980
|
return (0, combi_1.seq)("DATA", structure);
|
|
@@ -18678,7 +18678,8 @@ class Write {
|
|
|
18678
18678
|
const as = (0, combi_1.seq)("AS", (0, combi_1.altPrio)("LINE", "ICON", "CHECKBOX", "SYMBOL"));
|
|
18679
18679
|
const to = (0, combi_1.seq)("TO", expressions_1.Target);
|
|
18680
18680
|
const options = (0, combi_1.per)(mask, to, (0, combi_1.seq)("EXPONENT", expressions_1.Source), "NO-GROUPING", "NO-ZERO", "CENTERED", (0, combi_1.seq)("INPUT", (0, combi_1.opt)(onOff)), "NO-GAP", "LEFT-JUSTIFIED", as, (0, combi_1.seq)("FRAMES", onOff), (0, combi_1.seq)("HOTSPOT", (0, combi_1.opt)(onOff)), "RIGHT-JUSTIFIED", (0, combi_1.seq)("TIME ZONE", expressions_1.Source), (0, combi_1.seq)("UNDER", expressions_1.Source), (0, combi_1.seq)("STYLE", expressions_1.Source), (0, combi_1.seq)("ROUND", expressions_1.Source), (0, combi_1.seq)("QUICKINFO", expressions_1.Source), "ENVIRONMENT TIME FORMAT", dateFormat, (0, combi_1.seq)("UNIT", expressions_1.Source), (0, combi_1.seq)("INTENSIFIED", (0, combi_1.opt)(onOff)), (0, combi_1.seq)("INDEX", expressions_1.Source), (0, combi_1.seq)("DECIMALS", expressions_1.Source), (0, combi_1.seq)("INVERSE", (0, combi_1.opt)(onOff)), expressions_1.Color, (0, combi_1.seq)("CURRENCY", expressions_1.Source), "RESET", "NO-SIGN");
|
|
18681
|
-
|
|
18681
|
+
// Need to refactor all this sometime,
|
|
18682
|
+
const ret = (0, combi_1.seq)("WRITE", (0, combi_1.alt)((0, combi_1.seq)("AT /", (0, combi_1.opt)(expressions_1.Source), (0, combi_1.opt)("NO-GAP")), (0, combi_1.seq)((0, combi_1.opt)(expressions_1.WriteOffsetLength), (0, combi_1.alt)(expressions_1.Source, expressions_1.Dynamic, "/"), (0, combi_1.opt)(options))));
|
|
18682
18683
|
return (0, combi_1.verNot)(version_1.Version.Cloud, ret);
|
|
18683
18684
|
}
|
|
18684
18685
|
}
|
|
@@ -32881,13 +32882,18 @@ class InsertInternal {
|
|
|
32881
32882
|
}
|
|
32882
32883
|
}
|
|
32883
32884
|
if (node.findDirectTokenByText("INITIAL") === undefined) {
|
|
32884
|
-
|
|
32885
|
-
|
|
32886
|
-
|
|
32887
|
-
|
|
32885
|
+
let error = false;
|
|
32886
|
+
if (sourceType instanceof basic_1.IntegerType && targetType instanceof basic_1.Integer8Type) {
|
|
32887
|
+
error = true;
|
|
32888
|
+
}
|
|
32889
|
+
else if (new _type_utils_1.TypeUtils(input.scope).isAssignable(sourceType, targetType) === false) {
|
|
32890
|
+
error = true;
|
|
32888
32891
|
}
|
|
32889
32892
|
else if (sourceType instanceof basic_1.CharacterType && targetType instanceof basic_1.StringType) {
|
|
32890
32893
|
// yea, well, INSERT doesnt convert the values automatically, like everything else?
|
|
32894
|
+
error = true;
|
|
32895
|
+
}
|
|
32896
|
+
if (error === true) {
|
|
32891
32897
|
const message = "Types not compatible";
|
|
32892
32898
|
input.issues.push((0, _syntax_input_1.syntaxIssue)(input, node.getFirstToken(), message));
|
|
32893
32899
|
return;
|
|
@@ -42628,8 +42634,22 @@ class DDIC {
|
|
|
42628
42634
|
case "XSTRING":
|
|
42629
42635
|
return Types.XStringType.get({ qualifiedName: qualifiedName || name });
|
|
42630
42636
|
case "D":
|
|
42637
|
+
/*
|
|
42638
|
+
if (length && length > 0) {
|
|
42639
|
+
throw new Error("Length for type D not possible");
|
|
42640
|
+
} else if (decimals && decimals > 0) {
|
|
42641
|
+
throw new Error("Decimals for type D not possible");
|
|
42642
|
+
}
|
|
42643
|
+
*/
|
|
42631
42644
|
return new Types.DateType({ qualifiedName: qualifiedName || name });
|
|
42632
42645
|
case "T":
|
|
42646
|
+
/*
|
|
42647
|
+
if (length && length > 0) {
|
|
42648
|
+
throw new Error("Length for type T not possible");
|
|
42649
|
+
} else if (decimals && decimals > 0) {
|
|
42650
|
+
throw new Error("Decimals for type T not possible");
|
|
42651
|
+
}
|
|
42652
|
+
*/
|
|
42633
42653
|
return new Types.TimeType({ qualifiedName: qualifiedName || name });
|
|
42634
42654
|
case "XSEQUENCE":
|
|
42635
42655
|
return new Types.XSequenceType({ qualifiedName: qualifiedName });
|
|
@@ -42662,6 +42682,13 @@ class DDIC {
|
|
|
42662
42682
|
case "INT8": // todo, take version into account
|
|
42663
42683
|
return new Types.Integer8Type({ qualifiedName: qualifiedName || name });
|
|
42664
42684
|
case "F":
|
|
42685
|
+
/*
|
|
42686
|
+
if (length && length > 0) {
|
|
42687
|
+
throw new Error("Length for type F not possible");
|
|
42688
|
+
} else if (decimals && decimals > 0) {
|
|
42689
|
+
throw new Error("Decimals for type F not possible");
|
|
42690
|
+
}
|
|
42691
|
+
*/
|
|
42665
42692
|
return new Types.FloatType({ qualifiedName: qualifiedName || name });
|
|
42666
42693
|
case "P":
|
|
42667
42694
|
if (length && decimals) {
|
|
@@ -52499,15 +52526,39 @@ class RenameICFService {
|
|
|
52499
52526
|
this.reg = reg;
|
|
52500
52527
|
}
|
|
52501
52528
|
buildEdits(obj, oldName, newName) {
|
|
52529
|
+
var _a, _b, _c, _d;
|
|
52502
52530
|
if (!(obj instanceof __1.ICFService)) {
|
|
52503
52531
|
throw new Error("RenameICFService, not a ICF Service");
|
|
52504
52532
|
}
|
|
52533
|
+
// Preserve GUID suffix from the stored object/file name for the filename rename
|
|
52534
|
+
// SICF files follow pattern: servicename.sicf or servicename {GUID}.sicf
|
|
52535
|
+
const fileNewName = (() => {
|
|
52536
|
+
// Look for pattern: space + GUID (32 hex chars in braces) + optional extension
|
|
52537
|
+
const guidPattern = / \{[0-9A-Fa-f]{16,32}\}/;
|
|
52538
|
+
const match = oldName.match(guidPattern);
|
|
52539
|
+
if (match) {
|
|
52540
|
+
// Extract everything from the GUID onwards (includes .sicf extension if present)
|
|
52541
|
+
const guidIndex = match.index;
|
|
52542
|
+
const suffix = oldName.substring(guidIndex);
|
|
52543
|
+
// Only append suffix if newName doesn't already contain it
|
|
52544
|
+
return newName.includes(suffix) ? newName : newName + suffix;
|
|
52545
|
+
}
|
|
52546
|
+
// Fallback: preserve any suffix after first space (legacy behavior)
|
|
52547
|
+
const space = oldName.indexOf(" ");
|
|
52548
|
+
if (space > -1) {
|
|
52549
|
+
const suffix = oldName.substring(space);
|
|
52550
|
+
return newName.includes(suffix) ? newName : newName + suffix;
|
|
52551
|
+
}
|
|
52552
|
+
return newName;
|
|
52553
|
+
})();
|
|
52554
|
+
const cleanOldName = (_b = (_a = oldName.match(/^[^ ]+/)) === null || _a === void 0 ? void 0 : _a[0]) !== null && _b !== void 0 ? _b : oldName;
|
|
52555
|
+
const cleanNewName = (_d = (_c = newName.match(/^[^ ]+/)) === null || _c === void 0 ? void 0 : _c[0]) !== null && _d !== void 0 ? _d : newName;
|
|
52505
52556
|
let changes = [];
|
|
52506
52557
|
const helper = new renamer_helper_1.RenamerHelper(this.reg);
|
|
52507
|
-
changes = changes.concat(helper.
|
|
52508
|
-
changes = changes.concat(helper.buildXMLFileEdits(obj, "ICF_NAME",
|
|
52509
|
-
changes = changes.concat(helper.buildXMLFileEdits(obj, "ORIG_NAME",
|
|
52510
|
-
changes = changes.concat(helper.renameFiles(obj, oldName,
|
|
52558
|
+
changes = changes.concat(helper.buildURLFileEdits(obj, cleanOldName, cleanNewName));
|
|
52559
|
+
changes = changes.concat(helper.buildXMLFileEdits(obj, "ICF_NAME", cleanOldName, cleanNewName));
|
|
52560
|
+
changes = changes.concat(helper.buildXMLFileEdits(obj, "ORIG_NAME", cleanOldName, cleanNewName, true));
|
|
52561
|
+
changes = changes.concat(helper.renameFiles(obj, oldName, fileNewName));
|
|
52511
52562
|
return {
|
|
52512
52563
|
documentChanges: changes,
|
|
52513
52564
|
};
|
|
@@ -52684,7 +52735,10 @@ class Renamer {
|
|
|
52684
52735
|
/** Builds edits, but does not apply to registry, used by LSP */
|
|
52685
52736
|
buildEdits(type, oldName, newName) {
|
|
52686
52737
|
this.reg.parse(); // the registry must be parsed to dermine references
|
|
52687
|
-
|
|
52738
|
+
let obj = this.reg.getObject(type, oldName);
|
|
52739
|
+
if (obj === undefined && type === "SICF") {
|
|
52740
|
+
obj = Array.from(this.reg.getObjects()).find(o => o.getType() === "SICF" && o.getName().toUpperCase().startsWith(oldName.toUpperCase() + " "));
|
|
52741
|
+
}
|
|
52688
52742
|
if (obj === undefined) {
|
|
52689
52743
|
throw new Error("rename, object not found");
|
|
52690
52744
|
}
|
|
@@ -52913,6 +52967,34 @@ class RenamerHelper {
|
|
|
52913
52967
|
}
|
|
52914
52968
|
return changes;
|
|
52915
52969
|
}
|
|
52970
|
+
buildURLFileEdits(object, oldName, newName) {
|
|
52971
|
+
const changes = [];
|
|
52972
|
+
const xml = object.getXMLFile();
|
|
52973
|
+
if (xml === undefined) {
|
|
52974
|
+
return [];
|
|
52975
|
+
}
|
|
52976
|
+
const oldNameLower = oldName.toLowerCase();
|
|
52977
|
+
const newNameLower = newName.toLowerCase();
|
|
52978
|
+
const rows = xml.getRawRows();
|
|
52979
|
+
for (let i = 0; i < rows.length; i++) {
|
|
52980
|
+
const row = rows[i];
|
|
52981
|
+
const urlTagStart = row.indexOf("<URL>");
|
|
52982
|
+
if (urlTagStart === -1) {
|
|
52983
|
+
continue;
|
|
52984
|
+
}
|
|
52985
|
+
const urlTagEnd = row.indexOf("</URL>");
|
|
52986
|
+
if (urlTagEnd === -1) {
|
|
52987
|
+
continue;
|
|
52988
|
+
}
|
|
52989
|
+
const urlContent = row.substring(urlTagStart + 5, urlTagEnd);
|
|
52990
|
+
const updatedUrl = urlContent.replace(oldNameLower, newNameLower);
|
|
52991
|
+
if (updatedUrl !== urlContent) {
|
|
52992
|
+
const range = vscode_languageserver_types_1.Range.create(i, urlTagStart + 5, i, urlTagEnd);
|
|
52993
|
+
changes.push(vscode_languageserver_types_1.TextDocumentEdit.create({ uri: xml.getFilename(), version: 1 }, [vscode_languageserver_types_1.TextEdit.replace(range, updatedUrl)]));
|
|
52994
|
+
}
|
|
52995
|
+
}
|
|
52996
|
+
return changes;
|
|
52997
|
+
}
|
|
52916
52998
|
renameFiles(obj, oldName, name) {
|
|
52917
52999
|
const list = [];
|
|
52918
53000
|
const newName = name.toLowerCase().replace(/\//g, "#");
|
|
@@ -55155,7 +55237,7 @@ class Registry {
|
|
|
55155
55237
|
}
|
|
55156
55238
|
static abaplintVersion() {
|
|
55157
55239
|
// magic, see build script "version.sh"
|
|
55158
|
-
return "2.115.
|
|
55240
|
+
return "2.115.4";
|
|
55159
55241
|
}
|
|
55160
55242
|
getDDICReferences() {
|
|
55161
55243
|
return this.ddicReferences;
|
|
@@ -68388,7 +68470,7 @@ ENDIF.
|
|
|
68388
68470
|
return [];
|
|
68389
68471
|
}
|
|
68390
68472
|
for (const cond of structure.findAllExpressionsMulti([Expressions.Cond, Expressions.ComponentCond])) {
|
|
68391
|
-
issues.push(...this.
|
|
68473
|
+
issues.push(...this.analyzeCondition(file, cond));
|
|
68392
68474
|
}
|
|
68393
68475
|
for (const sub of structure.findAllExpressionsMulti([Expressions.CondSub, Expressions.ComponentCondSub])) {
|
|
68394
68476
|
let cond = [];
|
|
@@ -68442,18 +68524,20 @@ ENDIF.
|
|
|
68442
68524
|
}
|
|
68443
68525
|
analyzeMove(file, m) {
|
|
68444
68526
|
const issues = [];
|
|
68445
|
-
const
|
|
68446
|
-
|
|
68447
|
-
|
|
68448
|
-
|
|
68449
|
-
|
|
68450
|
-
|
|
68451
|
-
|
|
68452
|
-
|
|
68527
|
+
for (const source of m.findAllExpressionsRecursive(Expressions.Source)) {
|
|
68528
|
+
const lastChildren = source.getChildren();
|
|
68529
|
+
if (lastChildren.length === 3
|
|
68530
|
+
&& lastChildren[0].getFirstToken().getStr() === "("
|
|
68531
|
+
&& lastChildren[1].getChildren().length === 1
|
|
68532
|
+
&& lastChildren[1].getFirstToken().getStr().startsWith("-") === false
|
|
68533
|
+
&& lastChildren[2].getFirstToken().getStr() === ")") {
|
|
68534
|
+
const issue = issue_1.Issue.atToken(file, lastChildren[0].getFirstToken(), "Too many parentheses", this.getMetadata().key, this.conf.severity);
|
|
68535
|
+
issues.push(issue);
|
|
68536
|
+
}
|
|
68453
68537
|
}
|
|
68454
68538
|
return issues;
|
|
68455
68539
|
}
|
|
68456
|
-
|
|
68540
|
+
analyzeCondition(file, cond) {
|
|
68457
68541
|
var _a, _b;
|
|
68458
68542
|
const issues = [];
|
|
68459
68543
|
let comparator = "";
|
|
@@ -70910,6 +70994,8 @@ class ObsoleteStatementConf extends _basic_rule_config_1.BasicRuleConfig {
|
|
|
70910
70994
|
this.fieldGroups = true;
|
|
70911
70995
|
/** Check for REPLACE INTO */
|
|
70912
70996
|
this.replaceInto = true;
|
|
70997
|
+
this.loopExtract = true;
|
|
70998
|
+
this.sortExtract = true;
|
|
70913
70999
|
}
|
|
70914
71000
|
}
|
|
70915
71001
|
exports.ObsoleteStatementConf = ObsoleteStatementConf;
|
|
@@ -71163,6 +71249,14 @@ ENDIF.`,
|
|
|
71163
71249
|
issues.push(issue);
|
|
71164
71250
|
}
|
|
71165
71251
|
}
|
|
71252
|
+
if (this.conf.loopExtract && sta instanceof Statements.LoopExtract) {
|
|
71253
|
+
const issue = issue_1.Issue.atStatement(file, staNode, "LOOP extract", this.getMetadata().key, this.conf.severity);
|
|
71254
|
+
issues.push(issue);
|
|
71255
|
+
}
|
|
71256
|
+
if (this.conf.sortExtract && sta instanceof Statements.SortDataset && staNode.getChildren().length === 2) {
|
|
71257
|
+
const issue = issue_1.Issue.atStatement(file, staNode, "SORT extract", this.getMetadata().key, this.conf.severity);
|
|
71258
|
+
issues.push(issue);
|
|
71259
|
+
}
|
|
71166
71260
|
if (configVersion >= version_1.Version.v754 && this.conf.clientSpecified
|
|
71167
71261
|
&& (sta instanceof Statements.Select
|
|
71168
71262
|
|| sta instanceof Statements.SelectLoop
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@abaplint/cli",
|
|
3
|
-
"version": "2.115.
|
|
3
|
+
"version": "2.115.4",
|
|
4
4
|
"description": "abaplint - Command Line Interface",
|
|
5
5
|
"funding": "https://github.com/sponsors/larshp",
|
|
6
6
|
"bin": {
|
|
@@ -38,7 +38,7 @@
|
|
|
38
38
|
},
|
|
39
39
|
"homepage": "https://abaplint.org",
|
|
40
40
|
"devDependencies": {
|
|
41
|
-
"@abaplint/core": "^2.115.
|
|
41
|
+
"@abaplint/core": "^2.115.4",
|
|
42
42
|
"@types/chai": "^4.3.20",
|
|
43
43
|
"@types/minimist": "^1.2.5",
|
|
44
44
|
"@types/mocha": "^10.0.10",
|