Press n or j to go to the next uncovered block, b, p or k for the previous block.
| 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 | 14x 14x 14x 15x 15x 15x 15x 5x 5x 3x 10x 14x 41x 10x 4x 37x 15x 15x 14x 1x 1x 1x 13x 3x 1x 12x 12x 22x 27x 27x 18x 18x 27x 27x 27x 15x 3x 3x 12x 27x 27x 27x 15x 3x 27x 27x | import {
normalizeTangoAttributeInputs,
toInputScalarString,
type TangoAttributeInput
} from '@ska-octopus-widget-sdk/widget-sdk';
const DEFAULT_ENDPOINT = '1';
const URL_SCHEMES = new Set(['http', 'https', 'ws', 'wss']);
const parseRoutedEndpoint = (value: string): string => {
const trimmed = String(value ?? '').trim();
Iif (!trimmed) return '';
const routed = /^(.+):\/\/.+$/.exec(trimmed);
if (routed?.[1]) {
const selector = routed[1].trim();
if (URL_SCHEMES.has(selector.toLowerCase())) return '';
return selector;
}
return trimmed.includes('/') ? '' : trimmed;
};
const collectLegacyEntries = (input: unknown, out: unknown[]): void => {
if (Array.isArray(input)) {
input.forEach((entry) => collectLegacyEntries(entry, out));
return;
}
if (typeof input === 'string') {
const raw = input.trim();
if (!raw) return;
if (raw.startsWith('[') && raw.endsWith(']')) {
try {
collectLegacyEntries(JSON.parse(raw), out);
return;
} catch {
// Fall through and treat as regular string.
}
}
if (raw.includes(',')) {
raw.split(',').forEach((entry) => collectLegacyEntries(entry, out));
return;
}
out.push(raw);
return;
}
if (input != null) out.push(input);
};
export function normalizeEndpoints(
input: unknown,
opts?: { variables?: Record<string, unknown> | null }
): string[] {
const uniq = new Set<string>();
const add = (value: unknown) => {
const endpoint = toInputScalarString(value);
if (endpoint) uniq.add(endpoint);
};
const entries: unknown[] = [];
collectLegacyEntries(input, entries);
const tangoEntries: TangoAttributeInput[] = entries.map((entry) => {
if (entry && typeof entry === 'object') {
const candidate = entry as Record<string, unknown>;
return {
endpoint: candidate.endpoint,
attribute: candidate.attribute ?? candidate.device ?? candidate.value ?? '__endpoint__'
};
}
return toInputScalarString(entry);
});
const routed = normalizeTangoAttributeInputs({
attributes: tangoEntries,
variables: opts?.variables ?? undefined
});
routed.forEach((value) => add(parseRoutedEndpoint(value)));
// Backward-compat: preserve endpoint values from object entries even when attribute is empty.
entries.forEach((entry) => {
if (!entry || typeof entry !== 'object') return;
add((entry as Record<string, unknown>).endpoint);
});
if (uniq.size === 0) uniq.add(DEFAULT_ENDPOINT);
return Array.from(uniq);
}
|