@ui5/builder 3.1.1 → 3.3.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/.reuse/dep5 +2 -2
- package/CHANGELOG.md +22 -2
- package/LICENSE.txt +1 -1
- package/lib/lbt/bundle/AutoSplitter.js +53 -0
- package/lib/lbt/bundle/Builder.js +63 -0
- package/lib/lbt/bundle/BundleDefinition.js +8 -1
- package/lib/lbt/bundle/ResolvedBundleDefinition.js +5 -1
- package/lib/lbt/bundle/Resolver.js +2 -2
- package/lib/lbt/resources/ResourceFilterList.js +1 -1
- package/lib/processors/bundlers/flexChangesBundler.js +27 -3
- package/lib/processors/jsdoc/lib/createIndexFiles.cjs +19 -7
- package/lib/processors/jsdoc/lib/transformApiJson.cjs +6 -3
- package/lib/processors/jsdoc/lib/ui5/plugin.cjs +5 -5
- package/lib/processors/jsdoc/lib/ui5/template/publish.cjs +15 -5
- package/lib/processors/manifestCreator.js +8 -2
- package/lib/tasks/bundlers/generateFlexChangesBundle.js +7 -1
- package/package.json +9 -9
package/.reuse/dep5
CHANGED
|
@@ -25,9 +25,9 @@ Disclaimer: The code in this project may include calls to APIs (“API Calls”)
|
|
|
25
25
|
parties the right to use of access any SAP External Product, through API Calls.
|
|
26
26
|
|
|
27
27
|
Files: *
|
|
28
|
-
Copyright: 2018-
|
|
28
|
+
Copyright: 2018-2024 SAP SE or an SAP affiliate company and UI5 Tooling contributors
|
|
29
29
|
License: Apache-2.0
|
|
30
30
|
|
|
31
31
|
Files: lib/processors/jsdoc/lib/*
|
|
32
|
-
Copyright: 2009-
|
|
32
|
+
Copyright: 2009-2024 SAP SE or an SAP affiliate company and OpenUI5 contributors
|
|
33
33
|
License: Apache-2.0
|
package/CHANGELOG.md
CHANGED
|
@@ -2,10 +2,28 @@
|
|
|
2
2
|
All notable changes to this project will be documented in this file.
|
|
3
3
|
This project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0.html).
|
|
4
4
|
|
|
5
|
-
A list of unreleased changes can be found [here](https://github.com/SAP/ui5-builder/compare/v3.
|
|
5
|
+
A list of unreleased changes can be found [here](https://github.com/SAP/ui5-builder/compare/v3.3.0...HEAD).
|
|
6
|
+
|
|
7
|
+
<a name="v3.3.0"></a>
|
|
8
|
+
## [v3.3.0] - 2024-01-18
|
|
9
|
+
### Features
|
|
10
|
+
- **flexChangesBundler:** Merge existing with new flexibility-bundle.json [`fd070ab`](https://github.com/SAP/ui5-builder/commit/fd070abaa22680ee70b448fa0ac406a8f2b57cc5)
|
|
11
|
+
|
|
12
|
+
|
|
13
|
+
<a name="v3.2.0"></a>
|
|
14
|
+
## [v3.2.0] - 2023-12-12
|
|
15
|
+
### Bug Fixes
|
|
16
|
+
- Incomplete multi-character sanitization ([#959](https://github.com/SAP/ui5-builder/issues/959)) [`d61f1b7`](https://github.com/SAP/ui5-builder/commit/d61f1b744495f5428db33467218077e7996f1575)
|
|
17
|
+
- Add guard against prototype pollution ([#960](https://github.com/SAP/ui5-builder/issues/960)) [`ba230d9`](https://github.com/SAP/ui5-builder/commit/ba230d922cac0acd291dfe18b0ae7a95eae8b190)
|
|
18
|
+
- Incomplete string escaping or encoding ([#958](https://github.com/SAP/ui5-builder/issues/958)) [`50bb0d9`](https://github.com/SAP/ui5-builder/commit/50bb0d97e76fb312412cf29fae18b76cc88df6f4)
|
|
19
|
+
- **manifestCreator:** set fallbackLocale to empty string if no locale is present ([#962](https://github.com/SAP/ui5-builder/issues/962)) [`26526a0`](https://github.com/SAP/ui5-builder/commit/26526a08ff38ee11ed3bd506f7ef0610f1d1ccb0)
|
|
20
|
+
|
|
21
|
+
### Features
|
|
22
|
+
- depCache bundling mode ([#951](https://github.com/SAP/ui5-builder/issues/951)) [`f2cf564`](https://github.com/SAP/ui5-builder/commit/f2cf564f0f71d635e58a743c7bdef1f427e341b2)
|
|
23
|
+
|
|
6
24
|
|
|
7
25
|
<a name="v3.1.1"></a>
|
|
8
|
-
## [v3.1.1] - 2023-11-
|
|
26
|
+
## [v3.1.1] - 2023-11-20
|
|
9
27
|
### Bug Fixes
|
|
10
28
|
- Handle graceful termination of workerpool for parallel builds ([#953](https://github.com/SAP/ui5-builder/issues/953)) [`f7b9f27`](https://github.com/SAP/ui5-builder/commit/f7b9f27ac5966bd89e52e4c2d5b03482a0f3dbb7)
|
|
11
29
|
- **Bundling:** Detect manifest.json dependency of libraries [`6f9995f`](https://github.com/SAP/ui5-builder/commit/6f9995f5b47a6094fa93b5d433be849b1d3cdc7e)
|
|
@@ -839,6 +857,8 @@ to load the custom bundle file instead.
|
|
|
839
857
|
|
|
840
858
|
### Features
|
|
841
859
|
- Add ability to configure component preloads and custom bundles [`2241e5f`](https://github.com/SAP/ui5-builder/commit/2241e5ff98fd95f1f80cc74959655ae7a9c660e7)
|
|
860
|
+
[v3.3.0]: https://github.com/SAP/ui5-builder/compare/v3.2.0...v3.3.0
|
|
861
|
+
[v3.2.0]: https://github.com/SAP/ui5-builder/compare/v3.1.1...v3.2.0
|
|
842
862
|
[v3.1.1]: https://github.com/SAP/ui5-builder/compare/v3.1.0...v3.1.1
|
|
843
863
|
[v3.1.0]: https://github.com/SAP/ui5-builder/compare/v3.0.9...v3.1.0
|
|
844
864
|
[v3.0.9]: https://github.com/SAP/ui5-builder/compare/v3.0.8...v3.0.9
|
package/LICENSE.txt
CHANGED
|
@@ -186,7 +186,7 @@
|
|
|
186
186
|
same "printed page" as the copyright notice for easier
|
|
187
187
|
identification within third-party archives.
|
|
188
188
|
|
|
189
|
-
Copyright 2018-
|
|
189
|
+
Copyright 2018-2024 SAP SE or an SAP affiliate company and UI5 Tooling contributors
|
|
190
190
|
|
|
191
191
|
Licensed under the Apache License, Version 2.0 (the "License");
|
|
192
192
|
you may not use this file except in compliance with the License.
|
|
@@ -41,6 +41,8 @@ class AutoSplitter {
|
|
|
41
41
|
const numberOfParts = options.numberOfParts;
|
|
42
42
|
let totalSize = 0;
|
|
43
43
|
const moduleSizes = Object.create(null);
|
|
44
|
+
const depCacheSizes = [];
|
|
45
|
+
let depCacheLoaderSize = 0;
|
|
44
46
|
this.optimize = !!options.optimize;
|
|
45
47
|
|
|
46
48
|
// ---- resolve module definition
|
|
@@ -74,6 +76,27 @@ class AutoSplitter {
|
|
|
74
76
|
totalSize += "sap.ui.requireSync('');".length + toRequireJSName(module).length;
|
|
75
77
|
});
|
|
76
78
|
break;
|
|
79
|
+
case SectionType.DepCache:
|
|
80
|
+
depCacheLoaderSize = "sap.ui.loader.config({depCacheUI5:{}});".length;
|
|
81
|
+
totalSize += depCacheLoaderSize;
|
|
82
|
+
|
|
83
|
+
section.modules.forEach( (module) => {
|
|
84
|
+
promises.push((async () => {
|
|
85
|
+
const resource = await this.pool.findResourceWithInfo(module);
|
|
86
|
+
const deps = resource.info.dependencies.filter(
|
|
87
|
+
(dep) =>
|
|
88
|
+
!resource.info.isConditionalDependency(dep) &&
|
|
89
|
+
!resource.info.isImplicitDependency(dep)
|
|
90
|
+
);
|
|
91
|
+
if (deps.length > 0) {
|
|
92
|
+
const depSize = `"${module}": [${deps.map((dep) => `"${dep}"`).join(",")}],`.length;
|
|
93
|
+
totalSize += depSize;
|
|
94
|
+
|
|
95
|
+
depCacheSizes.push({size: depSize, module});
|
|
96
|
+
}
|
|
97
|
+
})());
|
|
98
|
+
});
|
|
99
|
+
break;
|
|
77
100
|
default:
|
|
78
101
|
break;
|
|
79
102
|
}
|
|
@@ -180,6 +203,36 @@ class AutoSplitter {
|
|
|
180
203
|
totalSize += 21 + toRequireJSName(module).length;
|
|
181
204
|
});
|
|
182
205
|
break;
|
|
206
|
+
case SectionType.DepCache:
|
|
207
|
+
currentSection = {
|
|
208
|
+
mode: SectionType.DepCache,
|
|
209
|
+
filters: []
|
|
210
|
+
};
|
|
211
|
+
currentModule.sections.push( currentSection );
|
|
212
|
+
totalSize += depCacheLoaderSize;
|
|
213
|
+
|
|
214
|
+
depCacheSizes.forEach((depCache) => {
|
|
215
|
+
if ( part + 1 < numberOfParts && totalSize + depCache.size / 2 > partSize ) {
|
|
216
|
+
part++;
|
|
217
|
+
// start a new module
|
|
218
|
+
totalSize = depCacheLoaderSize;
|
|
219
|
+
currentSection = {
|
|
220
|
+
mode: SectionType.DepCache,
|
|
221
|
+
filters: []
|
|
222
|
+
};
|
|
223
|
+
currentModule = {
|
|
224
|
+
name: moduleNameWithPart.replace(/__part__/, part),
|
|
225
|
+
sections: [currentSection]
|
|
226
|
+
};
|
|
227
|
+
splittedModules.push(currentModule);
|
|
228
|
+
}
|
|
229
|
+
|
|
230
|
+
if (!currentSection.filters.includes(depCache.module)) {
|
|
231
|
+
currentSection.filters.push(depCache.module);
|
|
232
|
+
totalSize += depCache.size;
|
|
233
|
+
}
|
|
234
|
+
});
|
|
235
|
+
break;
|
|
183
236
|
default:
|
|
184
237
|
break;
|
|
185
238
|
}
|
|
@@ -71,6 +71,14 @@ const EVOBundleFormat = {
|
|
|
71
71
|
resolvedModule.executes(MODULE__UI5LOADER_AUTOCONFIG) ||
|
|
72
72
|
resolvedModule.executes(MODULE__JQUERY_SAP_GLOBAL) ||
|
|
73
73
|
resolvedModule.executes(MODULE__SAP_UI_CORE_CORE);
|
|
74
|
+
},
|
|
75
|
+
|
|
76
|
+
beforeDepCache(outW) {
|
|
77
|
+
outW.writeln(`sap.ui.loader.config({depCacheUI5:{`);
|
|
78
|
+
},
|
|
79
|
+
|
|
80
|
+
afterDepCache(outW) {
|
|
81
|
+
outW.writeln(`}});`);
|
|
74
82
|
}
|
|
75
83
|
};
|
|
76
84
|
|
|
@@ -220,6 +228,8 @@ class BundleBuilder {
|
|
|
220
228
|
return this.writeBundleInfos([section]);
|
|
221
229
|
case SectionType.Require:
|
|
222
230
|
return this.writeRequires(section);
|
|
231
|
+
case SectionType.DepCache:
|
|
232
|
+
return this.writeDepCache(section);
|
|
223
233
|
default:
|
|
224
234
|
throw new Error("unknown section mode " + section.mode);
|
|
225
235
|
}
|
|
@@ -549,6 +559,59 @@ class BundleBuilder {
|
|
|
549
559
|
});
|
|
550
560
|
}
|
|
551
561
|
|
|
562
|
+
// When AutoSplit is enabled for depCache, we need to ensure that modules
|
|
563
|
+
// are not duplicated across files. This might happen due to the filters provided.
|
|
564
|
+
// So, certain modules that are included in depCache could be dependencies of another
|
|
565
|
+
// module in the next file. This will also duplicate its dependency definition if we do not filter.
|
|
566
|
+
#depCacheSet = new Set();
|
|
567
|
+
async writeDepCache(section) {
|
|
568
|
+
const outW = this.outW;
|
|
569
|
+
let hasDepCache = false;
|
|
570
|
+
|
|
571
|
+
const sequence = section.modules.slice().sort();
|
|
572
|
+
|
|
573
|
+
if (sequence.length > 0) {
|
|
574
|
+
for (const module of sequence) {
|
|
575
|
+
if (this.#depCacheSet.has(module)) {
|
|
576
|
+
continue;
|
|
577
|
+
}
|
|
578
|
+
|
|
579
|
+
this.#depCacheSet.add(module);
|
|
580
|
+
let resource = null;
|
|
581
|
+
try {
|
|
582
|
+
resource = await this.pool.findResourceWithInfo(module);
|
|
583
|
+
} catch (e) {
|
|
584
|
+
log.error(` couldn't find ${module}`);
|
|
585
|
+
}
|
|
586
|
+
|
|
587
|
+
if (resource != null) {
|
|
588
|
+
const deps = resource.info.dependencies.filter(
|
|
589
|
+
(dep) =>
|
|
590
|
+
!resource.info.isConditionalDependency(dep) &&
|
|
591
|
+
!resource.info.isImplicitDependency(dep)
|
|
592
|
+
);
|
|
593
|
+
if (deps.length > 0) {
|
|
594
|
+
if (!hasDepCache) {
|
|
595
|
+
hasDepCache = true;
|
|
596
|
+
outW.ensureNewLine();
|
|
597
|
+
this.targetBundleFormat.beforeDepCache(outW, section);
|
|
598
|
+
}
|
|
599
|
+
|
|
600
|
+
outW.writeln(
|
|
601
|
+
`"${module}": [${deps.map((dep) => `"${dep}"`).join(",")}],`
|
|
602
|
+
);
|
|
603
|
+
} else {
|
|
604
|
+
log.verbose(` skipped ${module}, no dependencies`);
|
|
605
|
+
}
|
|
606
|
+
}
|
|
607
|
+
}
|
|
608
|
+
|
|
609
|
+
if (hasDepCache) {
|
|
610
|
+
this.targetBundleFormat.afterDepCache(outW, section);
|
|
611
|
+
}
|
|
612
|
+
}
|
|
613
|
+
}
|
|
614
|
+
|
|
552
615
|
async getSourceMapForModule({moduleName, moduleContent, resourcePath}) {
|
|
553
616
|
let moduleSourceMap = null;
|
|
554
617
|
let newModuleContent = moduleContent;
|
|
@@ -27,5 +27,12 @@ export const SectionType = {
|
|
|
27
27
|
* Usually used as the last section in a merged module to enforce loading and
|
|
28
28
|
* execution of some specific module or modules.
|
|
29
29
|
*/
|
|
30
|
-
Require: "require"
|
|
30
|
+
Require: "require",
|
|
31
|
+
|
|
32
|
+
/**
|
|
33
|
+
* Dependency cache information that lists modules and their dependencies
|
|
34
|
+
* of all types: JS, declarative views/fragments.
|
|
35
|
+
* Only the dependencies of the modules are stored as 'depCache' configuration.
|
|
36
|
+
*/
|
|
37
|
+
DepCache: "depCache"
|
|
31
38
|
};
|
|
@@ -64,7 +64,11 @@ class ResolvedBundleDefinition {
|
|
|
64
64
|
return Promise.all(
|
|
65
65
|
modules.map( (submodule) => {
|
|
66
66
|
return pool.getModuleInfo(submodule).then(
|
|
67
|
-
(subinfo) =>
|
|
67
|
+
(subinfo) => {
|
|
68
|
+
if (!bundleInfo.subModules.includes(subinfo.name)) {
|
|
69
|
+
bundleInfo.addSubModule(subinfo);
|
|
70
|
+
}
|
|
71
|
+
}
|
|
68
72
|
);
|
|
69
73
|
})
|
|
70
74
|
);
|
|
@@ -198,7 +198,7 @@ class BundleResolver {
|
|
|
198
198
|
let oldIgnoredResources;
|
|
199
199
|
let oldSelectedResourcesSequence;
|
|
200
200
|
|
|
201
|
-
if (
|
|
201
|
+
if ( [SectionType.Require, SectionType.DepCache].includes(section.mode) ) {
|
|
202
202
|
oldSelectedResources = selectedResources;
|
|
203
203
|
oldIgnoredResources = visitedResources;
|
|
204
204
|
oldSelectedResourcesSequence = selectedResourcesSequence;
|
|
@@ -254,7 +254,7 @@ class BundleResolver {
|
|
|
254
254
|
});
|
|
255
255
|
|
|
256
256
|
return Promise.all(promises).then( function() {
|
|
257
|
-
if (
|
|
257
|
+
if ( [SectionType.Require, SectionType.DepCache].includes(section.mode) ) {
|
|
258
258
|
newKeys = selectedResourcesSequence;
|
|
259
259
|
selectedResources = oldSelectedResources;
|
|
260
260
|
visitedResources = oldIgnoredResources;
|
|
@@ -20,9 +20,11 @@ import {createResource} from "@ui5/fs/resourceFactory";
|
|
|
20
20
|
* @param {string} parameters.options.pathPrefix Prefix for bundle path
|
|
21
21
|
* @param {string} parameters.options.hasFlexBundleVersion true if minUI5Version >= 1.73 than
|
|
22
22
|
* create flexibility-bundle.json
|
|
23
|
+
* @param {object} [parameters.existingFlexBundle={}] Object with existing flexibility-bundle.json
|
|
24
|
+
* to merge with new changes
|
|
23
25
|
* @returns {Promise<@ui5/fs/Resource[]>} Promise resolving with flex changes bundle resources
|
|
24
26
|
*/
|
|
25
|
-
export default function({resources, options: {pathPrefix, hasFlexBundleVersion}}) {
|
|
27
|
+
export default function({resources, options: {pathPrefix, hasFlexBundleVersion}, existingFlexBundle = {}}) {
|
|
26
28
|
let bundleName = "changes-bundle.json";
|
|
27
29
|
|
|
28
30
|
function sortByTimeStamp(a, b) {
|
|
@@ -86,7 +88,7 @@ export default function({resources, options: {pathPrefix, hasFlexBundleVersion}}
|
|
|
86
88
|
return JSON.stringify(changes);
|
|
87
89
|
} else {
|
|
88
90
|
bundleName = "flexibility-bundle.json";
|
|
89
|
-
|
|
91
|
+
let newChangeFormat = {
|
|
90
92
|
changes,
|
|
91
93
|
compVariants,
|
|
92
94
|
variants,
|
|
@@ -94,11 +96,33 @@ export default function({resources, options: {pathPrefix, hasFlexBundleVersion}}
|
|
|
94
96
|
variantDependentControlChanges,
|
|
95
97
|
variantManagementChanges
|
|
96
98
|
};
|
|
97
|
-
|
|
99
|
+
if (Object.keys(existingFlexBundle).length > 0) {
|
|
100
|
+
newChangeFormat = mergeFlexChangeBundles(newChangeFormat);
|
|
101
|
+
}
|
|
98
102
|
return JSON.stringify(newChangeFormat);
|
|
99
103
|
}
|
|
100
104
|
}
|
|
101
105
|
|
|
106
|
+
/**
|
|
107
|
+
* Merge new and existing bundles
|
|
108
|
+
*
|
|
109
|
+
* @param {object} newFlexBundle Object with new content of flexibility-bundle.json
|
|
110
|
+
* @returns {object} Object with merged content of new and existing flexibility-bundle.json
|
|
111
|
+
*/
|
|
112
|
+
function mergeFlexChangeBundles(newFlexBundle) {
|
|
113
|
+
const result = {};
|
|
114
|
+
|
|
115
|
+
Object.keys(newFlexBundle).forEach((key) => {
|
|
116
|
+
if (existingFlexBundle[key] && Array.isArray(existingFlexBundle[key])) {
|
|
117
|
+
result[key] = existingFlexBundle[key].concat(newFlexBundle[key]);
|
|
118
|
+
} else {
|
|
119
|
+
result[key] = newFlexBundle[key];
|
|
120
|
+
}
|
|
121
|
+
});
|
|
122
|
+
|
|
123
|
+
return result;
|
|
124
|
+
}
|
|
125
|
+
|
|
102
126
|
return Promise.all(resources.map((resource) => {
|
|
103
127
|
return resource.getBuffer().then((buffer) => {
|
|
104
128
|
return JSON.parse(buffer.toString());
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
/*
|
|
2
2
|
* Node script to create cross-library API index files for use in the UI5 SDKs.
|
|
3
3
|
*
|
|
4
|
-
* (c) Copyright 2009-
|
|
4
|
+
* (c) Copyright 2009-2024 SAP SE or an SAP affiliate company.
|
|
5
5
|
* Licensed under the Apache License, Version 2.0 - see LICENSE.txt.
|
|
6
6
|
*/
|
|
7
7
|
|
|
@@ -135,10 +135,11 @@ function createIndexFiles(versionInfoFile, unpackedTestresourcesRoot, targetFile
|
|
|
135
135
|
function collectLists(oSymbol) {
|
|
136
136
|
|
|
137
137
|
function addData(oDataType, oEntityObject, sObjectType, sSymbolName) {
|
|
138
|
-
|
|
139
|
-
|
|
138
|
+
const sSince = oDataType !== "since" ? oEntityObject[oDataType].since : oEntityObject.since;
|
|
139
|
+
const sText = oDataType !== "since" ? oEntityObject[oDataType].text : oEntityObject.description;
|
|
140
|
+
const oData = {
|
|
140
141
|
control: sSymbolName,
|
|
141
|
-
text:
|
|
142
|
+
text: sText || undefined,
|
|
142
143
|
type: sObjectType,
|
|
143
144
|
"static": !!oEntityObject.static,
|
|
144
145
|
visibility: oEntityObject.visibility
|
|
@@ -173,7 +174,7 @@ function createIndexFiles(versionInfoFile, unpackedTestresourcesRoot, targetFile
|
|
|
173
174
|
addData("deprecated", oSymbol, "class", oSymbol.name);
|
|
174
175
|
}
|
|
175
176
|
|
|
176
|
-
if (oSymbol.experimental) {
|
|
177
|
+
if (oSymbol.experimental && !oSymbol.deprecated) {
|
|
177
178
|
addData("experimental", oSymbol, "class", oSymbol.name);
|
|
178
179
|
}
|
|
179
180
|
|
|
@@ -187,7 +188,7 @@ function createIndexFiles(versionInfoFile, unpackedTestresourcesRoot, targetFile
|
|
|
187
188
|
addData("deprecated", oMethod, "methods", oSymbol.name);
|
|
188
189
|
}
|
|
189
190
|
|
|
190
|
-
if (oMethod.experimental) {
|
|
191
|
+
if (oMethod.experimental && !oSymbol.deprecated) {
|
|
191
192
|
addData("experimental", oMethod, "methods", oSymbol.name);
|
|
192
193
|
}
|
|
193
194
|
|
|
@@ -202,7 +203,7 @@ function createIndexFiles(versionInfoFile, unpackedTestresourcesRoot, targetFile
|
|
|
202
203
|
addData("deprecated", oEvent, "events", oSymbol.name);
|
|
203
204
|
}
|
|
204
205
|
|
|
205
|
-
if (oEvent.experimental) {
|
|
206
|
+
if (oEvent.experimental && !oSymbol.deprecated) {
|
|
206
207
|
addData("experimental", oEvent, "events", oSymbol.name);
|
|
207
208
|
}
|
|
208
209
|
|
|
@@ -469,6 +470,17 @@ function createIndexFiles(versionInfoFile, unpackedTestresourcesRoot, targetFile
|
|
|
469
470
|
|
|
470
471
|
aKeys.forEach((sKey) => {
|
|
471
472
|
oSorted[sKey] = oList[sKey];
|
|
473
|
+
oSorted[sKey].apis.sort((a,b) => {
|
|
474
|
+
const keyA = `${a.control}|${a.entityName || ""}`.toLowerCase();
|
|
475
|
+
const keyB = `${b.control}|${b.entityName || ""}`.toLowerCase();
|
|
476
|
+
if ( keyA === keyB ) {
|
|
477
|
+
if ( a.static === b.static ) {
|
|
478
|
+
return 0;
|
|
479
|
+
}
|
|
480
|
+
return a.static ? -1 : 1;
|
|
481
|
+
}
|
|
482
|
+
return keyA < keyB ? -1 : 1;
|
|
483
|
+
}); // sort entries within the same version alphabetically (case insensitive)
|
|
472
484
|
});
|
|
473
485
|
|
|
474
486
|
return oSorted;
|
|
@@ -1,10 +1,12 @@
|
|
|
1
1
|
/*
|
|
2
2
|
* Node script to preprocess api.json files for use in the UI5 SDKs.
|
|
3
3
|
*
|
|
4
|
-
* (c) Copyright 2009-
|
|
4
|
+
* (c) Copyright 2009-2024 SAP SE or an SAP affiliate company.
|
|
5
5
|
* Licensed under the Apache License, Version 2.0 - see LICENSE.txt.
|
|
6
6
|
*/
|
|
7
7
|
|
|
8
|
+
/* eslint-disable */
|
|
9
|
+
|
|
8
10
|
"use strict";
|
|
9
11
|
const cheerio = require("cheerio");
|
|
10
12
|
const path = require('path');
|
|
@@ -462,8 +464,9 @@ function transformer(sInputFile, sOutputFile, sLibraryFile, vDependencyAPIFiles,
|
|
|
462
464
|
|
|
463
465
|
// Description
|
|
464
466
|
if (oAggregation.deprecated) {
|
|
465
|
-
oAggregation.description = formatters.formatDescription(oAggregation.description
|
|
466
|
-
|
|
467
|
+
oAggregation.description = formatters.formatDescription(oAggregation.description);
|
|
468
|
+
oAggregation.deprecatedText = formatters.formatDeprecated(oAggregation.deprecated.since,
|
|
469
|
+
oAggregation.deprecated.text);
|
|
467
470
|
} else {
|
|
468
471
|
oAggregation.description = formatters.formatDescriptionSince(oAggregation.description, oAggregation.since);
|
|
469
472
|
}
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
/*
|
|
2
2
|
* JSDoc3 plugin for UI5 documentation generation.
|
|
3
3
|
*
|
|
4
|
-
* (c) Copyright 2009-
|
|
4
|
+
* (c) Copyright 2009-2024 SAP SE or an SAP affiliate company.
|
|
5
5
|
* Licensed under the Apache License, Version 2.0 - see LICENSE.txt.
|
|
6
6
|
*/
|
|
7
7
|
|
|
@@ -21,7 +21,7 @@
|
|
|
21
21
|
* experimental
|
|
22
22
|
*
|
|
23
23
|
* final
|
|
24
|
-
*
|
|
24
|
+
*
|
|
25
25
|
* hideconstructor
|
|
26
26
|
*
|
|
27
27
|
* interface
|
|
@@ -32,7 +32,7 @@
|
|
|
32
32
|
*
|
|
33
33
|
* ui5-restricted
|
|
34
34
|
*
|
|
35
|
-
*
|
|
35
|
+
*
|
|
36
36
|
*
|
|
37
37
|
* It furthermore listens to the following JSDoc3 events to implement additional functionality
|
|
38
38
|
*
|
|
@@ -2137,7 +2137,7 @@ function createAutoDoc(oClassInfo, classComment, doclet, node, parser, filename,
|
|
|
2137
2137
|
"",
|
|
2138
2138
|
newStyle && info.doc ? info.doc : "",
|
|
2139
2139
|
"",
|
|
2140
|
-
|
|
2140
|
+
`@returns {${info.cardinality === "0..n" ? "sap.ui.core.ID[]" : "sap.ui.core.ID|null"}}`,
|
|
2141
2141
|
info.since ? "@since " + info.since : "",
|
|
2142
2142
|
info.deprecation ? "@deprecated " + info.deprecation : "",
|
|
2143
2143
|
info.experimental ? "@experimental " + info.experimental : "",
|
|
@@ -2923,7 +2923,7 @@ exports.handlers = {
|
|
|
2923
2923
|
};
|
|
2924
2924
|
}
|
|
2925
2925
|
|
|
2926
|
-
if ( doclet.kind === 'member' && doclet.isEnum && Array.isArray(doclet.properties) ) {
|
|
2926
|
+
if ( (doclet.kind === 'member' || doclet.kind === 'constant') && doclet.isEnum && Array.isArray(doclet.properties) ) {
|
|
2927
2927
|
// determine unique enum identifier from key set
|
|
2928
2928
|
let enumID = doclet.properties.map(function(prop) {
|
|
2929
2929
|
return prop.name;
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
/*
|
|
2
2
|
* JSDoc3 template for UI5 documentation generation.
|
|
3
3
|
*
|
|
4
|
-
* (c) Copyright 2009-
|
|
4
|
+
* (c) Copyright 2009-2024 SAP SE or an SAP affiliate company.
|
|
5
5
|
* Licensed under the Apache License, Version 2.0 - see LICENSE.txt.
|
|
6
6
|
*/
|
|
7
7
|
|
|
@@ -89,6 +89,10 @@ function merge(target, source) {
|
|
|
89
89
|
if ( source != null ) {
|
|
90
90
|
// simple single source merge
|
|
91
91
|
Object.keys(source).forEach((prop) => {
|
|
92
|
+
// guarding against prototype pollution. (https://codeql.github.com/codeql-query-help/javascript/js-prototype-pollution-utility/#example)
|
|
93
|
+
if (prop === "__proto__" || prop === "constructor") {
|
|
94
|
+
return;
|
|
95
|
+
}
|
|
92
96
|
const value = source[prop];
|
|
93
97
|
if ( value != null && value.constructor === Object ) {
|
|
94
98
|
merge(target[prop] || {}, value);
|
|
@@ -169,7 +173,7 @@ function isModuleExport($) {
|
|
|
169
173
|
}
|
|
170
174
|
|
|
171
175
|
function isaClass($) {
|
|
172
|
-
return /^(namespace|interface|class|typedef)$/.test($.kind) || ($.kind === 'member' && $.isEnum )/* isNonEmptyNamespace($) */;
|
|
176
|
+
return /^(namespace|interface|class|typedef)$/.test($.kind) || (($.kind === 'member' || $.kind === 'constant') && $.isEnum )/* isNonEmptyNamespace($) */;
|
|
173
177
|
}
|
|
174
178
|
|
|
175
179
|
function supportsInheritance($) {
|
|
@@ -187,7 +191,7 @@ function supportsInheritance($) {
|
|
|
187
191
|
function isFirstClassSymbol($) {
|
|
188
192
|
return (
|
|
189
193
|
/^(namespace|interface|class|typedef)$/.test($.kind)
|
|
190
|
-
|| $.kind === 'member' && $.isEnum
|
|
194
|
+
|| ($.kind === 'member' || $.kind === 'constant') && $.isEnum
|
|
191
195
|
|| ['function', 'member'].includes($.kind) && isModuleExport($)
|
|
192
196
|
)/* isNonEmptyNamespace($) */;
|
|
193
197
|
}
|
|
@@ -723,7 +727,7 @@ function getMembersOfKind(data, kind) {
|
|
|
723
727
|
switch (kind) {
|
|
724
728
|
case 'property':
|
|
725
729
|
fnFilter = function($) {
|
|
726
|
-
return $.kind === 'constant' ||
|
|
730
|
+
return ($.kind === 'constant' || $.kind === 'member') && !$.isEnum;
|
|
727
731
|
};
|
|
728
732
|
break;
|
|
729
733
|
case 'event':
|
|
@@ -2030,7 +2034,7 @@ function createAPIJSON4Symbol(symbol, omitDefaults) {
|
|
|
2030
2034
|
}
|
|
2031
2035
|
*/
|
|
2032
2036
|
|
|
2033
|
-
const kind = (symbol.kind === 'member' && symbol.isEnum) ? "enum" : symbol.kind; // handle pseudo-kind 'enum'
|
|
2037
|
+
const kind = ((symbol.kind === 'member' || symbol.kind === 'constant') && symbol.isEnum) ? "enum" : symbol.kind; // handle pseudo-kind 'enum'
|
|
2034
2038
|
|
|
2035
2039
|
tag(kind);
|
|
2036
2040
|
|
|
@@ -2118,7 +2122,13 @@ function createAPIJSON4Symbol(symbol, omitDefaults) {
|
|
|
2118
2122
|
// secTags(symbol); // TODO repeat from class?
|
|
2119
2123
|
closeTag("constructor");
|
|
2120
2124
|
|
|
2125
|
+
} else {
|
|
2126
|
+
|
|
2127
|
+
// even though the constructor is omitted here, the "hide" information is needed because in TypeScript it even exists when omitted
|
|
2128
|
+
attrib("hideconstructor", true, /* default */ false, /* raw */ true); // as boolean
|
|
2129
|
+
|
|
2121
2130
|
}
|
|
2131
|
+
|
|
2122
2132
|
} else if ( kind === 'namespace' ) {
|
|
2123
2133
|
if ( symbol.__ui5.stereotype || symbol.__ui5.metadata ) {
|
|
2124
2134
|
tag("ui5-metadata");
|
|
@@ -233,7 +233,11 @@ async function createManifest(
|
|
|
233
233
|
if ( library.getDocumentation() ) {
|
|
234
234
|
let desc = library.getDocumentation();
|
|
235
235
|
// remove all tags
|
|
236
|
-
|
|
236
|
+
let prevDesc;
|
|
237
|
+
do { // Safely strip tags (https://codeql.github.com/codeql-query-help/javascript/js-incomplete-multi-character-sanitization/#example)
|
|
238
|
+
prevDesc = desc;
|
|
239
|
+
desc = desc.replace(/\s+/g, " ").replace(/<\/?[a-zA-Z][a-zA-Z0-9_$.]*(\s[^>]*)>/g, "");
|
|
240
|
+
} while (prevDesc !== desc);
|
|
237
241
|
// extract summary (first sentence)
|
|
238
242
|
const m = /^([\w\W]+?[.;!?])[^a-zA-Z0-9_$]/.exec(desc);
|
|
239
243
|
return m ? m[1] : desc;
|
|
@@ -556,9 +560,11 @@ async function createManifest(
|
|
|
556
560
|
|
|
557
561
|
const supportedLocalesArray = Array.from(supportedLocales);
|
|
558
562
|
supportedLocalesArray.sort();
|
|
563
|
+
|
|
559
564
|
return {
|
|
560
565
|
bundleUrl: i18n,
|
|
561
|
-
supportedLocales: supportedLocalesArray
|
|
566
|
+
supportedLocales: supportedLocalesArray,
|
|
567
|
+
fallbackLocale: supportedLocalesArray.length === 1 ? supportedLocalesArray[0] : undefined
|
|
562
568
|
};
|
|
563
569
|
}
|
|
564
570
|
|
|
@@ -83,15 +83,21 @@ export default async function({workspace, taskUtil, options = {}}) {
|
|
|
83
83
|
if (allResources.length > 0) {
|
|
84
84
|
const version = semver.coerce(await readManifestMinUI5Version());
|
|
85
85
|
let hasFlexBundleVersion = false;
|
|
86
|
+
let flexBundle = {};
|
|
86
87
|
if (semver.compare(version, "1.73.0") >= 0) {
|
|
87
88
|
hasFlexBundleVersion = true;
|
|
89
|
+
const flexBundleResource = await workspace.byPath(`${pathPrefix}/changes/flexibility-bundle.json`);
|
|
90
|
+
if (flexBundleResource) {
|
|
91
|
+
flexBundle = JSON.parse(await flexBundleResource.getString());
|
|
92
|
+
}
|
|
88
93
|
}
|
|
89
94
|
const processedResources = await flexChangesBundler({
|
|
90
95
|
resources: allResources,
|
|
91
96
|
options: {
|
|
92
97
|
pathPrefix,
|
|
93
98
|
hasFlexBundleVersion
|
|
94
|
-
}
|
|
99
|
+
},
|
|
100
|
+
existingFlexBundle: flexBundle
|
|
95
101
|
});
|
|
96
102
|
await Promise.all(processedResources.map((resource) => {
|
|
97
103
|
log.verbose("Writing flexibility changes bundle");
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@ui5/builder",
|
|
3
|
-
"version": "3.
|
|
3
|
+
"version": "3.3.0",
|
|
4
4
|
"description": "UI5 Tooling - Builder",
|
|
5
5
|
"author": {
|
|
6
6
|
"name": "SAP SE",
|
|
@@ -47,7 +47,7 @@
|
|
|
47
47
|
"jsdoc-watch": "npm run jsdoc && chokidar \"./lib/**/*.js\" -c \"npm run jsdoc-generate\"",
|
|
48
48
|
"preversion": "npm test",
|
|
49
49
|
"version": "git-chglog --sort semver --next-tag v$npm_package_version -o CHANGELOG.md v3.0.0.. && git add CHANGELOG.md",
|
|
50
|
-
"
|
|
50
|
+
"prepublishOnly": "git push --follow-tags",
|
|
51
51
|
"release-note": "git-chglog --sort semver -c .chglog/release-config.yml v$npm_package_version",
|
|
52
52
|
"depcheck": "depcheck --ignores @ui5/builder,docdash,@istanbuljs/esm-loader-hook,catharsis --parsers='**/*.js:es6,**/*.cjs:es6'"
|
|
53
53
|
},
|
|
@@ -131,26 +131,26 @@
|
|
|
131
131
|
"pretty-data": "^0.40.0",
|
|
132
132
|
"rimraf": "^5.0.5",
|
|
133
133
|
"semver": "^7.5.4",
|
|
134
|
-
"terser": "^5.
|
|
134
|
+
"terser": "^5.27.0",
|
|
135
135
|
"workerpool": "^6.5.1",
|
|
136
136
|
"xml2js": "^0.6.2"
|
|
137
137
|
},
|
|
138
138
|
"devDependencies": {
|
|
139
139
|
"@istanbuljs/esm-loader-hook": "^0.2.0",
|
|
140
|
-
"@jridgewell/trace-mapping": "^0.3.
|
|
141
|
-
"@ui5/project": "^3.
|
|
140
|
+
"@jridgewell/trace-mapping": "^0.3.21",
|
|
141
|
+
"@ui5/project": "^3.9.0",
|
|
142
142
|
"ava": "^5.3.1",
|
|
143
|
-
"chai": "^4.
|
|
143
|
+
"chai": "^4.4.1",
|
|
144
144
|
"chai-fs": "^2.0.0",
|
|
145
145
|
"chokidar-cli": "^3.0.0",
|
|
146
146
|
"cross-env": "^7.0.3",
|
|
147
147
|
"depcheck": "^1.4.7",
|
|
148
148
|
"docdash": "^2.0.2",
|
|
149
|
-
"eslint": "^8.
|
|
149
|
+
"eslint": "^8.56.0",
|
|
150
150
|
"eslint-config-google": "^0.14.0",
|
|
151
151
|
"eslint-plugin-ava": "^14.0.0",
|
|
152
|
-
"eslint-plugin-jsdoc": "^46.
|
|
153
|
-
"esmock": "^2.6.
|
|
152
|
+
"eslint-plugin-jsdoc": "^46.10.1",
|
|
153
|
+
"esmock": "^2.6.2",
|
|
154
154
|
"line-column": "^1.0.2",
|
|
155
155
|
"nyc": "^15.1.0",
|
|
156
156
|
"open-cli": "^7.2.0",
|