@loaders.gl/graphs 5.0.0-beta.1 → 5.0.0-beta.2

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/index.cjs CHANGED
@@ -5,14 +5,6 @@ var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
5
5
  var __getOwnPropNames = Object.getOwnPropertyNames;
6
6
  var __getProtoOf = Object.getPrototypeOf;
7
7
  var __hasOwnProp = Object.prototype.hasOwnProperty;
8
- var __esm = (fn, res, err) => function __init() {
9
- if (err) throw err[0];
10
- try {
11
- return fn && (res = (0, fn[__getOwnPropNames(fn)[0]])(fn = 0)), res;
12
- } catch (e) {
13
- throw err = [e], e;
14
- }
15
- };
16
8
  var __export = (target, all) => {
17
9
  for (var name in all)
18
10
  __defProp(target, name, { get: all[name], enumerable: true });
@@ -35,1921 +27,26 @@ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__ge
35
27
  ));
36
28
  var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
37
29
 
38
- // src/graphml-loader-types.ts
39
- async function preload() {
40
- const { GraphMLLoaderWithParser: GraphMLLoaderWithParser2 } = await Promise.resolve().then(() => (init_graphml_loader(), graphml_loader_exports));
41
- return GraphMLLoaderWithParser2;
42
- }
43
- var VERSION, GraphMLLoader;
44
- var init_graphml_loader_types = __esm({
45
- "src/graphml-loader-types.ts"() {
46
- "use strict";
47
- VERSION = typeof __VERSION__ !== "undefined" ? __VERSION__ : "latest";
48
- GraphMLLoader = {
49
- name: "GraphML",
50
- id: "graphml",
51
- module: "graphs",
52
- version: VERSION,
53
- extensions: ["graphml"],
54
- mimeTypes: ["application/graphml+xml"],
55
- text: true,
56
- worker: false,
57
- dataType: null,
58
- batchType: null,
59
- options: { graphml: { shape: "arrow-table" } },
60
- preload
61
- };
62
- }
63
- });
64
-
65
- // ../core/src/schema-utils/lib/schema/convert-arrow-schema.ts
66
- function convertArrowToSchema(arrowSchema) {
67
- return serializeArrowSchema(arrowSchema);
68
- }
69
- function serializeArrowSchema(arrowSchema) {
70
- return {
71
- fields: arrowSchema.fields.map((arrowField) => serializeArrowField(arrowField)),
72
- metadata: serializeArrowMetadata(arrowSchema.metadata)
73
- };
74
- }
75
- function serializeArrowMetadata(arrowMetadata) {
76
- return Object.fromEntries(arrowMetadata);
77
- }
78
- function serializeArrowField(field) {
79
- return {
80
- name: field.name,
81
- type: serializeArrowType(field.type),
82
- nullable: field.nullable,
83
- metadata: serializeArrowMetadata(field.metadata)
84
- };
85
- }
86
- function serializeArrowType(arrowType) {
87
- if (isArrowViewType(arrowType, "BinaryView")) {
88
- return "binary-view";
89
- }
90
- if (isArrowViewType(arrowType, "Utf8View")) {
91
- return "utf8-view";
92
- }
93
- if (isOptionalArrowType(arrowType, "LargeList")) {
94
- const largeListType = arrowType;
95
- return {
96
- type: "large-list",
97
- children: [serializeArrowField(largeListType.valueField)]
98
- };
99
- }
100
- switch (arrowType.constructor) {
101
- case arrow.Null:
102
- return "null";
103
- case arrow.Binary:
104
- return "binary";
105
- case arrow.FixedSizeBinary:
106
- return {
107
- type: "fixed-size-binary",
108
- byteWidth: arrowType.byteWidth
109
- };
110
- case arrow.Bool:
111
- return "bool";
112
- case arrow.Int:
113
- const intType = arrowType;
114
- return `${intType.isSigned ? "" : "u"}int${intType.bitWidth}`;
115
- case arrow.Int8:
116
- return "int8";
117
- case arrow.Int16:
118
- return "int16";
119
- case arrow.Int32:
120
- return "int32";
121
- case arrow.Int64:
122
- return "int64";
123
- case arrow.Uint8:
124
- return "uint8";
125
- case arrow.Uint16:
126
- return "uint16";
127
- case arrow.Uint32:
128
- return "uint32";
129
- case arrow.Uint64:
130
- return "uint64";
131
- case arrow.Float:
132
- const precision = arrowType.precision;
133
- switch (precision) {
134
- case arrow.Precision.HALF:
135
- return "float16";
136
- case arrow.Precision.SINGLE:
137
- return "float32";
138
- case arrow.Precision.DOUBLE:
139
- return "float64";
140
- default:
141
- return "float16";
142
- }
143
- case arrow.Float16:
144
- return "float16";
145
- case arrow.Float32:
146
- return "float32";
147
- case arrow.Float64:
148
- return "float64";
149
- case arrow.Utf8:
150
- return "utf8";
151
- case arrow.Decimal:
152
- const decimal = arrowType;
153
- return {
154
- type: "decimal",
155
- bitWidth: decimal.bitWidth,
156
- precision: decimal.precision,
157
- scale: decimal.scale
158
- };
159
- case arrow.Date_:
160
- const dateUnit = arrowType.unit;
161
- return dateUnit === arrow.DateUnit.DAY ? "date-day" : "date-millisecond";
162
- case arrow.DateDay:
163
- return "date-day";
164
- case arrow.DateMillisecond:
165
- return "date-millisecond";
166
- case arrow.Time:
167
- const timeUnit = arrowType.unit;
168
- switch (timeUnit) {
169
- case arrow.TimeUnit.SECOND:
170
- return "time-second";
171
- case arrow.TimeUnit.MILLISECOND:
172
- return "time-millisecond";
173
- case arrow.TimeUnit.MICROSECOND:
174
- return "time-microsecond";
175
- case arrow.TimeUnit.NANOSECOND:
176
- return "time-nanosecond";
177
- default:
178
- return "time-second";
179
- }
180
- case arrow.TimeMillisecond:
181
- return "time-millisecond";
182
- case arrow.TimeSecond:
183
- return "time-second";
184
- case arrow.TimeMicrosecond:
185
- return "time-microsecond";
186
- case arrow.TimeNanosecond:
187
- return "time-nanosecond";
188
- case arrow.Timestamp:
189
- const timeStampUnit = arrowType.unit;
190
- switch (timeStampUnit) {
191
- case arrow.TimeUnit.SECOND:
192
- return "timestamp-second";
193
- case arrow.TimeUnit.MILLISECOND:
194
- return "timestamp-millisecond";
195
- case arrow.TimeUnit.MICROSECOND:
196
- return "timestamp-microsecond";
197
- case arrow.TimeUnit.NANOSECOND:
198
- return "timestamp-nanosecond";
199
- default:
200
- return "timestamp-second";
201
- }
202
- case arrow.TimestampSecond:
203
- return "timestamp-second";
204
- case arrow.TimestampMillisecond:
205
- return "timestamp-millisecond";
206
- case arrow.TimestampMicrosecond:
207
- return "timestamp-microsecond";
208
- case arrow.TimestampNanosecond:
209
- return "timestamp-nanosecond";
210
- case arrow.Interval:
211
- const intervalUnit = arrowType.unit;
212
- switch (intervalUnit) {
213
- case arrow.IntervalUnit.DAY_TIME:
214
- return "interval-daytime";
215
- case arrow.IntervalUnit.YEAR_MONTH:
216
- return "interval-yearmonth";
217
- default:
218
- return "interval-daytime";
219
- }
220
- case arrow.IntervalDayTime:
221
- return "interval-daytime";
222
- case arrow.IntervalYearMonth:
223
- return "interval-yearmonth";
224
- case arrow.Map_:
225
- const mapType = arrowType;
226
- return {
227
- type: "map",
228
- keysSorted: mapType.keysSorted,
229
- children: mapType.children.map((arrowField) => serializeArrowField(arrowField))
230
- };
231
- case arrow.List:
232
- const listType = arrowType;
233
- const listField = listType.valueField;
234
- return {
235
- type: "list",
236
- children: [serializeArrowField(listField)]
237
- };
238
- case arrow.FixedSizeList:
239
- const fixedSizeList = arrowType;
240
- return {
241
- type: "fixed-size-list",
242
- listSize: fixedSizeList.listSize,
243
- children: [serializeArrowField(fixedSizeList.children[0])]
244
- };
245
- case arrow.Struct:
246
- const structType = arrowType;
247
- return {
248
- type: "struct",
249
- children: structType.children.map((arrowField) => serializeArrowField(arrowField))
250
- };
251
- case arrow.SparseUnion:
252
- case arrow.DenseUnion:
253
- const unionType = arrowType;
254
- return {
255
- type: unionType instanceof arrow.DenseUnion ? "dense-union" : "sparse-union",
256
- typeIds: unionType.typeIds,
257
- children: unionType.children.map((arrowField) => serializeArrowField(arrowField)),
258
- typeIdToChildIndex: { ...unionType.typeIdToChildIndex }
259
- };
260
- case arrow.Dictionary:
261
- const dictionaryType = arrowType;
262
- return {
263
- type: "dictionary",
264
- id: dictionaryType.id,
265
- indices: serializeArrowDictionaryKeyType(dictionaryType.indices),
266
- dictionary: serializeArrowType(dictionaryType.dictionary),
267
- isOrdered: dictionaryType.isOrdered
268
- };
269
- default:
270
- throw new Error(`arrow type not supported: ${arrowType.constructor.name}`);
271
- }
272
- }
273
- function getOptionalArrowConstructor(typeName) {
274
- return arrow[typeName];
275
- }
276
- function isArrowViewType(arrowType, viewTypeName) {
277
- const constructor = getOptionalArrowConstructor(viewTypeName);
278
- if (constructor && arrowType instanceof constructor) {
279
- return true;
280
- }
281
- const guards = arrow.DataType;
282
- const guard = viewTypeName === "BinaryView" ? guards.isBinaryView : guards.isUtf8View;
283
- return Boolean(guard == null ? void 0 : guard(arrowType));
284
- }
285
- function isOptionalArrowType(arrowType, typeName) {
286
- const constructor = getOptionalArrowConstructor(typeName);
287
- return Boolean(constructor && arrowType instanceof constructor);
288
- }
289
- function serializeArrowDictionaryKeyType(arrowType) {
290
- if (arrowType instanceof arrow.Int) {
291
- const prefix = arrowType.isSigned ? "int" : "uint";
292
- const keyType = `${prefix}${arrowType.bitWidth}`;
293
- if (isSchemaDictionaryKeyType(keyType)) {
294
- return keyType;
295
- }
296
- }
297
- switch (arrowType.constructor) {
298
- case arrow.Int8:
299
- return "int8";
300
- case arrow.Int16:
301
- return "int16";
302
- case arrow.Int32:
303
- return "int32";
304
- case arrow.Uint8:
305
- return "uint8";
306
- case arrow.Uint16:
307
- return "uint16";
308
- case arrow.Uint32:
309
- return "uint32";
310
- default:
311
- throw new Error(`arrow dictionary index type not supported: ${arrowType.constructor.name}`);
312
- }
313
- }
314
- function isSchemaDictionaryKeyType(keyType) {
315
- return ["int8", "int16", "int32", "uint8", "uint16", "uint32"].includes(keyType);
316
- }
317
- var arrow;
318
- var init_convert_arrow_schema = __esm({
319
- "../core/src/schema-utils/lib/schema/convert-arrow-schema.ts"() {
320
- "use strict";
321
- arrow = __toESM(require("apache-arrow"), 1);
322
- }
323
- });
324
-
325
- // ../core/src/schema-utils/index.ts
326
- var init_schema_utils = __esm({
327
- "../core/src/schema-utils/index.ts"() {
328
- "use strict";
329
- init_convert_arrow_schema();
330
- }
331
- });
332
-
333
- // src/lib/build-graph-tables.ts
334
- function buildGraphTables(nodes, edges, shape, declarations) {
335
- if (shape === "plain-graph-data") {
336
- return { shape, nodes: Array.from(nodes), edges: Array.from(edges) };
337
- }
338
- if (shape !== "arrow-table" && shape !== "object-row-table") {
339
- throw new Error(`Unsupported graph shape: ${shape}`);
340
- }
341
- const nodeTable = buildGraphTable(nodes, false, shape, declarations == null ? void 0 : declarations.nodes);
342
- const edgeTable = buildGraphTable(edges, true, shape, declarations == null ? void 0 : declarations.edges);
343
- return {
344
- shape: "tables",
345
- tables: [
346
- { name: "nodes", table: nodeTable },
347
- { name: "edges", table: edgeTable }
348
- ]
349
- };
350
- }
351
- function buildGraphTable(records, isEdge, shape, declarations) {
352
- const columnNames = isEdge ? ["id", "sourceId", "targetId", "directed", "label", "attributes"] : ["id", "label", "attributes"];
353
- const columns = new Map(columnNames.map((name) => [name, []]));
354
- for (const record of records) {
355
- for (const name of columnNames) {
356
- const value = record[name];
357
- columns.get(name).push(
358
- name === "id" || name === "sourceId" || name === "targetId" ? String(value) : value ?? null
359
- );
360
- }
361
- }
362
- if (shape === "object-row-table") {
363
- return {
364
- shape,
365
- data: columns.get("id").map(
366
- (_, index) => Object.fromEntries(columnNames.map((name) => [name, columns.get(name)[index]]))
367
- )
368
- };
369
- }
370
- const vectors = /* @__PURE__ */ Object.create(null);
371
- for (const [name, values] of columns) {
372
- const type = name === "attributes" ? inferAttributeType(values, declarations) : name === "directed" ? new import_apache_arrow.Bool() : new import_apache_arrow.Utf8();
373
- vectors[name] = (0, import_apache_arrow.vectorFromArray)(
374
- values.map((value) => normalizeValue(value, type)),
375
- type
376
- );
377
- }
378
- const data = new import_apache_arrow.Table(vectors);
379
- return { shape, schema: convertArrowToSchema(data.schema), data };
380
- }
381
- function inferAttributeType(values, declarations) {
382
- const names = new Set(declarations == null ? void 0 : declarations.keys());
383
- for (const value of values) {
384
- if (value && typeof value === "object") {
385
- for (const name of Object.keys(value)) {
386
- names.add(name);
387
- }
388
- }
389
- }
390
- return new import_apache_arrow.Struct(
391
- Array.from(names, (name) => {
392
- const fieldValues = values.map(
393
- (value) => (value == null ? void 0 : value[name]) ?? null
394
- );
395
- return new import_apache_arrow.Field(name, inferValueType(fieldValues, declarations == null ? void 0 : declarations.get(name)), true);
396
- })
397
- );
398
- }
399
- function inferValueType(values, declaration) {
400
- const present = values.filter((value) => value !== null && value !== void 0);
401
- if (declaration && typeof declaration === "object") {
402
- if (!present.every((value) => Array.isArray(value))) return new import_apache_arrow.Utf8();
403
- return new import_apache_arrow.List(
404
- new import_apache_arrow.Field(
405
- "item",
406
- inferValueType(
407
- present.flatMap((value) => value),
408
- declaration.list
409
- ),
410
- true
411
- )
412
- );
413
- }
414
- if (declaration) {
415
- const declaredTypes = {
416
- boolean: new import_apache_arrow.Bool(),
417
- int: new import_apache_arrow.Int32(),
418
- long: new import_apache_arrow.Int64(),
419
- float: new import_apache_arrow.Float32(),
420
- double: new import_apache_arrow.Float64(),
421
- string: new import_apache_arrow.Utf8()
422
- };
423
- const valid = present.every((value) => {
424
- switch (declaration) {
425
- case "boolean":
426
- return typeof value === "boolean";
427
- case "int":
428
- return typeof value === "number" && Number.isInteger(value) && value >= -2147483648 && value <= 2147483647;
429
- case "long":
430
- return typeof value === "bigint" && value >= -(2n ** 63n) && value < 2n ** 63n;
431
- case "float":
432
- case "double":
433
- return typeof value === "number";
434
- case "string":
435
- return typeof value === "string";
436
- }
437
- });
438
- return valid ? declaredTypes[declaration] : new import_apache_arrow.Utf8();
439
- }
440
- if (present.length && present.every((value) => typeof value === "boolean")) return new import_apache_arrow.Bool();
441
- if (present.length && present.every((value) => typeof value === "number")) return new import_apache_arrow.Float64();
442
- if (present.length && present.every((value) => Array.isArray(value))) {
443
- return new import_apache_arrow.List(
444
- new import_apache_arrow.Field("item", inferValueType(present.flatMap((value) => value)), true)
445
- );
446
- }
447
- if (present.length && present.every((value) => typeof value === "object" && !Array.isArray(value))) {
448
- return inferAttributeType(present);
449
- }
450
- return new import_apache_arrow.Utf8();
451
- }
452
- function normalizeValue(value, type) {
453
- if (value === null || value === void 0) return null;
454
- if (type instanceof import_apache_arrow.Struct) {
455
- return Object.fromEntries(
456
- type.children.map((field) => [
457
- field.name,
458
- normalizeValue(value[field.name], field.type)
459
- ])
460
- );
461
- }
462
- if (type instanceof import_apache_arrow.List)
463
- return value.map((item) => normalizeValue(item, type.valueType));
464
- if (type instanceof import_apache_arrow.Utf8 && typeof value !== "string") {
465
- return typeof value === "object" ? JSON.stringify(value) : String(value);
466
- }
467
- return value;
468
- }
469
- var import_apache_arrow;
470
- var init_build_graph_tables = __esm({
471
- "src/lib/build-graph-tables.ts"() {
472
- "use strict";
473
- import_apache_arrow = require("apache-arrow");
474
- init_schema_utils();
475
- }
476
- });
477
-
478
- // src/lib/parse-graphml.ts
479
- function parseGraphML(graphml, shape = "plain-graph-data") {
480
- const xmlText = decodeGraphML(graphml);
481
- const document = graphmlParser.parse(xmlText);
482
- const graphmlRoot = getGraphMLRoot(document);
483
- if (!graphmlRoot) {
484
- throw new Error("GraphML document does not contain a <graphml> element.");
485
- }
486
- const graphElement = getGraphElement(graphmlRoot);
487
- if (!graphElement) {
488
- throw new Error("GraphML document does not contain a <graph> element.");
489
- }
490
- const keyDefinitions = collectKeyDefinitions(
491
- graphmlRoot,
492
- graphElement,
493
- shape !== "plain-graph-data"
494
- );
495
- const defaultDirected = parseEdgeDefault(graphElement[`${XML_ATTRIBUTE_PREFIX}edgedefault`]);
496
- const declarations = { nodes: /* @__PURE__ */ new Map(), edges: /* @__PURE__ */ new Map() };
497
- for (const definition of keyDefinitions.values()) {
498
- if (definition.domain === "all" || definition.domain === "node")
499
- declarations.nodes.set(definition.name, definition.type);
500
- if (definition.domain === "all" || definition.domain === "edge")
501
- declarations.edges.set(definition.name, definition.type);
502
- }
503
- return buildGraphTables(
504
- iterateNodes(graphElement.node, keyDefinitions),
505
- iterateEdges(graphElement.edge, keyDefinitions, defaultDirected),
506
- shape,
507
- declarations
508
- );
509
- }
510
- function* iterateNodes(nodes, definitions) {
511
- for (const node of normalizeArray(nodes)) {
512
- const record = parseNode(node, definitions);
513
- if (record) yield record;
514
- }
515
- }
516
- function* iterateEdges(edges, definitions, directed) {
517
- let index = 0;
518
- for (const edge of normalizeArray(edges)) {
519
- const record = parseEdge(edge, index++, definitions, directed);
520
- if (record) yield record;
521
- }
522
- }
523
- function decodeGraphML(graphml) {
524
- if (typeof graphml === "string") {
525
- return graphml;
526
- }
527
- if (graphml instanceof Uint8Array) {
528
- return new TextDecoder().decode(graphml);
529
- }
530
- if (graphml instanceof ArrayBuffer) {
531
- return new TextDecoder().decode(new Uint8Array(graphml));
532
- }
533
- throw new Error("Unsupported GraphML input. Expected a string, ArrayBuffer, or Uint8Array.");
534
- }
535
- function getGraphMLRoot(document) {
536
- const root = document.graphml;
537
- if (isObject(root)) {
538
- return root;
539
- }
540
- return null;
541
- }
542
- function getGraphElement(graphmlRoot) {
543
- const graph = graphmlRoot.graph;
544
- if (typeof graph === "string" && !graph.trim()) {
545
- return {};
546
- }
547
- if (!graph) {
548
- return null;
549
- }
550
- if (Array.isArray(graph)) {
551
- const firstGraph = graph.find(
552
- (entry) => isObject(entry) || typeof entry === "string" && !entry.trim()
553
- );
554
- return isObject(firstGraph) ? firstGraph : typeof firstGraph === "string" ? {} : null;
555
- }
556
- return isObject(graph) ? graph : null;
557
- }
558
- function collectKeyDefinitions(graphmlRoot, graphElement, lossless) {
559
- const keys = /* @__PURE__ */ new Map();
560
- for (const candidate of [
561
- ...normalizeArray(graphmlRoot.key),
562
- ...normalizeArray(graphElement.key)
563
- ]) {
564
- if (isObject(candidate)) {
565
- const id = String(candidate[`${XML_ATTRIBUTE_PREFIX}id`] ?? "").trim();
566
- if (id) {
567
- const domain = normalizeDomain(candidate[`${XML_ATTRIBUTE_PREFIX}for`]);
568
- const name = String(candidate[`${XML_ATTRIBUTE_PREFIX}attr.name`] ?? id).trim();
569
- const type = normalizeType(candidate[`${XML_ATTRIBUTE_PREFIX}attr.type`]);
570
- const defaultNode = candidate.default ?? null;
571
- const defaultValue = defaultNode !== null ? castDataValue(defaultNode, type, lossless) : void 0;
572
- keys.set(id, { id, domain, name, type, defaultValue, lossless });
573
- }
574
- }
575
- }
576
- return keys;
577
- }
578
- function parseNode(node, keyDefinitions) {
579
- if (!isObject(node)) {
580
- return null;
581
- }
582
- const id = node[`${XML_ATTRIBUTE_PREFIX}id`];
583
- if (typeof id !== "string") {
584
- return null;
585
- }
586
- const attributes = buildAttributeBag("node", node.data, keyDefinitions);
587
- const graphNode = {
588
- id,
589
- attributes: Object.keys(attributes).length > 0 ? attributes : void 0
590
- };
591
- const label = attributes.label;
592
- if (typeof label === "string") {
593
- graphNode.label = label;
594
- }
595
- return graphNode;
596
- }
597
- function parseEdge(edge, index, keyDefinitions, defaultDirected) {
598
- if (!isObject(edge)) {
599
- return null;
600
- }
601
- const sourceId = edge[`${XML_ATTRIBUTE_PREFIX}source`];
602
- const targetId = edge[`${XML_ATTRIBUTE_PREFIX}target`];
603
- if (typeof sourceId !== "string") {
604
- return null;
605
- }
606
- if (typeof targetId !== "string") {
607
- return null;
608
- }
609
- const rawId = edge[`${XML_ATTRIBUTE_PREFIX}id`];
610
- const id = typeof rawId === "string" ? rawId : `edge-${index}`;
611
- const directed = parseDirected(edge[`${XML_ATTRIBUTE_PREFIX}directed`], defaultDirected);
612
- const attributes = buildAttributeBag("edge", edge.data, keyDefinitions);
613
- const graphEdge = {
614
- id,
615
- sourceId,
616
- targetId,
617
- directed,
618
- attributes: Object.keys(attributes).length > 0 ? attributes : void 0
619
- };
620
- const label = attributes.label;
621
- if (typeof label === "string") {
622
- graphEdge.label = label;
623
- }
624
- return graphEdge;
625
- }
626
- function buildAttributeBag(domain, data, keyDefinitions) {
627
- const attributes = /* @__PURE__ */ Object.create(null);
628
- for (const key of keyDefinitions.values()) {
629
- if (key.domain === "all" || key.domain === domain) {
630
- if (key.defaultValue !== void 0) {
631
- attributes[key.name] = key.defaultValue;
632
- }
633
- }
634
- }
635
- for (const entry of normalizeArray(data)) {
636
- assignAttributeFromDataEntry(entry, keyDefinitions, attributes);
637
- }
638
- return attributes;
639
- }
640
- function assignAttributeFromDataEntry(entry, keyDefinitions, attributes) {
641
- if (!isObject(entry)) {
642
- return;
643
- }
644
- const keyId = entry[`${XML_ATTRIBUTE_PREFIX}key`];
645
- if (typeof keyId !== "string") {
646
- return;
647
- }
648
- const definition = keyDefinitions.get(keyId);
649
- const attributeName = (definition == null ? void 0 : definition.name) ?? keyId;
650
- const value = (definition == null ? void 0 : definition.type) === "boolean" && extractTextContent(entry) === void 0 ? false : castDataValue(entry, (definition == null ? void 0 : definition.type) ?? "string", definition == null ? void 0 : definition.lossless);
651
- if (value !== void 0) {
652
- attributes[attributeName] = value;
653
- }
654
- }
655
- function castDataValue(value, type, lossless = false) {
656
- if (value === null || typeof value === "undefined") {
657
- return void 0;
658
- }
659
- const text = extractTextContent(value);
660
- if (text === void 0) {
661
- return void 0;
662
- }
663
- if (type === "boolean") {
664
- return parseBoolean(text);
665
- }
666
- if (type === "long" && lossless) {
667
- return /^[+-]?\d+$/.test(text.trim()) ? BigInt(text.trim()) : text;
668
- }
669
- if (type === "int" || type === "long") {
670
- const parsed = Number.parseInt(text, 10);
671
- return Number.isNaN(parsed) ? text : parsed;
672
- }
673
- if (type === "float" || type === "double") {
674
- const parsed = Number.parseFloat(text);
675
- return Number.isNaN(parsed) ? text : parsed;
676
- }
677
- return text;
678
- }
679
- function extractTextContent(value) {
680
- if (typeof value === "string") {
681
- return value;
682
- }
683
- if (typeof value === "number" || typeof value === "boolean") {
684
- return String(value);
685
- }
686
- if (Array.isArray(value)) {
687
- return extractTextContent(value[0]);
688
- }
689
- if (isObject(value)) {
690
- const text = value[XML_TEXT_KEY];
691
- const nonAttributeEntries = Object.entries(value).filter(
692
- ([key]) => !key.startsWith(XML_ATTRIBUTE_PREFIX) && key !== XML_TEXT_KEY
693
- );
694
- if (nonAttributeEntries.length === 0) {
695
- return typeof text === "string" ? text : void 0;
696
- }
697
- if (typeof text === "string" && text.trim()) {
698
- nonAttributeEntries.push([XML_TEXT_KEY, text]);
699
- }
700
- return JSON.stringify(Object.fromEntries(nonAttributeEntries));
701
- }
702
- return void 0;
703
- }
704
- function normalizeArray(value) {
705
- if (!value) {
706
- return [];
707
- }
708
- return Array.isArray(value) ? value : [value];
709
- }
710
- function isObject(value) {
711
- return Boolean(value) && typeof value === "object" && !Array.isArray(value);
712
- }
713
- function normalizeDomain(value) {
714
- if (typeof value !== "string") {
715
- return "all";
716
- }
717
- const lower = value.toLowerCase();
718
- if (lower === "node" || lower === "edge" || lower === "graph" || lower === "all") {
719
- return lower;
720
- }
721
- return "all";
722
- }
723
- function normalizeType(value) {
724
- if (typeof value !== "string") {
725
- return "string";
726
- }
727
- const lower = value.toLowerCase();
728
- if (lower === "boolean" || lower === "int" || lower === "long" || lower === "float" || lower === "double") {
729
- return lower;
730
- }
731
- return "string";
732
- }
733
- function parseEdgeDefault(value) {
734
- if (typeof value !== "string") {
735
- return false;
736
- }
737
- return value.toLowerCase() !== "undirected";
738
- }
739
- function parseDirected(value, defaultDirected) {
740
- if (typeof value === "string") {
741
- const normalized = value.trim().toLowerCase();
742
- if (normalized === "true" || normalized === "1" || normalized === "yes" || normalized === "directed") {
743
- return true;
744
- }
745
- if (normalized === "false" || normalized === "0" || normalized === "no" || normalized === "undirected") {
746
- return false;
747
- }
748
- }
749
- return defaultDirected;
750
- }
751
- function parseBoolean(value) {
752
- const normalized = value.trim().toLowerCase();
753
- if (normalized === "true" || normalized === "1" || normalized === "yes" || normalized === "y") {
754
- return true;
755
- }
756
- if (normalized === "false" || normalized === "0" || normalized === "no" || normalized === "n") {
757
- return false;
758
- }
759
- return Boolean(normalized);
760
- }
761
- var import_fast_xml_parser, XML_ATTRIBUTE_PREFIX, XML_TEXT_KEY, graphmlParser;
762
- var init_parse_graphml = __esm({
763
- "src/lib/parse-graphml.ts"() {
764
- "use strict";
765
- import_fast_xml_parser = require("fast-xml-parser");
766
- init_build_graph_tables();
767
- XML_ATTRIBUTE_PREFIX = "@_";
768
- XML_TEXT_KEY = "#text";
769
- graphmlParser = new import_fast_xml_parser.XMLParser({
770
- ignoreAttributes: false,
771
- attributeNamePrefix: XML_ATTRIBUTE_PREFIX,
772
- textNodeName: XML_TEXT_KEY,
773
- trimValues: false,
774
- parseAttributeValue: false,
775
- parseTagValue: false,
776
- removeNSPrefix: true
777
- });
778
- }
779
- });
780
-
781
- // src/graphml-loader.ts
782
- var graphml_loader_exports = {};
783
- __export(graphml_loader_exports, {
784
- GraphMLLoaderWithParser: () => GraphMLLoaderWithParser
785
- });
786
- var GraphMLLoaderWithParser;
787
- var init_graphml_loader = __esm({
788
- "src/graphml-loader.ts"() {
789
- "use strict";
790
- init_graphml_loader_types();
791
- init_parse_graphml();
792
- GraphMLLoaderWithParser = {
793
- ...GraphMLLoader,
794
- parse: async (data, options) => {
795
- var _a;
796
- return parseGraphML(data, ((_a = options == null ? void 0 : options.graphml) == null ? void 0 : _a.shape) ?? "arrow-table");
797
- },
798
- parseSync: (data, options) => {
799
- var _a;
800
- return parseGraphML(data, ((_a = options == null ? void 0 : options.graphml) == null ? void 0 : _a.shape) ?? "arrow-table");
801
- },
802
- parseTextSync: (data, options) => {
803
- var _a;
804
- return parseGraphML(data, ((_a = options == null ? void 0 : options.graphml) == null ? void 0 : _a.shape) ?? "arrow-table");
805
- }
806
- };
807
- }
808
- });
809
-
810
- // src/dot-loader-types.ts
811
- async function preload3() {
812
- const { DOTLoaderWithParser: DOTLoaderWithParser2 } = await Promise.resolve().then(() => (init_dot_loader(), dot_loader_exports));
813
- return DOTLoaderWithParser2;
814
- }
815
- var VERSION3, DOTLoader;
816
- var init_dot_loader_types = __esm({
817
- "src/dot-loader-types.ts"() {
818
- "use strict";
819
- VERSION3 = typeof __VERSION__ !== "undefined" ? __VERSION__ : "latest";
820
- DOTLoader = {
821
- name: "DOT",
822
- id: "dot",
823
- module: "graphs",
824
- version: VERSION3,
825
- extensions: ["dot", "gv"],
826
- mimeTypes: ["text/vnd.graphviz", "text/x-graphviz", "application/vnd.graphviz"],
827
- text: true,
828
- worker: false,
829
- dataType: null,
830
- batchType: null,
831
- options: { dot: { shape: "arrow-table" } },
832
- preload: preload3
833
- };
834
- }
835
- });
836
-
837
- // src/lib/parse-dot.ts
838
- function parseDOT(input, shape = "plain-graph-data") {
839
- const parsed = parseDOTDocument(input);
840
- return {
841
- ...buildGraphTables(iterateNodes2(parsed), iterateEdges2(parsed), shape),
842
- metadata: {
843
- id: parsed.id,
844
- directed: parsed.directed,
845
- strict: parsed.strict,
846
- attributes: { ...parsed.graphAttributes },
847
- subgraphs: Array.from(parsed.subgraphs.values(), (subgraph) => ({
848
- ...subgraph,
849
- attributes: { ...subgraph.attributes }
850
- }))
851
- }
852
- };
853
- }
854
- function* iterateNodes2(parsed) {
855
- for (const node of parsed.nodes.values()) {
856
- yield {
857
- id: node.id,
858
- ...typeof node.attributes.label === "string" ? { label: node.attributes.label } : {},
859
- attributes: {
860
- ...node.attributes,
861
- ...node.subgraphs.size ? { subgraphs: Array.from(node.subgraphs, (id) => describeSubgraph(id, parsed.subgraphs)) } : {}
862
- }
863
- };
864
- }
865
- }
866
- function* iterateEdges2(parsed) {
867
- for (const edge of parsed.edges) {
868
- yield {
869
- id: edge.id,
870
- sourceId: edge.sourceId,
871
- targetId: edge.targetId,
872
- directed: edge.directed,
873
- ...typeof edge.attributes.label === "string" ? { label: edge.attributes.label } : {},
874
- attributes: {
875
- ...edge.attributes,
876
- ...edge.subgraphs.length ? { subgraphs: edge.subgraphs.map((id) => describeSubgraph(id, parsed.subgraphs)) } : {}
877
- }
878
- };
879
- }
880
- }
881
- function describeSubgraph(id, descriptors) {
882
- const subgraph = descriptors.get(id);
883
- return {
884
- id,
885
- attributes: { ...subgraph.attributes },
886
- parentId: subgraph.parentId
887
- };
888
- }
889
- function parseDOTDocument(input) {
890
- const parser2 = new DOTParser(tokenize(input));
891
- return parser2.parse();
892
- }
893
- function tokenize(input) {
894
- const tokens = [];
895
- let index = 0;
896
- while (index < input.length) {
897
- const { token, nextIndex } = readNextToken(input, index);
898
- if (nextIndex <= index) {
899
- throw new Error(`Tokenizer did not advance at position ${index}.`);
900
- }
901
- if (token) {
902
- tokens.push(token);
903
- }
904
- index = nextIndex;
905
- }
906
- return tokens;
907
- }
908
- function readNextToken(input, index) {
909
- if (index >= input.length) {
910
- return { token: null, nextIndex: input.length };
911
- }
912
- const character = input[index];
913
- if (isWhitespace(character)) {
914
- return { token: null, nextIndex: index + 1 };
915
- }
916
- const commentEnd = skipComment(input, index);
917
- if (commentEnd !== null) {
918
- return { token: null, nextIndex: commentEnd };
919
- }
920
- const arrowToken = readArrowToken(input, index);
921
- if (arrowToken) {
922
- return arrowToken;
923
- }
924
- const punctuation = readPunctuationToken(character);
925
- if (punctuation) {
926
- return { token: punctuation, nextIndex: index + 1 };
927
- }
928
- if (character === '"') {
929
- const { value, nextIndex } = readQuotedString(input, index + 1);
930
- return { token: { type: "string", value }, nextIndex };
931
- }
932
- if (character === "<") {
933
- const { value, nextIndex } = readHtmlString(input, index + 1);
934
- return { token: { type: "html", value }, nextIndex };
935
- }
936
- const identifier = readIdentifier(input, index);
937
- if (identifier.value) {
938
- return {
939
- token: { type: "identifier", value: identifier.value },
940
- nextIndex: identifier.nextIndex
941
- };
942
- }
943
- throw new Error(`Unexpected token at position ${index}.`);
944
- }
945
- function skipComment(input, index) {
946
- const character = input[index];
947
- if (character === "/") {
948
- const next = input[index + 1];
949
- if (next === "/") {
950
- return skipLineComment(input, index + 2);
951
- }
952
- if (next === "*") {
953
- return skipBlockComment(input, index + 2);
954
- }
955
- return null;
956
- }
957
- if (character === "#") {
958
- return skipLineComment(input, index + 1);
959
- }
960
- return null;
961
- }
962
- function skipLineComment(input, startIndex) {
963
- let cursor = startIndex;
964
- while (cursor < input.length && !isLineBreak(input[cursor])) {
965
- cursor++;
966
- }
967
- return cursor;
968
- }
969
- function skipBlockComment(input, startIndex) {
970
- let cursor = startIndex;
971
- while (cursor < input.length) {
972
- if (input[cursor] === "*" && input[cursor + 1] === "/") {
973
- return cursor + 2;
974
- }
975
- cursor++;
976
- }
977
- throw new Error("Unterminated block comment in DOT source.");
978
- }
979
- function readArrowToken(input, index) {
980
- const next = input[index + 1];
981
- if (input[index] === "-" && next === "-") {
982
- return { token: { type: "arrow", value: "--" }, nextIndex: index + 2 };
983
- }
984
- if (input[index] === "-" && next === ">") {
985
- return { token: { type: "arrow", value: "->" }, nextIndex: index + 2 };
986
- }
987
- return null;
988
- }
989
- function readPunctuationToken(character) {
990
- switch (character) {
991
- case "{":
992
- return { type: "lbrace", value: character };
993
- case "}":
994
- return { type: "rbrace", value: character };
995
- case "[":
996
- return { type: "lbrack", value: character };
997
- case "]":
998
- return { type: "rbrack", value: character };
999
- case "=":
1000
- return { type: "equals", value: character };
1001
- case ",":
1002
- return { type: "comma", value: character };
1003
- case ";":
1004
- return { type: "semicolon", value: character };
1005
- default:
1006
- return null;
1007
- }
1008
- }
1009
- function readQuotedString(input, startIndex) {
1010
- let value = "";
1011
- let index = startIndex;
1012
- while (index < input.length) {
1013
- const character = input[index];
1014
- if (character === '"') {
1015
- return { value, nextIndex: index + 1 };
1016
- }
1017
- if (character === "\\") {
1018
- const escape = readEscapedCharacter(input, index + 1);
1019
- value += escape.value;
1020
- index = escape.nextIndex;
1021
- } else {
1022
- value += character;
1023
- index++;
1024
- }
1025
- }
1026
- throw new Error("Unterminated string literal in DOT source.");
1027
- }
1028
- function readEscapedCharacter(input, startIndex) {
1029
- const next = input[startIndex];
1030
- switch (next) {
1031
- case "\n":
1032
- return { value: "", nextIndex: startIndex + 1 };
1033
- case "\r":
1034
- return { value: "", nextIndex: startIndex + (input[startIndex + 1] === "\n" ? 2 : 1) };
1035
- case "n":
1036
- case "l":
1037
- case "L":
1038
- return { value: "\n", nextIndex: startIndex + 1 };
1039
- case "t":
1040
- return { value: " ", nextIndex: startIndex + 1 };
1041
- case "r":
1042
- return { value: "\r", nextIndex: startIndex + 1 };
1043
- case '"':
1044
- return { value: '"', nextIndex: startIndex + 1 };
1045
- case "\\":
1046
- return { value: "\\", nextIndex: startIndex + 1 };
1047
- default: {
1048
- if (typeof next === "undefined") {
1049
- throw new Error("Unterminated escape sequence in DOT source.");
1050
- }
1051
- return { value: `\\${next}`, nextIndex: startIndex + 1 };
1052
- }
1053
- }
1054
- }
1055
- function readHtmlString(input, startIndex) {
1056
- let value = "<";
1057
- let depth = 1;
1058
- let index = startIndex;
1059
- while (index < input.length) {
1060
- const character = input[index];
1061
- value += character;
1062
- if (character === "<") {
1063
- depth++;
1064
- } else if (character === ">") {
1065
- depth--;
1066
- if (depth === 0) {
1067
- return { value, nextIndex: index + 1 };
1068
- }
1069
- }
1070
- index++;
1071
- }
1072
- throw new Error("Unterminated HTML-like string literal in DOT source.");
1073
- }
1074
- function readIdentifier(input, startIndex) {
1075
- let index = startIndex;
1076
- let value = "";
1077
- while (index < input.length && !isIdentifierTerminator(input, index)) {
1078
- value += input[index];
1079
- index++;
1080
- }
1081
- if (value.includes(":")) {
1082
- throw new Error("DOT node ports are not supported; quote identifiers containing colons.");
1083
- }
1084
- return { value, nextIndex: index };
1085
- }
1086
- function isIdentifierTerminator(input, index) {
1087
- const character = input[index];
1088
- if (isWhitespace(character) || IDENTIFIER_TERMINATORS.has(character)) {
1089
- return true;
1090
- }
1091
- if (isArrowOperatorStart(input, index)) {
1092
- return true;
1093
- }
1094
- if (isCommentStart(input, index)) {
1095
- return true;
1096
- }
1097
- return false;
1098
- }
1099
- function isArrowOperatorStart(input, index) {
1100
- if (input[index] !== "-") {
1101
- return false;
1102
- }
1103
- const next = input[index + 1];
1104
- return next === "-" || next === ">";
1105
- }
1106
- function isCommentStart(input, index) {
1107
- if (input[index] !== "/") {
1108
- return false;
1109
- }
1110
- const next = input[index + 1];
1111
- return next === "/" || next === "*";
1112
- }
1113
- function isWhitespace(character) {
1114
- return character === " " || character === "\n" || character === "\r" || character === " " || character === "\f";
1115
- }
1116
- function isLineBreak(character) {
1117
- return character === "\n" || character === "\r";
1118
- }
1119
- function isKeyword(token, keyword) {
1120
- return token.type === "identifier" && token.value.toLowerCase() === keyword.toLowerCase();
1121
- }
1122
- function isGraphType(token) {
1123
- return isKeyword(token, "graph") || isKeyword(token, "digraph");
1124
- }
1125
- function isIdentifierLike(token) {
1126
- return token.type === "identifier" || token.type === "string" || token.type === "html";
1127
- }
1128
- function parseIdentifierValue(token) {
1129
- return token.value;
1130
- }
1131
- function parseAttributeValue(token) {
1132
- if (token.type === "string" || token.type === "html") {
1133
- return token.value;
1134
- }
1135
- if (token.type === "identifier") {
1136
- const numeric = Number(token.value);
1137
- if (!Number.isNaN(numeric)) {
1138
- return numeric;
1139
- }
1140
- return token.value;
1141
- }
1142
- throw new Error("Invalid attribute value in DOT input.");
1143
- }
1144
- function deriveEdgeId(attributes, sourceId, targetId, counter) {
1145
- const candidate = attributes.id ?? attributes.Id ?? attributes.ID;
1146
- if (typeof candidate === "string" || typeof candidate === "number") {
1147
- return String(candidate);
1148
- }
1149
- return `${String(sourceId)}-${String(targetId)}-${counter}`;
1150
- }
1151
- function deriveDirectedFlag(attributes, defaultDirected) {
1152
- const candidate = attributes.directed;
1153
- if (typeof candidate === "boolean") {
1154
- return candidate;
1155
- }
1156
- const directionAttribute = attributes.dir;
1157
- if (typeof directionAttribute === "string") {
1158
- const normalized = directionAttribute.toLowerCase();
1159
- if (normalized === "none") {
1160
- return false;
1161
- }
1162
- return true;
1163
- }
1164
- return defaultDirected;
1165
- }
1166
- var DOTParser, IDENTIFIER_TERMINATORS;
1167
- var init_parse_dot = __esm({
1168
- "src/lib/parse-dot.ts"() {
1169
- "use strict";
1170
- init_build_graph_tables();
1171
- DOTParser = class {
1172
- /** Tokens for DOT parsing. */
1173
- tokens;
1174
- /** Position for DOT parsing. */
1175
- position = 0;
1176
- /** Accumulated graph records and attributes. */
1177
- result = {
1178
- directed: false,
1179
- strict: false,
1180
- graphAttributes: /* @__PURE__ */ Object.create(null),
1181
- nodes: /* @__PURE__ */ new Map(),
1182
- edges: [],
1183
- subgraphs: /* @__PURE__ */ new Map()
1184
- };
1185
- /** Scopes for DOT parsing. */
1186
- scopes = [
1187
- {
1188
- nodeDefaults: /* @__PURE__ */ Object.create(null),
1189
- edgeDefaults: /* @__PURE__ */ Object.create(null),
1190
- graphAttributes: /* @__PURE__ */ Object.create(null)
1191
- }
1192
- ];
1193
- /** Subgraph counter for DOT parsing. */
1194
- subgraphCounter = 0;
1195
- /** Edge counter for DOT parsing. */
1196
- edgeCounter = 0;
1197
- /** Edge lookup used to coalesce parallel edges in strict graphs. */
1198
- strictEdges = /* @__PURE__ */ new Map();
1199
- /** Persistent attributes and defaults for reopened named subgraphs. */
1200
- subgraphScopes = /* @__PURE__ */ new Map();
1201
- /** Explicit names reserved so anonymous subgraph IDs cannot collide with them. */
1202
- namedSubgraphIds = /* @__PURE__ */ new Set();
1203
- /** Initializes the token stream. */
1204
- constructor(tokens) {
1205
- this.tokens = tokens;
1206
- for (let index = 0; index < tokens.length - 1; index++) {
1207
- if (isKeyword(tokens[index], "subgraph") && isIdentifierLike(tokens[index + 1])) {
1208
- this.namedSubgraphIds.add(tokens[index + 1].value);
1209
- }
1210
- }
1211
- }
1212
- /** Parses one complete DOT document. */
1213
- parse() {
1214
- this.parseGraph();
1215
- this.consumeOptionalSemicolon();
1216
- if (this.peek()) {
1217
- throw new Error("Unexpected content after DOT graph.");
1218
- }
1219
- return this.result;
1220
- }
1221
- /** Reads graph identity, declaration, and statements. */
1222
- parseGraph() {
1223
- const strictToken = this.peek();
1224
- if (strictToken && isKeyword(strictToken, "strict")) {
1225
- this.consume();
1226
- this.result.strict = true;
1227
- }
1228
- const typeToken = this.peek();
1229
- if (!typeToken || !isGraphType(typeToken)) {
1230
- throw new Error("DOT graph must start with graph or digraph keyword.");
1231
- }
1232
- this.consume();
1233
- this.result.directed = isKeyword(typeToken, "digraph");
1234
- const idToken = this.peek();
1235
- if (idToken && isIdentifierLike(idToken)) {
1236
- this.result.id = parseIdentifierValue(this.consume());
1237
- }
1238
- this.expect("lbrace");
1239
- while (!this.match("rbrace")) {
1240
- if (!this.parseStatement()) {
1241
- throw new Error("Expected closing brace in DOT graph.");
1242
- }
1243
- }
1244
- this.result.graphAttributes = { ...this.scopes[0].graphAttributes };
1245
- }
1246
- /** Dispatches a graph statement. */
1247
- parseStatement() {
1248
- if (this.consumeSemicolonIfPresent()) {
1249
- return true;
1250
- }
1251
- const token = this.peek();
1252
- if (!token) {
1253
- return false;
1254
- }
1255
- if (this.tryParseSubgraphStatement(token)) {
1256
- return true;
1257
- }
1258
- if (this.tryParseKeywordStatement(token)) {
1259
- return true;
1260
- }
1261
- if (this.tryParseAssignmentStatement(token)) {
1262
- return true;
1263
- }
1264
- if (isIdentifierLike(token)) {
1265
- this.parseNodeOrEdgeStatement();
1266
- this.consumeOptionalSemicolon();
1267
- return true;
1268
- }
1269
- throw new Error(`Unexpected token: ${token.value}`);
1270
- }
1271
- /** Consumes an empty statement. */
1272
- consumeSemicolonIfPresent() {
1273
- const next = this.peek();
1274
- if ((next == null ? void 0 : next.type) === "semicolon") {
1275
- this.consume();
1276
- return true;
1277
- }
1278
- return false;
1279
- }
1280
- /** Reads a standalone subgraph statement. */
1281
- tryParseSubgraphStatement(token) {
1282
- if (token.type !== "lbrace" && !isKeyword(token, "subgraph")) {
1283
- return false;
1284
- }
1285
- this.parseSubgraph();
1286
- return true;
1287
- }
1288
- /** Applies graph, node, or edge defaults. */
1289
- tryParseKeywordStatement(token) {
1290
- if (!(isKeyword(token, "graph") || isKeyword(token, "node") || isKeyword(token, "edge"))) {
1291
- return false;
1292
- }
1293
- this.consume();
1294
- const explicitAttributes = this.parseAttributeList();
1295
- if (isKeyword(token, "graph")) {
1296
- Object.assign(this.currentScope().graphAttributes, explicitAttributes);
1297
- } else if (isKeyword(token, "node")) {
1298
- Object.assign(this.currentScope().nodeDefaults, explicitAttributes);
1299
- } else {
1300
- Object.assign(this.currentScope().edgeDefaults, explicitAttributes);
1301
- }
1302
- this.consumeOptionalSemicolon();
1303
- return true;
1304
- }
1305
- /** Reads a graph attribute assignment. */
1306
- tryParseAssignmentStatement(token) {
1307
- if (!isIdentifierLike(token)) {
1308
- return false;
1309
- }
1310
- const next = this.peek(1);
1311
- if ((next == null ? void 0 : next.type) !== "equals") {
1312
- return false;
1313
- }
1314
- const key = parseIdentifierValue(this.consume());
1315
- this.consume();
1316
- const valueToken = this.consume();
1317
- const value = parseAttributeValue(valueToken);
1318
- this.currentScope().graphAttributes[key] = value;
1319
- this.consumeOptionalSemicolon();
1320
- return true;
1321
- }
1322
- /** Reads a node statement or chained edges. */
1323
- parseNodeOrEdgeStatement() {
1324
- const first = parseIdentifierValue(this.consume());
1325
- const references = [first];
1326
- const operators = [];
1327
- let operatorToken = this.match("arrow");
1328
- while (operatorToken) {
1329
- operators.push(operatorToken.value);
1330
- const referenceToken = this.consume();
1331
- if (!isIdentifierLike(referenceToken)) {
1332
- throw new Error("Expected node identifier in edge statement.");
1333
- }
1334
- references.push(parseIdentifierValue(referenceToken));
1335
- operatorToken = this.match("arrow");
1336
- }
1337
- if (operators.length === 0) {
1338
- const explicitAttributes2 = this.parseAttributeList();
1339
- this.addNode(first, explicitAttributes2);
1340
- return;
1341
- }
1342
- const explicitAttributes = this.parseAttributeList();
1343
- this.addEdgeChain(references, operators, explicitAttributes);
1344
- }
1345
- /** Merges explicit attributes into a node. */
1346
- addNode(id, explicitAttributes) {
1347
- const membership = this.getCurrentSubgraphChain();
1348
- const node = this.ensureNode(id, membership);
1349
- node.attributes = { ...node.attributes, ...explicitAttributes };
1350
- }
1351
- /** Expands an edge chain into node and edge records. */
1352
- addEdgeChain(nodes, operators, explicitAttributes) {
1353
- const membership = this.getCurrentSubgraphChain();
1354
- const defaults = this.currentScope().edgeDefaults;
1355
- const attributes = { ...defaults, ...explicitAttributes };
1356
- for (let index = 0; index < nodes.length - 1; index++) {
1357
- const sourceId = nodes[index];
1358
- const targetId = nodes[index + 1];
1359
- const operator = operators[index];
1360
- const directed = operator === "->";
1361
- if (directed !== this.result.directed) {
1362
- throw new Error("DOT edge operator must match graph or digraph declaration.");
1363
- }
1364
- const edgeId = deriveEdgeId(attributes, sourceId, targetId, ++this.edgeCounter);
1365
- const edgeAttributes = { ...attributes };
1366
- this.ensureNode(sourceId, membership);
1367
- this.ensureNode(targetId, membership);
1368
- const strictKey = JSON.stringify(
1369
- directed ? [sourceId, targetId] : [sourceId, targetId].sort()
1370
- );
1371
- const existingEdge = this.result.strict ? this.strictEdges.get(strictKey) : void 0;
1372
- if (existingEdge) {
1373
- existingEdge.attributes = { ...existingEdge.attributes, ...explicitAttributes };
1374
- const explicitId = explicitAttributes.id ?? explicitAttributes.Id ?? explicitAttributes.ID;
1375
- if (typeof explicitId === "string" || typeof explicitId === "number") {
1376
- existingEdge.id = String(explicitId);
1377
- }
1378
- existingEdge.directed = deriveDirectedFlag(existingEdge.attributes, directed);
1379
- existingEdge.subgraphs = Array.from(/* @__PURE__ */ new Set([...existingEdge.subgraphs, ...membership]));
1380
- continue;
1381
- }
1382
- const directedOverride = deriveDirectedFlag(edgeAttributes, directed);
1383
- const edge = {
1384
- id: edgeId,
1385
- sourceId,
1386
- targetId,
1387
- directed: directedOverride,
1388
- attributes: edgeAttributes,
1389
- subgraphs: membership
1390
- };
1391
- this.result.edges.push(edge);
1392
- if (this.result.strict) {
1393
- this.strictEdges.set(strictKey, edge);
1394
- }
1395
- }
1396
- }
1397
- /** Reads a nested scope with inherited defaults. */
1398
- parseSubgraph() {
1399
- let idToken = this.peek();
1400
- let subgraphId;
1401
- if (idToken && isKeyword(idToken, "subgraph")) {
1402
- this.consume();
1403
- idToken = this.peek();
1404
- }
1405
- if (idToken && isIdentifierLike(idToken)) {
1406
- subgraphId = parseIdentifierValue(this.consume());
1407
- } else {
1408
- do {
1409
- subgraphId = `subgraph_${++this.subgraphCounter}`;
1410
- } while (this.namedSubgraphIds.has(subgraphId));
1411
- }
1412
- this.expect("lbrace");
1413
- const parentId = this.findCurrentSubgraphId();
1414
- let context = this.subgraphScopes.get(subgraphId);
1415
- if (!context) {
1416
- context = {
1417
- id: subgraphId,
1418
- nodeDefaults: Object.assign(/* @__PURE__ */ Object.create(null), this.currentScope().nodeDefaults),
1419
- edgeDefaults: Object.assign(/* @__PURE__ */ Object.create(null), this.currentScope().edgeDefaults),
1420
- graphAttributes: /* @__PURE__ */ Object.create(null)
1421
- };
1422
- this.subgraphScopes.set(subgraphId, context);
1423
- this.result.subgraphs.set(subgraphId, {
1424
- id: subgraphId,
1425
- attributes: context.graphAttributes,
1426
- parentId
1427
- });
1428
- }
1429
- this.scopes.push(context);
1430
- let shouldContinue = true;
1431
- while (shouldContinue) {
1432
- if (this.match("rbrace")) {
1433
- break;
1434
- }
1435
- shouldContinue = this.parseStatement();
1436
- if (!shouldContinue) {
1437
- throw new Error("Expected closing brace in DOT subgraph.");
1438
- }
1439
- }
1440
- this.scopes.pop();
1441
- }
1442
- /** Reads repeated attribute lists. */
1443
- parseAttributeList() {
1444
- var _a, _b;
1445
- const attributes = /* @__PURE__ */ Object.create(null);
1446
- while (this.match("lbrack")) {
1447
- while (!this.match("rbrack")) {
1448
- const keyToken = this.consume();
1449
- if (!isIdentifierLike(keyToken)) {
1450
- throw new Error("Expected attribute name.");
1451
- }
1452
- const key = parseIdentifierValue(keyToken);
1453
- let value = true;
1454
- if (this.match("equals")) {
1455
- const valueToken = this.consume();
1456
- value = parseAttributeValue(valueToken);
1457
- }
1458
- attributes[key] = value;
1459
- if (((_a = this.peek()) == null ? void 0 : _a.type) === "comma" || ((_b = this.peek()) == null ? void 0 : _b.type) === "semicolon") {
1460
- this.consume();
1461
- }
1462
- }
1463
- }
1464
- return attributes;
1465
- }
1466
- /** Creates an implicit node and records its subgraph memberships. */
1467
- ensureNode(id, membership) {
1468
- let node = this.result.nodes.get(id);
1469
- if (!node) {
1470
- const defaults = this.currentScope().nodeDefaults;
1471
- node = { id, attributes: { ...defaults }, subgraphs: /* @__PURE__ */ new Set() };
1472
- this.result.nodes.set(id, node);
1473
- }
1474
- membership.forEach((subgraphId) => node.subgraphs.add(subgraphId));
1475
- return node;
1476
- }
1477
- /** Lists enclosing subgraphs. */
1478
- getCurrentSubgraphChain() {
1479
- const chain = [];
1480
- for (const scope of this.scopes) {
1481
- if (scope.id) {
1482
- chain.push(scope.id);
1483
- }
1484
- }
1485
- return chain;
1486
- }
1487
- /** Finds the nearest enclosing named or generated subgraph. */
1488
- findCurrentSubgraphId() {
1489
- for (let index = this.scopes.length - 1; index >= 0; index--) {
1490
- const scope = this.scopes[index];
1491
- if (scope.id) {
1492
- return scope.id;
1493
- }
1494
- }
1495
- return void 0;
1496
- }
1497
- /** Returns the active attribute scope. */
1498
- currentScope() {
1499
- return this.scopes[this.scopes.length - 1];
1500
- }
1501
- /** Consumes an optional statement terminator. */
1502
- consumeOptionalSemicolon() {
1503
- const next = this.peek();
1504
- if ((next == null ? void 0 : next.type) === "semicolon") {
1505
- this.consume();
1506
- }
1507
- }
1508
- /** Requires the next token to have the requested type. */
1509
- expect(type) {
1510
- const token = this.consume();
1511
- if (!token || token.type !== type) {
1512
- throw new Error(`Expected token ${type}.`);
1513
- }
1514
- return token;
1515
- }
1516
- /** Consumes the next token or reports truncated input. */
1517
- consume() {
1518
- const token = this.tokens[this.position];
1519
- if (!token) {
1520
- throw new Error("Unexpected end of DOT input.");
1521
- }
1522
- this.position++;
1523
- return token;
1524
- }
1525
- /** Consumes a token when its type matches. */
1526
- match(type) {
1527
- const token = this.peek();
1528
- if (token && token.type === type) {
1529
- this.position++;
1530
- return token;
1531
- }
1532
- return null;
1533
- }
1534
- /** Inspects a token without consuming it. */
1535
- peek(offset = 0) {
1536
- return this.tokens[this.position + offset] ?? null;
1537
- }
1538
- };
1539
- IDENTIFIER_TERMINATORS = /* @__PURE__ */ new Set(["{", "}", "[", "]", "=", ";", ",", '"', "<", "#"]);
1540
- }
1541
- });
1542
-
1543
- // src/dot-loader.ts
1544
- var dot_loader_exports = {};
1545
- __export(dot_loader_exports, {
1546
- DOTLoaderWithParser: () => DOTLoaderWithParser
1547
- });
1548
- var DOTLoaderWithParser;
1549
- var init_dot_loader = __esm({
1550
- "src/dot-loader.ts"() {
1551
- "use strict";
1552
- init_dot_loader_types();
1553
- init_parse_dot();
1554
- DOTLoaderWithParser = {
1555
- ...DOTLoader,
1556
- parse: async (data, options) => {
1557
- var _a;
1558
- return parseDOT(new TextDecoder().decode(data), ((_a = options == null ? void 0 : options.dot) == null ? void 0 : _a.shape) ?? "arrow-table");
1559
- },
1560
- parseSync: (data, options) => {
1561
- var _a;
1562
- return parseDOT(new TextDecoder().decode(data), ((_a = options == null ? void 0 : options.dot) == null ? void 0 : _a.shape) ?? "arrow-table");
1563
- },
1564
- parseTextSync: (data, options) => {
1565
- var _a;
1566
- return parseDOT(data, ((_a = options == null ? void 0 : options.dot) == null ? void 0 : _a.shape) ?? "arrow-table");
1567
- }
1568
- };
1569
- }
1570
- });
1571
-
1572
- // src/gexf-loader-types.ts
1573
- async function preload5() {
1574
- const { GEXFLoaderWithParser: GEXFLoaderWithParser2 } = await Promise.resolve().then(() => (init_gexf_loader(), gexf_loader_exports));
1575
- return GEXFLoaderWithParser2;
1576
- }
1577
- var VERSION5, GEXFLoader;
1578
- var init_gexf_loader_types = __esm({
1579
- "src/gexf-loader-types.ts"() {
1580
- "use strict";
1581
- VERSION5 = typeof __VERSION__ !== "undefined" ? __VERSION__ : "latest";
1582
- GEXFLoader = {
1583
- name: "GEXF",
1584
- id: "gexf",
1585
- module: "graphs",
1586
- version: VERSION5,
1587
- extensions: ["gexf"],
1588
- mimeTypes: ["application/gexf+xml"],
1589
- text: true,
1590
- worker: false,
1591
- dataType: null,
1592
- batchType: null,
1593
- options: { gexf: { shape: "arrow-table" } },
1594
- preload: preload5
1595
- };
1596
- }
1597
- });
1598
-
1599
- // src/lib/parse-gexf.ts
1600
- function parseGEXF(input, shape = "arrow-table") {
1601
- const text = typeof input === "string" ? input : new TextDecoder().decode(input);
1602
- const validation = import_fast_xml_parser2.XMLValidator.validate(text);
1603
- if (validation !== true) throw new Error(`Invalid GEXF XML: ${validation.err.msg}`);
1604
- if (/<!DOCTYPE\s/i.test(text)) throw new Error("GEXF document types are unsupported.");
1605
- const document = normalizeNamespaces(parser.parse(text), {});
1606
- const root = getElement(document.gexf, "gexf");
1607
- const version = root["@_version"];
1608
- if (version && !["1.2", "1.2draft", "1.3"].includes(version)) {
1609
- throw new Error(`Unsupported GEXF version: ${version}`);
1610
- }
1611
- const graph = getElement(root.graph, "graph");
1612
- const directed = parseDirection(graph["@_defaultedgetype"] ?? "undirected");
1613
- const definitions = {
1614
- nodes: /* @__PURE__ */ new Map(),
1615
- edges: /* @__PURE__ */ new Map()
1616
- };
1617
- for (const attributes of getElements(graph.attributes)) {
1618
- const domain = attributes["@_class"];
1619
- if (domain !== "node" && domain !== "edge")
1620
- throw new Error("GEXF attributes require a node or edge class.");
1621
- const scoped = domain === "node" ? definitions.nodes : definitions.edges;
1622
- const names = new Set(Array.from(scoped.values(), (definition) => definition.name));
1623
- for (const attribute of getElements(attributes.attribute)) {
1624
- const identifier = requireAttribute(attribute, "id");
1625
- const name = requireAttribute(attribute, "title");
1626
- if (name === "gexf" || names.has(name) || scoped.has(identifier)) {
1627
- throw new Error(`Duplicate or reserved GEXF attribute: ${name}`);
1628
- }
1629
- names.add(name);
1630
- const type = parseAttributeType(requireAttribute(attribute, "type"));
1631
- scoped.set(identifier, {
1632
- name,
1633
- type,
1634
- defaultValue: attribute.default === void 0 ? void 0 : castValue(readTextContent(attribute.default), type)
1635
- });
1636
- }
1637
- }
1638
- const nodeElements = getElements(getContainer(graph.nodes).node);
1639
- const edgeElements = getElements(getContainer(graph.edges).edge);
1640
- const nodeIdentifiers = /* @__PURE__ */ new Set();
1641
- for (const node of nodeElements) {
1642
- const identifier = requireAttribute(node, "id");
1643
- if (nodeIdentifiers.has(identifier)) throw new Error(`Duplicate GEXF node ID: ${identifier}`);
1644
- nodeIdentifiers.add(identifier);
1645
- }
1646
- const edgeIdentifiers = new Set(
1647
- edgeElements.map((edge) => edge["@_id"]).filter((identifier) => typeof identifier === "string")
1648
- );
1649
- const seenEdges = /* @__PURE__ */ new Set();
1650
- function* iterateNodes3() {
1651
- for (const node of nodeElements) yield parseRecord(node, definitions.nodes);
1652
- }
1653
- function* iterateEdges3() {
1654
- for (const [index, edge] of edgeElements.entries()) {
1655
- const sourceId = requireAttribute(edge, "source");
1656
- const targetId = requireAttribute(edge, "target");
1657
- if (!nodeIdentifiers.has(sourceId) || !nodeIdentifiers.has(targetId)) {
1658
- throw new Error("GEXF edge references an undeclared node.");
1659
- }
1660
- let identifier = edge["@_id"] === void 0 ? void 0 : requireAttribute(edge, "id");
1661
- if (identifier === void 0) {
1662
- identifier = `edge-${index}`;
1663
- while (edgeIdentifiers.has(identifier)) identifier = `_${identifier}`;
1664
- edgeIdentifiers.add(identifier);
1665
- }
1666
- if (seenEdges.has(identifier)) throw new Error(`Duplicate GEXF edge ID: ${identifier}`);
1667
- seenEdges.add(identifier);
1668
- yield {
1669
- ...parseRecord(edge, definitions.edges, identifier),
1670
- sourceId,
1671
- targetId,
1672
- directed: edge["@_type"] === void 0 ? directed : parseDirection(edge["@_type"])
1673
- };
1674
- }
1675
- }
1676
- const metadataAttributes = /* @__PURE__ */ Object.create(null);
1677
- const meta = getContainer(root.meta);
1678
- for (const name of ["creator", "description", "keywords"]) {
1679
- if (meta[name] !== void 0) metadataAttributes[name] = readTextContent(meta[name]);
1680
- }
1681
- if (typeof meta["@_lastmodifieddate"] === "string")
1682
- metadataAttributes.lastmodifieddate = meta["@_lastmodifieddate"];
1683
- const declarations = {
1684
- nodes: new Map(
1685
- Array.from(definitions.nodes.values(), (definition) => [definition.name, definition.type])
1686
- ),
1687
- edges: new Map(
1688
- Array.from(definitions.edges.values(), (definition) => [definition.name, definition.type])
1689
- )
1690
- };
1691
- return {
1692
- ...buildGraphTables(iterateNodes3(), iterateEdges3(), shape, declarations),
1693
- metadata: { version, directed, attributes: metadataAttributes }
1694
- };
1695
- }
1696
- function normalizeNamespaces(element, inherited) {
1697
- const namespaces = Object.assign(/* @__PURE__ */ Object.create(null), inherited);
1698
- for (const [name, value] of Object.entries(element)) {
1699
- if (name === "@_xmlns") namespaces[""] = String(value);
1700
- else if (name.startsWith("@_xmlns:")) namespaces[name.slice(8)] = String(value);
1701
- }
1702
- const normalized = /* @__PURE__ */ Object.create(null);
1703
- for (const [name, value] of Object.entries(element)) {
1704
- if (name.startsWith("@_") || name === "#text" || name.startsWith("?")) {
1705
- normalized[name] = value;
1706
- continue;
1707
- }
1708
- const separator = name.indexOf(":");
1709
- const prefix = separator < 0 ? "" : name.slice(0, separator);
1710
- const localName = name.slice(separator + 1);
1711
- const children = Array.isArray(value) ? value : [value];
1712
- for (const child of children) {
1713
- const object = typeof child === "object" && child !== null ? child : {};
1714
- const namespace = object[prefix ? `@_xmlns:${prefix}` : "@_xmlns"] ?? namespaces[prefix];
1715
- const match = typeof namespace === "string" ? GEXF_NAMESPACE.exec(namespace) : null;
1716
- const key = match ? `${match[1] ? "viz:" : ""}${localName}` : namespace || prefix ? `foreign:${name}` : localName;
1717
- const childValue = typeof child === "object" && child !== null ? match || !namespace && !prefix ? normalizeNamespaces(object, namespaces) : object : child;
1718
- if (normalized[key] === void 0) normalized[key] = childValue;
1719
- else
1720
- normalized[key] = [
1721
- ...Array.isArray(normalized[key]) ? normalized[key] : [normalized[key]],
1722
- childValue
1723
- ];
1724
- }
1725
- }
1726
- assertStaticElement(normalized);
1727
- return normalized;
1728
- }
1729
- function assertStaticElement(element) {
1730
- if (element["@_mode"] !== void 0 && element["@_mode"] !== "static" || TEMPORAL_ATTRIBUTES.some((name) => element[`@_${name}`] !== void 0) || element.spells !== void 0) {
1731
- throw new Error("Dynamic GEXF graphs and temporal values are unsupported.");
1732
- }
1733
- if (element["@_pid"] !== void 0 || element.parents !== void 0 || element["@_id"] !== void 0 && (element.nodes !== void 0 || element.edges !== void 0)) {
1734
- throw new Error("Hierarchical GEXF graphs are unsupported.");
1735
- }
1736
- }
1737
- function getElement(value, name) {
1738
- if (value === "") return {};
1739
- if (value && typeof value === "object" && !Array.isArray(value)) return value;
1740
- throw new Error(`GEXF requires one <${name}> element.`);
1741
- }
1742
- function readTextContent(value) {
1743
- if (typeof value === "string") return value;
1744
- const text = getElement(value, "text")["#text"];
1745
- return typeof text === "string" ? text : "";
1746
- }
1747
- function getContainer(value) {
1748
- return value === void 0 ? {} : getElement(value, "container");
1749
- }
1750
- function getElements(value) {
1751
- if (value === void 0) return [];
1752
- return (Array.isArray(value) ? value : [value]).map((entry) => getElement(entry, "record"));
1753
- }
1754
- function requireAttribute(element, name) {
1755
- const value = element[`@_${name}`];
1756
- if (typeof value !== "string" || value === "")
1757
- throw new Error(`GEXF requires a ${name} attribute.`);
1758
- return value;
1759
- }
1760
- function parseDirection(value) {
1761
- if (value !== "directed" && value !== "undirected")
1762
- throw new Error(`Unsupported GEXF edge type: ${String(value)}`);
1763
- return value === "directed";
1764
- }
1765
- function parseAttributeType(value) {
1766
- if (value.startsWith("list") && !value.slice(4).startsWith("list")) {
1767
- return { list: parseAttributeType(value.slice(4)) };
1768
- }
1769
- if (value === "integer" || value === "byte" || value === "short") return "int";
1770
- if (value === "boolean" || value === "long" || value === "float" || value === "double")
1771
- return value;
1772
- if (["string", "anyURI", "date", "char", "bigdecimal", "biginteger"].includes(value))
1773
- return "string";
1774
- throw new Error(`Unsupported GEXF attribute type: ${value}`);
1775
- }
1776
- function castValue(text, type) {
1777
- if (typeof type === "object") {
1778
- return parseListValues(text).map((value) => castValue(value, type.list));
1779
- }
1780
- if (type === "string") return text;
1781
- const trimmed = text.trim();
1782
- if (type === "boolean") {
1783
- if (trimmed === "true" || trimmed === "1") return true;
1784
- if (trimmed === "false" || trimmed === "0") return false;
1785
- return text;
1786
- }
1787
- if (type === "int" || type === "long") {
1788
- if (!/^[+-]?\d+$/.test(trimmed)) return text;
1789
- return type === "long" ? BigInt(trimmed) : Number.isSafeInteger(Number(trimmed)) ? Number(trimmed) : text;
1790
- }
1791
- if (trimmed === "INF") return Infinity;
1792
- if (trimmed === "-INF") return -Infinity;
1793
- if (trimmed === "NaN") return NaN;
1794
- if (!/^[+-]?(?:\d+(?:\.\d*)?|\.\d+)(?:[eE][+-]?\d+)?$/.test(trimmed)) return text;
1795
- const number = Number(trimmed);
1796
- const represented = type === "float" ? Math.fround(number) : number;
1797
- const nonzero = /[1-9]/.test(trimmed.split(/[eE]/)[0]);
1798
- return Number.isFinite(represented) && (represented !== 0 || !nonzero) ? number : text;
1799
- }
1800
- function parseListValues(text) {
1801
- const trimmed = text.trim();
1802
- const bracketed = trimmed.startsWith("[");
1803
- if (bracketed !== trimmed.endsWith("]")) throw new Error("Invalid GEXF list brackets.");
1804
- const contents = bracketed ? trimmed.slice(1, -1) : trimmed;
1805
- if (!contents.trim()) return [];
1806
- const values = [];
1807
- let value = "";
1808
- let quote = "";
1809
- let quoted = false;
1810
- let closed = false;
1811
- for (let index = 0; index < contents.length; index++) {
1812
- const character = contents[index];
1813
- if (quote) {
1814
- if (character === "\\" && (contents[index + 1] === quote || contents[index + 1] === "\\")) {
1815
- value += contents[++index];
1816
- } else if (character === quote) {
1817
- quote = "";
1818
- closed = true;
1819
- } else value += character;
1820
- } else if (character === "," || !bracketed && (character === "|" || character === ";")) {
1821
- values.push(quoted ? value : value.trim());
1822
- value = "";
1823
- quoted = false;
1824
- closed = false;
1825
- } else if (closed) {
1826
- if (character.trim()) throw new Error("Invalid GEXF list text after a quote.");
1827
- } else if ((character === "'" || character === '"') && !value.trim()) {
1828
- quote = character;
1829
- quoted = true;
1830
- value = "";
1831
- } else value += character;
1832
- }
1833
- if (quote) throw new Error("Unterminated GEXF list quote.");
1834
- values.push(quoted ? value : value.trim());
1835
- return values;
1836
- }
1837
- function parseRecord(element, definitions, identifier) {
1838
- const attributes = /* @__PURE__ */ Object.create(null);
1839
- for (const definition of definitions.values()) {
1840
- if (definition.defaultValue !== void 0)
1841
- attributes[definition.name] = Array.isArray(definition.defaultValue) ? [...definition.defaultValue] : definition.defaultValue;
1842
- }
1843
- for (const attvalue of getElements(getContainer(element.attvalues).attvalue)) {
1844
- const key = requireAttribute(attvalue, "for");
1845
- const definition = definitions.get(key);
1846
- if (!definition) throw new Error(`Undeclared GEXF attribute: ${key}`);
1847
- attributes[definition.name] = castValue(requireValue(attvalue), definition.type);
1848
- }
1849
- const native = /* @__PURE__ */ Object.create(null);
1850
- if (element["@_weight"] !== void 0)
1851
- native.weight = castValue(String(element["@_weight"]), "double");
1852
- if (element["@_kind"] !== void 0) native.kind = element["@_kind"];
1853
- const visualization = /* @__PURE__ */ Object.create(null);
1854
- for (const name of ["color", "position", "size", "shape", "thickness"]) {
1855
- const value = element[`viz:${name}`];
1856
- if (value === void 0) continue;
1857
- const properties = /* @__PURE__ */ Object.create(null);
1858
- for (const [key, property] of Object.entries(getElement(value, `viz:${name}`))) {
1859
- if (key.startsWith("@_") && !key.startsWith("@_xmlns")) {
1860
- const propertyName = key.slice(2);
1861
- properties[propertyName] = ["r", "g", "b", "a", "x", "y", "z"].includes(propertyName) || propertyName === "value" && (name === "size" || name === "thickness") ? castValue(String(property), "double") : property;
1862
- }
1863
- }
1864
- visualization[name] = properties;
1865
- }
1866
- if (Object.keys(visualization).length) native.viz = visualization;
1867
- if (Object.keys(native).length) attributes.gexf = native;
1868
- return {
1869
- id: identifier ?? requireAttribute(element, "id"),
1870
- label: element["@_label"],
1871
- attributes
1872
- };
1873
- }
1874
- function requireValue(element) {
1875
- const value = element["@_value"];
1876
- if (typeof value !== "string") throw new Error("GEXF attvalue requires a value attribute.");
1877
- return value;
1878
- }
1879
- var import_fast_xml_parser2, parser, GEXF_NAMESPACE, TEMPORAL_ATTRIBUTES;
1880
- var init_parse_gexf = __esm({
1881
- "src/lib/parse-gexf.ts"() {
1882
- "use strict";
1883
- import_fast_xml_parser2 = require("fast-xml-parser");
1884
- init_build_graph_tables();
1885
- parser = new import_fast_xml_parser2.XMLParser({
1886
- ignoreAttributes: false,
1887
- parseAttributeValue: false,
1888
- parseTagValue: false,
1889
- trimValues: false
1890
- });
1891
- GEXF_NAMESPACE = /^https?:\/\/(?:www\.)?gexf.net\/1\.(?:2(?:draft)?|3)(\/viz)?$/;
1892
- TEMPORAL_ATTRIBUTES = [
1893
- "start",
1894
- "end",
1895
- "startopen",
1896
- "endopen",
1897
- "timestamp",
1898
- "timestamps",
1899
- "intervals"
1900
- ];
1901
- }
1902
- });
1903
-
1904
- // src/gexf-loader.ts
1905
- var gexf_loader_exports = {};
1906
- __export(gexf_loader_exports, {
1907
- GEXFLoaderWithParser: () => GEXFLoaderWithParser
1908
- });
1909
- var GEXFLoaderWithParser;
1910
- var init_gexf_loader = __esm({
1911
- "src/gexf-loader.ts"() {
1912
- "use strict";
1913
- init_gexf_loader_types();
1914
- init_parse_gexf();
1915
- GEXFLoaderWithParser = {
1916
- ...GEXFLoader,
1917
- parse: async (data, options) => {
1918
- var _a;
1919
- return parseGEXF(data, ((_a = options == null ? void 0 : options.gexf) == null ? void 0 : _a.shape) ?? "arrow-table");
1920
- },
1921
- parseSync: (data, options) => {
1922
- var _a;
1923
- return parseGEXF(data, ((_a = options == null ? void 0 : options.gexf) == null ? void 0 : _a.shape) ?? "arrow-table");
1924
- },
1925
- parseTextSync: (data, options) => {
1926
- var _a;
1927
- return parseGEXF(data, ((_a = options == null ? void 0 : options.gexf) == null ? void 0 : _a.shape) ?? "arrow-table");
1928
- }
1929
- };
1930
- }
1931
- });
1932
-
1933
30
  // dist/index.js
1934
31
  var index_exports = {};
1935
32
  __export(index_exports, {
1936
- DOTLoader: () => DOTLoader2,
1937
- GEXFLoader: () => GEXFLoader2,
1938
- GraphMLLoader: () => GraphMLLoader2
33
+ DOTLoader: () => DOTLoader,
34
+ GEXFLoader: () => GEXFLoader,
35
+ GraphMLLoader: () => GraphMLLoader
1939
36
  });
1940
37
  module.exports = __toCommonJS(index_exports);
1941
38
 
1942
39
  // dist/graphml-loader-types.js
1943
- var VERSION2 = true ? "5.0.0-beta.1" : "latest";
1944
- async function preload2() {
1945
- const { GraphMLLoaderWithParser: GraphMLLoaderWithParser2 } = await Promise.resolve().then(() => (init_graphml_loader(), graphml_loader_exports));
1946
- return GraphMLLoaderWithParser2;
40
+ var VERSION = true ? "5.0.0-beta.2" : "latest";
41
+ async function preload() {
42
+ const { GraphMLLoaderWithParser } = await import("@loaders.gl/graphs/graphml-loader");
43
+ return GraphMLLoaderWithParser;
1947
44
  }
1948
- var GraphMLLoader2 = {
45
+ var GraphMLLoader = {
1949
46
  name: "GraphML",
1950
47
  id: "graphml",
1951
48
  module: "graphs",
1952
- version: VERSION2,
49
+ version: VERSION,
1953
50
  extensions: ["graphml"],
1954
51
  mimeTypes: ["application/graphml+xml"],
1955
52
  text: true,
@@ -1957,20 +54,20 @@ var GraphMLLoader2 = {
1957
54
  dataType: null,
1958
55
  batchType: null,
1959
56
  options: { graphml: { shape: "arrow-table" } },
1960
- preload: preload2
57
+ preload
1961
58
  };
1962
59
 
1963
60
  // dist/dot-loader-types.js
1964
- var VERSION4 = true ? "5.0.0-beta.1" : "latest";
1965
- async function preload4() {
1966
- const { DOTLoaderWithParser: DOTLoaderWithParser2 } = await Promise.resolve().then(() => (init_dot_loader(), dot_loader_exports));
1967
- return DOTLoaderWithParser2;
61
+ var VERSION2 = true ? "5.0.0-beta.2" : "latest";
62
+ async function preload2() {
63
+ const { DOTLoaderWithParser } = await import("@loaders.gl/graphs/dot-loader");
64
+ return DOTLoaderWithParser;
1968
65
  }
1969
- var DOTLoader2 = {
66
+ var DOTLoader = {
1970
67
  name: "DOT",
1971
68
  id: "dot",
1972
69
  module: "graphs",
1973
- version: VERSION4,
70
+ version: VERSION2,
1974
71
  extensions: ["dot", "gv"],
1975
72
  mimeTypes: ["text/vnd.graphviz", "text/x-graphviz", "application/vnd.graphviz"],
1976
73
  text: true,
@@ -1978,20 +75,20 @@ var DOTLoader2 = {
1978
75
  dataType: null,
1979
76
  batchType: null,
1980
77
  options: { dot: { shape: "arrow-table" } },
1981
- preload: preload4
78
+ preload: preload2
1982
79
  };
1983
80
 
1984
81
  // dist/gexf-loader-types.js
1985
- var VERSION6 = true ? "5.0.0-beta.1" : "latest";
1986
- async function preload6() {
1987
- const { GEXFLoaderWithParser: GEXFLoaderWithParser2 } = await Promise.resolve().then(() => (init_gexf_loader(), gexf_loader_exports));
1988
- return GEXFLoaderWithParser2;
82
+ var VERSION3 = true ? "5.0.0-beta.2" : "latest";
83
+ async function preload3() {
84
+ const { GEXFLoaderWithParser } = await import("@loaders.gl/graphs/gexf-loader");
85
+ return GEXFLoaderWithParser;
1989
86
  }
1990
- var GEXFLoader2 = {
87
+ var GEXFLoader = {
1991
88
  name: "GEXF",
1992
89
  id: "gexf",
1993
90
  module: "graphs",
1994
- version: VERSION6,
91
+ version: VERSION3,
1995
92
  extensions: ["gexf"],
1996
93
  mimeTypes: ["application/gexf+xml"],
1997
94
  text: true,
@@ -1999,6 +96,12 @@ var GEXFLoader2 = {
1999
96
  dataType: null,
2000
97
  batchType: null,
2001
98
  options: { gexf: { shape: "arrow-table" } },
2002
- preload: preload6
99
+ preload: preload3
2003
100
  };
101
+ // Annotate the CommonJS export names for ESM import in node:
102
+ 0 && (module.exports = {
103
+ DOTLoader,
104
+ GEXFLoader,
105
+ GraphMLLoader
106
+ });
2004
107
  //# sourceMappingURL=index.cjs.map