textbrowser 0.49.1 → 0.51.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/.ncurc.cjs +3 -0
- package/CHANGES.md +14 -0
- package/dist/WorkInfo-es.js +262 -13
- package/dist/activateCallback-es.js +72 -10
- package/dist/dist/WorkInfo-es.d.ts +331 -0
- package/dist/dist/WorkInfo-es.d.ts.map +1 -0
- package/dist/dist/activateCallback-es.d.ts +17 -0
- package/dist/dist/activateCallback-es.d.ts.map +1 -0
- package/dist/dist/index-es.d.ts +619 -0
- package/dist/dist/index-es.d.ts.map +1 -0
- package/dist/dist/sw-helper.d.ts +3 -0
- package/dist/dist/sw-helper.d.ts.map +1 -0
- package/dist/eslint.config.d.ts +126 -0
- package/dist/eslint.config.d.ts.map +1 -0
- package/dist/index-es.js +860 -134
- package/dist/index-es.min.js +2 -2
- package/dist/resources/activateCallback.d.ts +23 -0
- package/dist/resources/activateCallback.d.ts.map +1 -0
- package/dist/resources/index.d.ts +128 -0
- package/dist/resources/index.d.ts.map +1 -0
- package/dist/resources/resultsDisplay.d.ts +110 -0
- package/dist/resources/resultsDisplay.d.ts.map +1 -0
- package/dist/resources/templates/index.d.ts +59 -0
- package/dist/resources/templates/index.d.ts.map +1 -0
- package/dist/resources/templates/languageSelect.d.ts +18 -0
- package/dist/resources/templates/languageSelect.d.ts.map +1 -0
- package/dist/resources/templates/resultsDisplayClient.d.ts +26 -0
- package/dist/resources/templates/resultsDisplayClient.d.ts.map +1 -0
- package/dist/resources/templates/resultsDisplayServerOrClient.d.ts +131 -0
- package/dist/resources/templates/resultsDisplayServerOrClient.d.ts.map +1 -0
- package/dist/resources/templates/utils/dom.d.ts +15 -0
- package/dist/resources/templates/utils/dom.d.ts.map +1 -0
- package/dist/resources/templates/utils/html.d.ts +3 -0
- package/dist/resources/templates/utils/html.d.ts.map +1 -0
- package/dist/resources/templates/workDisplay.d.ts +183 -0
- package/dist/resources/templates/workDisplay.d.ts.map +1 -0
- package/dist/resources/templates/workSelect.d.ts +18 -0
- package/dist/resources/templates/workSelect.d.ts.map +1 -0
- package/dist/resources/user-sample.d.ts +2 -0
- package/dist/resources/user-sample.d.ts.map +1 -0
- package/dist/resources/user.d.ts +2 -0
- package/dist/resources/user.d.ts.map +1 -0
- package/dist/resources/utils/IntlURLSearchParams.d.ts +56 -0
- package/dist/resources/utils/IntlURLSearchParams.d.ts.map +1 -0
- package/dist/resources/utils/Languages.d.ts +81 -0
- package/dist/resources/utils/Languages.d.ts.map +1 -0
- package/dist/resources/utils/Metadata.d.ts +133 -0
- package/dist/resources/utils/Metadata.d.ts.map +1 -0
- package/dist/resources/utils/Params.d.ts +30 -0
- package/dist/resources/utils/Params.d.ts.map +1 -0
- package/dist/resources/utils/Plugin.d.ts +274 -0
- package/dist/resources/utils/Plugin.d.ts.map +1 -0
- package/dist/resources/utils/ServiceWorker.d.ts +26 -0
- package/dist/resources/utils/ServiceWorker.d.ts.map +1 -0
- package/dist/resources/utils/WorkInfo.d.ts +104 -0
- package/dist/resources/utils/WorkInfo.d.ts.map +1 -0
- package/dist/resources/utils/dialogs.d.ts +155 -0
- package/dist/resources/utils/dialogs.d.ts.map +1 -0
- package/dist/resources/utils/getLocaleFallbackResults.d.ts +19 -0
- package/dist/resources/utils/getLocaleFallbackResults.d.ts.map +1 -0
- package/dist/resources/utils/sanitize.d.ts +6 -0
- package/dist/resources/utils/sanitize.d.ts.map +1 -0
- package/dist/resources/vendor/json-refs-min.d.ts +3 -0
- package/dist/resources/vendor/json-refs-min.d.ts.map +1 -0
- package/dist/resources/workDisplay.d.ts +81 -0
- package/dist/resources/workDisplay.d.ts.map +1 -0
- package/dist/resources/workSelect.d.ts +17 -0
- package/dist/resources/workSelect.d.ts.map +1 -0
- package/dist/rollup.config.d.ts +19 -0
- package/dist/rollup.config.d.ts.map +1 -0
- package/dist/server/main.d.ts +46 -0
- package/dist/server/main.d.ts.map +1 -0
- package/dist/sw-helper.d.ts +3 -0
- package/dist/sw-helper.d.ts.map +1 -0
- package/dist/sw-helper.js +52 -12
- package/dist/sw-sample.d.ts +2 -0
- package/dist/sw-sample.d.ts.map +1 -0
- package/general-schemas/files.jsonschema +6 -0
- package/package.json +22 -9
- package/resources/activateCallback.js +75 -10
- package/resources/index.js +161 -49
- package/resources/resultsDisplay.js +517 -152
- package/resources/templates/index.js +39 -16
- package/resources/templates/languageSelect.js +14 -1
- package/resources/templates/resultsDisplayClient.js +22 -3
- package/resources/templates/resultsDisplayServerOrClient.js +188 -49
- package/resources/templates/utils/dom.js +13 -2
- package/resources/templates/workDisplay.js +299 -75
- package/resources/templates/workSelect.js +16 -3
- package/resources/utils/IntlURLSearchParams.js +46 -4
- package/resources/utils/Languages.js +71 -4
- package/resources/utils/Metadata.js +219 -22
- package/resources/utils/Params.js +70 -23
- package/resources/utils/Plugin.js +169 -1
- package/resources/utils/ServiceWorker.js +48 -19
- package/resources/utils/WorkInfo.js +255 -43
- package/resources/utils/dialogs.js +105 -7
- package/resources/utils/getLocaleFallbackResults.js +12 -2
- package/resources/utils/sanitize.js +4 -0
- package/resources/workDisplay.js +151 -25
- package/resources/workSelect.js +37 -17
- package/server/main.js +111 -19
- package/tsconfig.json +30 -0
- package/resources/user.js +0 -20
|
@@ -10,6 +10,67 @@ import {
|
|
|
10
10
|
import {Languages} from './utils/Languages.js';
|
|
11
11
|
import {getWorkData} from './utils/WorkInfo.js';
|
|
12
12
|
|
|
13
|
+
/**
|
|
14
|
+
* @callback GetCanonicalID
|
|
15
|
+
* @param {{
|
|
16
|
+
* tr: (string|Integer)[]
|
|
17
|
+
* }} cfg
|
|
18
|
+
* @returns {string}
|
|
19
|
+
*/
|
|
20
|
+
/**
|
|
21
|
+
* @callback DetermineEnd
|
|
22
|
+
* @param {{
|
|
23
|
+
* tr: (string|Integer)[]
|
|
24
|
+
* foundState: {
|
|
25
|
+
* start: boolean,
|
|
26
|
+
* end: boolean
|
|
27
|
+
* }
|
|
28
|
+
* }} cfg
|
|
29
|
+
* @returns {string|boolean}
|
|
30
|
+
*/
|
|
31
|
+
|
|
32
|
+
/**
|
|
33
|
+
* @typedef {import('./utils/Plugin.js').PluginObject} Plugin
|
|
34
|
+
*/
|
|
35
|
+
|
|
36
|
+
/**
|
|
37
|
+
* @typedef {{
|
|
38
|
+
* field?: string,
|
|
39
|
+
* fieldAliasOrName: string|string[]|import('../server/main.js').LocalizationStrings,
|
|
40
|
+
* escapeColumn: boolean,
|
|
41
|
+
* fieldLang: string,
|
|
42
|
+
* plugin?: Plugin,
|
|
43
|
+
* applicableField?: string,
|
|
44
|
+
* meta?: {[key: string]: string},
|
|
45
|
+
* j?: number,
|
|
46
|
+
* placement?: number
|
|
47
|
+
* metaApplicableField?: {
|
|
48
|
+
* [key: string]: string
|
|
49
|
+
* },
|
|
50
|
+
* onByDefault?: boolean
|
|
51
|
+
* }[]} FieldInfo
|
|
52
|
+
*/
|
|
53
|
+
|
|
54
|
+
/**
|
|
55
|
+
* @typedef {import('./utils/Metadata.js').FieldValueAliases} FieldValueAliases
|
|
56
|
+
*/
|
|
57
|
+
/**
|
|
58
|
+
* @typedef {any} AnyValue
|
|
59
|
+
*/
|
|
60
|
+
/**
|
|
61
|
+
* @param {AnyValue} val
|
|
62
|
+
* @returns {val is null | undefined}
|
|
63
|
+
*/
|
|
64
|
+
const isNullish = (val) => {
|
|
65
|
+
return val === null || val === undefined;
|
|
66
|
+
};
|
|
67
|
+
|
|
68
|
+
/**
|
|
69
|
+
* @typedef {number} Integer
|
|
70
|
+
*/
|
|
71
|
+
/**
|
|
72
|
+
* @param {string} locale
|
|
73
|
+
*/
|
|
13
74
|
const getLangDir = (locale) => {
|
|
14
75
|
const {direction} = new Locale(locale).textInfo;
|
|
15
76
|
return direction;
|
|
@@ -17,12 +78,25 @@ const getLangDir = (locale) => {
|
|
|
17
78
|
|
|
18
79
|
const fieldValueAliasRegex = /^.* \((.*?)\)$/;
|
|
19
80
|
|
|
81
|
+
/**
|
|
82
|
+
* @param {string} v
|
|
83
|
+
*/
|
|
20
84
|
const getRawFieldValue = (v) => {
|
|
21
85
|
return typeof v === 'string'
|
|
22
86
|
? v.replace(fieldValueAliasRegex, '$1')
|
|
23
87
|
: v;
|
|
24
88
|
};
|
|
25
89
|
|
|
90
|
+
/**
|
|
91
|
+
* @param {{
|
|
92
|
+
* applicableBrowseFieldSet: import('./utils/Metadata.js').BrowseFields,
|
|
93
|
+
* fieldValueAliasMapPreferred: (FieldValueAliases|null|undefined)[],
|
|
94
|
+
* lParamRaw: (key: string, suffix?: string) => string,
|
|
95
|
+
* lIndexedParam: (key: string) => string,
|
|
96
|
+
* max: number,
|
|
97
|
+
* $p: import('./utils/IntlURLSearchParams.js').default
|
|
98
|
+
* }} cfg
|
|
99
|
+
*/
|
|
26
100
|
const setAnchor = ({
|
|
27
101
|
applicableBrowseFieldSet,
|
|
28
102
|
fieldValueAliasMapPreferred, lParamRaw, lIndexedParam, max, $p
|
|
@@ -40,6 +114,8 @@ const setAnchor = ({
|
|
|
40
114
|
}
|
|
41
115
|
if (!anchor) {
|
|
42
116
|
const anchors = [];
|
|
117
|
+
|
|
118
|
+
/** @type {string|null} */
|
|
43
119
|
let anchorField = '';
|
|
44
120
|
// eslint-disable-next-line sonarjs/misplaced-loop-counter -- Ok
|
|
45
121
|
for (let i = 1, breakout; !breakout && !anchors.length; i++) {
|
|
@@ -65,6 +141,9 @@ const setAnchor = ({
|
|
|
65
141
|
}
|
|
66
142
|
}
|
|
67
143
|
if (anchors.length) {
|
|
144
|
+
/**
|
|
145
|
+
* @param {string} str
|
|
146
|
+
*/
|
|
68
147
|
const escapeSelectorAttValue = (str) => (str || '').replaceAll(
|
|
69
148
|
/["\\]/g, String.raw`\$&`
|
|
70
149
|
);
|
|
@@ -82,10 +161,17 @@ const setAnchor = ({
|
|
|
82
161
|
}
|
|
83
162
|
};
|
|
84
163
|
|
|
164
|
+
/**
|
|
165
|
+
* @this {import('./index.js').default}
|
|
166
|
+
* @param {Omit<ResultsDisplayServerOrClientArg, "skipIndexedDB"|"prefI18n">} args
|
|
167
|
+
*/
|
|
85
168
|
export const resultsDisplayClient = async function resultsDisplayClient (args) {
|
|
86
169
|
const persistent = await navigator.storage.persisted();
|
|
87
|
-
const skipIndexedDB = this.skipIndexedDB || !persistent ||
|
|
88
|
-
|
|
170
|
+
const skipIndexedDB = this.skipIndexedDB || !persistent ||
|
|
171
|
+
!navigator.serviceWorker.controller;
|
|
172
|
+
const prefI18n = /** @type {"true"|"false"|null} */ (
|
|
173
|
+
localStorage.getItem(this.namespace + '-localizeParamNames')
|
|
174
|
+
);
|
|
89
175
|
|
|
90
176
|
const {
|
|
91
177
|
fieldInfo, $p,
|
|
@@ -97,14 +183,14 @@ export const resultsDisplayClient = async function resultsDisplayClient (args) {
|
|
|
97
183
|
} = await resultsDisplayServerOrClient.call(this, {
|
|
98
184
|
...args, skipIndexedDB, prefI18n
|
|
99
185
|
});
|
|
100
|
-
document.title = workI18n(
|
|
186
|
+
document.title = /** @type {string} */ (workI18n(
|
|
101
187
|
'browserfile-resultsdisplay',
|
|
102
188
|
{
|
|
103
189
|
work: fileData
|
|
104
|
-
? getMetaProp(lang, metadataObj, 'alias')
|
|
190
|
+
? /** @type {string} */ (getMetaProp(lang, metadataObj, 'alias'))
|
|
105
191
|
: ''
|
|
106
192
|
}
|
|
107
|
-
);
|
|
193
|
+
));
|
|
108
194
|
Templates.resultsDisplayClient.main(templateArgs);
|
|
109
195
|
setAnchor({
|
|
110
196
|
applicableBrowseFieldSet,
|
|
@@ -123,9 +209,12 @@ export const resultsDisplayClient = async function resultsDisplayClient (args) {
|
|
|
123
209
|
};
|
|
124
210
|
|
|
125
211
|
/**
|
|
212
|
+
* @this {import('../server/main.js').ResultsDisplayServerContext}
|
|
126
213
|
* This is server-only code, but kept here as the function is similar.
|
|
127
|
-
* @param {
|
|
128
|
-
*
|
|
214
|
+
* @param {ResultsDisplayServerOrClientArg & {
|
|
215
|
+
* serverOutput?: "jamilih"|"html"|"json"|null
|
|
216
|
+
* }} args
|
|
217
|
+
* @returns {Promise<import('jamilih').JamilihArray|string|(string | number)[][]>}
|
|
129
218
|
*/
|
|
130
219
|
export const resultsDisplayServer = async function resultsDisplayServer (args) {
|
|
131
220
|
const {
|
|
@@ -149,17 +238,61 @@ export const resultsDisplayServer = async function resultsDisplayServer (args) {
|
|
|
149
238
|
}
|
|
150
239
|
};
|
|
151
240
|
|
|
241
|
+
/**
|
|
242
|
+
* @typedef {(info: {
|
|
243
|
+
* tr: (string|Integer)[],
|
|
244
|
+
* idx: number,
|
|
245
|
+
* }) => {
|
|
246
|
+
* tdVal: string|Integer,
|
|
247
|
+
* htmlEscaped: boolean
|
|
248
|
+
* }|{
|
|
249
|
+
* tdVal: string|Integer,
|
|
250
|
+
* htmlEscaped?: undefined
|
|
251
|
+
* }} GetCellValue
|
|
252
|
+
*/
|
|
253
|
+
|
|
254
|
+
/**
|
|
255
|
+
* @todo For `locales`, should export `LocaleObject` from intl-dom
|
|
256
|
+
* @typedef {{
|
|
257
|
+
* l: import('intl-dom').I18NCallback,
|
|
258
|
+
* lang: string[],
|
|
259
|
+
* fallbackLanguages: string[]|undefined,
|
|
260
|
+
* locales: {head?: any, body: any},
|
|
261
|
+
* $p: import('./utils/IntlURLSearchParams.js').default,
|
|
262
|
+
* skipIndexedDB: boolean,
|
|
263
|
+
* noIndexedDB?: boolean,
|
|
264
|
+
* prefI18n: "true"|"false"|null,
|
|
265
|
+
* files?: string,
|
|
266
|
+
* allowPlugins?: boolean,
|
|
267
|
+
* langData: import('../server/main.js').LanguagesData,
|
|
268
|
+
* basePath: string,
|
|
269
|
+
* dynamicBasePath?: string
|
|
270
|
+
* }} ResultsDisplayServerOrClientArg
|
|
271
|
+
*/
|
|
272
|
+
|
|
273
|
+
/**
|
|
274
|
+
* @this {import('../server/main.js').ResultsDisplayServerContext|import('./index.js').default}
|
|
275
|
+
* @param {ResultsDisplayServerOrClientArg} cfg
|
|
276
|
+
*/
|
|
152
277
|
export const resultsDisplayServerOrClient = async function resultsDisplayServerOrClient ({
|
|
153
278
|
l, lang, fallbackLanguages, locales, $p, skipIndexedDB, noIndexedDB, prefI18n,
|
|
154
279
|
files, allowPlugins, langData, basePath = '', dynamicBasePath = ''
|
|
155
280
|
}) {
|
|
156
281
|
const languages = new Languages({langData});
|
|
282
|
+
|
|
283
|
+
/**
|
|
284
|
+
* @param {{
|
|
285
|
+
* fieldValueAliasMapPreferred: (FieldValueAliases|null|undefined)[],
|
|
286
|
+
* escapeColumnIndexes: boolean[]
|
|
287
|
+
* }} cfg
|
|
288
|
+
* @returns {GetCellValue}
|
|
289
|
+
*/
|
|
157
290
|
const getCellValue = ({
|
|
158
291
|
fieldValueAliasMapPreferred, escapeColumnIndexes
|
|
159
292
|
}) => ({
|
|
160
293
|
tr, idx
|
|
161
294
|
}) => {
|
|
162
|
-
let tdVal = (fieldValueAliasMapPreferred[idx]
|
|
295
|
+
let tdVal = (!isNullish(fieldValueAliasMapPreferred[idx])
|
|
163
296
|
? fieldValueAliasMapPreferred[idx][tr[idx]]
|
|
164
297
|
: tr[idx]
|
|
165
298
|
);
|
|
@@ -167,90 +300,130 @@ export const resultsDisplayServerOrClient = async function resultsDisplayServerO
|
|
|
167
300
|
tdVal = Object.values(tdVal);
|
|
168
301
|
}
|
|
169
302
|
if (Array.isArray(tdVal)) {
|
|
170
|
-
tdVal = tdVal.join(l('comma-space'));
|
|
303
|
+
tdVal = tdVal.join(/** @type {string} */ (l('comma-space')));
|
|
171
304
|
}
|
|
172
305
|
return ((escapeColumnIndexes[idx] || !this.trustFormatHTML) &&
|
|
173
306
|
typeof tdVal === 'string')
|
|
174
307
|
? {tdVal: escapeHTML(tdVal), htmlEscaped: true}
|
|
175
308
|
: {tdVal};
|
|
176
309
|
};
|
|
310
|
+
|
|
311
|
+
/**
|
|
312
|
+
* @param {{
|
|
313
|
+
* fieldValueAliasMap: (FieldValueAliases|null|undefined)[],
|
|
314
|
+
* fieldValueAliasMapPreferred: (FieldValueAliases|null|undefined)[],
|
|
315
|
+
* localizedFieldNames: (string | string[]|import('../server/main.js').LocalizationStrings)[],
|
|
316
|
+
* canonicalBrowseFieldNames: string[]
|
|
317
|
+
* }} cfg
|
|
318
|
+
*/
|
|
177
319
|
const getCanonicalID = ({
|
|
178
320
|
fieldValueAliasMap, fieldValueAliasMapPreferred, localizedFieldNames,
|
|
179
321
|
canonicalBrowseFieldNames
|
|
180
|
-
}) =>
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
//
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
|
|
322
|
+
}) =>
|
|
323
|
+
/** @type {GetCanonicalID} */
|
|
324
|
+
// eslint-disable-next-line @stylistic/implicit-arrow-linebreak -- Ok
|
|
325
|
+
({
|
|
326
|
+
tr // , foundState
|
|
327
|
+
}) => {
|
|
328
|
+
return canonicalBrowseFieldNames.map((fieldName) => {
|
|
329
|
+
const idx = localizedFieldNames.indexOf(fieldName);
|
|
330
|
+
// This works to put alias in anchor but this includes
|
|
331
|
+
// our ending parenthetical, the alias may be harder
|
|
332
|
+
// to remember and/or automated than original (e.g.,
|
|
333
|
+
// for a number representing a book); we may wish to
|
|
334
|
+
// switch this (and also for other browse field-based
|
|
335
|
+
// items).
|
|
336
|
+
if (
|
|
337
|
+
fieldValueAliasMap[idx] !== undefined &&
|
|
338
|
+
// Added this condition after imf->intl-dom conversion; concealing a
|
|
339
|
+
// bug?
|
|
340
|
+
fieldValueAliasMap[idx] !== null
|
|
341
|
+
) {
|
|
342
|
+
return /** @type {FieldValueAliases} */ (
|
|
343
|
+
fieldValueAliasMapPreferred[idx]
|
|
344
|
+
)[tr[idx]];
|
|
345
|
+
}
|
|
346
|
+
return tr[idx];
|
|
347
|
+
}).join('-'); // rowID;
|
|
348
|
+
};
|
|
349
|
+
|
|
350
|
+
/**
|
|
351
|
+
* @param {{
|
|
352
|
+
* fieldValueAliasMap: (FieldValueAliases|null|undefined)[],
|
|
353
|
+
* fieldValueAliasMapPreferred: (FieldValueAliases|null|undefined)[],
|
|
354
|
+
* localizedFieldNames: (string|string[]|import('../server/main.js').LocalizationStrings)[],
|
|
355
|
+
* applicableBrowseFieldNames: string[],
|
|
356
|
+
* startsRaw: (string|Integer)[],
|
|
357
|
+
* endsRaw: (string|Integer)[]
|
|
358
|
+
* }} cfg
|
|
359
|
+
*/
|
|
202
360
|
const determineEnd = ({
|
|
203
361
|
fieldValueAliasMap, fieldValueAliasMapPreferred, localizedFieldNames,
|
|
204
362
|
applicableBrowseFieldNames, startsRaw, endsRaw
|
|
205
|
-
}) =>
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
|
|
211
|
-
|
|
212
|
-
|
|
213
|
-
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
|
|
219
|
-
|
|
220
|
-
//
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
363
|
+
}) =>
|
|
364
|
+
/** @type {DetermineEnd} */
|
|
365
|
+
// eslint-disable-next-line @stylistic/implicit-arrow-linebreak -- Ok
|
|
366
|
+
({
|
|
367
|
+
tr, foundState
|
|
368
|
+
}) => {
|
|
369
|
+
const rowIDPartsPreferred = /** @type {(string|Integer)[]} */ ([]);
|
|
370
|
+
const rowIDParts = applicableBrowseFieldNames.map((fieldName) => {
|
|
371
|
+
const idx = localizedFieldNames.indexOf(fieldName);
|
|
372
|
+
// This works to put alias in anchor but this includes
|
|
373
|
+
// our ending parenthetical, the alias may be harder
|
|
374
|
+
// to remember and/or automated than original (e.g.,
|
|
375
|
+
// for a number representing a book), and there could
|
|
376
|
+
// be multiple aliases for a value; we may wish to
|
|
377
|
+
// switch this (and also for other browse field-based
|
|
378
|
+
// items).
|
|
379
|
+
if (
|
|
380
|
+
fieldValueAliasMap[idx] !== undefined &&
|
|
381
|
+
// Added this condition after imf->intl-dom conversion; concealing a
|
|
382
|
+
// bug?
|
|
383
|
+
fieldValueAliasMap[idx] !== null
|
|
384
|
+
) {
|
|
385
|
+
rowIDPartsPreferred.push(
|
|
386
|
+
/** @type {string|Integer} */
|
|
387
|
+
(fieldValueAliasMapPreferred[idx]?.[tr[idx]])
|
|
388
|
+
);
|
|
389
|
+
} else {
|
|
390
|
+
rowIDPartsPreferred.push(tr[idx]);
|
|
391
|
+
}
|
|
392
|
+
return tr[idx];
|
|
393
|
+
});
|
|
230
394
|
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
395
|
+
// Todo: Use schema to determine field type and use `Number.parseInt`
|
|
396
|
+
// on other value instead of `String` conversions
|
|
397
|
+
if (!foundState.start) {
|
|
398
|
+
if (startsRaw.some((part, i) => {
|
|
399
|
+
const rowIDPart = rowIDParts[i];
|
|
400
|
+
return part !== rowIDPart;
|
|
401
|
+
})) {
|
|
402
|
+
// Trigger skip of this row
|
|
403
|
+
return false;
|
|
404
|
+
}
|
|
405
|
+
foundState.start = true;
|
|
406
|
+
}
|
|
407
|
+
// This doesn't go in an `else` for the above in case the start is the end
|
|
408
|
+
if (endsRaw.every((part, i) => {
|
|
235
409
|
const rowIDPart = rowIDParts[i];
|
|
236
|
-
return part
|
|
410
|
+
return part === rowIDPart;
|
|
237
411
|
})) {
|
|
238
|
-
|
|
239
|
-
|
|
412
|
+
foundState.end = true;
|
|
413
|
+
} else if (foundState.end) { // If no longer matching, trigger end of the table
|
|
414
|
+
return true;
|
|
240
415
|
}
|
|
241
|
-
|
|
242
|
-
}
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
|
|
246
|
-
|
|
247
|
-
|
|
248
|
-
|
|
249
|
-
|
|
250
|
-
|
|
251
|
-
|
|
252
|
-
return rowIDPartsPreferred.join('-'); // rowID;
|
|
253
|
-
};
|
|
416
|
+
return rowIDPartsPreferred.join('-'); // rowID;
|
|
417
|
+
};
|
|
418
|
+
|
|
419
|
+
/**
|
|
420
|
+
* @param {{
|
|
421
|
+
* localizedFieldNames: (
|
|
422
|
+
* string|string[]|import('../server/main.js').LocalizationStrings
|
|
423
|
+
* )[],
|
|
424
|
+
* }} cfg
|
|
425
|
+
* @returns {[string[], number[], ("" | number[] | null)[]]}
|
|
426
|
+
*/
|
|
254
427
|
const getCheckedAndInterlinearFieldInfo = ({
|
|
255
428
|
localizedFieldNames
|
|
256
429
|
}) => {
|
|
@@ -279,35 +452,46 @@ export const resultsDisplayServerOrClient = async function resultsDisplayServerO
|
|
|
279
452
|
});
|
|
280
453
|
return [checkedFields, checkedFieldIndexes, allInterlinearColIndexes];
|
|
281
454
|
};
|
|
455
|
+
|
|
456
|
+
/**
|
|
457
|
+
* @param {{
|
|
458
|
+
* starts: string[],
|
|
459
|
+
* ends: string[],
|
|
460
|
+
* applicableBrowseFieldNames: string[],
|
|
461
|
+
* heading: string
|
|
462
|
+
* }} cfg
|
|
463
|
+
* @returns {[boolean, string|undefined]}
|
|
464
|
+
*/
|
|
282
465
|
const getCaption = ({starts, ends, applicableBrowseFieldNames, heading}) => {
|
|
283
466
|
let caption;
|
|
284
467
|
const hasCaption = $pRaw('caption') !== '0';
|
|
285
468
|
if (hasCaption) {
|
|
286
469
|
/*
|
|
287
|
-
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
|
|
291
|
-
|
|
292
|
-
(j > 0 ? l('comma-space') : '') + bf + ' ' +
|
|
293
|
-
$pRaw(startOrEnd + (i + 1) + '-' + (j + 1))
|
|
294
|
-
).join('') + (txt ? ')' : ''), '')
|
|
295
|
-
);
|
|
296
|
-
*/
|
|
297
|
-
/*
|
|
298
|
-
// Works but overly long
|
|
299
|
-
const buildRangePoint = (startOrEnd) => escapeHTML(
|
|
300
|
-
applicableBrowseFieldSet.map((bf, j) =>
|
|
470
|
+
// Works but displays in parentheses browse fields which
|
|
471
|
+
// may be non-applicable
|
|
472
|
+
const buildRangePoint = (startOrEnd) => escapeHTML(
|
|
473
|
+
browseFieldSets.reduce((txt, bfs, i) =>
|
|
474
|
+
(txt ? txt + ' (' : '') + bfs.map((bf, j) =>
|
|
301
475
|
(j > 0 ? l('comma-space') : '') + bf + ' ' +
|
|
302
|
-
$pRaw(startOrEnd + (
|
|
303
|
-
).join('')
|
|
304
|
-
|
|
305
|
-
|
|
476
|
+
$pRaw(startOrEnd + (i + 1) + '-' + (j + 1))
|
|
477
|
+
).join('') + (txt ? ')' : ''), '')
|
|
478
|
+
);
|
|
479
|
+
*/
|
|
480
|
+
/*
|
|
481
|
+
// Works but overly long
|
|
482
|
+
const buildRangePoint = (startOrEnd) => escapeHTML(
|
|
483
|
+
applicableBrowseFieldSet.map((bf, j) =>
|
|
484
|
+
(j > 0 ? l('comma-space') : '') + bf + ' ' +
|
|
485
|
+
$pRaw(startOrEnd + (browseFieldSetIdx + 1) + '-' + (j + 1))
|
|
486
|
+
).join('')
|
|
487
|
+
);
|
|
488
|
+
*/
|
|
306
489
|
const startSep = Templates.resultsDisplayServerOrClient.startSeparator({l});
|
|
307
490
|
const innerBrowseFieldSeparator = Templates.resultsDisplayServerOrClient.
|
|
308
491
|
innerBrowseFieldSeparator({l});
|
|
309
492
|
|
|
310
493
|
const buildRanges = () => {
|
|
494
|
+
/** @type {string[]} */
|
|
311
495
|
const endVals = [];
|
|
312
496
|
const startRange = starts.reduce((str, startFieldValue, i) => {
|
|
313
497
|
const ret = str + startFieldValue;
|
|
@@ -332,11 +516,20 @@ export const resultsDisplayServerOrClient = async function resultsDisplayServerO
|
|
|
332
516
|
}
|
|
333
517
|
return [hasCaption, caption];
|
|
334
518
|
};
|
|
519
|
+
|
|
520
|
+
/**
|
|
521
|
+
* @param {{
|
|
522
|
+
* presort: boolean|undefined,
|
|
523
|
+
* tableData: (string|Integer)[][],
|
|
524
|
+
* applicableBrowseFieldNames: string[],
|
|
525
|
+
* localizedFieldNames: (string|string[]|import('../server/main.js').LocalizationStrings)[]
|
|
526
|
+
* }} cfg
|
|
527
|
+
*/
|
|
335
528
|
const runPresort = ({presort, tableData, applicableBrowseFieldNames, localizedFieldNames}) => {
|
|
336
529
|
// Todo: Ought to be checking against an aliased table
|
|
337
530
|
if (presort) {
|
|
338
531
|
tableData.sort((rowA, rowB) => {
|
|
339
|
-
let precedence;
|
|
532
|
+
let precedence = 0;
|
|
340
533
|
applicableBrowseFieldNames.some((fieldName) => {
|
|
341
534
|
const idx = localizedFieldNames.indexOf(fieldName);
|
|
342
535
|
const rowAFirst = rowA[idx] < rowB[idx];
|
|
@@ -348,6 +541,18 @@ export const resultsDisplayServerOrClient = async function resultsDisplayServerO
|
|
|
348
541
|
});
|
|
349
542
|
}
|
|
350
543
|
};
|
|
544
|
+
|
|
545
|
+
/**
|
|
546
|
+
* @param {{
|
|
547
|
+
* schemaItems: {title: string, type: string}[],
|
|
548
|
+
* fieldInfo: FieldInfo,
|
|
549
|
+
* metadataObj: import('./utils/Metadata.js').MetadataObj,
|
|
550
|
+
* getFieldAliasOrName: (
|
|
551
|
+
* field: string
|
|
552
|
+
* ) => string|string[]|import('../server/main.js').LocalizationStrings,
|
|
553
|
+
* usePreferAlias: boolean
|
|
554
|
+
* }} cfg
|
|
555
|
+
*/
|
|
351
556
|
const getFieldValueAliasMap = ({
|
|
352
557
|
schemaItems, fieldInfo, metadataObj, getFieldAliasOrName, usePreferAlias
|
|
353
558
|
}) => {
|
|
@@ -356,7 +561,9 @@ export const resultsDisplayServerOrClient = async function resultsDisplayServerO
|
|
|
356
561
|
return undefined;
|
|
357
562
|
}
|
|
358
563
|
const {preferAlias, fieldValueAliasMap} = getFieldNameAndValueAliases({
|
|
359
|
-
|
|
564
|
+
// eslint-disable-next-line object-shorthand -- TS
|
|
565
|
+
field: /** @type {string} */ (field),
|
|
566
|
+
schemaItems, metadataObj, getFieldAliasOrName, lang
|
|
360
567
|
});
|
|
361
568
|
if (!usePreferAlias) {
|
|
362
569
|
return preferAlias !== false ? fieldValueAliasMap : undefined;
|
|
@@ -372,36 +579,49 @@ export const resultsDisplayServerOrClient = async function resultsDisplayServerO
|
|
|
372
579
|
if (val && typeof val === 'object') {
|
|
373
580
|
if (typeof preferAlias === 'string') {
|
|
374
581
|
fieldValueAliasMap[key] =
|
|
375
|
-
|
|
376
|
-
|
|
377
|
-
|
|
582
|
+
Templates.resultsDisplayServerOrClient.fieldValueAlias({
|
|
583
|
+
key, value: val[preferAlias]
|
|
584
|
+
});
|
|
378
585
|
} else {
|
|
379
586
|
Object.entries(val).forEach(([k, value]) => {
|
|
380
|
-
|
|
381
|
-
|
|
382
|
-
|
|
383
|
-
|
|
587
|
+
/** @type {{[key: string]: string|number}} */
|
|
588
|
+
(fieldValueAliasMap[key])[k] =
|
|
589
|
+
Templates.resultsDisplayServerOrClient.fieldValueAlias({
|
|
590
|
+
key, value
|
|
591
|
+
});
|
|
384
592
|
});
|
|
385
593
|
}
|
|
386
594
|
return;
|
|
387
595
|
}
|
|
388
596
|
fieldValueAliasMap[key] =
|
|
389
|
-
|
|
597
|
+
Templates.resultsDisplayServerOrClient.fieldValueAlias({key, value: val});
|
|
390
598
|
});
|
|
391
599
|
return preferAlias !== false ? fieldValueAliasMap : undefined;
|
|
392
600
|
}
|
|
393
601
|
return undefined;
|
|
394
602
|
});
|
|
395
603
|
};
|
|
604
|
+
|
|
605
|
+
/**
|
|
606
|
+
* @param {string} param
|
|
607
|
+
* @param {boolean} [avoidLog]
|
|
608
|
+
*/
|
|
396
609
|
const $pRaw = (param, avoidLog) => {
|
|
397
610
|
// Todo: Should work with i18n=true (if names i18nized, need reverse look-up)
|
|
611
|
+
|
|
612
|
+
/** @type {string} */
|
|
398
613
|
let key;
|
|
399
614
|
const p = $p.get(param, true);
|
|
400
615
|
/**
|
|
401
|
-
|
|
402
|
-
|
|
403
|
-
|
|
404
|
-
|
|
616
|
+
* @typedef {{
|
|
617
|
+
* [key: string]: string|LocaleObj
|
|
618
|
+
* }} LocaleObj
|
|
619
|
+
*/
|
|
620
|
+
/**
|
|
621
|
+
*
|
|
622
|
+
* @param {LocaleObj[]|LocaleObj} locale
|
|
623
|
+
* @returns {boolean}
|
|
624
|
+
*/
|
|
405
625
|
function reverseLocaleLookup (locale) {
|
|
406
626
|
if (Array.isArray(locale)) {
|
|
407
627
|
return locale.some(reverseLocaleLookup);
|
|
@@ -419,17 +639,33 @@ export const resultsDisplayServerOrClient = async function resultsDisplayServerO
|
|
|
419
639
|
});
|
|
420
640
|
}
|
|
421
641
|
reverseLocaleLookup(locales);
|
|
642
|
+
// @ts-expect-error TS defect
|
|
422
643
|
if (!key && !avoidLog) {
|
|
423
644
|
console.log('Bad param/value', param, '::', p);
|
|
424
645
|
}
|
|
646
|
+
// @ts-expect-error TS defect
|
|
425
647
|
return key; // || p; // $p.get(param, true);
|
|
426
648
|
};
|
|
427
649
|
|
|
428
650
|
const escapeCSS = escapeHTML;
|
|
651
|
+
|
|
652
|
+
/**
|
|
653
|
+
* @param {string} param
|
|
654
|
+
*/
|
|
429
655
|
const $pRawEsc = (param) => escapeHTML($pRaw(param));
|
|
430
|
-
|
|
656
|
+
/**
|
|
657
|
+
* @param {string} param
|
|
658
|
+
*/
|
|
659
|
+
const $pEscArbitrary = (param) => escapeHTML(
|
|
660
|
+
/** @type {string} */
|
|
661
|
+
($p.get(param, true))
|
|
662
|
+
);
|
|
431
663
|
|
|
432
664
|
// Not currently in use
|
|
665
|
+
|
|
666
|
+
/**
|
|
667
|
+
* @param {string} s
|
|
668
|
+
*/
|
|
433
669
|
const escapeQuotedCSS = (s) => s.replaceAll('\\', '\\\\').replaceAll(
|
|
434
670
|
'"', String.raw`\"`
|
|
435
671
|
);
|
|
@@ -437,6 +673,7 @@ export const resultsDisplayServerOrClient = async function resultsDisplayServerO
|
|
|
437
673
|
const {
|
|
438
674
|
fileData, workI18n, getFieldAliasOrName, schemaObj, metadataObj,
|
|
439
675
|
pluginsForWork
|
|
676
|
+
// @ts-expect-error Not using `this` given no `languages` arg is passed
|
|
440
677
|
} = await getWorkData({
|
|
441
678
|
files: files || this.files,
|
|
442
679
|
allowPlugins: typeof allowPlugins === 'boolean' ? allowPlugins : this.allowPlugins,
|
|
@@ -446,11 +683,15 @@ export const resultsDisplayServerOrClient = async function resultsDisplayServerO
|
|
|
446
683
|
});
|
|
447
684
|
console.log('pluginsForWork', pluginsForWork);
|
|
448
685
|
|
|
449
|
-
const heading = getMetaProp(lang, metadataObj, 'heading');
|
|
686
|
+
const heading = /** @type {string} */ (getMetaProp(lang, metadataObj, 'heading'));
|
|
450
687
|
const schemaItems = schemaObj.items.items;
|
|
451
688
|
|
|
689
|
+
/** @type {string[]} */
|
|
452
690
|
const setNames = [];
|
|
691
|
+
/** @type {(boolean|undefined)[]} */
|
|
453
692
|
const presorts = [];
|
|
693
|
+
|
|
694
|
+
/** @type {import('./utils/Metadata.js').BrowseFields[]} */
|
|
454
695
|
const browseFieldSets = [];
|
|
455
696
|
getBrowseFieldData({
|
|
456
697
|
metadataObj, schemaItems, getFieldAliasOrName, lang,
|
|
@@ -461,6 +702,7 @@ export const resultsDisplayServerOrClient = async function resultsDisplayServerO
|
|
|
461
702
|
}
|
|
462
703
|
});
|
|
463
704
|
|
|
705
|
+
/** @type {FieldInfo} */
|
|
464
706
|
const fieldInfo = schemaItems.map(({title: field, format}) => {
|
|
465
707
|
return {
|
|
466
708
|
field,
|
|
@@ -484,12 +726,26 @@ export const resultsDisplayServerOrClient = async function resultsDisplayServerO
|
|
|
484
726
|
placement = placement === 'end'
|
|
485
727
|
? Number.POSITIVE_INFINITY // push
|
|
486
728
|
: placement;
|
|
729
|
+
|
|
730
|
+
/**
|
|
731
|
+
* @param {{
|
|
732
|
+
* applicableField?: string,
|
|
733
|
+
* targetLanguage?: string,
|
|
734
|
+
* onByDefault?: boolean,
|
|
735
|
+
* metaApplicableField?: {
|
|
736
|
+
* [key: string]: string
|
|
737
|
+
* },
|
|
738
|
+
* }} [cfg]
|
|
739
|
+
*/
|
|
487
740
|
const processField = ({applicableField, targetLanguage, onByDefault, metaApplicableField} = {}) => {
|
|
488
741
|
const plugin = pluginsForWork.getPluginObject(pluginName) || {};
|
|
489
|
-
const applicableFieldLang = metadata.getFieldLang(
|
|
742
|
+
const applicableFieldLang = metadata.getFieldLang(
|
|
743
|
+
/** @type {string} */ (applicableField)
|
|
744
|
+
);
|
|
490
745
|
if (plugin.getTargetLanguage) {
|
|
491
746
|
targetLanguage = plugin.getTargetLanguage({
|
|
492
|
-
|
|
747
|
+
// eslint-disable-next-line object-shorthand -- TS
|
|
748
|
+
applicableField: /** @type {string} */ (applicableField),
|
|
493
749
|
targetLanguage,
|
|
494
750
|
// Default lang for plug-in (from files.json)
|
|
495
751
|
pluginLang,
|
|
@@ -502,27 +758,47 @@ export const resultsDisplayServerOrClient = async function resultsDisplayServerO
|
|
|
502
758
|
if (targetLanguage === '{locale}') {
|
|
503
759
|
targetLanguage = preferredLocale;
|
|
504
760
|
}
|
|
505
|
-
const applicableFieldI18N = getMetaProp(
|
|
761
|
+
const applicableFieldI18N = getMetaProp(
|
|
762
|
+
lang,
|
|
763
|
+
metadataObj,
|
|
764
|
+
[
|
|
765
|
+
'fieldnames',
|
|
766
|
+
/** @type {string} */
|
|
767
|
+
(applicableField)
|
|
768
|
+
]
|
|
769
|
+
);
|
|
506
770
|
const fieldAliasOrName = plugin.getFieldAliasOrName
|
|
507
771
|
? plugin.getFieldAliasOrName({
|
|
508
772
|
locales: lang,
|
|
509
773
|
workI18n,
|
|
510
|
-
|
|
511
|
-
|
|
774
|
+
// eslint-disable-next-line object-shorthand -- TS
|
|
775
|
+
targetLanguage: /** @type {string} */ (targetLanguage),
|
|
776
|
+
// eslint-disable-next-line object-shorthand -- TS
|
|
777
|
+
applicableField: /** @type {string} */ (applicableField),
|
|
512
778
|
applicableFieldI18N,
|
|
513
779
|
meta,
|
|
514
|
-
|
|
515
|
-
|
|
780
|
+
// eslint-disable-next-line object-shorthand -- TS
|
|
781
|
+
metaApplicableField: /** @type {{[key: string]: string }} */ (
|
|
782
|
+
metaApplicableField
|
|
783
|
+
),
|
|
784
|
+
targetLanguageI18N: languages.getLanguageFromCode(
|
|
785
|
+
/** @type {string} */ (targetLanguage)
|
|
786
|
+
)
|
|
516
787
|
})
|
|
517
788
|
: languages.getFieldNameFromPluginNameAndLocales({
|
|
518
789
|
pluginName,
|
|
519
|
-
locales: lang,
|
|
790
|
+
// locales: lang,
|
|
520
791
|
workI18n,
|
|
521
|
-
|
|
522
|
-
|
|
792
|
+
// eslint-disable-next-line object-shorthand -- TS
|
|
793
|
+
targetLanguage: /** @type {string} */ (targetLanguage),
|
|
794
|
+
// eslint-disable-next-line object-shorthand -- TS
|
|
795
|
+
applicableFieldI18N: /** @type {string|string[]} */ (applicableFieldI18N),
|
|
523
796
|
// Todo: Should have formal way to i18nize meta
|
|
524
797
|
meta,
|
|
525
|
-
|
|
798
|
+
// eslint-disable-next-line object-shorthand -- TS
|
|
799
|
+
metaApplicableField: /** @type {{[key: string]: string }} */ (
|
|
800
|
+
metaApplicableField
|
|
801
|
+
)
|
|
526
802
|
});
|
|
527
803
|
fieldInfo.splice(
|
|
528
804
|
// Todo: Allow default placement overriding for
|
|
@@ -546,7 +822,7 @@ export const resultsDisplayServerOrClient = async function resultsDisplayServerO
|
|
|
546
822
|
// not need here)
|
|
547
823
|
applicableField,
|
|
548
824
|
metaApplicableField,
|
|
549
|
-
fieldLang: targetLanguage
|
|
825
|
+
fieldLang: /** @type {string} */ (targetLanguage)
|
|
550
826
|
}
|
|
551
827
|
);
|
|
552
828
|
};
|
|
@@ -576,21 +852,81 @@ export const resultsDisplayServerOrClient = async function resultsDisplayServerO
|
|
|
576
852
|
prefI18n !== 'false' && this.localizeParamNames
|
|
577
853
|
);
|
|
578
854
|
const lParam = localizeParamNames
|
|
579
|
-
|
|
580
|
-
|
|
855
|
+
// eslint-disable-next-line @stylistic/operator-linebreak -- Ok
|
|
856
|
+
?
|
|
857
|
+
/**
|
|
858
|
+
* @param {string} key
|
|
859
|
+
* @returns {string}
|
|
860
|
+
*/
|
|
861
|
+
(key) => /** @type {string} */ (l(['params', key]))
|
|
862
|
+
// eslint-disable-next-line @stylistic/operator-linebreak -- Ok
|
|
863
|
+
:
|
|
864
|
+
/**
|
|
865
|
+
* @param {string} key
|
|
866
|
+
* @returns {string}
|
|
867
|
+
*/
|
|
868
|
+
(key) => key;
|
|
581
869
|
const lIndexedParam = localizeParamNames
|
|
582
|
-
|
|
583
|
-
|
|
870
|
+
// eslint-disable-next-line @stylistic/operator-linebreak -- Ok
|
|
871
|
+
?
|
|
872
|
+
/**
|
|
873
|
+
* @param {string} key
|
|
874
|
+
* @returns {string}
|
|
875
|
+
*/
|
|
876
|
+
(key) => /** @type {string} */ (l(['params', 'indexed', key]))
|
|
877
|
+
// eslint-disable-next-line @stylistic/operator-linebreak -- Ok
|
|
878
|
+
:
|
|
879
|
+
/**
|
|
880
|
+
* @param {string} key
|
|
881
|
+
* @returns {string}
|
|
882
|
+
*/
|
|
883
|
+
(key) => key;
|
|
584
884
|
const lParamRaw = localizeParamNames
|
|
585
|
-
|
|
586
|
-
|
|
885
|
+
// eslint-disable-next-line @stylistic/operator-linebreak -- Ok
|
|
886
|
+
?
|
|
887
|
+
/**
|
|
888
|
+
* @param {string} key
|
|
889
|
+
* @param {string} [suffix]
|
|
890
|
+
* @returns {string}
|
|
891
|
+
*/
|
|
892
|
+
(key, suffix = '') => /** @type {string} */ (
|
|
893
|
+
$p.get(lParam(key) + suffix, true)
|
|
894
|
+
)
|
|
895
|
+
// eslint-disable-next-line @stylistic/operator-linebreak -- Ok
|
|
896
|
+
:
|
|
897
|
+
/**
|
|
898
|
+
* @param {string} key
|
|
899
|
+
* @param {string} [suffix]
|
|
900
|
+
* @returns {string}
|
|
901
|
+
*/
|
|
902
|
+
(key, suffix = '') => /** @type {string} */ (
|
|
903
|
+
$p.get(key + suffix, true)
|
|
904
|
+
);
|
|
587
905
|
const lIndexedParamRaw = localizeParamNames
|
|
588
|
-
|
|
589
|
-
|
|
906
|
+
// eslint-disable-next-line @stylistic/operator-linebreak -- Ok
|
|
907
|
+
?
|
|
908
|
+
/**
|
|
909
|
+
* @param {string} key
|
|
910
|
+
* @param {string} [suffix]
|
|
911
|
+
* @returns {string}
|
|
912
|
+
*/
|
|
913
|
+
(key, suffix = '') => /** @type {string} */ (
|
|
914
|
+
$p.get($p.get('work') + '-' + lIndexedParam(key) + suffix, true)
|
|
915
|
+
)
|
|
916
|
+
// eslint-disable-next-line @stylistic/operator-linebreak -- Ok
|
|
917
|
+
:
|
|
918
|
+
/**
|
|
919
|
+
* @param {string} key
|
|
920
|
+
* @param {string} [suffix]
|
|
921
|
+
* @returns {string}
|
|
922
|
+
*/
|
|
923
|
+
(key, suffix = '') => /** @type {string} */ (
|
|
924
|
+
$p.get($p.get('work') + '-' + key + suffix, true)
|
|
925
|
+
);
|
|
590
926
|
|
|
591
927
|
// Now that we know `browseFieldSets`, we can parse `startEnd`
|
|
592
928
|
const browseFieldSetStartEndIdx = browseFieldSets.findIndex((item, i) => {
|
|
593
|
-
return lIndexedParamRaw('startEnd', (i + 1));
|
|
929
|
+
return lIndexedParamRaw('startEnd', String(i + 1));
|
|
594
930
|
});
|
|
595
931
|
if (browseFieldSetStartEndIdx !== -1) {
|
|
596
932
|
// Todo: i18nize (by work and/or by whole app?)
|
|
@@ -603,7 +939,7 @@ export const resultsDisplayServerOrClient = async function resultsDisplayServerO
|
|
|
603
939
|
// Todo: Change query beginning at 0 to 1 if none present?
|
|
604
940
|
// Todo: Support i18nized or canonical aliases (but don't
|
|
605
941
|
// over-trim in such cases)
|
|
606
|
-
const rawSearch = (lIndexedParamRaw('startEnd', browseFieldSetStartEndIdx + 1) || '').trim();
|
|
942
|
+
const rawSearch = (lIndexedParamRaw('startEnd', String(browseFieldSetStartEndIdx + 1)) || '').trim();
|
|
607
943
|
const [startFull, endFull] = rawSearch.split(rangeSep);
|
|
608
944
|
if (endFull !== undefined) {
|
|
609
945
|
const startPartVals = startFull.split(partSep);
|
|
@@ -642,12 +978,16 @@ export const resultsDisplayServerOrClient = async function resultsDisplayServerO
|
|
|
642
978
|
});
|
|
643
979
|
|
|
644
980
|
const fieldSchemaTypes = applicableBrowseFieldSet.map((abfs) => abfs.fieldSchema.type);
|
|
981
|
+
|
|
982
|
+
/**
|
|
983
|
+
* @param {"start"|"end"} startOrEnd
|
|
984
|
+
*/
|
|
645
985
|
const buildRangePoint = (startOrEnd) => {
|
|
646
986
|
return applicableBrowseFieldNames.map((bfn, j) => {
|
|
647
|
-
return $p.get(
|
|
987
|
+
return /** @type {string} */ ($p.get(
|
|
648
988
|
$p.get('work') + '-' + startOrEnd + (browseFieldSetIdx + 1) + '-' + (j + 1),
|
|
649
989
|
true
|
|
650
|
-
);
|
|
990
|
+
));
|
|
651
991
|
});
|
|
652
992
|
};
|
|
653
993
|
const starts = buildRangePoint('start');
|
|
@@ -660,6 +1000,11 @@ export const resultsDisplayServerOrClient = async function resultsDisplayServerO
|
|
|
660
1000
|
|
|
661
1001
|
console.log('rand', lParamRaw('rand') === 'yes');
|
|
662
1002
|
|
|
1003
|
+
/**
|
|
1004
|
+
* @param {string} v
|
|
1005
|
+
* @param {Integer} i
|
|
1006
|
+
* @returns {Integer|string}
|
|
1007
|
+
*/
|
|
663
1008
|
const stripToRawFieldValue = (v, i) => {
|
|
664
1009
|
let val;
|
|
665
1010
|
if ((/^\d+$/).test(v) || fieldValueAliasRegex.test(v)) {
|
|
@@ -672,7 +1017,7 @@ export const resultsDisplayServerOrClient = async function resultsDisplayServerO
|
|
|
672
1017
|
const fvEntries = Object.entries(rawFieldValueAliasMap);
|
|
673
1018
|
if (Array.isArray(fvEntries[0][1])) {
|
|
674
1019
|
fvEntries.some(([key, arr]) => {
|
|
675
|
-
if (arr.includes(v)) {
|
|
1020
|
+
if (/** @type {(string | number)[]} */ (arr).includes(v)) {
|
|
676
1021
|
dealiased = key;
|
|
677
1022
|
return true;
|
|
678
1023
|
}
|
|
@@ -699,7 +1044,9 @@ export const resultsDisplayServerOrClient = async function resultsDisplayServerO
|
|
|
699
1044
|
const startsRaw = starts.map(stripToRawFieldValue);
|
|
700
1045
|
const endsRaw = ends.map(stripToRawFieldValue);
|
|
701
1046
|
|
|
702
|
-
|
|
1047
|
+
/** @type {(string|Integer)[][]} */
|
|
1048
|
+
let tableData;
|
|
1049
|
+
let usingServerData = false;
|
|
703
1050
|
// Site owner may have configured to skip (e.g., testing)
|
|
704
1051
|
if (!skipIndexedDB &&
|
|
705
1052
|
// User may have refused, not yet agreed, or are visiting the
|
|
@@ -713,7 +1060,8 @@ export const resultsDisplayServerOrClient = async function resultsDisplayServerO
|
|
|
713
1060
|
// Todo: Fetch the work in code based on the non-localized `datafileName`
|
|
714
1061
|
const dbName = this.namespace + '-textbrowser-cache-data';
|
|
715
1062
|
const req = indexedDB.open(dbName);
|
|
716
|
-
req.onsuccess = (
|
|
1063
|
+
req.onsuccess = (e) => {
|
|
1064
|
+
const db = /** @type {EventTarget & {result: IDBDatabase}} */ (e.target).result;
|
|
717
1065
|
const storeName = 'files-to-cache-' + unlocalizedWorkName;
|
|
718
1066
|
const trans = db.transaction(storeName);
|
|
719
1067
|
const store = trans.objectStore(storeName);
|
|
@@ -727,10 +1075,22 @@ export const resultsDisplayServerOrClient = async function resultsDisplayServerO
|
|
|
727
1075
|
// console.log('applicableBrowseFieldSetName', 'browseFields-' + applicableBrowseFieldSetName);
|
|
728
1076
|
|
|
729
1077
|
const r = index.getAll(IDBKeyRange.bound(startsRaw, endsRaw));
|
|
730
|
-
r.
|
|
731
|
-
|
|
732
|
-
|
|
733
|
-
|
|
1078
|
+
r.addEventListener(
|
|
1079
|
+
'success',
|
|
1080
|
+
/**
|
|
1081
|
+
* @param {Event} e
|
|
1082
|
+
* @returns {void}
|
|
1083
|
+
*/
|
|
1084
|
+
(e) => {
|
|
1085
|
+
// eslint-disable-next-line prefer-destructuring -- TS
|
|
1086
|
+
const result =
|
|
1087
|
+
/** @type {EventTarget & {result: {value: (string|Integer)[]}[]}} */ (
|
|
1088
|
+
e.target
|
|
1089
|
+
).result;
|
|
1090
|
+
const converted = result.map((r) => r.value);
|
|
1091
|
+
resolve(converted);
|
|
1092
|
+
}
|
|
1093
|
+
);
|
|
734
1094
|
};
|
|
735
1095
|
});
|
|
736
1096
|
} else {
|
|
@@ -742,18 +1102,19 @@ export const resultsDisplayServerOrClient = async function resultsDisplayServerO
|
|
|
742
1102
|
// needed
|
|
743
1103
|
// if (presort || this.noDynamic) {
|
|
744
1104
|
if (this.noDynamic) {
|
|
745
|
-
|
|
746
|
-
resolved
|
|
747
|
-
} = await JsonRefs.resolveRefs(fileData.file)
|
|
1105
|
+
const {
|
|
1106
|
+
resolved
|
|
1107
|
+
} = await JsonRefs.resolveRefs(fileData.file);
|
|
1108
|
+
(tableData = /** @type {{data: (string|Integer)[][]}} */ (resolved).data);
|
|
748
1109
|
runPresort({presort, tableData, applicableBrowseFieldNames, localizedFieldNames});
|
|
749
1110
|
} else {
|
|
750
1111
|
/*
|
|
751
|
-
|
|
752
|
-
|
|
753
|
-
|
|
754
|
-
|
|
755
|
-
|
|
756
|
-
|
|
1112
|
+
const jsonURL = Object.entries({
|
|
1113
|
+
prefI18n, unlocalizedWorkName, startsRaw, endsRaw
|
|
1114
|
+
}).reduce((url, [arg, argVal]) => {
|
|
1115
|
+
return url + '&' + arg + '=' + encodeURIComponent((argVal));
|
|
1116
|
+
}, `${dynamicBasePath}textbrowser?`);
|
|
1117
|
+
*/
|
|
757
1118
|
const jsonURL = `${dynamicBasePath}textbrowser?${$p.toString()}`;
|
|
758
1119
|
tableData = await (await fetch(jsonURL)).json();
|
|
759
1120
|
usingServerData = true;
|
|
@@ -767,8 +1128,9 @@ export const resultsDisplayServerOrClient = async function resultsDisplayServerO
|
|
|
767
1128
|
tableData.forEach((tr) => {
|
|
768
1129
|
// Todo: We should pass on other arguments (like `meta` but on `applicableFields`)
|
|
769
1130
|
tr.splice(
|
|
770
|
-
placement,
|
|
1131
|
+
placement ?? 0,
|
|
771
1132
|
0,
|
|
1133
|
+
// @ts-expect-error Only used for `plugin` type?
|
|
772
1134
|
null // `${i}-${j}`);
|
|
773
1135
|
);
|
|
774
1136
|
});
|
|
@@ -808,6 +1170,8 @@ export const resultsDisplayServerOrClient = async function resultsDisplayServerO
|
|
|
808
1170
|
escapeQuotedCSS, escapeCSS, escapeHTML,
|
|
809
1171
|
l, localizedFieldNames, fieldLangs, fieldDirs,
|
|
810
1172
|
caption, hasCaption, showInterlinTitles,
|
|
1173
|
+
showEmptyInterlinear: this.showEmptyInterlinear,
|
|
1174
|
+
showTitleOnSingleInterlinear: this.showTitleOnSingleInterlinear,
|
|
811
1175
|
determineEnd: determineEnd({
|
|
812
1176
|
applicableBrowseFieldNames,
|
|
813
1177
|
fieldValueAliasMap, fieldValueAliasMapPreferred,
|
|
@@ -821,7 +1185,8 @@ export const resultsDisplayServerOrClient = async function resultsDisplayServerO
|
|
|
821
1185
|
localizedFieldNames
|
|
822
1186
|
}),
|
|
823
1187
|
getCellValue: getCellValue({
|
|
824
|
-
fieldValueAliasMapPreferred, escapeColumnIndexes
|
|
1188
|
+
fieldValueAliasMapPreferred, escapeColumnIndexes
|
|
1189
|
+
// escapeHTML
|
|
825
1190
|
}),
|
|
826
1191
|
checkedAndInterlinearFieldInfo: getCheckedAndInterlinearFieldInfo({
|
|
827
1192
|
localizedFieldNames
|