@stoplight/elements-core 9.0.13 → 9.0.15
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/components/TryIt/Parameters/parameter-utils.d.ts +5 -5
- package/index.esm.js +121 -18
- package/index.js +121 -18
- package/index.mjs +121 -18
- package/package.json +1 -1
|
@@ -4,19 +4,19 @@ import { JSONSchema7, JSONSchema7Definition } from 'json-schema';
|
|
|
4
4
|
export declare type ParameterSpec = Pick<IHttpParam, 'name' | 'schema' | 'required'> & {
|
|
5
5
|
examples?: (Omit<INodeExample, 'id'> | Omit<INodeExternalExample, 'id'>)[];
|
|
6
6
|
};
|
|
7
|
-
export declare function
|
|
7
|
+
export declare function encodeSafeSelectorValue(value: string | number): string | number;
|
|
8
|
+
export declare function decodeSafeSelectorValue(value: string | number): string | number;
|
|
9
|
+
export declare function parameterOptions(parameter: ParameterSpec): {
|
|
8
10
|
value: string | number;
|
|
9
|
-
} | {
|
|
10
11
|
label: string;
|
|
11
|
-
|
|
12
|
-
})[] | null;
|
|
12
|
+
}[] | null;
|
|
13
13
|
export declare const selectExampleOption: {
|
|
14
14
|
value: string;
|
|
15
15
|
label: string;
|
|
16
16
|
};
|
|
17
17
|
export declare function exampleOptions(parameter: ParameterSpec): {
|
|
18
|
-
value: string;
|
|
19
18
|
label: string;
|
|
19
|
+
value: string | number;
|
|
20
20
|
}[] | null;
|
|
21
21
|
export declare function parameterSupportsFileUpload(parameter?: Pick<ParameterSpec, 'schema'>): boolean | undefined;
|
|
22
22
|
export declare function getPlaceholderForParameter(parameter: ParameterSpec): string;
|
package/index.esm.js
CHANGED
|
@@ -1340,8 +1340,50 @@ const booleanOptions = [
|
|
|
1340
1340
|
{ label: 'False', value: 'false' },
|
|
1341
1341
|
{ label: 'True', value: 'true' },
|
|
1342
1342
|
];
|
|
1343
|
+
function encodeSafeSelectorValue(value) {
|
|
1344
|
+
if (typeof value === 'number') {
|
|
1345
|
+
return value;
|
|
1346
|
+
}
|
|
1347
|
+
const hasSpecialChars = /["'\[\]\\(){}]/.test(value);
|
|
1348
|
+
if (!hasSpecialChars) {
|
|
1349
|
+
return value;
|
|
1350
|
+
}
|
|
1351
|
+
try {
|
|
1352
|
+
return 'b64:' + btoa(value);
|
|
1353
|
+
}
|
|
1354
|
+
catch (e) {
|
|
1355
|
+
return 'enc:' + encodeURIComponent(value);
|
|
1356
|
+
}
|
|
1357
|
+
}
|
|
1358
|
+
function decodeSafeSelectorValue(value) {
|
|
1359
|
+
if (typeof value === 'number') {
|
|
1360
|
+
return value;
|
|
1361
|
+
}
|
|
1362
|
+
if (value.startsWith('b64:')) {
|
|
1363
|
+
try {
|
|
1364
|
+
return atob(value.substring(4));
|
|
1365
|
+
}
|
|
1366
|
+
catch (e) {
|
|
1367
|
+
return value;
|
|
1368
|
+
}
|
|
1369
|
+
}
|
|
1370
|
+
if (value.startsWith('enc:')) {
|
|
1371
|
+
try {
|
|
1372
|
+
return decodeURIComponent(value.substring(4));
|
|
1373
|
+
}
|
|
1374
|
+
catch (e) {
|
|
1375
|
+
return value;
|
|
1376
|
+
}
|
|
1377
|
+
}
|
|
1378
|
+
return value;
|
|
1379
|
+
}
|
|
1343
1380
|
function enumOptions(enumValues, required) {
|
|
1344
|
-
const options = map(enumValues, v =>
|
|
1381
|
+
const options = map(enumValues, v => {
|
|
1382
|
+
var _a;
|
|
1383
|
+
const stringValue = typeof v === 'object' && v !== null ? (_a = safeStringify(v)) !== null && _a !== void 0 ? _a : String(v) : typeof v === 'number' ? v : String(v);
|
|
1384
|
+
const safeValue = encodeSafeSelectorValue(stringValue);
|
|
1385
|
+
return { value: safeValue, label: String(stringValue) };
|
|
1386
|
+
});
|
|
1345
1387
|
return required ? options : [{ label: 'Not Set', value: '' }, ...options];
|
|
1346
1388
|
}
|
|
1347
1389
|
function parameterOptions(parameter) {
|
|
@@ -1358,7 +1400,10 @@ function exampleOptions(parameter) {
|
|
|
1358
1400
|
return ((_a = parameter.examples) === null || _a === void 0 ? void 0 : _a.length) && parameter.examples.length > 1
|
|
1359
1401
|
? [
|
|
1360
1402
|
selectExampleOption,
|
|
1361
|
-
...parameter.examples.map(example => ({
|
|
1403
|
+
...parameter.examples.map(example => ({
|
|
1404
|
+
label: example.key,
|
|
1405
|
+
value: encodeSafeSelectorValue(exampleValue(example)),
|
|
1406
|
+
})),
|
|
1362
1407
|
]
|
|
1363
1408
|
: null;
|
|
1364
1409
|
}
|
|
@@ -1371,15 +1416,19 @@ function parameterSupportsFileUpload(parameter) {
|
|
|
1371
1416
|
((_c = parameter.schema) === null || _c === void 0 ? void 0 : _c.contentMediaType) === 'application/octet-stream'));
|
|
1372
1417
|
}
|
|
1373
1418
|
function stringifyValue(value) {
|
|
1374
|
-
|
|
1375
|
-
|
|
1376
|
-
|
|
1377
|
-
|
|
1378
|
-
return
|
|
1419
|
+
var _a;
|
|
1420
|
+
if (typeof value === 'object' && value !== null) {
|
|
1421
|
+
return (_a = safeStringify(value)) !== null && _a !== void 0 ? _a : String(value);
|
|
1422
|
+
}
|
|
1423
|
+
return String(value);
|
|
1379
1424
|
}
|
|
1380
1425
|
function escapeQuotes(value) {
|
|
1381
1426
|
return value.replace(/"/g, '\\"');
|
|
1382
1427
|
}
|
|
1428
|
+
function exampleValue(example) {
|
|
1429
|
+
const value = 'value' in example ? example.value : example.externalValue;
|
|
1430
|
+
return escapeQuotes(stringifyValue(value));
|
|
1431
|
+
}
|
|
1383
1432
|
function getPlaceholderForParameter(parameter) {
|
|
1384
1433
|
var _a, _b;
|
|
1385
1434
|
const { value: parameterValue, isDefault } = getValueForParameter(parameter);
|
|
@@ -1405,14 +1454,14 @@ const getValueForParameter = (parameter) => {
|
|
|
1405
1454
|
if (typeof defaultValue !== 'undefined') {
|
|
1406
1455
|
return { value: stringifyValue(defaultValue), isDefault: true };
|
|
1407
1456
|
}
|
|
1408
|
-
const
|
|
1409
|
-
if (examples.length > 0) {
|
|
1410
|
-
return { value: exampleValue(examples[0]) };
|
|
1411
|
-
}
|
|
1412
|
-
const enums = (_c = (_b = parameter.schema) === null || _b === void 0 ? void 0 : _b.enum) !== null && _c !== void 0 ? _c : [];
|
|
1457
|
+
const enums = (_b = (_a = parameter.schema) === null || _a === void 0 ? void 0 : _a.enum) !== null && _b !== void 0 ? _b : [];
|
|
1413
1458
|
if (enums.length > 0) {
|
|
1414
1459
|
return { value: stringifyValue(enums[0]) };
|
|
1415
1460
|
}
|
|
1461
|
+
const examples = (_c = parameter.examples) !== null && _c !== void 0 ? _c : [];
|
|
1462
|
+
if (examples.length > 0) {
|
|
1463
|
+
return { value: exampleValue(examples[0]) };
|
|
1464
|
+
}
|
|
1416
1465
|
return { value: '' };
|
|
1417
1466
|
};
|
|
1418
1467
|
const getInitialValueForParameter = (parameter) => {
|
|
@@ -1461,20 +1510,35 @@ function isRequired(n) {
|
|
|
1461
1510
|
}
|
|
1462
1511
|
|
|
1463
1512
|
const ParameterEditor = ({ parameter, value, onChange, isOptional, onChangeOptional, canChangeOptional, validate, }) => {
|
|
1464
|
-
var _a
|
|
1513
|
+
var _a;
|
|
1465
1514
|
const inputId = useUniqueId(`id_${parameter.name}_`);
|
|
1466
1515
|
const inputCheckId = useUniqueId(`id_${parameter.name}_checked`);
|
|
1467
1516
|
const parameterValueOptions = parameterOptions(parameter);
|
|
1468
1517
|
const examples = exampleOptions(parameter);
|
|
1469
|
-
const selectedExample =
|
|
1518
|
+
const selectedExample = React.useMemo(() => {
|
|
1519
|
+
if (!examples)
|
|
1520
|
+
return selectExampleOption;
|
|
1521
|
+
const matchingExample = examples.find(e => {
|
|
1522
|
+
return String(decodeSafeSelectorValue(e.value)) === value;
|
|
1523
|
+
});
|
|
1524
|
+
return matchingExample !== null && matchingExample !== void 0 ? matchingExample : selectExampleOption;
|
|
1525
|
+
}, [examples, value]);
|
|
1470
1526
|
const parameterDisplayName = `${parameter.name}${parameter.required ? '*' : ''}`;
|
|
1527
|
+
const encodedValue = React.useMemo(() => {
|
|
1528
|
+
if (!value || !parameterValueOptions)
|
|
1529
|
+
return value || '';
|
|
1530
|
+
const matchingOption = parameterValueOptions.find(opt => {
|
|
1531
|
+
return String(decodeSafeSelectorValue(opt.value)) === value;
|
|
1532
|
+
});
|
|
1533
|
+
return matchingOption ? String(matchingOption.value) : value;
|
|
1534
|
+
}, [value, parameterValueOptions]);
|
|
1471
1535
|
const requiredButEmpty = validate && parameter.required && !value;
|
|
1472
1536
|
return (React.createElement(React.Fragment, null,
|
|
1473
1537
|
React.createElement(Text, { as: "label", "aria-hidden": "true", "data-testid": "param-label", htmlFor: inputId, fontSize: "base" }, parameterDisplayName),
|
|
1474
1538
|
React.createElement(Text, { mx: 3 }, ":"),
|
|
1475
|
-
React.createElement("div", null, parameterValueOptions ? (React.createElement(Select, { flex: 1, "aria-label": parameter.name, options: parameterValueOptions, value:
|
|
1476
|
-
React.createElement(Input, { id: inputId, "aria-label": parameter.name, appearance: requiredButEmpty ? 'default' : 'minimal', flex: 1, placeholder: getPlaceholderForParameter(parameter), type: ((
|
|
1477
|
-
examples && (React.createElement(Select, { "aria-label": `${parameter.name}-select`, flex: 1, value: selectedExample.value, options: examples, onChange: onChange }))))),
|
|
1539
|
+
React.createElement("div", null, parameterValueOptions ? (React.createElement(Select, { flex: 1, "aria-label": parameter.name, options: parameterValueOptions, value: encodedValue, onChange: val => onChange && onChange(String(decodeSafeSelectorValue(val))), placeholder: getPlaceholderForSelectedParameter(parameter) })) : (React.createElement(Flex, { flex: 1 },
|
|
1540
|
+
React.createElement(Input, { id: inputId, "aria-label": parameter.name, appearance: requiredButEmpty ? 'default' : 'minimal', flex: 1, placeholder: getPlaceholderForParameter(parameter), type: ((_a = parameter.schema) === null || _a === void 0 ? void 0 : _a.type) === 'number' ? 'number' : 'text', required: true, intent: requiredButEmpty ? 'danger' : 'default', value: value || '', onChange: e => onChange && onChange(e.currentTarget.value) }),
|
|
1541
|
+
examples && (React.createElement(Select, { "aria-label": `${parameter.name}-select`, flex: 1, value: selectedExample.value, options: examples, onChange: val => onChange && onChange(String(decodeSafeSelectorValue(val))) }))))),
|
|
1478
1542
|
canChangeOptional && !parameter.required && (React.createElement(React.Fragment, null,
|
|
1479
1543
|
React.createElement("div", null),
|
|
1480
1544
|
React.createElement("div", null),
|
|
@@ -2327,10 +2391,17 @@ ServersDropdown.displayName = 'ServersDropdown';
|
|
|
2327
2391
|
|
|
2328
2392
|
const VariableEditor = ({ variable, value, onChange }) => {
|
|
2329
2393
|
const inputId = useUniqueId(`id_${variable.name}_`);
|
|
2394
|
+
const encodedOptions = React.useMemo(() => (variable.enum ? variable.enum.map(s => ({ value: encodeSafeSelectorValue(s), label: String(s) })) : []), [variable.enum]);
|
|
2395
|
+
const encodedValue = React.useMemo(() => {
|
|
2396
|
+
if (!value || !variable.enum)
|
|
2397
|
+
return value || variable.default;
|
|
2398
|
+
const matchingOption = encodedOptions.find(opt => decodeSafeSelectorValue(String(opt.value)) === value);
|
|
2399
|
+
return matchingOption ? String(matchingOption.value) : value;
|
|
2400
|
+
}, [value, variable.enum, variable.default, encodedOptions]);
|
|
2330
2401
|
return (React.createElement(React.Fragment, null,
|
|
2331
2402
|
React.createElement(Text, { as: "label", "aria-hidden": "true", "data-testid": "param-label", htmlFor: inputId, fontSize: "base" }, variable.name),
|
|
2332
2403
|
React.createElement(Text, { mx: 3 }, ":"),
|
|
2333
|
-
React.createElement("div", null, variable.enum ? (React.createElement(Select, { flex: 1, "aria-label": variable.name, options:
|
|
2404
|
+
React.createElement("div", null, variable.enum ? (React.createElement(Select, { flex: 1, "aria-label": variable.name, options: encodedOptions, value: encodedValue, onChange: val => onChange && onChange(decodeSafeSelectorValue(String(val))) })) : (React.createElement(Flex, { flex: 1 },
|
|
2334
2405
|
React.createElement(Input, { id: inputId, "aria-label": variable.name, appearance: 'minimal', flex: 1, placeholder: variable.default, type: "text", required: true, intent: 'default', value: value || '', onChange: e => onChange && onChange(e.currentTarget.value) }))))));
|
|
2335
2406
|
};
|
|
2336
2407
|
|
|
@@ -3535,6 +3606,38 @@ const TableOfContents = React.memo(({ tree, activeId, Link, maxDepthOpenByDefaul
|
|
|
3535
3606
|
});
|
|
3536
3607
|
}, []);
|
|
3537
3608
|
const updatedTree = updateTocTree(tree, '');
|
|
3609
|
+
const findFirstMatchAndIndexMatch = React.useCallback((items, id) => {
|
|
3610
|
+
let firstMatch;
|
|
3611
|
+
let hasAnyLastIndexMatch = false;
|
|
3612
|
+
if (!id)
|
|
3613
|
+
return [firstMatch, hasAnyLastIndexMatch];
|
|
3614
|
+
const walk = (arr, stack) => {
|
|
3615
|
+
for (const itm of arr) {
|
|
3616
|
+
const newStack = stack.concat(itm);
|
|
3617
|
+
const matches = ('slug' in itm && itm.slug === id) || ('id' in itm && itm.id === id);
|
|
3618
|
+
if (matches) {
|
|
3619
|
+
if (!firstMatch)
|
|
3620
|
+
firstMatch = itm;
|
|
3621
|
+
const hasLastIndexMatch = newStack.some(el => 'index' in el && el.index === lastActiveIndex);
|
|
3622
|
+
if (hasLastIndexMatch)
|
|
3623
|
+
hasAnyLastIndexMatch = true;
|
|
3624
|
+
}
|
|
3625
|
+
if ('items' in itm && Array.isArray(itm.items)) {
|
|
3626
|
+
if (walk(itm.items, newStack))
|
|
3627
|
+
return true;
|
|
3628
|
+
}
|
|
3629
|
+
}
|
|
3630
|
+
return false;
|
|
3631
|
+
};
|
|
3632
|
+
walk(items, []);
|
|
3633
|
+
return [firstMatch, hasAnyLastIndexMatch];
|
|
3634
|
+
}, [lastActiveIndex]);
|
|
3635
|
+
const [firstMatchItem, hasAnyLastIndexMatch] = React.useMemo(() => findFirstMatchAndIndexMatch(updatedTree, activeId), [updatedTree, activeId, findFirstMatchAndIndexMatch]);
|
|
3636
|
+
React.useEffect(() => {
|
|
3637
|
+
if (!hasAnyLastIndexMatch && firstMatchItem && 'index' in firstMatchItem && firstMatchItem.index) {
|
|
3638
|
+
setLastActiveIndex(firstMatchItem.index);
|
|
3639
|
+
}
|
|
3640
|
+
}, [firstMatchItem, hasAnyLastIndexMatch]);
|
|
3538
3641
|
const container = React.useRef(null);
|
|
3539
3642
|
const child = React.useRef(null);
|
|
3540
3643
|
const firstRender = useFirstRender();
|
package/index.js
CHANGED
|
@@ -1361,8 +1361,50 @@ const booleanOptions = [
|
|
|
1361
1361
|
{ label: 'False', value: 'false' },
|
|
1362
1362
|
{ label: 'True', value: 'true' },
|
|
1363
1363
|
];
|
|
1364
|
+
function encodeSafeSelectorValue(value) {
|
|
1365
|
+
if (typeof value === 'number') {
|
|
1366
|
+
return value;
|
|
1367
|
+
}
|
|
1368
|
+
const hasSpecialChars = /["'\[\]\\(){}]/.test(value);
|
|
1369
|
+
if (!hasSpecialChars) {
|
|
1370
|
+
return value;
|
|
1371
|
+
}
|
|
1372
|
+
try {
|
|
1373
|
+
return 'b64:' + btoa(value);
|
|
1374
|
+
}
|
|
1375
|
+
catch (e) {
|
|
1376
|
+
return 'enc:' + encodeURIComponent(value);
|
|
1377
|
+
}
|
|
1378
|
+
}
|
|
1379
|
+
function decodeSafeSelectorValue(value) {
|
|
1380
|
+
if (typeof value === 'number') {
|
|
1381
|
+
return value;
|
|
1382
|
+
}
|
|
1383
|
+
if (value.startsWith('b64:')) {
|
|
1384
|
+
try {
|
|
1385
|
+
return atob(value.substring(4));
|
|
1386
|
+
}
|
|
1387
|
+
catch (e) {
|
|
1388
|
+
return value;
|
|
1389
|
+
}
|
|
1390
|
+
}
|
|
1391
|
+
if (value.startsWith('enc:')) {
|
|
1392
|
+
try {
|
|
1393
|
+
return decodeURIComponent(value.substring(4));
|
|
1394
|
+
}
|
|
1395
|
+
catch (e) {
|
|
1396
|
+
return value;
|
|
1397
|
+
}
|
|
1398
|
+
}
|
|
1399
|
+
return value;
|
|
1400
|
+
}
|
|
1364
1401
|
function enumOptions(enumValues, required) {
|
|
1365
|
-
const options = map(enumValues, v =>
|
|
1402
|
+
const options = map(enumValues, v => {
|
|
1403
|
+
var _a;
|
|
1404
|
+
const stringValue = typeof v === 'object' && v !== null ? (_a = json.safeStringify(v)) !== null && _a !== void 0 ? _a : String(v) : typeof v === 'number' ? v : String(v);
|
|
1405
|
+
const safeValue = encodeSafeSelectorValue(stringValue);
|
|
1406
|
+
return { value: safeValue, label: String(stringValue) };
|
|
1407
|
+
});
|
|
1366
1408
|
return required ? options : [{ label: 'Not Set', value: '' }, ...options];
|
|
1367
1409
|
}
|
|
1368
1410
|
function parameterOptions(parameter) {
|
|
@@ -1379,7 +1421,10 @@ function exampleOptions(parameter) {
|
|
|
1379
1421
|
return ((_a = parameter.examples) === null || _a === void 0 ? void 0 : _a.length) && parameter.examples.length > 1
|
|
1380
1422
|
? [
|
|
1381
1423
|
selectExampleOption,
|
|
1382
|
-
...parameter.examples.map(example => ({
|
|
1424
|
+
...parameter.examples.map(example => ({
|
|
1425
|
+
label: example.key,
|
|
1426
|
+
value: encodeSafeSelectorValue(exampleValue(example)),
|
|
1427
|
+
})),
|
|
1383
1428
|
]
|
|
1384
1429
|
: null;
|
|
1385
1430
|
}
|
|
@@ -1392,15 +1437,19 @@ function parameterSupportsFileUpload(parameter) {
|
|
|
1392
1437
|
((_c = parameter.schema) === null || _c === void 0 ? void 0 : _c.contentMediaType) === 'application/octet-stream'));
|
|
1393
1438
|
}
|
|
1394
1439
|
function stringifyValue(value) {
|
|
1395
|
-
|
|
1396
|
-
|
|
1397
|
-
|
|
1398
|
-
|
|
1399
|
-
return
|
|
1440
|
+
var _a;
|
|
1441
|
+
if (typeof value === 'object' && value !== null) {
|
|
1442
|
+
return (_a = json.safeStringify(value)) !== null && _a !== void 0 ? _a : String(value);
|
|
1443
|
+
}
|
|
1444
|
+
return String(value);
|
|
1400
1445
|
}
|
|
1401
1446
|
function escapeQuotes(value) {
|
|
1402
1447
|
return value.replace(/"/g, '\\"');
|
|
1403
1448
|
}
|
|
1449
|
+
function exampleValue(example) {
|
|
1450
|
+
const value = 'value' in example ? example.value : example.externalValue;
|
|
1451
|
+
return escapeQuotes(stringifyValue(value));
|
|
1452
|
+
}
|
|
1404
1453
|
function getPlaceholderForParameter(parameter) {
|
|
1405
1454
|
var _a, _b;
|
|
1406
1455
|
const { value: parameterValue, isDefault } = getValueForParameter(parameter);
|
|
@@ -1426,14 +1475,14 @@ const getValueForParameter = (parameter) => {
|
|
|
1426
1475
|
if (typeof defaultValue !== 'undefined') {
|
|
1427
1476
|
return { value: stringifyValue(defaultValue), isDefault: true };
|
|
1428
1477
|
}
|
|
1429
|
-
const
|
|
1430
|
-
if (examples.length > 0) {
|
|
1431
|
-
return { value: exampleValue(examples[0]) };
|
|
1432
|
-
}
|
|
1433
|
-
const enums = (_c = (_b = parameter.schema) === null || _b === void 0 ? void 0 : _b.enum) !== null && _c !== void 0 ? _c : [];
|
|
1478
|
+
const enums = (_b = (_a = parameter.schema) === null || _a === void 0 ? void 0 : _a.enum) !== null && _b !== void 0 ? _b : [];
|
|
1434
1479
|
if (enums.length > 0) {
|
|
1435
1480
|
return { value: stringifyValue(enums[0]) };
|
|
1436
1481
|
}
|
|
1482
|
+
const examples = (_c = parameter.examples) !== null && _c !== void 0 ? _c : [];
|
|
1483
|
+
if (examples.length > 0) {
|
|
1484
|
+
return { value: exampleValue(examples[0]) };
|
|
1485
|
+
}
|
|
1437
1486
|
return { value: '' };
|
|
1438
1487
|
};
|
|
1439
1488
|
const getInitialValueForParameter = (parameter) => {
|
|
@@ -1482,20 +1531,35 @@ function isRequired(n) {
|
|
|
1482
1531
|
}
|
|
1483
1532
|
|
|
1484
1533
|
const ParameterEditor = ({ parameter, value, onChange, isOptional, onChangeOptional, canChangeOptional, validate, }) => {
|
|
1485
|
-
var _a
|
|
1534
|
+
var _a;
|
|
1486
1535
|
const inputId = useUniqueId(`id_${parameter.name}_`);
|
|
1487
1536
|
const inputCheckId = useUniqueId(`id_${parameter.name}_checked`);
|
|
1488
1537
|
const parameterValueOptions = parameterOptions(parameter);
|
|
1489
1538
|
const examples = exampleOptions(parameter);
|
|
1490
|
-
const selectedExample =
|
|
1539
|
+
const selectedExample = React__namespace.useMemo(() => {
|
|
1540
|
+
if (!examples)
|
|
1541
|
+
return selectExampleOption;
|
|
1542
|
+
const matchingExample = examples.find(e => {
|
|
1543
|
+
return String(decodeSafeSelectorValue(e.value)) === value;
|
|
1544
|
+
});
|
|
1545
|
+
return matchingExample !== null && matchingExample !== void 0 ? matchingExample : selectExampleOption;
|
|
1546
|
+
}, [examples, value]);
|
|
1491
1547
|
const parameterDisplayName = `${parameter.name}${parameter.required ? '*' : ''}`;
|
|
1548
|
+
const encodedValue = React__namespace.useMemo(() => {
|
|
1549
|
+
if (!value || !parameterValueOptions)
|
|
1550
|
+
return value || '';
|
|
1551
|
+
const matchingOption = parameterValueOptions.find(opt => {
|
|
1552
|
+
return String(decodeSafeSelectorValue(opt.value)) === value;
|
|
1553
|
+
});
|
|
1554
|
+
return matchingOption ? String(matchingOption.value) : value;
|
|
1555
|
+
}, [value, parameterValueOptions]);
|
|
1492
1556
|
const requiredButEmpty = validate && parameter.required && !value;
|
|
1493
1557
|
return (React__namespace.createElement(React__namespace.Fragment, null,
|
|
1494
1558
|
React__namespace.createElement(mosaic.Text, { as: "label", "aria-hidden": "true", "data-testid": "param-label", htmlFor: inputId, fontSize: "base" }, parameterDisplayName),
|
|
1495
1559
|
React__namespace.createElement(mosaic.Text, { mx: 3 }, ":"),
|
|
1496
|
-
React__namespace.createElement("div", null, parameterValueOptions ? (React__namespace.createElement(mosaic.Select, { flex: 1, "aria-label": parameter.name, options: parameterValueOptions, value:
|
|
1497
|
-
React__namespace.createElement(mosaic.Input, { id: inputId, "aria-label": parameter.name, appearance: requiredButEmpty ? 'default' : 'minimal', flex: 1, placeholder: getPlaceholderForParameter(parameter), type: ((
|
|
1498
|
-
examples && (React__namespace.createElement(mosaic.Select, { "aria-label": `${parameter.name}-select`, flex: 1, value: selectedExample.value, options: examples, onChange: onChange }))))),
|
|
1560
|
+
React__namespace.createElement("div", null, parameterValueOptions ? (React__namespace.createElement(mosaic.Select, { flex: 1, "aria-label": parameter.name, options: parameterValueOptions, value: encodedValue, onChange: val => onChange && onChange(String(decodeSafeSelectorValue(val))), placeholder: getPlaceholderForSelectedParameter(parameter) })) : (React__namespace.createElement(mosaic.Flex, { flex: 1 },
|
|
1561
|
+
React__namespace.createElement(mosaic.Input, { id: inputId, "aria-label": parameter.name, appearance: requiredButEmpty ? 'default' : 'minimal', flex: 1, placeholder: getPlaceholderForParameter(parameter), type: ((_a = parameter.schema) === null || _a === void 0 ? void 0 : _a.type) === 'number' ? 'number' : 'text', required: true, intent: requiredButEmpty ? 'danger' : 'default', value: value || '', onChange: e => onChange && onChange(e.currentTarget.value) }),
|
|
1562
|
+
examples && (React__namespace.createElement(mosaic.Select, { "aria-label": `${parameter.name}-select`, flex: 1, value: selectedExample.value, options: examples, onChange: val => onChange && onChange(String(decodeSafeSelectorValue(val))) }))))),
|
|
1499
1563
|
canChangeOptional && !parameter.required && (React__namespace.createElement(React__namespace.Fragment, null,
|
|
1500
1564
|
React__namespace.createElement("div", null),
|
|
1501
1565
|
React__namespace.createElement("div", null),
|
|
@@ -2348,10 +2412,17 @@ ServersDropdown.displayName = 'ServersDropdown';
|
|
|
2348
2412
|
|
|
2349
2413
|
const VariableEditor = ({ variable, value, onChange }) => {
|
|
2350
2414
|
const inputId = useUniqueId(`id_${variable.name}_`);
|
|
2415
|
+
const encodedOptions = React__namespace.useMemo(() => (variable.enum ? variable.enum.map(s => ({ value: encodeSafeSelectorValue(s), label: String(s) })) : []), [variable.enum]);
|
|
2416
|
+
const encodedValue = React__namespace.useMemo(() => {
|
|
2417
|
+
if (!value || !variable.enum)
|
|
2418
|
+
return value || variable.default;
|
|
2419
|
+
const matchingOption = encodedOptions.find(opt => decodeSafeSelectorValue(String(opt.value)) === value);
|
|
2420
|
+
return matchingOption ? String(matchingOption.value) : value;
|
|
2421
|
+
}, [value, variable.enum, variable.default, encodedOptions]);
|
|
2351
2422
|
return (React__namespace.createElement(React__namespace.Fragment, null,
|
|
2352
2423
|
React__namespace.createElement(mosaic.Text, { as: "label", "aria-hidden": "true", "data-testid": "param-label", htmlFor: inputId, fontSize: "base" }, variable.name),
|
|
2353
2424
|
React__namespace.createElement(mosaic.Text, { mx: 3 }, ":"),
|
|
2354
|
-
React__namespace.createElement("div", null, variable.enum ? (React__namespace.createElement(mosaic.Select, { flex: 1, "aria-label": variable.name, options:
|
|
2425
|
+
React__namespace.createElement("div", null, variable.enum ? (React__namespace.createElement(mosaic.Select, { flex: 1, "aria-label": variable.name, options: encodedOptions, value: encodedValue, onChange: val => onChange && onChange(decodeSafeSelectorValue(String(val))) })) : (React__namespace.createElement(mosaic.Flex, { flex: 1 },
|
|
2355
2426
|
React__namespace.createElement(mosaic.Input, { id: inputId, "aria-label": variable.name, appearance: 'minimal', flex: 1, placeholder: variable.default, type: "text", required: true, intent: 'default', value: value || '', onChange: e => onChange && onChange(e.currentTarget.value) }))))));
|
|
2356
2427
|
};
|
|
2357
2428
|
|
|
@@ -3556,6 +3627,38 @@ const TableOfContents = React__namespace.memo(({ tree, activeId, Link, maxDepthO
|
|
|
3556
3627
|
});
|
|
3557
3628
|
}, []);
|
|
3558
3629
|
const updatedTree = updateTocTree(tree, '');
|
|
3630
|
+
const findFirstMatchAndIndexMatch = React__namespace.useCallback((items, id) => {
|
|
3631
|
+
let firstMatch;
|
|
3632
|
+
let hasAnyLastIndexMatch = false;
|
|
3633
|
+
if (!id)
|
|
3634
|
+
return [firstMatch, hasAnyLastIndexMatch];
|
|
3635
|
+
const walk = (arr, stack) => {
|
|
3636
|
+
for (const itm of arr) {
|
|
3637
|
+
const newStack = stack.concat(itm);
|
|
3638
|
+
const matches = ('slug' in itm && itm.slug === id) || ('id' in itm && itm.id === id);
|
|
3639
|
+
if (matches) {
|
|
3640
|
+
if (!firstMatch)
|
|
3641
|
+
firstMatch = itm;
|
|
3642
|
+
const hasLastIndexMatch = newStack.some(el => 'index' in el && el.index === lastActiveIndex);
|
|
3643
|
+
if (hasLastIndexMatch)
|
|
3644
|
+
hasAnyLastIndexMatch = true;
|
|
3645
|
+
}
|
|
3646
|
+
if ('items' in itm && Array.isArray(itm.items)) {
|
|
3647
|
+
if (walk(itm.items, newStack))
|
|
3648
|
+
return true;
|
|
3649
|
+
}
|
|
3650
|
+
}
|
|
3651
|
+
return false;
|
|
3652
|
+
};
|
|
3653
|
+
walk(items, []);
|
|
3654
|
+
return [firstMatch, hasAnyLastIndexMatch];
|
|
3655
|
+
}, [lastActiveIndex]);
|
|
3656
|
+
const [firstMatchItem, hasAnyLastIndexMatch] = React__namespace.useMemo(() => findFirstMatchAndIndexMatch(updatedTree, activeId), [updatedTree, activeId, findFirstMatchAndIndexMatch]);
|
|
3657
|
+
React__namespace.useEffect(() => {
|
|
3658
|
+
if (!hasAnyLastIndexMatch && firstMatchItem && 'index' in firstMatchItem && firstMatchItem.index) {
|
|
3659
|
+
setLastActiveIndex(firstMatchItem.index);
|
|
3660
|
+
}
|
|
3661
|
+
}, [firstMatchItem, hasAnyLastIndexMatch]);
|
|
3559
3662
|
const container = React__namespace.useRef(null);
|
|
3560
3663
|
const child = React__namespace.useRef(null);
|
|
3561
3664
|
const firstRender = useFirstRender();
|
package/index.mjs
CHANGED
|
@@ -1340,8 +1340,50 @@ const booleanOptions = [
|
|
|
1340
1340
|
{ label: 'False', value: 'false' },
|
|
1341
1341
|
{ label: 'True', value: 'true' },
|
|
1342
1342
|
];
|
|
1343
|
+
function encodeSafeSelectorValue(value) {
|
|
1344
|
+
if (typeof value === 'number') {
|
|
1345
|
+
return value;
|
|
1346
|
+
}
|
|
1347
|
+
const hasSpecialChars = /["'\[\]\\(){}]/.test(value);
|
|
1348
|
+
if (!hasSpecialChars) {
|
|
1349
|
+
return value;
|
|
1350
|
+
}
|
|
1351
|
+
try {
|
|
1352
|
+
return 'b64:' + btoa(value);
|
|
1353
|
+
}
|
|
1354
|
+
catch (e) {
|
|
1355
|
+
return 'enc:' + encodeURIComponent(value);
|
|
1356
|
+
}
|
|
1357
|
+
}
|
|
1358
|
+
function decodeSafeSelectorValue(value) {
|
|
1359
|
+
if (typeof value === 'number') {
|
|
1360
|
+
return value;
|
|
1361
|
+
}
|
|
1362
|
+
if (value.startsWith('b64:')) {
|
|
1363
|
+
try {
|
|
1364
|
+
return atob(value.substring(4));
|
|
1365
|
+
}
|
|
1366
|
+
catch (e) {
|
|
1367
|
+
return value;
|
|
1368
|
+
}
|
|
1369
|
+
}
|
|
1370
|
+
if (value.startsWith('enc:')) {
|
|
1371
|
+
try {
|
|
1372
|
+
return decodeURIComponent(value.substring(4));
|
|
1373
|
+
}
|
|
1374
|
+
catch (e) {
|
|
1375
|
+
return value;
|
|
1376
|
+
}
|
|
1377
|
+
}
|
|
1378
|
+
return value;
|
|
1379
|
+
}
|
|
1343
1380
|
function enumOptions(enumValues, required) {
|
|
1344
|
-
const options = map(enumValues, v =>
|
|
1381
|
+
const options = map(enumValues, v => {
|
|
1382
|
+
var _a;
|
|
1383
|
+
const stringValue = typeof v === 'object' && v !== null ? (_a = safeStringify(v)) !== null && _a !== void 0 ? _a : String(v) : typeof v === 'number' ? v : String(v);
|
|
1384
|
+
const safeValue = encodeSafeSelectorValue(stringValue);
|
|
1385
|
+
return { value: safeValue, label: String(stringValue) };
|
|
1386
|
+
});
|
|
1345
1387
|
return required ? options : [{ label: 'Not Set', value: '' }, ...options];
|
|
1346
1388
|
}
|
|
1347
1389
|
function parameterOptions(parameter) {
|
|
@@ -1358,7 +1400,10 @@ function exampleOptions(parameter) {
|
|
|
1358
1400
|
return ((_a = parameter.examples) === null || _a === void 0 ? void 0 : _a.length) && parameter.examples.length > 1
|
|
1359
1401
|
? [
|
|
1360
1402
|
selectExampleOption,
|
|
1361
|
-
...parameter.examples.map(example => ({
|
|
1403
|
+
...parameter.examples.map(example => ({
|
|
1404
|
+
label: example.key,
|
|
1405
|
+
value: encodeSafeSelectorValue(exampleValue(example)),
|
|
1406
|
+
})),
|
|
1362
1407
|
]
|
|
1363
1408
|
: null;
|
|
1364
1409
|
}
|
|
@@ -1371,15 +1416,19 @@ function parameterSupportsFileUpload(parameter) {
|
|
|
1371
1416
|
((_c = parameter.schema) === null || _c === void 0 ? void 0 : _c.contentMediaType) === 'application/octet-stream'));
|
|
1372
1417
|
}
|
|
1373
1418
|
function stringifyValue(value) {
|
|
1374
|
-
|
|
1375
|
-
|
|
1376
|
-
|
|
1377
|
-
|
|
1378
|
-
return
|
|
1419
|
+
var _a;
|
|
1420
|
+
if (typeof value === 'object' && value !== null) {
|
|
1421
|
+
return (_a = safeStringify(value)) !== null && _a !== void 0 ? _a : String(value);
|
|
1422
|
+
}
|
|
1423
|
+
return String(value);
|
|
1379
1424
|
}
|
|
1380
1425
|
function escapeQuotes(value) {
|
|
1381
1426
|
return value.replace(/"/g, '\\"');
|
|
1382
1427
|
}
|
|
1428
|
+
function exampleValue(example) {
|
|
1429
|
+
const value = 'value' in example ? example.value : example.externalValue;
|
|
1430
|
+
return escapeQuotes(stringifyValue(value));
|
|
1431
|
+
}
|
|
1383
1432
|
function getPlaceholderForParameter(parameter) {
|
|
1384
1433
|
var _a, _b;
|
|
1385
1434
|
const { value: parameterValue, isDefault } = getValueForParameter(parameter);
|
|
@@ -1405,14 +1454,14 @@ const getValueForParameter = (parameter) => {
|
|
|
1405
1454
|
if (typeof defaultValue !== 'undefined') {
|
|
1406
1455
|
return { value: stringifyValue(defaultValue), isDefault: true };
|
|
1407
1456
|
}
|
|
1408
|
-
const
|
|
1409
|
-
if (examples.length > 0) {
|
|
1410
|
-
return { value: exampleValue(examples[0]) };
|
|
1411
|
-
}
|
|
1412
|
-
const enums = (_c = (_b = parameter.schema) === null || _b === void 0 ? void 0 : _b.enum) !== null && _c !== void 0 ? _c : [];
|
|
1457
|
+
const enums = (_b = (_a = parameter.schema) === null || _a === void 0 ? void 0 : _a.enum) !== null && _b !== void 0 ? _b : [];
|
|
1413
1458
|
if (enums.length > 0) {
|
|
1414
1459
|
return { value: stringifyValue(enums[0]) };
|
|
1415
1460
|
}
|
|
1461
|
+
const examples = (_c = parameter.examples) !== null && _c !== void 0 ? _c : [];
|
|
1462
|
+
if (examples.length > 0) {
|
|
1463
|
+
return { value: exampleValue(examples[0]) };
|
|
1464
|
+
}
|
|
1416
1465
|
return { value: '' };
|
|
1417
1466
|
};
|
|
1418
1467
|
const getInitialValueForParameter = (parameter) => {
|
|
@@ -1461,20 +1510,35 @@ function isRequired(n) {
|
|
|
1461
1510
|
}
|
|
1462
1511
|
|
|
1463
1512
|
const ParameterEditor = ({ parameter, value, onChange, isOptional, onChangeOptional, canChangeOptional, validate, }) => {
|
|
1464
|
-
var _a
|
|
1513
|
+
var _a;
|
|
1465
1514
|
const inputId = useUniqueId(`id_${parameter.name}_`);
|
|
1466
1515
|
const inputCheckId = useUniqueId(`id_${parameter.name}_checked`);
|
|
1467
1516
|
const parameterValueOptions = parameterOptions(parameter);
|
|
1468
1517
|
const examples = exampleOptions(parameter);
|
|
1469
|
-
const selectedExample =
|
|
1518
|
+
const selectedExample = React.useMemo(() => {
|
|
1519
|
+
if (!examples)
|
|
1520
|
+
return selectExampleOption;
|
|
1521
|
+
const matchingExample = examples.find(e => {
|
|
1522
|
+
return String(decodeSafeSelectorValue(e.value)) === value;
|
|
1523
|
+
});
|
|
1524
|
+
return matchingExample !== null && matchingExample !== void 0 ? matchingExample : selectExampleOption;
|
|
1525
|
+
}, [examples, value]);
|
|
1470
1526
|
const parameterDisplayName = `${parameter.name}${parameter.required ? '*' : ''}`;
|
|
1527
|
+
const encodedValue = React.useMemo(() => {
|
|
1528
|
+
if (!value || !parameterValueOptions)
|
|
1529
|
+
return value || '';
|
|
1530
|
+
const matchingOption = parameterValueOptions.find(opt => {
|
|
1531
|
+
return String(decodeSafeSelectorValue(opt.value)) === value;
|
|
1532
|
+
});
|
|
1533
|
+
return matchingOption ? String(matchingOption.value) : value;
|
|
1534
|
+
}, [value, parameterValueOptions]);
|
|
1471
1535
|
const requiredButEmpty = validate && parameter.required && !value;
|
|
1472
1536
|
return (React.createElement(React.Fragment, null,
|
|
1473
1537
|
React.createElement(Text, { as: "label", "aria-hidden": "true", "data-testid": "param-label", htmlFor: inputId, fontSize: "base" }, parameterDisplayName),
|
|
1474
1538
|
React.createElement(Text, { mx: 3 }, ":"),
|
|
1475
|
-
React.createElement("div", null, parameterValueOptions ? (React.createElement(Select, { flex: 1, "aria-label": parameter.name, options: parameterValueOptions, value:
|
|
1476
|
-
React.createElement(Input, { id: inputId, "aria-label": parameter.name, appearance: requiredButEmpty ? 'default' : 'minimal', flex: 1, placeholder: getPlaceholderForParameter(parameter), type: ((
|
|
1477
|
-
examples && (React.createElement(Select, { "aria-label": `${parameter.name}-select`, flex: 1, value: selectedExample.value, options: examples, onChange: onChange }))))),
|
|
1539
|
+
React.createElement("div", null, parameterValueOptions ? (React.createElement(Select, { flex: 1, "aria-label": parameter.name, options: parameterValueOptions, value: encodedValue, onChange: val => onChange && onChange(String(decodeSafeSelectorValue(val))), placeholder: getPlaceholderForSelectedParameter(parameter) })) : (React.createElement(Flex, { flex: 1 },
|
|
1540
|
+
React.createElement(Input, { id: inputId, "aria-label": parameter.name, appearance: requiredButEmpty ? 'default' : 'minimal', flex: 1, placeholder: getPlaceholderForParameter(parameter), type: ((_a = parameter.schema) === null || _a === void 0 ? void 0 : _a.type) === 'number' ? 'number' : 'text', required: true, intent: requiredButEmpty ? 'danger' : 'default', value: value || '', onChange: e => onChange && onChange(e.currentTarget.value) }),
|
|
1541
|
+
examples && (React.createElement(Select, { "aria-label": `${parameter.name}-select`, flex: 1, value: selectedExample.value, options: examples, onChange: val => onChange && onChange(String(decodeSafeSelectorValue(val))) }))))),
|
|
1478
1542
|
canChangeOptional && !parameter.required && (React.createElement(React.Fragment, null,
|
|
1479
1543
|
React.createElement("div", null),
|
|
1480
1544
|
React.createElement("div", null),
|
|
@@ -2327,10 +2391,17 @@ ServersDropdown.displayName = 'ServersDropdown';
|
|
|
2327
2391
|
|
|
2328
2392
|
const VariableEditor = ({ variable, value, onChange }) => {
|
|
2329
2393
|
const inputId = useUniqueId(`id_${variable.name}_`);
|
|
2394
|
+
const encodedOptions = React.useMemo(() => (variable.enum ? variable.enum.map(s => ({ value: encodeSafeSelectorValue(s), label: String(s) })) : []), [variable.enum]);
|
|
2395
|
+
const encodedValue = React.useMemo(() => {
|
|
2396
|
+
if (!value || !variable.enum)
|
|
2397
|
+
return value || variable.default;
|
|
2398
|
+
const matchingOption = encodedOptions.find(opt => decodeSafeSelectorValue(String(opt.value)) === value);
|
|
2399
|
+
return matchingOption ? String(matchingOption.value) : value;
|
|
2400
|
+
}, [value, variable.enum, variable.default, encodedOptions]);
|
|
2330
2401
|
return (React.createElement(React.Fragment, null,
|
|
2331
2402
|
React.createElement(Text, { as: "label", "aria-hidden": "true", "data-testid": "param-label", htmlFor: inputId, fontSize: "base" }, variable.name),
|
|
2332
2403
|
React.createElement(Text, { mx: 3 }, ":"),
|
|
2333
|
-
React.createElement("div", null, variable.enum ? (React.createElement(Select, { flex: 1, "aria-label": variable.name, options:
|
|
2404
|
+
React.createElement("div", null, variable.enum ? (React.createElement(Select, { flex: 1, "aria-label": variable.name, options: encodedOptions, value: encodedValue, onChange: val => onChange && onChange(decodeSafeSelectorValue(String(val))) })) : (React.createElement(Flex, { flex: 1 },
|
|
2334
2405
|
React.createElement(Input, { id: inputId, "aria-label": variable.name, appearance: 'minimal', flex: 1, placeholder: variable.default, type: "text", required: true, intent: 'default', value: value || '', onChange: e => onChange && onChange(e.currentTarget.value) }))))));
|
|
2335
2406
|
};
|
|
2336
2407
|
|
|
@@ -3535,6 +3606,38 @@ const TableOfContents = React.memo(({ tree, activeId, Link, maxDepthOpenByDefaul
|
|
|
3535
3606
|
});
|
|
3536
3607
|
}, []);
|
|
3537
3608
|
const updatedTree = updateTocTree(tree, '');
|
|
3609
|
+
const findFirstMatchAndIndexMatch = React.useCallback((items, id) => {
|
|
3610
|
+
let firstMatch;
|
|
3611
|
+
let hasAnyLastIndexMatch = false;
|
|
3612
|
+
if (!id)
|
|
3613
|
+
return [firstMatch, hasAnyLastIndexMatch];
|
|
3614
|
+
const walk = (arr, stack) => {
|
|
3615
|
+
for (const itm of arr) {
|
|
3616
|
+
const newStack = stack.concat(itm);
|
|
3617
|
+
const matches = ('slug' in itm && itm.slug === id) || ('id' in itm && itm.id === id);
|
|
3618
|
+
if (matches) {
|
|
3619
|
+
if (!firstMatch)
|
|
3620
|
+
firstMatch = itm;
|
|
3621
|
+
const hasLastIndexMatch = newStack.some(el => 'index' in el && el.index === lastActiveIndex);
|
|
3622
|
+
if (hasLastIndexMatch)
|
|
3623
|
+
hasAnyLastIndexMatch = true;
|
|
3624
|
+
}
|
|
3625
|
+
if ('items' in itm && Array.isArray(itm.items)) {
|
|
3626
|
+
if (walk(itm.items, newStack))
|
|
3627
|
+
return true;
|
|
3628
|
+
}
|
|
3629
|
+
}
|
|
3630
|
+
return false;
|
|
3631
|
+
};
|
|
3632
|
+
walk(items, []);
|
|
3633
|
+
return [firstMatch, hasAnyLastIndexMatch];
|
|
3634
|
+
}, [lastActiveIndex]);
|
|
3635
|
+
const [firstMatchItem, hasAnyLastIndexMatch] = React.useMemo(() => findFirstMatchAndIndexMatch(updatedTree, activeId), [updatedTree, activeId, findFirstMatchAndIndexMatch]);
|
|
3636
|
+
React.useEffect(() => {
|
|
3637
|
+
if (!hasAnyLastIndexMatch && firstMatchItem && 'index' in firstMatchItem && firstMatchItem.index) {
|
|
3638
|
+
setLastActiveIndex(firstMatchItem.index);
|
|
3639
|
+
}
|
|
3640
|
+
}, [firstMatchItem, hasAnyLastIndexMatch]);
|
|
3538
3641
|
const container = React.useRef(null);
|
|
3539
3642
|
const child = React.useRef(null);
|
|
3540
3643
|
const firstRender = useFirstRender();
|