@ui5/webcomponents-tools 2.20.0-rc.2 → 2.20.0-rc.3
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/CHANGELOG.md +8 -0
- package/components-package/nps.js +3 -3
- package/lib/cem/custom-elements-manifest.config.mjs +42 -3
- package/lib/cem/merge.mjs +220 -0
- package/lib/cem/schema-internal.json +41 -1
- package/lib/cem/schema.json +41 -1
- package/lib/cem/types-internal.d.ts +32 -2
- package/lib/cem/types.d.ts +32 -2
- package/lib/cem/utils.mjs +6 -2
- package/package.json +2 -2
package/CHANGELOG.md
CHANGED
|
@@ -3,6 +3,14 @@
|
|
|
3
3
|
All notable changes to this project will be documented in this file.
|
|
4
4
|
See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
|
|
5
5
|
|
|
6
|
+
# [2.20.0-rc.3](https://github.com/UI5/webcomponents/compare/v2.20.0-rc.2...v2.20.0-rc.3) (2026-03-05)
|
|
7
|
+
|
|
8
|
+
**Note:** Version bump only for package @ui5/webcomponents-tools
|
|
9
|
+
|
|
10
|
+
|
|
11
|
+
|
|
12
|
+
|
|
13
|
+
|
|
6
14
|
# [2.20.0-rc.2](https://github.com/UI5/webcomponents/compare/v2.20.0-rc.1...v2.20.0-rc.2) (2026-02-26)
|
|
7
15
|
|
|
8
16
|
|
|
@@ -68,7 +68,7 @@ const getScripts = (options) => {
|
|
|
68
68
|
|
|
69
69
|
const scripts = {
|
|
70
70
|
__ui5envs: {
|
|
71
|
-
UI5_CEM_MODE: options.dev,
|
|
71
|
+
UI5_CEM_MODE: typeof options.dev === "boolean" ? (options.dev ? "dev" : undefined) : options.dev,
|
|
72
72
|
UI5_TS: `${tsOption}`,
|
|
73
73
|
CSS_VARIABLES_TARGET: options.cssVariablesTarget ?? "root",
|
|
74
74
|
CYPRESS_COVERAGE: !!(options.internal?.cypress_code_coverage),
|
|
@@ -86,7 +86,7 @@ const getScripts = (options) => {
|
|
|
86
86
|
styleRelated: "ui5nps build.styles build.jsonImports build.jsImports",
|
|
87
87
|
},
|
|
88
88
|
prepare: {
|
|
89
|
-
default: `ui5nps clean prepare.all copy copyProps prepare.typescript
|
|
89
|
+
default: `ui5nps clean prepare.all copy copyProps prepare.typescript`,
|
|
90
90
|
all: `ui5nps-p build.templates build.i18n prepare.styleRelated build.illustrations`, // concurently
|
|
91
91
|
styleRelated: "ui5nps build.styles build.jsonImports build.jsImports",
|
|
92
92
|
typescript: tsCommandOld,
|
|
@@ -165,9 +165,9 @@ const getScripts = (options) => {
|
|
|
165
165
|
bundle: `ui5nps-script ${LIB}dev-server/dev-server.mjs ${viteConfig}`,
|
|
166
166
|
},
|
|
167
167
|
generateAPI: {
|
|
168
|
-
default: tsOption ? "ui5nps generateAPI.generateCEM generateAPI.validateCEM" : "",
|
|
169
168
|
generateCEM: `ui5nps-script "${LIB}cem/cem.js" analyze --config "${LIB}cem/custom-elements-manifest.config.mjs"`,
|
|
170
169
|
validateCEM: `ui5nps-script "${LIB}cem/validate.js"`,
|
|
170
|
+
mergeCEM: `ui5nps-script "${LIB}cem/merge.mjs"`,
|
|
171
171
|
},
|
|
172
172
|
};
|
|
173
173
|
|
|
@@ -48,7 +48,7 @@ const wrapPluginForQuietMode = (plugin) => {
|
|
|
48
48
|
...plugin,
|
|
49
49
|
packageLinkPhase(context) {
|
|
50
50
|
const originalLog = console.log;
|
|
51
|
-
console.log = () => {};
|
|
51
|
+
console.log = () => { };
|
|
52
52
|
try {
|
|
53
53
|
return originalPackageLinkPhase.call(plugin, context);
|
|
54
54
|
} finally {
|
|
@@ -135,6 +135,13 @@ function processClass(ts, classNode, moduleDoc) {
|
|
|
135
135
|
if (currClass.superclass?.name === "UI5Element") {
|
|
136
136
|
currClass.customElement = true;
|
|
137
137
|
}
|
|
138
|
+
} else if (currClass.customElement && classNode?.heritageClauses) {
|
|
139
|
+
// Find the extends clause (not implements)
|
|
140
|
+
const extendsClause = classNode.heritageClauses.find(clause => clause.token === ts.SyntaxKind.ExtendsKeyword);
|
|
141
|
+
if (extendsClause?.types?.[0]?.expression?.text) {
|
|
142
|
+
const extendedClass = extendsClause.types[0].expression.text;
|
|
143
|
+
logDocumentationError(moduleDoc.path, `Class extends ${extendedClass} but @extends tag is missing in JSDoc`);
|
|
144
|
+
}
|
|
138
145
|
}
|
|
139
146
|
|
|
140
147
|
if (!currClass._ui5implements.length) delete currClass._ui5implements;
|
|
@@ -417,10 +424,10 @@ const processPublicAPI = object => {
|
|
|
417
424
|
return true;
|
|
418
425
|
}
|
|
419
426
|
for (const key of keys) {
|
|
420
|
-
if ((key === "privacy" && object[key] !== "public") || (key === "_ui5privacy" && object[key] !== "public")) {
|
|
427
|
+
if (((key === "privacy" && object[key] !== "public") || (key === "_ui5privacy" && object[key] !== "public")) && !object.customElement) {
|
|
421
428
|
return true;
|
|
422
429
|
} else if (typeof object[key] === "object") {
|
|
423
|
-
if (key === "cssParts" || key === "attributes" || key === "_ui5implements") {
|
|
430
|
+
if (key === "cssParts" || key === "cssStates" || key === "attributes" || key === "_ui5implements") {
|
|
424
431
|
continue;
|
|
425
432
|
}
|
|
426
433
|
|
|
@@ -569,6 +576,38 @@ export default {
|
|
|
569
576
|
}
|
|
570
577
|
}
|
|
571
578
|
},
|
|
579
|
+
{
|
|
580
|
+
name: 'alphabetical-sort-plugin',
|
|
581
|
+
packageLinkPhase({ customElementsManifest }) {
|
|
582
|
+
const sortByName = (arr) => {
|
|
583
|
+
if (Array.isArray(arr)) {
|
|
584
|
+
arr.sort((a, b) => {
|
|
585
|
+
if (a?.name && b?.name) {
|
|
586
|
+
return a.name.localeCompare(b.name);
|
|
587
|
+
}
|
|
588
|
+
return 0;
|
|
589
|
+
});
|
|
590
|
+
}
|
|
591
|
+
};
|
|
592
|
+
|
|
593
|
+
const sortArraysInObject = (obj) => {
|
|
594
|
+
if (!obj || typeof obj !== 'object') return;
|
|
595
|
+
|
|
596
|
+
for (const key in obj) {
|
|
597
|
+
if (Array.isArray(obj[key])) {
|
|
598
|
+
sortByName(obj[key]);
|
|
599
|
+
obj[key].forEach(item => sortArraysInObject(item));
|
|
600
|
+
} else if (typeof obj[key] === 'object') {
|
|
601
|
+
sortArraysInObject(obj[key]);
|
|
602
|
+
}
|
|
603
|
+
}
|
|
604
|
+
};
|
|
605
|
+
|
|
606
|
+
customElementsManifest.modules?.forEach(moduleDoc => {
|
|
607
|
+
sortArraysInObject(moduleDoc);
|
|
608
|
+
});
|
|
609
|
+
}
|
|
610
|
+
},
|
|
572
611
|
wrapPluginForQuietMode(generateCustomData({ outdir: "dist", cssFileName: null, cssPropertiesDocs: false })),
|
|
573
612
|
wrapPluginForQuietMode(customElementJetBrainsPlugin({ outdir: "dist", cssFileName: null, cssPropertiesDocs: false }))
|
|
574
613
|
],
|
|
@@ -0,0 +1,220 @@
|
|
|
1
|
+
import { pathToFileURL } from "url";
|
|
2
|
+
import path from "path";
|
|
3
|
+
import { createRequire } from 'module';
|
|
4
|
+
import { readFile, writeFile } from "fs/promises";
|
|
5
|
+
|
|
6
|
+
const require = createRequire(import.meta.url);
|
|
7
|
+
|
|
8
|
+
const UI5_BASE_CLASS = "UI5Element";
|
|
9
|
+
|
|
10
|
+
const main = async (argv) => {
|
|
11
|
+
let customElementsPath = null;
|
|
12
|
+
const CACHED_CEMS = new Map();
|
|
13
|
+
const DECLARATION_PACKAGE = new WeakMap();
|
|
14
|
+
const DECLARATION_MODULE = new WeakMap();
|
|
15
|
+
|
|
16
|
+
function removeInheritedFrom(obj) {
|
|
17
|
+
if (obj === null || typeof obj !== 'object') {
|
|
18
|
+
return obj;
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
if (Array.isArray(obj)) {
|
|
22
|
+
return obj.map(item => removeInheritedFrom(item));
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
const result = {};
|
|
26
|
+
for (const [key, value] of Object.entries(obj)) {
|
|
27
|
+
if (key === 'inheritedFrom') {
|
|
28
|
+
continue;
|
|
29
|
+
}
|
|
30
|
+
result[key] = removeInheritedFrom(value);
|
|
31
|
+
}
|
|
32
|
+
return result;
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
async function readPackageJson(filePath) {
|
|
36
|
+
try {
|
|
37
|
+
return JSON.parse(await readFile(filePath, "utf-8"));
|
|
38
|
+
} catch (error) {
|
|
39
|
+
throw new Error(`Failed to read package.json at ${filePath}: ${error.message}`);
|
|
40
|
+
}
|
|
41
|
+
}
|
|
42
|
+
|
|
43
|
+
async function loadPackageJson(depName) {
|
|
44
|
+
try {
|
|
45
|
+
// First try the standard require method (works when exports includes package.json)
|
|
46
|
+
const pkg = require(`${depName}/package.json`);
|
|
47
|
+
const pkgPath = require.resolve(`${depName}/package.json`);
|
|
48
|
+
return { path: path.dirname(pkgPath), pkg };
|
|
49
|
+
} catch (e) {
|
|
50
|
+
// If that fails, resolve the package path and read package.json directly
|
|
51
|
+
try {
|
|
52
|
+
const packagePath = require.resolve(depName);
|
|
53
|
+
let currentDir = path.dirname(packagePath);
|
|
54
|
+
|
|
55
|
+
// Navigate up to find package.json (the resolved path might be deep in dist/ or similar)
|
|
56
|
+
while (currentDir !== path.parse(currentDir).root) {
|
|
57
|
+
try {
|
|
58
|
+
const pkgPath = path.join(currentDir, 'package.json');
|
|
59
|
+
const content = await readFile(pkgPath, 'utf-8');
|
|
60
|
+
const pkg = JSON.parse(content);
|
|
61
|
+
|
|
62
|
+
// Verify this is the correct package.json by checking the name
|
|
63
|
+
if (pkg.name === depName) {
|
|
64
|
+
return { path: currentDir, pkg };
|
|
65
|
+
}
|
|
66
|
+
} catch {
|
|
67
|
+
// Continue searching up the directory tree
|
|
68
|
+
}
|
|
69
|
+
currentDir = path.dirname(currentDir);
|
|
70
|
+
}
|
|
71
|
+
} catch (resolveError) {
|
|
72
|
+
// console.warn(`Could not resolve ${depName}:`, resolveError.message);
|
|
73
|
+
}
|
|
74
|
+
return null;
|
|
75
|
+
}
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
async function collectThirdPartyCem() {
|
|
79
|
+
const packageJSONPath = path.resolve(process.cwd(), "package.json");
|
|
80
|
+
const packageJSON = await readPackageJson(packageJSONPath);
|
|
81
|
+
|
|
82
|
+
const dependencyKeys = Object.keys(packageJSON).filter(key => key.toLowerCase().includes("dependencies"));
|
|
83
|
+
const dependencies = dependencyKeys.flatMap(key => Object.keys(packageJSON[key]));
|
|
84
|
+
|
|
85
|
+
const thirdPartCEM = (await Promise.all(dependencies.map(async dep => {
|
|
86
|
+
const result = await loadPackageJson(dep);
|
|
87
|
+
if (!result?.pkg?.customElements) return null;
|
|
88
|
+
|
|
89
|
+
return {
|
|
90
|
+
path: result.path,
|
|
91
|
+
name: dep,
|
|
92
|
+
cem: result.pkg.customElements
|
|
93
|
+
};
|
|
94
|
+
}))).filter(Boolean);
|
|
95
|
+
|
|
96
|
+
await Promise.all(thirdPartCEM.map(async dep => {
|
|
97
|
+
const cemPath = path.resolve(dep.path, dep.cem);
|
|
98
|
+
try {
|
|
99
|
+
const cemContent = JSON.parse(await readFile(cemPath, "utf-8"));
|
|
100
|
+
CACHED_CEMS.set(dep.name, cemContent);
|
|
101
|
+
} catch (error) {
|
|
102
|
+
console.warn(`Failed to read CEM for ${dep.name} from ${cemPath}: ${error.message}`);
|
|
103
|
+
}
|
|
104
|
+
}));
|
|
105
|
+
}
|
|
106
|
+
|
|
107
|
+
async function readCurrentCEM() {
|
|
108
|
+
const packageJSONPath = path.resolve(process.cwd(), "package.json");
|
|
109
|
+
const packageJSON = await readPackageJson(packageJSONPath);
|
|
110
|
+
|
|
111
|
+
if (!packageJSON?.customElements) {
|
|
112
|
+
return null;
|
|
113
|
+
}
|
|
114
|
+
|
|
115
|
+
customElementsPath = packageJSON.customElements;
|
|
116
|
+
const cemPath = path.resolve(process.cwd(), customElementsPath);
|
|
117
|
+
|
|
118
|
+
try {
|
|
119
|
+
const cemContent = JSON.parse(await readFile(cemPath, "utf-8"));
|
|
120
|
+
CACHED_CEMS.set(packageJSON.name, cemContent);
|
|
121
|
+
return cemContent;
|
|
122
|
+
} catch (error) {
|
|
123
|
+
throw new Error(`Failed to read CEM from ${cemPath}: ${error.message}`);
|
|
124
|
+
}
|
|
125
|
+
}
|
|
126
|
+
|
|
127
|
+
async function resolveReference(ref) {
|
|
128
|
+
const pkg = CACHED_CEMS.get(ref.package);
|
|
129
|
+
|
|
130
|
+
if (!pkg) {
|
|
131
|
+
return null;
|
|
132
|
+
}
|
|
133
|
+
|
|
134
|
+
const mod = (pkg.modules || []).find(m => m.path === ref.module);
|
|
135
|
+
|
|
136
|
+
if (!mod) {
|
|
137
|
+
return null;
|
|
138
|
+
}
|
|
139
|
+
|
|
140
|
+
const declaration = (mod.declarations || []).find(d => d.name === ref.name);
|
|
141
|
+
|
|
142
|
+
if (!declaration) {
|
|
143
|
+
return null;
|
|
144
|
+
}
|
|
145
|
+
|
|
146
|
+
DECLARATION_PACKAGE.set(declaration, ref.package);
|
|
147
|
+
DECLARATION_MODULE.set(declaration, ref.module);
|
|
148
|
+
|
|
149
|
+
return resolveDeclaration(declaration);
|
|
150
|
+
}
|
|
151
|
+
|
|
152
|
+
async function resolveDeclaration(declaration) {
|
|
153
|
+
if (!declaration.superclass || declaration.superclass.name === UI5_BASE_CLASS) {
|
|
154
|
+
return [declaration];
|
|
155
|
+
}
|
|
156
|
+
|
|
157
|
+
const superclassDeclarations = await resolveReference(declaration.superclass);
|
|
158
|
+
return [declaration, superclassDeclarations].flat().filter(Boolean);
|
|
159
|
+
}
|
|
160
|
+
|
|
161
|
+
const merge = async () => {
|
|
162
|
+
const currentCEM = await readCurrentCEM();
|
|
163
|
+
if (!currentCEM) {
|
|
164
|
+
throw new Error("No custom elements manifest found in current project");
|
|
165
|
+
}
|
|
166
|
+
|
|
167
|
+
await collectThirdPartyCem();
|
|
168
|
+
|
|
169
|
+
const modules = currentCEM.modules || [];
|
|
170
|
+
|
|
171
|
+
for (const mod of modules) {
|
|
172
|
+
const declarations = (mod.declarations || []).filter(d => d.kind === "class");
|
|
173
|
+
|
|
174
|
+
for (const declaration of declarations) {
|
|
175
|
+
const declarationHierarchy = await resolveDeclaration(declaration);
|
|
176
|
+
const allKeys = declarationHierarchy.flatMap(dec => Object.keys(dec));
|
|
177
|
+
const uniqueKeys = [...new Set(allKeys)];
|
|
178
|
+
const arrayKeys = uniqueKeys
|
|
179
|
+
.filter(key => !key.startsWith("_ui5"))
|
|
180
|
+
.filter(key => declarationHierarchy.some(dec => Array.isArray(dec[key])));
|
|
181
|
+
|
|
182
|
+
for (const key of arrayKeys) {
|
|
183
|
+
const allItems = declarationHierarchy.flatMap(dec => dec[key] || []);
|
|
184
|
+
|
|
185
|
+
// Remove duplicates based on name property
|
|
186
|
+
const seen = new Set();
|
|
187
|
+
declaration[key] = allItems.filter(item => {
|
|
188
|
+
if (!item.name) return true;
|
|
189
|
+
if (seen.has(item.name)) return false;
|
|
190
|
+
seen.add(item.name);
|
|
191
|
+
return true;
|
|
192
|
+
});
|
|
193
|
+
}
|
|
194
|
+
}
|
|
195
|
+
}
|
|
196
|
+
|
|
197
|
+
const cleanedCEM = removeInheritedFrom(currentCEM);
|
|
198
|
+
const outputPath = path.resolve(process.cwd(), customElementsPath);
|
|
199
|
+
|
|
200
|
+
try {
|
|
201
|
+
await writeFile(outputPath, JSON.stringify(cleanedCEM, null, 2), "utf-8");
|
|
202
|
+
console.log(`Successfully merged CEM to ${outputPath}`);
|
|
203
|
+
} catch (error) {
|
|
204
|
+
throw new Error(`Failed to write merged CEM to ${outputPath}: ${error.message}`);
|
|
205
|
+
}
|
|
206
|
+
};
|
|
207
|
+
|
|
208
|
+
await merge();
|
|
209
|
+
}
|
|
210
|
+
|
|
211
|
+
const filePath = process.argv[1];
|
|
212
|
+
const fileUrl = pathToFileURL(filePath).href;
|
|
213
|
+
|
|
214
|
+
if (import.meta.url === fileUrl) {
|
|
215
|
+
main(process.argv)
|
|
216
|
+
}
|
|
217
|
+
|
|
218
|
+
export default {
|
|
219
|
+
_ui5mainFn: main
|
|
220
|
+
}
|
|
@@ -1,6 +1,34 @@
|
|
|
1
1
|
{
|
|
2
2
|
"$schema": "http://json-schema.org/draft-07/schema#",
|
|
3
3
|
"definitions": {
|
|
4
|
+
"CssCustomState": {
|
|
5
|
+
"description": "The description of a CSS Custom State\nhttps://developer.mozilla.org/en-US/docs/Web/API/CustomStateSet",
|
|
6
|
+
"properties": {
|
|
7
|
+
"deprecated": {
|
|
8
|
+
"description": "Whether the CSS custom state is deprecated.\nIf the value is a string, it's the reason for the deprecation.",
|
|
9
|
+
"type": [
|
|
10
|
+
"string",
|
|
11
|
+
"boolean"
|
|
12
|
+
]
|
|
13
|
+
},
|
|
14
|
+
"description": {
|
|
15
|
+
"description": "A markdown description.",
|
|
16
|
+
"type": "string"
|
|
17
|
+
},
|
|
18
|
+
"name": {
|
|
19
|
+
"description": "The name of the state. Note: Unlike CSS custom properties, custom states\ndo not have a leading `--`.",
|
|
20
|
+
"type": "string"
|
|
21
|
+
},
|
|
22
|
+
"summary": {
|
|
23
|
+
"description": "A markdown summary suitable for display in a listing.",
|
|
24
|
+
"type": "string"
|
|
25
|
+
}
|
|
26
|
+
},
|
|
27
|
+
"required": [
|
|
28
|
+
"name"
|
|
29
|
+
],
|
|
30
|
+
"type": "object"
|
|
31
|
+
},
|
|
4
32
|
"Attribute": {
|
|
5
33
|
"additionalProperties": false,
|
|
6
34
|
"properties": {
|
|
@@ -521,6 +549,12 @@
|
|
|
521
549
|
},
|
|
522
550
|
"type": "array"
|
|
523
551
|
},
|
|
552
|
+
"cssStates": {
|
|
553
|
+
"items": {
|
|
554
|
+
"$ref": "#/definitions/CssCustomState"
|
|
555
|
+
},
|
|
556
|
+
"type": "array"
|
|
557
|
+
},
|
|
524
558
|
"customElement": {
|
|
525
559
|
"description": "Distinguishes a regular JavaScript class from a\ncustom element class",
|
|
526
560
|
"enum": [
|
|
@@ -676,6 +710,12 @@
|
|
|
676
710
|
},
|
|
677
711
|
"type": "array"
|
|
678
712
|
},
|
|
713
|
+
"cssStates": {
|
|
714
|
+
"items": {
|
|
715
|
+
"$ref": "#/definitions/CssCustomState"
|
|
716
|
+
},
|
|
717
|
+
"type": "array"
|
|
718
|
+
},
|
|
679
719
|
"customElement": {
|
|
680
720
|
"description": "Distinguishes a regular JavaScript class from a\ncustom element class",
|
|
681
721
|
"enum": [
|
|
@@ -1039,7 +1079,7 @@
|
|
|
1039
1079
|
"type": "string"
|
|
1040
1080
|
},
|
|
1041
1081
|
"path": {
|
|
1042
|
-
"description": "Path to the javascript file needed to be imported
|
|
1082
|
+
"description": "Path to the javascript file needed to be imported.\n(not the path for example to a typescript file.)",
|
|
1043
1083
|
"type": "string"
|
|
1044
1084
|
},
|
|
1045
1085
|
"summary": {
|
package/lib/cem/schema.json
CHANGED
|
@@ -258,6 +258,34 @@
|
|
|
258
258
|
],
|
|
259
259
|
"type": "object"
|
|
260
260
|
},
|
|
261
|
+
"CssCustomState": {
|
|
262
|
+
"description": "The description of a CSS Custom State\nhttps://developer.mozilla.org/en-US/docs/Web/API/CustomStateSet",
|
|
263
|
+
"properties": {
|
|
264
|
+
"deprecated": {
|
|
265
|
+
"description": "Whether the CSS custom state is deprecated.\nIf the value is a string, it's the reason for the deprecation.",
|
|
266
|
+
"type": [
|
|
267
|
+
"string",
|
|
268
|
+
"boolean"
|
|
269
|
+
]
|
|
270
|
+
},
|
|
271
|
+
"description": {
|
|
272
|
+
"description": "A markdown description.",
|
|
273
|
+
"type": "string"
|
|
274
|
+
},
|
|
275
|
+
"name": {
|
|
276
|
+
"description": "The name of the state. Note: Unlike CSS custom properties, custom states\ndo not have a leading `--`.",
|
|
277
|
+
"type": "string"
|
|
278
|
+
},
|
|
279
|
+
"summary": {
|
|
280
|
+
"description": "A markdown summary suitable for display in a listing.",
|
|
281
|
+
"type": "string"
|
|
282
|
+
}
|
|
283
|
+
},
|
|
284
|
+
"required": [
|
|
285
|
+
"name"
|
|
286
|
+
],
|
|
287
|
+
"type": "object"
|
|
288
|
+
},
|
|
261
289
|
"CssPart": {
|
|
262
290
|
"description": "The description of a CSS Part",
|
|
263
291
|
"properties": {
|
|
@@ -307,6 +335,12 @@
|
|
|
307
335
|
},
|
|
308
336
|
"type": "array"
|
|
309
337
|
},
|
|
338
|
+
"cssStates": {
|
|
339
|
+
"items": {
|
|
340
|
+
"$ref": "#/definitions/CssCustomState"
|
|
341
|
+
},
|
|
342
|
+
"type": "array"
|
|
343
|
+
},
|
|
310
344
|
"customElement": {
|
|
311
345
|
"description": "Distinguishes a regular JavaScript class from a\ncustom element class",
|
|
312
346
|
"enum": [
|
|
@@ -451,6 +485,12 @@
|
|
|
451
485
|
},
|
|
452
486
|
"type": "array"
|
|
453
487
|
},
|
|
488
|
+
"cssStates": {
|
|
489
|
+
"items": {
|
|
490
|
+
"$ref": "#/definitions/CssCustomState"
|
|
491
|
+
},
|
|
492
|
+
"type": "array"
|
|
493
|
+
},
|
|
454
494
|
"customElement": {
|
|
455
495
|
"description": "Distinguishes a regular JavaScript class from a\ncustom element class",
|
|
456
496
|
"enum": [
|
|
@@ -765,7 +805,7 @@
|
|
|
765
805
|
"type": "string"
|
|
766
806
|
},
|
|
767
807
|
"path": {
|
|
768
|
-
"description": "Path to the javascript file needed to be imported
|
|
808
|
+
"description": "Path to the javascript file needed to be imported.\n(not the path for example to a typescript file.)",
|
|
769
809
|
"type": "string"
|
|
770
810
|
},
|
|
771
811
|
"summary": {
|
|
@@ -56,7 +56,7 @@ export interface JavaScriptModule {
|
|
|
56
56
|
kind: 'javascript-module';
|
|
57
57
|
|
|
58
58
|
/**
|
|
59
|
-
* Path to the javascript file needed to be imported.
|
|
59
|
+
* Path to the javascript file needed to be imported.
|
|
60
60
|
* (not the path for example to a typescript file.)
|
|
61
61
|
*/
|
|
62
62
|
path: string;
|
|
@@ -258,6 +258,8 @@ export interface CustomElement extends ClassLike {
|
|
|
258
258
|
|
|
259
259
|
cssProperties?: CssCustomProperty[];
|
|
260
260
|
|
|
261
|
+
cssStates?: CssCustomState[];
|
|
262
|
+
|
|
261
263
|
demos?: Demo[];
|
|
262
264
|
|
|
263
265
|
/**
|
|
@@ -416,6 +418,34 @@ export interface CssPart {
|
|
|
416
418
|
deprecated?: boolean | string;
|
|
417
419
|
}
|
|
418
420
|
|
|
421
|
+
/**
|
|
422
|
+
* The description of a CSS Custom State
|
|
423
|
+
* https://developer.mozilla.org/en-US/docs/Web/API/CustomStateSet
|
|
424
|
+
*/
|
|
425
|
+
export interface CssCustomState {
|
|
426
|
+
/**
|
|
427
|
+
* The name of the state. Note: Unlike CSS custom properties, custom states
|
|
428
|
+
* do not have a leading `--`.
|
|
429
|
+
*/
|
|
430
|
+
name: string;
|
|
431
|
+
|
|
432
|
+
/**
|
|
433
|
+
* A markdown summary suitable for display in a listing.
|
|
434
|
+
*/
|
|
435
|
+
summary?: string;
|
|
436
|
+
|
|
437
|
+
/**
|
|
438
|
+
* A markdown description.
|
|
439
|
+
*/
|
|
440
|
+
description?: string;
|
|
441
|
+
|
|
442
|
+
/**
|
|
443
|
+
* Whether the CSS custom state is deprecated.
|
|
444
|
+
* If the value is a string, it's the reason for the deprecation.
|
|
445
|
+
*/
|
|
446
|
+
deprecated?: boolean | string;
|
|
447
|
+
}
|
|
448
|
+
|
|
419
449
|
export interface CssCustomProperty {
|
|
420
450
|
/**
|
|
421
451
|
* The name of the property, including leading `--`.
|
|
@@ -632,7 +662,7 @@ export interface ClassField extends PropertyLike {
|
|
|
632
662
|
export interface CustomElementField extends ClassField {
|
|
633
663
|
/**
|
|
634
664
|
* The corresponding attribute name if there is one.
|
|
635
|
-
*
|
|
665
|
+
*
|
|
636
666
|
* If this property is defined, the attribute must be listed in the classes'
|
|
637
667
|
* `attributes` array.
|
|
638
668
|
*/
|
package/lib/cem/types.d.ts
CHANGED
|
@@ -56,7 +56,7 @@ export interface JavaScriptModule {
|
|
|
56
56
|
kind: 'javascript-module';
|
|
57
57
|
|
|
58
58
|
/**
|
|
59
|
-
* Path to the javascript file needed to be imported.
|
|
59
|
+
* Path to the javascript file needed to be imported.
|
|
60
60
|
* (not the path for example to a typescript file.)
|
|
61
61
|
*/
|
|
62
62
|
path: string;
|
|
@@ -250,6 +250,8 @@ export interface CustomElement extends ClassLike {
|
|
|
250
250
|
|
|
251
251
|
cssProperties?: CssCustomProperty[];
|
|
252
252
|
|
|
253
|
+
cssStates?: CssCustomState[];
|
|
254
|
+
|
|
253
255
|
demos?: Demo[];
|
|
254
256
|
|
|
255
257
|
/**
|
|
@@ -372,6 +374,34 @@ export interface CssPart {
|
|
|
372
374
|
deprecated?: boolean | string;
|
|
373
375
|
}
|
|
374
376
|
|
|
377
|
+
/**
|
|
378
|
+
* The description of a CSS Custom State
|
|
379
|
+
* https://developer.mozilla.org/en-US/docs/Web/API/CustomStateSet
|
|
380
|
+
*/
|
|
381
|
+
export interface CssCustomState {
|
|
382
|
+
/**
|
|
383
|
+
* The name of the state. Note: Unlike CSS custom properties, custom states
|
|
384
|
+
* do not have a leading `--`.
|
|
385
|
+
*/
|
|
386
|
+
name: string;
|
|
387
|
+
|
|
388
|
+
/**
|
|
389
|
+
* A markdown summary suitable for display in a listing.
|
|
390
|
+
*/
|
|
391
|
+
summary?: string;
|
|
392
|
+
|
|
393
|
+
/**
|
|
394
|
+
* A markdown description.
|
|
395
|
+
*/
|
|
396
|
+
description?: string;
|
|
397
|
+
|
|
398
|
+
/**
|
|
399
|
+
* Whether the CSS custom state is deprecated.
|
|
400
|
+
* If the value is a string, it's the reason for the deprecation.
|
|
401
|
+
*/
|
|
402
|
+
deprecated?: boolean | string;
|
|
403
|
+
}
|
|
404
|
+
|
|
375
405
|
export interface CssCustomProperty {
|
|
376
406
|
/**
|
|
377
407
|
* The name of the property, including leading `--`.
|
|
@@ -573,7 +603,7 @@ export interface ClassField extends PropertyLike {
|
|
|
573
603
|
export interface CustomElementField extends ClassField {
|
|
574
604
|
/**
|
|
575
605
|
* The corresponding attribute name if there is one.
|
|
576
|
-
*
|
|
606
|
+
*
|
|
577
607
|
* If this property is defined, the attribute must be listed in the classes'
|
|
578
608
|
* `attributes` array.
|
|
579
609
|
*/
|
package/lib/cem/utils.mjs
CHANGED
|
@@ -240,7 +240,7 @@ const allowedTags = {
|
|
|
240
240
|
event: [...commonTags, "param", "native", "allowPreventDefault"],
|
|
241
241
|
eventParam: [...commonTags],
|
|
242
242
|
method: [...commonTags, "param", "returns", "override"],
|
|
243
|
-
class: [...commonTags, "constructor", "class", "abstract", "experimental", "implements", "extends", "slot", "csspart"],
|
|
243
|
+
class: [...commonTags, "constructor", "class", "abstract", "experimental", "implements", "extends", "slot", "csspart", "cssstate", "cssState"],
|
|
244
244
|
enum: [...commonTags, "experimental",],
|
|
245
245
|
enumMember: [...commonTags, "experimental",],
|
|
246
246
|
interface: [...commonTags, "experimental",],
|
|
@@ -330,6 +330,9 @@ const validateJSDocTag = (tag) => {
|
|
|
330
330
|
return tag.type && tag.name && tag.description;
|
|
331
331
|
case "csspart":
|
|
332
332
|
return !tag.type && tag.name && tag.description;
|
|
333
|
+
case "cssState":
|
|
334
|
+
case "cssstate":
|
|
335
|
+
return !tag.type && tag.name && tag.description;
|
|
333
336
|
case "since":
|
|
334
337
|
return !tag.type && tag.name;
|
|
335
338
|
case "returns":
|
|
@@ -360,7 +363,8 @@ const validateJSDocComment = (fieldType, jsdocComment, node, moduleDoc) => {
|
|
|
360
363
|
}
|
|
361
364
|
|
|
362
365
|
if (!isValid) {
|
|
363
|
-
|
|
366
|
+
const nodeName = node ? ` in '${node}'` : '';
|
|
367
|
+
logDocumentationError(moduleDoc.path, `Incorrect use of @${tag.tag}${nodeName}. Ensure it is part of ${fieldType} JSDoc tags.`)
|
|
364
368
|
}
|
|
365
369
|
|
|
366
370
|
return !!isValid;
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@ui5/webcomponents-tools",
|
|
3
|
-
"version": "2.20.0-rc.
|
|
3
|
+
"version": "2.20.0-rc.3",
|
|
4
4
|
"description": "UI5 Web Components: webcomponents.tools",
|
|
5
5
|
"author": "SAP SE (https://www.sap.com)",
|
|
6
6
|
"license": "Apache-2.0",
|
|
@@ -82,5 +82,5 @@
|
|
|
82
82
|
"esbuild": "^0.25.0",
|
|
83
83
|
"yargs": "^17.5.1"
|
|
84
84
|
},
|
|
85
|
-
"gitHead": "
|
|
85
|
+
"gitHead": "d1767f2375f2b81e1187f9c58bb3b0eaf28b139e"
|
|
86
86
|
}
|