ochre-sdk 1.0.52 → 1.0.54
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/dist/constants.mjs +5 -5
- package/dist/fetchers/gallery.d.mts +6 -6
- package/dist/fetchers/gallery.mjs +6 -8
- package/dist/fetchers/item-children.mjs +3 -6
- package/dist/fetchers/item-links.mjs +2 -4
- package/dist/fetchers/item.mjs +12 -7
- package/dist/fetchers/set/items.d.mts +7 -7
- package/dist/fetchers/set/items.mjs +20 -22
- package/dist/fetchers/set/property-values.d.mts +8 -8
- package/dist/fetchers/set/property-values.mjs +48 -46
- package/dist/fetchers/website-metadata.mjs +6 -7
- package/dist/fetchers/website.mjs +1 -1
- package/dist/getters.mjs +21 -27
- package/dist/helpers.mjs +1 -1
- package/dist/parsers/helpers.d.mts +1 -1
- package/dist/parsers/helpers.mjs +2 -2
- package/dist/parsers/index.mjs +62 -84
- package/dist/parsers/multilingual.d.mts +13 -13
- package/dist/parsers/multilingual.mjs +55 -63
- package/dist/parsers/string.mjs +58 -51
- package/dist/parsers/website/index.mjs +54 -28
- package/dist/parsers/website/reader.mjs +3 -4
- package/dist/query.d.mts +1 -1
- package/dist/query.mjs +89 -92
- package/dist/schemas.d.mts +3 -3
- package/dist/schemas.mjs +5 -5
- package/dist/types/index.d.mts +12 -3
- package/dist/types/website.d.mts +5 -0
- package/dist/{utils.d.mts → utilities.d.mts} +2 -4
- package/dist/{utils.mjs → utilities.mjs} +4 -4
- package/dist/xml/schemas.mjs +70 -18
- package/dist/xml/types.d.mts +15 -4
- package/package.json +6 -6
|
@@ -13,7 +13,8 @@ function normalizeInputText(text) {
|
|
|
13
13
|
}
|
|
14
14
|
function normalizeAliases(aliases) {
|
|
15
15
|
const normalizedAliases = [];
|
|
16
|
-
|
|
16
|
+
const candidateAliases = aliases ?? [];
|
|
17
|
+
for (const alias of candidateAliases) if (alias !== "") normalizedAliases.push(alias);
|
|
17
18
|
return normalizedAliases;
|
|
18
19
|
}
|
|
19
20
|
function entriesFromTexts(texts) {
|
|
@@ -27,15 +28,11 @@ function entriesFromTexts(texts) {
|
|
|
27
28
|
function cloneContent(content) {
|
|
28
29
|
const clonedContent = {};
|
|
29
30
|
const entriesByLanguage = Object.entries(content);
|
|
30
|
-
for (const [language, entries] of entriesByLanguage) {
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
isPrimary: entry.isPrimary
|
|
36
|
-
});
|
|
37
|
-
clonedContent[language] = normalizePrimary(clonedEntries);
|
|
38
|
-
}
|
|
31
|
+
for (const [language, entries] of entriesByLanguage) clonedContent[language] = normalizePrimary(Array.from(entries ?? [], (entry) => ({
|
|
32
|
+
text: entry.text,
|
|
33
|
+
richText: entry.richText,
|
|
34
|
+
isPrimary: entry.isPrimary
|
|
35
|
+
})));
|
|
39
36
|
return clonedContent;
|
|
40
37
|
}
|
|
41
38
|
function normalizePrimary(entries) {
|
|
@@ -54,35 +51,18 @@ function getLanguagesWithEntries(content, languages) {
|
|
|
54
51
|
}
|
|
55
52
|
function getImplicitLanguages(content, options) {
|
|
56
53
|
const languages = [];
|
|
57
|
-
|
|
54
|
+
const availableLanguages = options.availableLanguages ?? [];
|
|
55
|
+
for (const language of availableLanguages) if (!languages.includes(language)) languages.push(language);
|
|
58
56
|
for (const language of Object.keys(content)) if (!languages.includes(language)) languages.push(language);
|
|
59
57
|
return languages.length > 0 ? languages : [...DEFAULT_LANGUAGES];
|
|
60
58
|
}
|
|
61
59
|
function isInternalInit(value) {
|
|
62
|
-
return typeof value === "object" && value != null && MULTILINGUAL_STRING_INTERNAL_INIT
|
|
60
|
+
return typeof value === "object" && value != null && Object.hasOwn(value, MULTILINGUAL_STRING_INTERNAL_INIT);
|
|
63
61
|
}
|
|
64
62
|
/**
|
|
65
63
|
* Multilingual string
|
|
66
64
|
*/
|
|
67
65
|
var MultilingualString = class MultilingualString {
|
|
68
|
-
_content;
|
|
69
|
-
_options;
|
|
70
|
-
_availableLanguages;
|
|
71
|
-
_aliases;
|
|
72
|
-
constructor(content = {}, languages, options = {}) {
|
|
73
|
-
if (isInternalInit(content)) {
|
|
74
|
-
this._content = Object.freeze(cloneContent(content.content));
|
|
75
|
-
this._options = Object.freeze({ ...content.options });
|
|
76
|
-
this._availableLanguages = Object.freeze([...content.availableLanguages]);
|
|
77
|
-
this._aliases = Object.freeze([...content.options.aliases]);
|
|
78
|
-
return;
|
|
79
|
-
}
|
|
80
|
-
const parsed = languages === void 0 ? MultilingualString.fromObject(content, void 0, options) : MultilingualString.fromObject(content, languages, options);
|
|
81
|
-
this._content = parsed._content;
|
|
82
|
-
this._options = parsed._options;
|
|
83
|
-
this._availableLanguages = parsed._availableLanguages;
|
|
84
|
-
this._aliases = parsed._aliases;
|
|
85
|
-
}
|
|
86
66
|
static fromNormalized(content, options, availableLanguages) {
|
|
87
67
|
return new MultilingualString({
|
|
88
68
|
[MULTILINGUAL_STRING_INTERNAL_INIT]: true,
|
|
@@ -94,8 +74,8 @@ var MultilingualString = class MultilingualString {
|
|
|
94
74
|
static fromObject(content, languages, options = {}) {
|
|
95
75
|
const entries = {};
|
|
96
76
|
for (const [language, text] of Object.entries(content)) if (text != null) entries[language] = [text];
|
|
97
|
-
if (languages === void 0) return
|
|
98
|
-
return
|
|
77
|
+
if (languages === void 0) return this.fromEntries(entries, void 0, options);
|
|
78
|
+
return this.fromEntries(entries, languages, options);
|
|
99
79
|
}
|
|
100
80
|
static fromEntries(content, languages, options = {}) {
|
|
101
81
|
if (languages === void 0) {
|
|
@@ -108,7 +88,7 @@ var MultilingualString = class MultilingualString {
|
|
|
108
88
|
availableLanguages: actualLanguages,
|
|
109
89
|
aliases: normalizeAliases(options.aliases)
|
|
110
90
|
};
|
|
111
|
-
return
|
|
91
|
+
return this.fromNormalized(normalizedContent, defaultOptions, availableLanguages);
|
|
112
92
|
}
|
|
113
93
|
const normalizedContent = {};
|
|
114
94
|
for (const language of languages) {
|
|
@@ -121,21 +101,21 @@ var MultilingualString = class MultilingualString {
|
|
|
121
101
|
availableLanguages: languages,
|
|
122
102
|
aliases: normalizeAliases(options.aliases)
|
|
123
103
|
};
|
|
124
|
-
return
|
|
104
|
+
return this.fromNormalized(normalizedContent, defaultOptions, availableLanguages);
|
|
125
105
|
}
|
|
126
106
|
static create(language, text, languages, options = {}) {
|
|
127
|
-
if (languages === void 0) return
|
|
107
|
+
if (languages === void 0) return this.fromObject({ [language]: text }, void 0, {
|
|
128
108
|
...options,
|
|
129
109
|
defaultLanguage: language
|
|
130
110
|
});
|
|
131
|
-
return
|
|
111
|
+
return this.fromObject({ [language]: text }, languages, {
|
|
132
112
|
...options,
|
|
133
113
|
defaultLanguage: language
|
|
134
114
|
});
|
|
135
115
|
}
|
|
136
116
|
static empty(languages, options = {}) {
|
|
137
|
-
if (languages === void 0) return
|
|
138
|
-
return
|
|
117
|
+
if (languages === void 0) return this.fromObject({}, void 0, options);
|
|
118
|
+
return this.fromObject({}, languages, options);
|
|
139
119
|
}
|
|
140
120
|
static fromJSON(json, languages, options = {}) {
|
|
141
121
|
const content = json.content;
|
|
@@ -143,8 +123,26 @@ var MultilingualString = class MultilingualString {
|
|
|
143
123
|
...options,
|
|
144
124
|
aliases: json.aliases
|
|
145
125
|
};
|
|
146
|
-
if (languages === void 0) return
|
|
147
|
-
return
|
|
126
|
+
if (languages === void 0) return this.fromEntries(content, void 0, mergedOptions);
|
|
127
|
+
return this.fromEntries(content, languages, mergedOptions);
|
|
128
|
+
}
|
|
129
|
+
_content;
|
|
130
|
+
_options;
|
|
131
|
+
_availableLanguages;
|
|
132
|
+
_aliases;
|
|
133
|
+
constructor(content = {}, languages, options = {}) {
|
|
134
|
+
if (isInternalInit(content)) {
|
|
135
|
+
this._content = Object.freeze(cloneContent(content.content));
|
|
136
|
+
this._options = Object.freeze({ ...content.options });
|
|
137
|
+
this._availableLanguages = Object.freeze([...content.availableLanguages]);
|
|
138
|
+
this._aliases = Object.freeze([...content.options.aliases]);
|
|
139
|
+
return;
|
|
140
|
+
}
|
|
141
|
+
const parsed = languages === void 0 ? MultilingualString.fromObject(content, void 0, options) : MultilingualString.fromObject(content, languages, options);
|
|
142
|
+
this._content = parsed._content;
|
|
143
|
+
this._options = parsed._options;
|
|
144
|
+
this._availableLanguages = parsed._availableLanguages;
|
|
145
|
+
this._aliases = parsed._aliases;
|
|
148
146
|
}
|
|
149
147
|
getPrimaryEntry(language) {
|
|
150
148
|
const entries = this._content[language] ?? [];
|
|
@@ -207,17 +205,13 @@ var MultilingualString = class MultilingualString {
|
|
|
207
205
|
* Get all text entries in a specific language without fallback
|
|
208
206
|
*/
|
|
209
207
|
getExactTexts(language) {
|
|
210
|
-
|
|
211
|
-
for (const entry of this._content[language] ?? []) texts.push(entry.text);
|
|
212
|
-
return texts;
|
|
208
|
+
return Array.from(this._content[language] ?? [], (entry) => entry.text);
|
|
213
209
|
}
|
|
214
210
|
/**
|
|
215
211
|
* Get all rich text entries in a specific language without fallback
|
|
216
212
|
*/
|
|
217
213
|
getExactRichTexts(language) {
|
|
218
|
-
|
|
219
|
-
for (const entry of this._content[language] ?? []) texts.push(entry.richText);
|
|
220
|
-
return texts;
|
|
214
|
+
return Array.from(this._content[language] ?? [], (entry) => entry.richText);
|
|
221
215
|
}
|
|
222
216
|
/**
|
|
223
217
|
* Get all text entries in a specific language with fallback
|
|
@@ -243,13 +237,11 @@ var MultilingualString = class MultilingualString {
|
|
|
243
237
|
* Get all entries in a specific language without fallback
|
|
244
238
|
*/
|
|
245
239
|
getExactEntries(language) {
|
|
246
|
-
|
|
247
|
-
for (const entry of this._content[language] ?? []) entries.push({
|
|
240
|
+
return Array.from(this._content[language] ?? [], (entry) => ({
|
|
248
241
|
text: entry.text,
|
|
249
242
|
richText: entry.richText,
|
|
250
243
|
isPrimary: entry.isPrimary
|
|
251
|
-
});
|
|
252
|
-
return entries;
|
|
244
|
+
}));
|
|
253
245
|
}
|
|
254
246
|
/**
|
|
255
247
|
* Get all entries in a specific language with fallback
|
|
@@ -301,7 +293,10 @@ var MultilingualString = class MultilingualString {
|
|
|
301
293
|
* Check if the multilingual string has any content
|
|
302
294
|
*/
|
|
303
295
|
hasContent() {
|
|
304
|
-
for (const language of this._availableLanguages)
|
|
296
|
+
for (const language of this._availableLanguages) {
|
|
297
|
+
const entries = this._content[language] ?? [];
|
|
298
|
+
for (const entry of entries) if (entry.text.trim().length > 0 || entry.richText.trim().length > 0) return true;
|
|
299
|
+
}
|
|
305
300
|
return false;
|
|
306
301
|
}
|
|
307
302
|
/**
|
|
@@ -357,27 +352,24 @@ var MultilingualString = class MultilingualString {
|
|
|
357
352
|
/**
|
|
358
353
|
* Transform all language versions (returns new instance)
|
|
359
354
|
*/
|
|
360
|
-
map(
|
|
355
|
+
map(function_) {
|
|
361
356
|
const newContent = {};
|
|
362
|
-
for (const language of this._availableLanguages) {
|
|
363
|
-
|
|
364
|
-
|
|
365
|
-
|
|
366
|
-
|
|
367
|
-
isPrimary: entry.isPrimary
|
|
368
|
-
});
|
|
369
|
-
newContent[language] = normalizePrimary(mappedEntries);
|
|
370
|
-
}
|
|
357
|
+
for (const language of this._availableLanguages) newContent[language] = normalizePrimary(Array.from(this._content[language] ?? [], (entry) => ({
|
|
358
|
+
text: function_(entry.text, language),
|
|
359
|
+
richText: function_(entry.richText, language),
|
|
360
|
+
isPrimary: entry.isPrimary
|
|
361
|
+
})));
|
|
371
362
|
return MultilingualString.fromNormalized(newContent, this._options, this._availableLanguages);
|
|
372
363
|
}
|
|
373
364
|
/**
|
|
374
365
|
* Filter languages based on predicate (returns new instance)
|
|
375
366
|
*/
|
|
376
|
-
filter(
|
|
367
|
+
filter(shouldInclude) {
|
|
377
368
|
const newContent = {};
|
|
378
369
|
for (const language of this._availableLanguages) {
|
|
379
370
|
const entries = [];
|
|
380
|
-
|
|
371
|
+
const languageEntries = this._content[language] ?? [];
|
|
372
|
+
for (const entry of languageEntries) if (shouldInclude(entry.text, language)) entries.push(entry);
|
|
381
373
|
newContent[language] = normalizePrimary(entries);
|
|
382
374
|
}
|
|
383
375
|
const newAvailableLanguages = getLanguagesWithEntries(newContent, this._options.availableLanguages);
|
package/dist/parsers/string.mjs
CHANGED
|
@@ -174,12 +174,12 @@ function parsePropertyValueText(property, options) {
|
|
|
174
174
|
function normalizePropertyToken(value) {
|
|
175
175
|
return value.trim().toLowerCase().replaceAll(/[\s_]+/g, "-");
|
|
176
176
|
}
|
|
177
|
-
function
|
|
177
|
+
function hasMatchingPropertyLabel(property, uuid, tokens, options) {
|
|
178
178
|
if (uuid !== "" && property.label.uuid === uuid) return true;
|
|
179
179
|
const label = normalizePropertyToken(parseContentLikeForLanguage(property.label, options));
|
|
180
180
|
return tokens.includes(label);
|
|
181
181
|
}
|
|
182
|
-
function
|
|
182
|
+
function hasMatchingPropertyValue(property, uuid, tokens, options) {
|
|
183
183
|
if (uuid !== "" && getPropertyValueUuid(property) === uuid) return true;
|
|
184
184
|
const value = normalizePropertyToken(parsePropertyValueText(property, options));
|
|
185
185
|
return tokens.includes(value);
|
|
@@ -191,33 +191,35 @@ function extractAnnotationMetadata(item, options) {
|
|
|
191
191
|
};
|
|
192
192
|
const itemProperty = item.properties?.property[0];
|
|
193
193
|
if (itemProperty == null) return result;
|
|
194
|
-
if (!
|
|
195
|
-
|
|
196
|
-
|
|
194
|
+
if (!hasMatchingPropertyLabel(itemProperty, "f1c131b6-1498-48a4-95bf-a9edae9fd518", ["presentation"], options) || !hasMatchingPropertyValue(itemProperty, "b9ca2732-78f4-416e-b77f-dae7647e68a9", [TEXT_ANNOTATION_TOKEN], options)) return result;
|
|
195
|
+
const textAnnotationProperties = itemProperty.property ?? [];
|
|
196
|
+
for (const textAnnotationProperty of textAnnotationProperties) {
|
|
197
|
+
if (hasMatchingPropertyValue(textAnnotationProperty, "c7f6a08a-f07b-49b6-bcb1-af485da3c58f", [HOVER_CARD_TOKEN], options)) {
|
|
197
198
|
result.linkVariant = "hover-card";
|
|
198
199
|
continue;
|
|
199
200
|
}
|
|
200
|
-
if (
|
|
201
|
+
if (hasMatchingPropertyValue(textAnnotationProperty, "bf4476ab-6bc8-40d0-a001-1446213c72ce", [ITEM_PAGE_TOKEN], options)) {
|
|
201
202
|
result.linkVariant = "item-page";
|
|
202
203
|
continue;
|
|
203
204
|
}
|
|
204
|
-
if (
|
|
205
|
+
if (hasMatchingPropertyValue(textAnnotationProperty, "9d52db95-a9cf-45f7-a0bf-fc9ba9f0aae0", [ENTRY_PAGE_TOKEN], options)) {
|
|
205
206
|
result.linkVariant = "entry-page";
|
|
206
207
|
continue;
|
|
207
208
|
}
|
|
208
|
-
if (
|
|
209
|
+
if (hasMatchingPropertyValue(textAnnotationProperty, "3e6f86ab-df81-45ae-8257-e2867357df56", [TEXT_STYLING_TOKEN], options)) {
|
|
209
210
|
let variant = "block";
|
|
210
211
|
let size = "md";
|
|
211
212
|
let headingLevel = null;
|
|
212
213
|
const cssStyles = [];
|
|
213
214
|
const textStylingProperties = textAnnotationProperty.property ?? [];
|
|
214
215
|
for (const textStylingProperty of textStylingProperties) {
|
|
215
|
-
if (
|
|
216
|
+
if (hasMatchingPropertyLabel(textStylingProperty, "e1647bef-d801-4100-bdde-d081c422f763", [VARIANT_TOKEN], options)) {
|
|
216
217
|
variant = parsePropertyValueText(textStylingProperty, options);
|
|
217
|
-
|
|
218
|
+
const nestedProperties = textStylingProperty.property ?? [];
|
|
219
|
+
for (const nestedProperty of nestedProperties) if (hasMatchingPropertyLabel(nestedProperty, "", ["size"], options)) size = parsePropertyValueText(nestedProperty, options);
|
|
218
220
|
continue;
|
|
219
221
|
}
|
|
220
|
-
if (
|
|
222
|
+
if (hasMatchingPropertyLabel(textStylingProperty, "d4266f0b-3f8d-4b32-8c15-4b229c8bb11e", [HEADING_LEVEL_TOKEN], options)) {
|
|
221
223
|
headingLevel = parsePropertyValueText(textStylingProperty, options);
|
|
222
224
|
continue;
|
|
223
225
|
}
|
|
@@ -232,7 +234,6 @@ function extractAnnotationMetadata(item, options) {
|
|
|
232
234
|
headingLevel,
|
|
233
235
|
cssStyles
|
|
234
236
|
};
|
|
235
|
-
continue;
|
|
236
237
|
}
|
|
237
238
|
}
|
|
238
239
|
return result;
|
|
@@ -243,10 +244,10 @@ function hasRichTextEnvelope(item) {
|
|
|
243
244
|
function parseXMLStringItem(item, contentItem, options) {
|
|
244
245
|
if (!(item.payload != null && item.payload !== "" || item.string != null) && getXMLRichTextLinks(item).length === 0) {
|
|
245
246
|
const hasNewlineWhitespace = item.whitespace?.split(" ").includes("newline") === true;
|
|
246
|
-
const
|
|
247
|
-
if (hasNewlineWhitespace && options.rendering === "plain") return
|
|
248
|
-
if (hasNewlineWhitespace && options.rendering === "rawMDX") return
|
|
249
|
-
if (hasNewlineWhitespace && options.rendering === "rich") return
|
|
247
|
+
const isNextContainingNewlineWhitespace = options.nextItem?.whitespace?.split(" ").includes("newline") === true;
|
|
248
|
+
if (hasNewlineWhitespace && options.rendering === "plain") return isNextContainingNewlineWhitespace ? "\n" : "\n\n";
|
|
249
|
+
if (hasNewlineWhitespace && options.rendering === "rawMDX") return isNextContainingNewlineWhitespace ? "\n<br />" : "\n<br />\n";
|
|
250
|
+
if (hasNewlineWhitespace && options.rendering === "rich") return isNextContainingNewlineWhitespace ? "<br />\n" : "<br />\n<br />\n";
|
|
250
251
|
return applyNewlineWhitespace("", item.whitespace, options.rendering);
|
|
251
252
|
}
|
|
252
253
|
if (hasRichTextEnvelope(item)) {
|
|
@@ -319,9 +320,11 @@ function createInternalLinkComponent(properties) {
|
|
|
319
320
|
function getXMLRichTextLinks(item) {
|
|
320
321
|
const links = [];
|
|
321
322
|
let fallbackIndex = 0;
|
|
322
|
-
|
|
323
|
+
const linkGroups = Object.values(item.links ?? {});
|
|
324
|
+
for (const rawLinks of linkGroups) {
|
|
323
325
|
if (!Array.isArray(rawLinks)) continue;
|
|
324
|
-
for (const rawLink of rawLinks)
|
|
326
|
+
for (const rawLink of rawLinks) {
|
|
327
|
+
if (!(isXMLRichTextLink(rawLink) && !isTextAnnotationMarkerLink(rawLink))) continue;
|
|
325
328
|
links.push({
|
|
326
329
|
link: rawLink,
|
|
327
330
|
fallbackIndex
|
|
@@ -350,34 +353,30 @@ function renderRichTextItem(item, linkString, contentItem, options) {
|
|
|
350
353
|
const contentText = (rendering === "plain" ? linkContent.getExactText(contentItem.lang) : linkContent.getExactRichText(contentItem.lang)) ?? "";
|
|
351
354
|
if ("type" in link && link.type != null) switch (link.type) {
|
|
352
355
|
case "IIIF":
|
|
353
|
-
case "image":
|
|
354
|
-
|
|
355
|
-
|
|
356
|
-
|
|
357
|
-
|
|
358
|
-
|
|
359
|
-
|
|
360
|
-
|
|
361
|
-
|
|
362
|
-
|
|
363
|
-
|
|
364
|
-
|
|
365
|
-
|
|
366
|
-
|
|
367
|
-
|
|
368
|
-
|
|
369
|
-
|
|
370
|
-
|
|
371
|
-
|
|
372
|
-
|
|
373
|
-
|
|
374
|
-
|
|
375
|
-
text: linkString,
|
|
376
|
-
content: contentText
|
|
377
|
-
});
|
|
378
|
-
result += component;
|
|
379
|
-
}
|
|
356
|
+
case "image": {
|
|
357
|
+
let component;
|
|
358
|
+
if ("rend" in link && link.rend === "inline") component = createMDXComponent("inlineImage", {
|
|
359
|
+
uuid: getLinkStringProperty(link, "uuid"),
|
|
360
|
+
href: getLinkStringProperty(link, "href") ?? void 0,
|
|
361
|
+
height: getLinkStringProperty(link, "height") ?? void 0,
|
|
362
|
+
width: getLinkStringProperty(link, "width") ?? void 0,
|
|
363
|
+
content: contentText,
|
|
364
|
+
text: linkString
|
|
365
|
+
});
|
|
366
|
+
else if (link.publicationDateTime != null) component = createInternalLinkComponent({
|
|
367
|
+
uuid: getLinkStringProperty(link, "uuid"),
|
|
368
|
+
text: linkString,
|
|
369
|
+
content: contentText,
|
|
370
|
+
annotationMetadata
|
|
371
|
+
});
|
|
372
|
+
else component = createMDXComponent("tooltipSpan", {
|
|
373
|
+
uuid: getLinkStringProperty(link, "uuid"),
|
|
374
|
+
text: linkString,
|
|
375
|
+
content: contentText
|
|
376
|
+
});
|
|
377
|
+
result += component;
|
|
380
378
|
break;
|
|
379
|
+
}
|
|
381
380
|
case "internalDocument": {
|
|
382
381
|
const component = createInternalLinkComponent({
|
|
383
382
|
uuid: getLinkStringProperty(link, "uuid"),
|
|
@@ -390,11 +389,7 @@ function renderRichTextItem(item, linkString, contentItem, options) {
|
|
|
390
389
|
break;
|
|
391
390
|
}
|
|
392
391
|
case "externalDocument": {
|
|
393
|
-
const component = link.publicationDateTime != null ?
|
|
394
|
-
uuid: getLinkStringProperty(link, "uuid"),
|
|
395
|
-
text: linkString,
|
|
396
|
-
content: contentText
|
|
397
|
-
}) : createMDXComponent("tooltipSpan", {
|
|
392
|
+
const component = createMDXComponent(link.publicationDateTime != null ? "documentLink" : "tooltipSpan", {
|
|
398
393
|
uuid: getLinkStringProperty(link, "uuid"),
|
|
399
394
|
text: linkString,
|
|
400
395
|
content: contentText
|
|
@@ -412,6 +407,18 @@ function renderRichTextItem(item, linkString, contentItem, options) {
|
|
|
412
407
|
result += component;
|
|
413
408
|
break;
|
|
414
409
|
}
|
|
410
|
+
default:
|
|
411
|
+
result += link.publicationDateTime != null ? createInternalLinkComponent({
|
|
412
|
+
uuid: getLinkStringProperty(link, "uuid"),
|
|
413
|
+
text: linkString,
|
|
414
|
+
content: contentText,
|
|
415
|
+
annotationMetadata
|
|
416
|
+
}) : createMDXComponent("tooltipSpan", {
|
|
417
|
+
uuid: getLinkStringProperty(link, "uuid"),
|
|
418
|
+
text: linkString,
|
|
419
|
+
content: contentText
|
|
420
|
+
});
|
|
421
|
+
break;
|
|
415
422
|
}
|
|
416
423
|
else if (link.publicationDateTime != null) {
|
|
417
424
|
const component = createInternalLinkComponent({
|
|
@@ -470,7 +477,7 @@ function parseXMLContentItem(contentItem, options) {
|
|
|
470
477
|
rendering: "rich",
|
|
471
478
|
rawMDXBlocks
|
|
472
479
|
}));
|
|
473
|
-
for (const [index, rawMDXBlock] of rawMDXBlocks.entries()) serializedRichText = serializedRichText.replaceAll(`${RAW_MDX_BLOCK_PLACEHOLDER_PREFIX}${index}${RAW_MDX_BLOCK_PLACEHOLDER_SUFFIX}`, rawMDXBlock);
|
|
480
|
+
for (const [index, rawMDXBlock] of rawMDXBlocks.entries()) serializedRichText = serializedRichText.replaceAll(`${RAW_MDX_BLOCK_PLACEHOLDER_PREFIX}${index}${RAW_MDX_BLOCK_PLACEHOLDER_SUFFIX}`, () => rawMDXBlock);
|
|
474
481
|
return {
|
|
475
482
|
text: parseNestedStringItems(contentItem.string, contentItem, {
|
|
476
483
|
...options,
|
|
@@ -8,8 +8,8 @@ import * as v from "valibot";
|
|
|
8
8
|
function isWebsiteLink(link, category) {
|
|
9
9
|
return link.category === category;
|
|
10
10
|
}
|
|
11
|
-
function findWebsiteLink(links, category,
|
|
12
|
-
for (const link of links) if (isWebsiteLink(link, category) && (
|
|
11
|
+
function findWebsiteLink(links, category, isMatch) {
|
|
12
|
+
for (const link of links) if (isWebsiteLink(link, category) && (isMatch == null || isMatch(link))) return link;
|
|
13
13
|
return null;
|
|
14
14
|
}
|
|
15
15
|
function findWebsiteLinkByCategories(links, categories) {
|
|
@@ -26,7 +26,8 @@ function transformPermanentIdentificationUrlToItemLink(url) {
|
|
|
26
26
|
}
|
|
27
27
|
function normalizeWebsiteResources(resources) {
|
|
28
28
|
const normalized = [];
|
|
29
|
-
|
|
29
|
+
const resourcesToNormalize = resources ?? [];
|
|
30
|
+
for (const resource of resourcesToNormalize) {
|
|
30
31
|
if ("identification" in resource) {
|
|
31
32
|
normalized.push(resource);
|
|
32
33
|
continue;
|
|
@@ -45,7 +46,8 @@ function prefixSlug(slug, slugPrefix) {
|
|
|
45
46
|
return `${slugPrefix}/${slug}`;
|
|
46
47
|
}
|
|
47
48
|
function collectWebsitePageSlugs(resources, options, slugPrefix, pageSlugsByUuid = /* @__PURE__ */ new Map(), segmentSlugPrefix = slugPrefix) {
|
|
48
|
-
|
|
49
|
+
const slugResources = resources ?? [];
|
|
50
|
+
for (const resource of slugResources) {
|
|
49
51
|
if ("segments" in resource) {
|
|
50
52
|
for (const tree of resource.segments.tree) {
|
|
51
53
|
const segmentSlug = tree.identification.abbreviation == null ? null : parseStringContent(tree.identification.abbreviation, options);
|
|
@@ -124,7 +126,7 @@ function parseResponsiveCssStyles(properties) {
|
|
|
124
126
|
* @returns Parsed bounds object
|
|
125
127
|
*/
|
|
126
128
|
function parseBounds(bounds) {
|
|
127
|
-
const [southWest, northEast] = bounds.trim().startsWith("[") ? parseJsonBounds(bounds) : bounds.split(";").map((pair) => pair.split(",").map((coordinate) => Number
|
|
129
|
+
const [southWest, northEast] = bounds.trim().startsWith("[") ? parseJsonBounds(bounds) : bounds.split(";").map((pair) => pair.split(",").map((coordinate) => Number(coordinate.trim())));
|
|
128
130
|
if (southWest?.length !== 2 || northEast?.length !== 2 || southWest.some((coordinate) => Number.isNaN(coordinate)) || northEast.some((coordinate) => Number.isNaN(coordinate))) throw new Error(`Invalid bounds: ${bounds}`, { cause: bounds });
|
|
129
131
|
return [[southWest[0], southWest[1]], [northEast[0], northEast[1]]];
|
|
130
132
|
}
|
|
@@ -175,13 +177,11 @@ function parseAllOptionContexts(options, parserOptions) {
|
|
|
175
177
|
}
|
|
176
178
|
function parseWebsiteScopes(scopes, options) {
|
|
177
179
|
if (scopes == null) return null;
|
|
178
|
-
|
|
179
|
-
for (const scope of scopes.scope) parsedScopes.push({
|
|
180
|
+
return Array.from(scopes.scope, (scope) => ({
|
|
180
181
|
uuid: scope.uuid.payload,
|
|
181
182
|
type: scope.uuid.type,
|
|
182
183
|
identification: parseIdentification(scope.identification, options)
|
|
183
|
-
});
|
|
184
|
-
return parsedScopes;
|
|
184
|
+
}));
|
|
185
185
|
}
|
|
186
186
|
function parseWebsiteOptions(rawOptions, options) {
|
|
187
187
|
const parsedOptions = {
|
|
@@ -189,7 +189,9 @@ function parseWebsiteOptions(rawOptions, options) {
|
|
|
189
189
|
contextTree: rawOptions == null ? null : parseAllOptionContexts(rawOptions, options),
|
|
190
190
|
labels: { title: null }
|
|
191
191
|
};
|
|
192
|
-
|
|
192
|
+
const notes = parseNotes(rawOptions?.notes, options);
|
|
193
|
+
for (const note of notes) {
|
|
194
|
+
if (note.title?.getText() !== "Title label") continue;
|
|
193
195
|
parsedOptions.labels.title = note.content;
|
|
194
196
|
break;
|
|
195
197
|
}
|
|
@@ -200,7 +202,13 @@ function parseStylesheets(styles) {
|
|
|
200
202
|
for (const style of styles) {
|
|
201
203
|
const defaultStyles = [];
|
|
202
204
|
for (const [label, value] of Object.entries(style)) {
|
|
203
|
-
if (
|
|
205
|
+
if ([
|
|
206
|
+
"variableUuid",
|
|
207
|
+
"valueUuid",
|
|
208
|
+
"category",
|
|
209
|
+
"payload",
|
|
210
|
+
"content"
|
|
211
|
+
].includes(label)) continue;
|
|
204
212
|
const valueString = value?.toString();
|
|
205
213
|
if (valueString != null) defaultStyles.push({
|
|
206
214
|
label,
|
|
@@ -389,10 +397,8 @@ function parseWebElementProperties(componentProperty, elementResource, options,
|
|
|
389
397
|
if (href === null) {
|
|
390
398
|
href = parseWebsiteLinkTarget(componentReader.valueNode("link-to"), context);
|
|
391
399
|
if (href === null) throw new Error(formatComponentError("Properties “navigate-to” or “link-to” not found", componentName, elementResource), { cause: componentProperty });
|
|
392
|
-
|
|
393
|
-
|
|
394
|
-
isRelative = !href.startsWith("/");
|
|
395
|
-
}
|
|
400
|
+
isExternal = href.startsWith("http");
|
|
401
|
+
isRelative = !href.startsWith("/");
|
|
396
402
|
}
|
|
397
403
|
const startIcon = componentReader.value("start-icon");
|
|
398
404
|
const endIcon = componentReader.value("end-icon");
|
|
@@ -406,6 +412,14 @@ function parseWebElementProperties(componentProperty, elementResource, options,
|
|
|
406
412
|
description: imageLink.description,
|
|
407
413
|
quality: "high"
|
|
408
414
|
};
|
|
415
|
+
const childResources = elementResource.resource ? normalizeWebsiteResources(elementResource.resource) : [];
|
|
416
|
+
const elements = [];
|
|
417
|
+
for (const childResource of childResources) {
|
|
418
|
+
const childReader = websitePresentationReader(childResource.properties ? parseSimplifiedProperties(childResource.properties, options) : []);
|
|
419
|
+
if (childReader.value("presentation") !== "element") continue;
|
|
420
|
+
if (childReader.nestedByValue("presentation", "element").value("component") === "button") continue;
|
|
421
|
+
elements.push(parseWebElement(childResource, options, context));
|
|
422
|
+
}
|
|
409
423
|
properties = {
|
|
410
424
|
component: "button",
|
|
411
425
|
variant,
|
|
@@ -415,7 +429,8 @@ function parseWebElementProperties(componentProperty, elementResource, options,
|
|
|
415
429
|
label: elementResource.document && "content" in elementResource.document ? parseXMLContent(elementResource.document, options) : null,
|
|
416
430
|
startIcon,
|
|
417
431
|
endIcon,
|
|
418
|
-
image
|
|
432
|
+
image,
|
|
433
|
+
elements
|
|
419
434
|
};
|
|
420
435
|
break;
|
|
421
436
|
}
|
|
@@ -492,28 +507,27 @@ function parseWebElementProperties(componentProperty, elementResource, options,
|
|
|
492
507
|
case "image": {
|
|
493
508
|
if (websiteLinks.length === 0) throw new Error(formatComponentError("No links found", componentName, elementResource), { cause: componentProperty });
|
|
494
509
|
const imageQuality = componentReader.valueOr("image-quality", "high");
|
|
495
|
-
const images =
|
|
496
|
-
for (const link of websiteLinks) images.push({
|
|
510
|
+
const images = Array.from(websiteLinks, (link) => ({
|
|
497
511
|
uuid: link.uuid,
|
|
498
512
|
label: link.identification.label,
|
|
499
513
|
width: "image" in link ? link.image?.width ?? 0 : 0,
|
|
500
514
|
height: "image" in link ? link.image?.height ?? 0 : 0,
|
|
501
515
|
description: link.description,
|
|
502
516
|
quality: imageQuality
|
|
503
|
-
});
|
|
517
|
+
}));
|
|
504
518
|
const variant = componentReader.valueOr("variant", "default");
|
|
505
519
|
const captionLayout = componentReader.valueOr("layout-caption", "bottom");
|
|
506
520
|
let width = null;
|
|
507
521
|
const widthProperty = componentReader.value("width");
|
|
508
522
|
if (widthProperty !== null) {
|
|
509
523
|
if (typeof widthProperty === "number") width = widthProperty;
|
|
510
|
-
else if (typeof widthProperty === "string") width = Number
|
|
524
|
+
else if (typeof widthProperty === "string") width = Number(widthProperty);
|
|
511
525
|
}
|
|
512
526
|
let height = null;
|
|
513
527
|
const heightProperty = componentReader.value("height");
|
|
514
528
|
if (heightProperty !== null) {
|
|
515
529
|
if (typeof heightProperty === "number") height = heightProperty;
|
|
516
|
-
else if (typeof heightProperty === "string") height = Number
|
|
530
|
+
else if (typeof heightProperty === "string") height = Number(heightProperty);
|
|
517
531
|
}
|
|
518
532
|
const isFullWidth = componentReader.valueOr("is-full-width", true);
|
|
519
533
|
const isFullHeight = componentReader.valueOr("is-full-height", true);
|
|
@@ -529,7 +543,7 @@ function parseWebElementProperties(componentProperty, elementResource, options,
|
|
|
529
543
|
const secondsPerImageProperty = variantReader.value("seconds-per-image");
|
|
530
544
|
if (secondsPerImageProperty !== null) {
|
|
531
545
|
if (typeof secondsPerImageProperty === "number") secondsPerImage = secondsPerImageProperty;
|
|
532
|
-
else if (typeof secondsPerImageProperty === "string") secondsPerImage = Number
|
|
546
|
+
else if (typeof secondsPerImageProperty === "string") secondsPerImage = Number(secondsPerImageProperty);
|
|
533
547
|
}
|
|
534
548
|
}
|
|
535
549
|
carouselOptions = { secondsPerImage };
|
|
@@ -601,8 +615,8 @@ function parseWebElementProperties(componentProperty, elementResource, options,
|
|
|
601
615
|
case "query": {
|
|
602
616
|
const setLinks = getWebsiteLinks(websiteLinks, "set");
|
|
603
617
|
if (setLinks.length === 0) throw new Error(formatComponentError("Set links not found", componentName, elementResource), { cause: componentProperty });
|
|
604
|
-
const items = [];
|
|
605
618
|
if (componentProperty.properties.length === 0) throw new Error(formatComponentError("Query properties not found", componentName, elementResource), { cause: componentProperty });
|
|
619
|
+
const items = [];
|
|
606
620
|
for (const queryItem of componentProperty.properties) {
|
|
607
621
|
const queryReader = websitePresentationReader(queryItem.properties);
|
|
608
622
|
const label = queryReader.multilingualValue("query-prompt", options);
|
|
@@ -776,7 +790,11 @@ function parseWebElement(elementResource, options, context) {
|
|
|
776
790
|
const properties = parseWebElementProperties(websitePresentationReader(websitePresentationReader(elementProperties).requiredProperty("presentation", `Presentation property not found for element (${formatXMLWebsiteResourceMetadata(elementResource)})`).properties).requiredProperty("component", `Component property not found for element (${formatXMLWebsiteResourceMetadata(elementResource)})`), elementResource, options, context);
|
|
777
791
|
const cssStyles = parseResponsiveCssStyles(elementProperties);
|
|
778
792
|
const title = parseWebTitle(elementProperties, identification, {
|
|
779
|
-
isNameDisplayed:
|
|
793
|
+
isNameDisplayed: [
|
|
794
|
+
"annotated-image",
|
|
795
|
+
"annotated-document",
|
|
796
|
+
"collection"
|
|
797
|
+
].includes(properties.component),
|
|
780
798
|
isCountDisplayed: properties.component === "collection"
|
|
781
799
|
});
|
|
782
800
|
return {
|
|
@@ -816,6 +834,7 @@ function parseWebpage(webpageResource, options, context, slugPrefix) {
|
|
|
816
834
|
isSidebarDisplayed: true,
|
|
817
835
|
isDisplayedInNavbar: true,
|
|
818
836
|
isNavbarSearchBarDisplayed: true,
|
|
837
|
+
redirect: null,
|
|
819
838
|
backgroundImage: null,
|
|
820
839
|
sidebar: null,
|
|
821
840
|
cssStyles: {
|
|
@@ -859,6 +878,11 @@ function parseWebpage(webpageResource, options, context, slugPrefix) {
|
|
|
859
878
|
returnWebpage.properties.isSidebarDisplayed = pageReader.valueOr("sidebar-displayed", true);
|
|
860
879
|
returnWebpage.properties.isBreadcrumbsDisplayed = pageReader.valueOr("breadcrumbs-displayed", false);
|
|
861
880
|
returnWebpage.properties.isNavbarSearchBarDisplayed = pageReader.valueOr("navbar-search-bar-displayed", true);
|
|
881
|
+
const redirectHref = parseWebsiteLinkTarget(pageReader.valueNode("redirect-to"), context);
|
|
882
|
+
if (redirectHref != null) returnWebpage.properties.redirect = {
|
|
883
|
+
href: redirectHref,
|
|
884
|
+
isExternal: redirectHref.startsWith("http")
|
|
885
|
+
};
|
|
862
886
|
}
|
|
863
887
|
if (imageLink != null) returnWebpage.properties.backgroundImage = {
|
|
864
888
|
uuid: imageLink.uuid,
|
|
@@ -890,7 +914,8 @@ function parseWebpageView(view, options, context) {
|
|
|
890
914
|
}
|
|
891
915
|
function parseWebsiteSegments(resources, context, options, slugPrefix) {
|
|
892
916
|
const segments = [];
|
|
893
|
-
|
|
917
|
+
const segmentResources = resources ?? [];
|
|
918
|
+
for (const resource of segmentResources) {
|
|
894
919
|
if (!("segments" in resource)) continue;
|
|
895
920
|
for (const tree of resource.segments.tree) {
|
|
896
921
|
const segmentSlug = tree.identification.abbreviation == null ? null : parseStringContent(tree.identification.abbreviation, options);
|
|
@@ -1066,7 +1091,7 @@ function parseWebBlock(blockResource, options, context) {
|
|
|
1066
1091
|
}
|
|
1067
1092
|
}
|
|
1068
1093
|
const blockResources = blockResource.resource ? normalizeWebsiteResources(blockResource.resource) : [];
|
|
1069
|
-
const
|
|
1094
|
+
const isSupportingAccordionItems = returnBlock.properties.default.layout === "accordion" || returnBlock.properties.tablet?.layout === "accordion" || returnBlock.properties.mobile?.layout === "accordion";
|
|
1070
1095
|
const blockItems = [];
|
|
1071
1096
|
for (const resource of blockResources) {
|
|
1072
1097
|
const resourceReader = websitePresentationReader(resource.properties ? parseSimplifiedProperties(resource.properties, options) : []);
|
|
@@ -1076,7 +1101,7 @@ function parseWebBlock(blockResource, options, context) {
|
|
|
1076
1101
|
case "element": {
|
|
1077
1102
|
const childResources = resource.resource ? normalizeWebsiteResources(resource.resource) : [];
|
|
1078
1103
|
const componentType = resourceReader.nestedByValue("presentation", "element").value("component");
|
|
1079
|
-
if (
|
|
1104
|
+
if (isSupportingAccordionItems && componentType === "text" && childResources.length > 0) {
|
|
1080
1105
|
const item = parseWebAccordionItem(resource, childResources, options, context);
|
|
1081
1106
|
blockItems.push(item);
|
|
1082
1107
|
break;
|
|
@@ -1204,7 +1229,8 @@ function parseWebsiteProperties(properties, websiteTree, sidebar, options) {
|
|
|
1204
1229
|
function parseContextItem(contextItemToParse, options) {
|
|
1205
1230
|
let type = "";
|
|
1206
1231
|
const levels = [];
|
|
1207
|
-
|
|
1232
|
+
const levelsToParse = contextItemToParse.levels?.level ?? [];
|
|
1233
|
+
for (const level of levelsToParse) {
|
|
1208
1234
|
const [rawVariableUuid = "", rawValueUuid] = level.payload.split(",");
|
|
1209
1235
|
const valueUuid = rawValueUuid == null || rawValueUuid.trim() === "null" ? null : rawValueUuid.trim();
|
|
1210
1236
|
type = level.dataType ?? type;
|