@graphty/graph-io 0.3.24 → 0.3.26
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/README.md +49 -414
- package/dist/chunks/children-CL3Cy0ez.js.map +1 -1
- package/dist/chunks/choose-BbJI55dx.js +56 -0
- package/dist/chunks/choose-BbJI55dx.js.map +1 -0
- package/dist/chunks/constants-BCsFsMj4.js +231 -0
- package/dist/chunks/constants-BCsFsMj4.js.map +1 -0
- package/dist/chunks/{escape-B-tkk_Cl.js → escape-D0g6NNUy.js} +382 -92
- package/dist/chunks/escape-D0g6NNUy.js.map +1 -0
- package/dist/chunks/export-BTI4yQgy.js +4333 -0
- package/dist/chunks/export-BTI4yQgy.js.map +1 -0
- package/dist/chunks/exporter-BMqk5oxW.js +3465 -0
- package/dist/chunks/exporter-BMqk5oxW.js.map +1 -0
- package/dist/chunks/{importer-eUREhBGj.js → exporter-Cra2GYcN.js} +4969 -3201
- package/dist/chunks/exporter-Cra2GYcN.js.map +1 -0
- package/dist/chunks/{exporter-BGrsWamJ.js → exporter-Dxh231ZF.js} +38 -229
- package/dist/chunks/exporter-Dxh231ZF.js.map +1 -0
- package/dist/chunks/{exporter-DIeGJXAZ.js → exporter-tne475KK.js} +22 -20
- package/dist/chunks/exporter-tne475KK.js.map +1 -0
- package/dist/chunks/importer-90YWhJoF.js +2811 -0
- package/dist/chunks/importer-90YWhJoF.js.map +1 -0
- package/dist/chunks/{importer-D_e7e7LX.js → importer-Bcl1d4xH.js} +398 -145
- package/dist/chunks/importer-Bcl1d4xH.js.map +1 -0
- package/dist/chunks/{importer-BWY2FFc5.js → importer-BfIsp1f9.js} +255 -77
- package/dist/chunks/importer-BfIsp1f9.js.map +1 -0
- package/dist/chunks/{importer-zGLo8Dg_.js → importer-C_TEA1zJ.js} +484 -157
- package/dist/chunks/importer-C_TEA1zJ.js.map +1 -0
- package/dist/chunks/{importer-DET1tg6s.js → importer-DCjOvO7U.js} +1687 -310
- package/dist/chunks/importer-DCjOvO7U.js.map +1 -0
- package/dist/chunks/{importer-vi3bSdtw.js → importer-DfVu6j59.js} +509 -76
- package/dist/chunks/importer-DfVu6j59.js.map +1 -0
- package/dist/chunks/{importer-DIrbbnAf.js → importer-Dku_VAIY.js} +585 -226
- package/dist/chunks/importer-Dku_VAIY.js.map +1 -0
- package/dist/chunks/json-elements-3tnyt5uZ.js +1225 -0
- package/dist/chunks/json-elements-3tnyt5uZ.js.map +1 -0
- package/dist/chunks/ontology-export-B9Tcf37D.js +357 -0
- package/dist/chunks/ontology-export-B9Tcf37D.js.map +1 -0
- package/dist/chunks/{records-dbRkxwaq.js → records-CQXT__mY.js} +298 -114
- package/dist/chunks/records-CQXT__mY.js.map +1 -0
- package/dist/chunks/{text-Dr0Ifpag.js → text-DmcUs5_Q.js} +29 -11
- package/dist/chunks/text-DmcUs5_Q.js.map +1 -0
- package/dist/chunks/{writer-C7flM-Ih.js → writer-DxjgHwSe.js} +19 -1
- package/dist/chunks/writer-DxjgHwSe.js.map +1 -0
- package/dist/csv.js +951 -261
- package/dist/csv.js.map +1 -1
- package/dist/cx.js +6 -3
- package/dist/cx2.js +2 -2
- package/dist/cys.js +6 -3
- package/dist/dot.js +1 -1
- package/dist/gexf.js +554 -122
- package/dist/gexf.js.map +1 -1
- package/dist/gml.js +342 -85
- package/dist/gml.js.map +1 -1
- package/dist/graph-io.js +1105 -213
- package/dist/graph-io.js.map +1 -1
- package/dist/graphml.js +3 -2
- package/dist/graphml.js.map +1 -1
- package/dist/json.js +3 -2
- package/dist/neo4j.js +564 -157
- package/dist/neo4j.js.map +1 -1
- package/dist/obo.js +6 -3
- package/dist/pajek.js +1 -1
- package/dist/src/children.d.ts +18 -6
- package/dist/src/children.d.ts.map +1 -1
- package/dist/src/children.js +6 -3
- package/dist/src/children.js.map +1 -1
- package/dist/src/common/attributes.d.ts +29 -11
- package/dist/src/common/attributes.d.ts.map +1 -1
- package/dist/src/common/attributes.js +25 -7
- package/dist/src/common/attributes.js.map +1 -1
- package/dist/src/common/cell-budget.d.ts +9 -2
- package/dist/src/common/cell-budget.d.ts.map +1 -1
- package/dist/src/common/cell-budget.js +11 -3
- package/dist/src/common/cell-budget.js.map +1 -1
- package/dist/src/common/choose.d.ts +19 -0
- package/dist/src/common/choose.d.ts.map +1 -0
- package/dist/src/common/choose.js +72 -0
- package/dist/src/common/choose.js.map +1 -0
- package/dist/src/common/codes.d.ts +456 -66
- package/dist/src/common/codes.d.ts.map +1 -1
- package/dist/src/common/codes.js +458 -66
- package/dist/src/common/codes.js.map +1 -1
- package/dist/src/common/compare.d.ts +81 -0
- package/dist/src/common/compare.d.ts.map +1 -0
- package/dist/src/common/compare.js +394 -0
- package/dist/src/common/compare.js.map +1 -0
- package/dist/src/common/cx-export.d.ts +123 -0
- package/dist/src/common/cx-export.d.ts.map +1 -0
- package/dist/src/common/cx-export.js +334 -0
- package/dist/src/common/cx-export.js.map +1 -0
- package/dist/src/common/declared-types.d.ts +22 -2
- package/dist/src/common/declared-types.d.ts.map +1 -1
- package/dist/src/common/declared-types.js +19 -1
- package/dist/src/common/declared-types.js.map +1 -1
- package/dist/src/common/direction.d.ts +74 -50
- package/dist/src/common/direction.d.ts.map +1 -1
- package/dist/src/common/direction.js +47 -27
- package/dist/src/common/direction.js.map +1 -1
- package/dist/src/common/escape.d.ts +21 -9
- package/dist/src/common/escape.d.ts.map +1 -1
- package/dist/src/common/escape.js +33 -17
- package/dist/src/common/escape.js.map +1 -1
- package/dist/src/common/export.d.ts +144 -32
- package/dist/src/common/export.d.ts.map +1 -1
- package/dist/src/common/export.js +216 -42
- package/dist/src/common/export.js.map +1 -1
- package/dist/src/common/format.d.ts +23 -1
- package/dist/src/common/format.d.ts.map +1 -1
- package/dist/src/common/format.js +26 -1
- package/dist/src/common/format.js.map +1 -1
- package/dist/src/common/ids.d.ts +9 -2
- package/dist/src/common/ids.d.ts.map +1 -1
- package/dist/src/common/ids.js +6 -2
- package/dist/src/common/ids.js.map +1 -1
- package/dist/src/common/input.d.ts +122 -28
- package/dist/src/common/input.d.ts.map +1 -1
- package/dist/src/common/input.js +890 -124
- package/dist/src/common/input.js.map +1 -1
- package/dist/src/common/json-elements.d.ts +144 -20
- package/dist/src/common/json-elements.d.ts.map +1 -1
- package/dist/src/common/json-elements.js +868 -188
- package/dist/src/common/json-elements.js.map +1 -1
- package/dist/src/common/line-format.d.ts +90 -0
- package/dist/src/common/line-format.d.ts.map +1 -0
- package/dist/src/common/line-format.js +185 -0
- package/dist/src/common/line-format.js.map +1 -0
- package/dist/src/common/lists.d.ts +6 -1
- package/dist/src/common/lists.d.ts.map +1 -1
- package/dist/src/common/lists.js +2 -0
- package/dist/src/common/lists.js.map +1 -1
- package/dist/src/common/ontology-export.d.ts +167 -0
- package/dist/src/common/ontology-export.d.ts.map +1 -0
- package/dist/src/common/ontology-export.js +359 -0
- package/dist/src/common/ontology-export.js.map +1 -0
- package/dist/src/common/ontology.d.ts +25 -3
- package/dist/src/common/ontology.d.ts.map +1 -1
- package/dist/src/common/ontology.js +30 -9
- package/dist/src/common/ontology.js.map +1 -1
- package/dist/src/common/options.d.ts +62 -12
- package/dist/src/common/options.d.ts.map +1 -1
- package/dist/src/common/options.js +89 -11
- package/dist/src/common/options.js.map +1 -1
- package/dist/src/common/plural.d.ts +31 -0
- package/dist/src/common/plural.d.ts.map +1 -0
- package/dist/src/common/plural.js +46 -0
- package/dist/src/common/plural.js.map +1 -0
- package/dist/src/common/report.d.ts +72 -14
- package/dist/src/common/report.d.ts.map +1 -1
- package/dist/src/common/report.js +146 -22
- package/dist/src/common/report.js.map +1 -1
- package/dist/src/common/temporal.d.ts +22 -5
- package/dist/src/common/temporal.d.ts.map +1 -1
- package/dist/src/common/temporal.js +13 -2
- package/dist/src/common/temporal.js.map +1 -1
- package/dist/src/common/text.d.ts +39 -23
- package/dist/src/common/text.d.ts.map +1 -1
- package/dist/src/common/text.js +51 -21
- package/dist/src/common/text.js.map +1 -1
- package/dist/src/common/weights.d.ts +37 -4
- package/dist/src/common/weights.d.ts.map +1 -1
- package/dist/src/common/weights.js +61 -2
- package/dist/src/common/weights.js.map +1 -1
- package/dist/src/common/writer.d.ts +19 -3
- package/dist/src/common/writer.d.ts.map +1 -1
- package/dist/src/common/writer.js +30 -2
- package/dist/src/common/writer.js.map +1 -1
- package/dist/src/common/xml.d.ts +125 -9
- package/dist/src/common/xml.d.ts.map +1 -1
- package/dist/src/common/xml.js +400 -83
- package/dist/src/common/xml.js.map +1 -1
- package/dist/src/common/zip.d.ts +44 -4
- package/dist/src/common/zip.d.ts.map +1 -1
- package/dist/src/common/zip.js +134 -5
- package/dist/src/common/zip.js.map +1 -1
- package/dist/src/formats/csv/exporter.d.ts +80 -24
- package/dist/src/formats/csv/exporter.d.ts.map +1 -1
- package/dist/src/formats/csv/exporter.js +145 -32
- package/dist/src/formats/csv/exporter.js.map +1 -1
- package/dist/src/formats/csv/header.d.ts +38 -9
- package/dist/src/formats/csv/header.d.ts.map +1 -1
- package/dist/src/formats/csv/header.js +46 -10
- package/dist/src/formats/csv/header.js.map +1 -1
- package/dist/src/formats/csv/importer.d.ts +187 -37
- package/dist/src/formats/csv/importer.d.ts.map +1 -1
- package/dist/src/formats/csv/importer.js +835 -204
- package/dist/src/formats/csv/importer.js.map +1 -1
- package/dist/src/formats/csv/index.d.ts +100 -19
- package/dist/src/formats/csv/index.d.ts.map +1 -1
- package/dist/src/formats/csv/index.js +94 -21
- package/dist/src/formats/csv/index.js.map +1 -1
- package/dist/src/formats/csv/records.d.ts +95 -10
- package/dist/src/formats/csv/records.d.ts.map +1 -1
- package/dist/src/formats/csv/records.js +333 -122
- package/dist/src/formats/csv/records.js.map +1 -1
- package/dist/src/formats/csv/values.d.ts +1 -0
- package/dist/src/formats/csv/values.d.ts.map +1 -1
- package/dist/src/formats/csv/values.js +1 -0
- package/dist/src/formats/csv/values.js.map +1 -1
- package/dist/src/formats/cx/exporter.d.ts +102 -0
- package/dist/src/formats/cx/exporter.d.ts.map +1 -0
- package/dist/src/formats/cx/exporter.js +1217 -0
- package/dist/src/formats/cx/exporter.js.map +1 -0
- package/dist/src/formats/cx/importer.d.ts +79 -32
- package/dist/src/formats/cx/importer.d.ts.map +1 -1
- package/dist/src/formats/cx/importer.js +680 -285
- package/dist/src/formats/cx/importer.js.map +1 -1
- package/dist/src/formats/cx/index.d.ts +4 -3
- package/dist/src/formats/cx/index.d.ts.map +1 -1
- package/dist/src/formats/cx/index.js +4 -3
- package/dist/src/formats/cx/index.js.map +1 -1
- package/dist/src/formats/cx2/exporter.d.ts +29 -11
- package/dist/src/formats/cx2/exporter.d.ts.map +1 -1
- package/dist/src/formats/cx2/exporter.js +39 -268
- package/dist/src/formats/cx2/exporter.js.map +1 -1
- package/dist/src/formats/cx2/importer.d.ts +78 -28
- package/dist/src/formats/cx2/importer.d.ts.map +1 -1
- package/dist/src/formats/cx2/importer.js +226 -79
- package/dist/src/formats/cx2/importer.js.map +1 -1
- package/dist/src/formats/cx2/index.d.ts +2 -1
- package/dist/src/formats/cx2/index.d.ts.map +1 -1
- package/dist/src/formats/cx2/index.js +2 -1
- package/dist/src/formats/cx2/index.js.map +1 -1
- package/dist/src/formats/cys/constants.d.ts +66 -17
- package/dist/src/formats/cys/constants.d.ts.map +1 -1
- package/dist/src/formats/cys/constants.js +59 -18
- package/dist/src/formats/cys/constants.js.map +1 -1
- package/dist/src/formats/cys/exporter.d.ts +118 -0
- package/dist/src/formats/cys/exporter.d.ts.map +1 -0
- package/dist/src/formats/cys/exporter.js +1072 -0
- package/dist/src/formats/cys/exporter.js.map +1 -0
- package/dist/src/formats/cys/importer.d.ts +22 -8
- package/dist/src/formats/cys/importer.d.ts.map +1 -1
- package/dist/src/formats/cys/importer.js +510 -149
- package/dist/src/formats/cys/importer.js.map +1 -1
- package/dist/src/formats/cys/index.d.ts +4 -2
- package/dist/src/formats/cys/index.d.ts.map +1 -1
- package/dist/src/formats/cys/index.js +4 -2
- package/dist/src/formats/cys/index.js.map +1 -1
- package/dist/src/formats/cys/session.d.ts +46 -7
- package/dist/src/formats/cys/session.d.ts.map +1 -1
- package/dist/src/formats/cys/session.js +98 -24
- package/dist/src/formats/cys/session.js.map +1 -1
- package/dist/src/formats/cys/tables.d.ts +9 -2
- package/dist/src/formats/cys/tables.d.ts.map +1 -1
- package/dist/src/formats/cys/tables.js +29 -7
- package/dist/src/formats/cys/tables.js.map +1 -1
- package/dist/src/formats/dot/exporter.d.ts +42 -14
- package/dist/src/formats/dot/exporter.d.ts.map +1 -1
- package/dist/src/formats/dot/exporter.js +56 -29
- package/dist/src/formats/dot/exporter.js.map +1 -1
- package/dist/src/formats/dot/importer.d.ts +91 -29
- package/dist/src/formats/dot/importer.d.ts.map +1 -1
- package/dist/src/formats/dot/importer.js +190 -39
- package/dist/src/formats/dot/importer.js.map +1 -1
- package/dist/src/formats/dot/index.d.ts +2 -1
- package/dist/src/formats/dot/index.d.ts.map +1 -1
- package/dist/src/formats/dot/index.js +2 -1
- package/dist/src/formats/dot/index.js.map +1 -1
- package/dist/src/formats/dot/names.d.ts +44 -11
- package/dist/src/formats/dot/names.d.ts.map +1 -1
- package/dist/src/formats/dot/names.js +44 -11
- package/dist/src/formats/dot/names.js.map +1 -1
- package/dist/src/formats/dot/tokenizer.d.ts +9 -2
- package/dist/src/formats/dot/tokenizer.d.ts.map +1 -1
- package/dist/src/formats/dot/tokenizer.js +20 -5
- package/dist/src/formats/dot/tokenizer.js.map +1 -1
- package/dist/src/formats/gexf/exporter.d.ts +46 -15
- package/dist/src/formats/gexf/exporter.d.ts.map +1 -1
- package/dist/src/formats/gexf/exporter.js +45 -15
- package/dist/src/formats/gexf/exporter.js.map +1 -1
- package/dist/src/formats/gexf/importer.d.ts +87 -23
- package/dist/src/formats/gexf/importer.d.ts.map +1 -1
- package/dist/src/formats/gexf/importer.js +471 -90
- package/dist/src/formats/gexf/importer.js.map +1 -1
- package/dist/src/formats/gexf/index.d.ts +84 -21
- package/dist/src/formats/gexf/index.d.ts.map +1 -1
- package/dist/src/formats/gexf/index.js +80 -23
- package/dist/src/formats/gexf/index.js.map +1 -1
- package/dist/src/formats/gexf/schema.d.ts +67 -15
- package/dist/src/formats/gexf/schema.d.ts.map +1 -1
- package/dist/src/formats/gexf/schema.js +59 -13
- package/dist/src/formats/gexf/schema.js.map +1 -1
- package/dist/src/formats/gml/exporter.d.ts +69 -21
- package/dist/src/formats/gml/exporter.d.ts.map +1 -1
- package/dist/src/formats/gml/exporter.js +74 -29
- package/dist/src/formats/gml/exporter.js.map +1 -1
- package/dist/src/formats/gml/importer.d.ts +116 -25
- package/dist/src/formats/gml/importer.d.ts.map +1 -1
- package/dist/src/formats/gml/importer.js +290 -61
- package/dist/src/formats/gml/importer.js.map +1 -1
- package/dist/src/formats/gml/index.d.ts +87 -24
- package/dist/src/formats/gml/index.d.ts.map +1 -1
- package/dist/src/formats/gml/index.js +79 -26
- package/dist/src/formats/gml/index.js.map +1 -1
- package/dist/src/formats/gml/syntax.d.ts +67 -18
- package/dist/src/formats/gml/syntax.d.ts.map +1 -1
- package/dist/src/formats/gml/syntax.js +108 -26
- package/dist/src/formats/gml/syntax.js.map +1 -1
- package/dist/src/formats/graphml/constants.d.ts +174 -44
- package/dist/src/formats/graphml/constants.d.ts.map +1 -1
- package/dist/src/formats/graphml/constants.js +165 -44
- package/dist/src/formats/graphml/constants.js.map +1 -1
- package/dist/src/formats/graphml/exporter.d.ts +17 -9
- package/dist/src/formats/graphml/exporter.d.ts.map +1 -1
- package/dist/src/formats/graphml/exporter.js +33 -12
- package/dist/src/formats/graphml/exporter.js.map +1 -1
- package/dist/src/formats/graphml/importer.d.ts +19 -7
- package/dist/src/formats/graphml/importer.d.ts.map +1 -1
- package/dist/src/formats/graphml/importer.js +466 -39
- package/dist/src/formats/graphml/importer.js.map +1 -1
- package/dist/src/formats/graphml/index.d.ts +2 -1
- package/dist/src/formats/graphml/index.d.ts.map +1 -1
- package/dist/src/formats/graphml/index.js +2 -1
- package/dist/src/formats/graphml/index.js.map +1 -1
- package/dist/src/formats/graphml/tree.d.ts +6 -2
- package/dist/src/formats/graphml/tree.d.ts.map +1 -1
- package/dist/src/formats/graphml/tree.js +6 -2
- package/dist/src/formats/graphml/tree.js.map +1 -1
- package/dist/src/formats/graphml/yfiles.d.ts +8 -3
- package/dist/src/formats/graphml/yfiles.d.ts.map +1 -1
- package/dist/src/formats/graphml/yfiles.js +36 -15
- package/dist/src/formats/graphml/yfiles.js.map +1 -1
- package/dist/src/formats/json/dialect.d.ts +88 -24
- package/dist/src/formats/json/dialect.d.ts.map +1 -1
- package/dist/src/formats/json/dialect.js +109 -19
- package/dist/src/formats/json/dialect.js.map +1 -1
- package/dist/src/formats/json/exporter.d.ts +134 -22
- package/dist/src/formats/json/exporter.d.ts.map +1 -1
- package/dist/src/formats/json/exporter.js +135 -54
- package/dist/src/formats/json/exporter.js.map +1 -1
- package/dist/src/formats/json/importer.d.ts +173 -52
- package/dist/src/formats/json/importer.d.ts.map +1 -1
- package/dist/src/formats/json/importer.js +899 -220
- package/dist/src/formats/json/importer.js.map +1 -1
- package/dist/src/formats/json/index.d.ts +3 -2
- package/dist/src/formats/json/index.d.ts.map +1 -1
- package/dist/src/formats/json/index.js +3 -2
- package/dist/src/formats/json/index.js.map +1 -1
- package/dist/src/formats/json/obographs-export.d.ts +68 -0
- package/dist/src/formats/json/obographs-export.d.ts.map +1 -0
- package/dist/src/formats/json/obographs-export.js +941 -0
- package/dist/src/formats/json/obographs-export.js.map +1 -0
- package/dist/src/formats/json/obographs.d.ts +26 -0
- package/dist/src/formats/json/obographs.d.ts.map +1 -1
- package/dist/src/formats/json/obographs.js +297 -80
- package/dist/src/formats/json/obographs.js.map +1 -1
- package/dist/src/formats/neo4j/exporter.d.ts +109 -21
- package/dist/src/formats/neo4j/exporter.d.ts.map +1 -1
- package/dist/src/formats/neo4j/exporter.js +238 -85
- package/dist/src/formats/neo4j/exporter.js.map +1 -1
- package/dist/src/formats/neo4j/header.d.ts +17 -4
- package/dist/src/formats/neo4j/header.d.ts.map +1 -1
- package/dist/src/formats/neo4j/header.js +36 -4
- package/dist/src/formats/neo4j/header.js.map +1 -1
- package/dist/src/formats/neo4j/importer.d.ts +107 -27
- package/dist/src/formats/neo4j/importer.d.ts.map +1 -1
- package/dist/src/formats/neo4j/importer.js +415 -63
- package/dist/src/formats/neo4j/importer.js.map +1 -1
- package/dist/src/formats/neo4j/index.d.ts +73 -23
- package/dist/src/formats/neo4j/index.d.ts.map +1 -1
- package/dist/src/formats/neo4j/index.js +65 -25
- package/dist/src/formats/neo4j/index.js.map +1 -1
- package/dist/src/formats/obo/exporter.d.ts +150 -0
- package/dist/src/formats/obo/exporter.d.ts.map +1 -0
- package/dist/src/formats/obo/exporter.js +1736 -0
- package/dist/src/formats/obo/exporter.js.map +1 -0
- package/dist/src/formats/obo/importer.d.ts +95 -19
- package/dist/src/formats/obo/importer.d.ts.map +1 -1
- package/dist/src/formats/obo/importer.js +475 -104
- package/dist/src/formats/obo/importer.js.map +1 -1
- package/dist/src/formats/obo/index.d.ts +6 -3
- package/dist/src/formats/obo/index.d.ts.map +1 -1
- package/dist/src/formats/obo/index.js +6 -3
- package/dist/src/formats/obo/index.js.map +1 -1
- package/dist/src/formats/obo/syntax.d.ts +108 -4
- package/dist/src/formats/obo/syntax.d.ts.map +1 -1
- package/dist/src/formats/obo/syntax.js +211 -34
- package/dist/src/formats/obo/syntax.js.map +1 -1
- package/dist/src/formats/pajek/exporter.d.ts +54 -16
- package/dist/src/formats/pajek/exporter.d.ts.map +1 -1
- package/dist/src/formats/pajek/exporter.js +66 -34
- package/dist/src/formats/pajek/exporter.js.map +1 -1
- package/dist/src/formats/pajek/importer.d.ts +84 -22
- package/dist/src/formats/pajek/importer.d.ts.map +1 -1
- package/dist/src/formats/pajek/importer.js +303 -83
- package/dist/src/formats/pajek/importer.js.map +1 -1
- package/dist/src/formats/pajek/index.d.ts +2 -1
- package/dist/src/formats/pajek/index.d.ts.map +1 -1
- package/dist/src/formats/pajek/index.js +2 -1
- package/dist/src/formats/pajek/index.js.map +1 -1
- package/dist/src/formats/pajek/syntax.d.ts +77 -14
- package/dist/src/formats/pajek/syntax.d.ts.map +1 -1
- package/dist/src/formats/pajek/syntax.js +183 -51
- package/dist/src/formats/pajek/syntax.js.map +1 -1
- package/dist/src/formats/xgmml/columns.d.ts +1 -0
- package/dist/src/formats/xgmml/columns.d.ts.map +1 -1
- package/dist/src/formats/xgmml/columns.js +4 -0
- package/dist/src/formats/xgmml/columns.js.map +1 -1
- package/dist/src/formats/xgmml/constants.d.ts +186 -56
- package/dist/src/formats/xgmml/constants.d.ts.map +1 -1
- package/dist/src/formats/xgmml/constants.js +181 -57
- package/dist/src/formats/xgmml/constants.js.map +1 -1
- package/dist/src/formats/xgmml/document.d.ts +65 -11
- package/dist/src/formats/xgmml/document.d.ts.map +1 -1
- package/dist/src/formats/xgmml/document.js +157 -28
- package/dist/src/formats/xgmml/document.js.map +1 -1
- package/dist/src/formats/xgmml/emit.d.ts +61 -3
- package/dist/src/formats/xgmml/emit.d.ts.map +1 -1
- package/dist/src/formats/xgmml/emit.js +129 -26
- package/dist/src/formats/xgmml/emit.js.map +1 -1
- package/dist/src/formats/xgmml/exporter.d.ts +13 -6
- package/dist/src/formats/xgmml/exporter.d.ts.map +1 -1
- package/dist/src/formats/xgmml/exporter.js +20 -21
- package/dist/src/formats/xgmml/exporter.js.map +1 -1
- package/dist/src/formats/xgmml/importer.d.ts +33 -12
- package/dist/src/formats/xgmml/importer.d.ts.map +1 -1
- package/dist/src/formats/xgmml/importer.js +35 -72
- package/dist/src/formats/xgmml/importer.js.map +1 -1
- package/dist/src/formats/xgmml/index.d.ts +1 -0
- package/dist/src/formats/xgmml/index.d.ts.map +1 -1
- package/dist/src/formats/xgmml/index.js +1 -0
- package/dist/src/formats/xgmml/index.js.map +1 -1
- package/dist/src/formats/xgmml/values.d.ts +8 -1
- package/dist/src/formats/xgmml/values.d.ts.map +1 -1
- package/dist/src/formats/xgmml/values.js +7 -2
- package/dist/src/formats/xgmml/values.js.map +1 -1
- package/dist/src/index.d.ts +23 -18
- package/dist/src/index.d.ts.map +1 -1
- package/dist/src/index.js +28 -16
- package/dist/src/index.js.map +1 -1
- package/dist/src/registry.d.ts +478 -92
- package/dist/src/registry.d.ts.map +1 -1
- package/dist/src/registry.js +807 -88
- package/dist/src/registry.js.map +1 -1
- package/dist/src/sniff.d.ts +61 -19
- package/dist/src/sniff.d.ts.map +1 -1
- package/dist/src/sniff.js +121 -29
- package/dist/src/sniff.js.map +1 -1
- package/dist/src/types.d.ts +362 -112
- package/dist/src/types.d.ts.map +1 -1
- package/dist/src/types.js +28 -7
- package/dist/src/types.js.map +1 -1
- package/dist/xgmml.js +2 -2
- package/docs/samples/README.md +25 -0
- package/docs/samples/got-edges.csv +353 -0
- package/docs/samples/got-network.graphml +1384 -0
- package/docs/samples/got-nodes.csv +108 -0
- package/docs/samples/got.cx +930 -0
- package/docs/samples/got.cx2 +465 -0
- package/docs/samples/got.gexf +471 -0
- package/docs/samples/got.gml +2650 -0
- package/docs/samples/got.json +2546 -0
- package/docs/samples/got.net +461 -0
- package/docs/samples/movies-nodes.csv +9 -0
- package/docs/samples/movies-rels.csv +8 -0
- package/docs/samples/networks.cys +0 -0
- package/docs/samples/proteins.xgmml +9 -0
- package/docs/samples/teams.gv +24 -0
- package/docs/samples/vehicles.obo +25 -0
- package/package.json +9 -4
- package/src/children.ts +18 -6
- package/src/common/attributes.ts +29 -11
- package/src/common/cell-budget.ts +11 -3
- package/src/common/choose.ts +89 -0
- package/src/common/codes.ts +490 -66
- package/src/common/compare.ts +472 -0
- package/src/common/cx-export.ts +432 -0
- package/src/common/declared-types.ts +38 -4
- package/src/common/direction.ts +78 -51
- package/src/common/escape.ts +33 -17
- package/src/common/export.ts +284 -47
- package/src/common/format.ts +30 -1
- package/src/common/ids.ts +14 -3
- package/src/common/input.ts +1057 -134
- package/src/common/json-elements.ts +1034 -198
- package/src/common/line-format.ts +249 -0
- package/src/common/lists.ts +6 -1
- package/src/common/ontology-export.ts +461 -0
- package/src/common/ontology.ts +31 -9
- package/src/common/options.ts +110 -15
- package/src/common/plural.ts +49 -0
- package/src/common/report.ts +168 -25
- package/src/common/temporal.ts +22 -5
- package/src/common/text.ts +62 -23
- package/src/common/weights.ts +74 -4
- package/src/common/writer.ts +37 -3
- package/src/common/xml.ts +477 -88
- package/src/common/zip.ts +169 -7
- package/src/formats/csv/exporter.ts +201 -46
- package/src/formats/csv/header.ts +50 -11
- package/src/formats/csv/importer.ts +1133 -245
- package/src/formats/csv/index.ts +106 -19
- package/src/formats/csv/records.ts +396 -122
- package/src/formats/csv/values.ts +1 -0
- package/src/formats/cx/exporter.ts +1483 -0
- package/src/formats/cx/importer.ts +888 -300
- package/src/formats/cx/index.ts +4 -3
- package/src/formats/cx2/exporter.ts +61 -338
- package/src/formats/cx2/importer.ts +317 -86
- package/src/formats/cx2/index.ts +2 -1
- package/src/formats/cys/constants.ts +62 -17
- package/src/formats/cys/exporter.ts +1368 -0
- package/src/formats/cys/importer.ts +659 -157
- package/src/formats/cys/index.ts +4 -2
- package/src/formats/cys/session.ts +139 -31
- package/src/formats/cys/tables.ts +47 -9
- package/src/formats/dot/exporter.ts +83 -37
- package/src/formats/dot/importer.ts +248 -54
- package/src/formats/dot/index.ts +2 -1
- package/src/formats/dot/names.ts +44 -11
- package/src/formats/dot/tokenizer.ts +25 -6
- package/src/formats/gexf/exporter.ts +57 -18
- package/src/formats/gexf/importer.ts +636 -105
- package/src/formats/gexf/index.ts +90 -21
- package/src/formats/gexf/schema.ts +67 -15
- package/src/formats/gml/exporter.ts +90 -36
- package/src/formats/gml/importer.ts +388 -67
- package/src/formats/gml/index.ts +85 -24
- package/src/formats/gml/syntax.ts +111 -26
- package/src/formats/graphml/constants.ts +178 -44
- package/src/formats/graphml/exporter.ts +52 -18
- package/src/formats/graphml/importer.ts +640 -60
- package/src/formats/graphml/index.ts +2 -1
- package/src/formats/graphml/tree.ts +6 -2
- package/src/formats/graphml/yfiles.ts +37 -15
- package/src/formats/json/dialect.ts +128 -29
- package/src/formats/json/exporter.ts +205 -68
- package/src/formats/json/importer.ts +1163 -253
- package/src/formats/json/index.ts +3 -1
- package/src/formats/json/obographs-export.ts +1197 -0
- package/src/formats/json/obographs.ts +353 -92
- package/src/formats/neo4j/exporter.ts +320 -101
- package/src/formats/neo4j/header.ts +44 -6
- package/src/formats/neo4j/importer.ts +512 -73
- package/src/formats/neo4j/index.ts +75 -23
- package/src/formats/obo/exporter.ts +2210 -0
- package/src/formats/obo/importer.ts +622 -109
- package/src/formats/obo/index.ts +6 -3
- package/src/formats/obo/syntax.ts +232 -37
- package/src/formats/pajek/exporter.ts +89 -41
- package/src/formats/pajek/importer.ts +407 -93
- package/src/formats/pajek/index.ts +2 -1
- package/src/formats/pajek/syntax.ts +213 -52
- package/src/formats/xgmml/columns.ts +10 -0
- package/src/formats/xgmml/constants.ts +183 -56
- package/src/formats/xgmml/document.ts +212 -34
- package/src/formats/xgmml/emit.ts +175 -34
- package/src/formats/xgmml/exporter.ts +35 -27
- package/src/formats/xgmml/importer.ts +64 -86
- package/src/formats/xgmml/index.ts +1 -0
- package/src/formats/xgmml/values.ts +11 -3
- package/src/index.ts +81 -11
- package/src/registry.ts +1121 -135
- package/src/sniff.ts +163 -32
- package/src/types.ts +385 -114
- package/dist/chunks/escape-B-tkk_Cl.js.map +0 -1
- package/dist/chunks/export-Bh60Dv-n.js +0 -582
- package/dist/chunks/export-Bh60Dv-n.js.map +0 -1
- package/dist/chunks/exporter-BGrsWamJ.js.map +0 -1
- package/dist/chunks/exporter-DIeGJXAZ.js.map +0 -1
- package/dist/chunks/importer-BWY2FFc5.js.map +0 -1
- package/dist/chunks/importer-DD-xv9_Y.js +0 -1471
- package/dist/chunks/importer-DD-xv9_Y.js.map +0 -1
- package/dist/chunks/importer-DET1tg6s.js.map +0 -1
- package/dist/chunks/importer-DEcKhsmQ.js +0 -1614
- package/dist/chunks/importer-DEcKhsmQ.js.map +0 -1
- package/dist/chunks/importer-DIrbbnAf.js.map +0 -1
- package/dist/chunks/importer-D_e7e7LX.js.map +0 -1
- package/dist/chunks/importer-eUREhBGj.js.map +0 -1
- package/dist/chunks/importer-vi3bSdtw.js.map +0 -1
- package/dist/chunks/importer-zGLo8Dg_.js.map +0 -1
- package/dist/chunks/json-elements-DDS8N2Dd.js +0 -779
- package/dist/chunks/json-elements-DDS8N2Dd.js.map +0 -1
- package/dist/chunks/ontology-BnrJ4I98.js +0 -113
- package/dist/chunks/ontology-BnrJ4I98.js.map +0 -1
- package/dist/chunks/records-dbRkxwaq.js.map +0 -1
- package/dist/chunks/report-B1z4WT9e.js +0 -2372
- package/dist/chunks/report-B1z4WT9e.js.map +0 -1
- package/dist/chunks/text-Dr0Ifpag.js.map +0 -1
- package/dist/chunks/weights-Dzba96G3.js +0 -176
- package/dist/chunks/weights-Dzba96G3.js.map +0 -1
- package/dist/chunks/writer-C7flM-Ih.js.map +0 -1
|
@@ -1,8 +1,7 @@
|
|
|
1
1
|
import { INVALID_INDEX, GraphFormatError } from "@graphty/graph-format";
|
|
2
|
-
import {
|
|
3
|
-
import { l as localName, a as escapeXmlText,
|
|
4
|
-
import { p as
|
|
5
|
-
import { p as parseTextCell, i as inferTextDtype } from "./text-Dr0Ifpag.js";
|
|
2
|
+
import { M as MIXED_DIRECTION_CODE, D as DIRECTION_FORCED_CODE, d as DIRECTION_REFUSED_CODE, S as SINK_OPTION_CODE, O as OPTION_IGNORED_CODE, I as ID_MERGED_CODE, R as ROLE_TAKEN_CODE, C as COLUMN_RENAMED_CODE, ae as AMBIGUOUS_GRAPH_NAME_CODE, af as GRAPH_NOT_FOUND_CODE, l as MULTIPLE_GRAPHS_CODE, f as STRAY_TEXT_CODE, g as UNKNOWN_ELEMENT_CODE, U as UNKNOWN_ATTR_TYPE_CODE, b7 as EQUATION_AS_TEXT_CODE, ai as PARENT_CYCLE_CODE, q as UNKNOWN_PARENT_CODE, o as DUPLICATE_ATTRIBUTE_CODE, i as DANGLING_REFERENCE_CODE, P as PRECISION_CODE, aj as WIDENED_CODE, a3 as BAD_VALUE_CODE, m as DUPLICATE_EDGE_ID_CODE, n as DUPLICATE_NODE_CODE, s as MISSING_ENDPOINT_CODE, t as MISSING_ID_CODE, N as NO_GRAPH_CODE, v as ENCODING_CONFLICT_CODE, w as UNKNOWN_ENCODING_CODE, x as ENCODING_FALLBACK_CODE, y as INVALID_ENCODING_CODE, z as INVALID_UTF8_CODE, E as EMPTY_INPUT_CODE, X as XML_SYNTAX_CODE, F as ELEMENT_ISSUE, G as INPUT_ISSUE, bk as STORAGE_CLASS_CODE, bq as WEIGHT_KEY_CLASH_CODE, au as ROLE_ASSUMED_CODE, b0 as COLUMN_RENAMED_LOSS_CODE, J as ID_TEXT_TYPE_CODE, bd as MUTUAL_EXPANDED_CODE, Q as PARENTS_DROPPED_CODE, K as ROLE_DROPPED_CODE, bm as TEMPORAL_TEXT_DROPPED_CODE, bl as TEMPORAL_DROPPED_CODE, ax as XML_ILLEGAL_CHAR_CODE, a0 as uniqueColumnName, a1 as declareResolved, ac as DictHeuristic, ar as IdCoercer, aq as DirectionResolver, b as plural, $ as agree, am as throwIfAborted, aL as parseWeightText, ao as reportSinkOptions, an as reportUnusedOptions, a7 as chooseGraph, ap as graphChosen, al as resolveImportOptions, a8 as ImportReportBuilder, a4 as textChunks, c1 as elementCount } from "./export-BTI4yQgy.js";
|
|
3
|
+
import { l as localName, a as escapeXmlText, j as isWhitespace, e as escapeXmlAttribute, t as tokenizeXml, f as xmlDeclaredEncoding, X as XmlSyntaxError } from "./escape-D0g6NNUy.js";
|
|
4
|
+
import { p as parseTextCell, i as inferTextDtype } from "./text-DmcUs5_Q.js";
|
|
6
5
|
const FORMAT = "xgmml";
|
|
7
6
|
const EXTENSIONS = Object.freeze([".xgmml", ".xml"]);
|
|
8
7
|
const MIME_TYPES = Object.freeze(["application/xgmml", "text/xgmml", "text/xgmml+xml"]);
|
|
@@ -25,26 +24,41 @@ const INTERACTION_COLUMN = "interaction";
|
|
|
25
24
|
const XGMML_ORIGIN_NAMESPACE = "xgmml";
|
|
26
25
|
const CYTOSCAPE_ORIGIN_NAMESPACE = "cytoscape";
|
|
27
26
|
const XGMML_ISSUE = Object.freeze({
|
|
28
|
-
|
|
27
|
+
...INPUT_ISSUE,
|
|
28
|
+
...ELEMENT_ISSUE,
|
|
29
|
+
/** The input is not well-formed XML. The import stops. */
|
|
29
30
|
XML_SYNTAX: XML_SYNTAX_CODE,
|
|
30
|
-
/**
|
|
31
|
+
/** The input is empty or whitespace only. The import stops. */
|
|
31
32
|
EMPTY_INPUT: EMPTY_INPUT_CODE,
|
|
32
|
-
/**
|
|
33
|
+
/** The input is not valid UTF-8. The import stops. */
|
|
33
34
|
INVALID_UTF8: INVALID_UTF8_CODE,
|
|
34
|
-
/**
|
|
35
|
+
/**
|
|
36
|
+
* Some bytes are not valid in the encoding that was chosen (by a byte order mark, the file's declaration or the
|
|
37
|
+
* `encoding` option). The import stops.
|
|
38
|
+
*/
|
|
35
39
|
INVALID_ENCODING: INVALID_ENCODING_CODE,
|
|
36
40
|
/** Undeclared non-UTF-8 bytes were read as windows-1252. */
|
|
37
41
|
ENCODING_FALLBACK: ENCODING_FALLBACK_CODE,
|
|
38
42
|
/** A declared encoding the platform cannot decode was ignored. */
|
|
39
43
|
UNKNOWN_ENCODING: UNKNOWN_ENCODING_CODE,
|
|
40
|
-
/**
|
|
44
|
+
/** A declared encoding the byte order mark contradicts (the mark wins). */
|
|
45
|
+
ENCODING_CONFLICT: ENCODING_CONFLICT_CODE,
|
|
46
|
+
/**
|
|
47
|
+
* The root element is not `<graph>` (it may be an XHTML page with a graph inside, or a GraphML file). The import
|
|
48
|
+
* stops.
|
|
49
|
+
*/
|
|
41
50
|
NO_GRAPH: NO_GRAPH_CODE,
|
|
42
|
-
/**
|
|
51
|
+
/**
|
|
52
|
+
* The file is a Cytoscape session view (`cy:view="1"`), which holds only view settings and no nodes or edges. The
|
|
53
|
+
* import stops.
|
|
54
|
+
*/
|
|
43
55
|
VIEW_DOCUMENT: "E_XGMML_VIEW_DOCUMENT",
|
|
44
56
|
/** A node with neither an id nor a label; it is skipped with its subtree. */
|
|
45
57
|
MISSING_ID: MISSING_ID_CODE,
|
|
46
58
|
/** A node without an id; its label is used as the id. */
|
|
47
59
|
ID_FROM_LABEL: "W_XGMML_ID_FROM_LABEL",
|
|
60
|
+
/** A node or edge with both an id and an `xlink:href`; it is read as the reference. */
|
|
61
|
+
ID_AND_HREF: "W_XGMML_ID_AND_HREF",
|
|
48
62
|
/** An edge without a source or a target that no label alias resolves. */
|
|
49
63
|
MISSING_ENDPOINT: MISSING_ENDPOINT_CODE,
|
|
50
64
|
/** An edge endpoint that names no node (addMissingNodes false); the edge is skipped. */
|
|
@@ -55,7 +69,10 @@ const XGMML_ISSUE = Object.freeze({
|
|
|
55
69
|
DUPLICATE_NODE: DUPLICATE_NODE_CODE,
|
|
56
70
|
/** An edge id used twice; the second edge is skipped. */
|
|
57
71
|
DUPLICATE_EDGE_ID: DUPLICATE_EDGE_ID_CODE,
|
|
58
|
-
/**
|
|
72
|
+
/**
|
|
73
|
+
* Cytoscape 2.x writes each edge of a group a second time, inside the group. The repeats are dropped, so every edge
|
|
74
|
+
* is read once; nothing is lost.
|
|
75
|
+
*/
|
|
59
76
|
GROUP_DUPLICATE_EDGE: "W_XGMML_GROUP_DUPLICATE_EDGE",
|
|
60
77
|
/** A `directed` or `cy:directed` value other than 0 / 1. */
|
|
61
78
|
BAD_DIRECTED: "W_XGMML_BAD_DIRECTED",
|
|
@@ -71,19 +88,28 @@ const XGMML_ISSUE = Object.freeze({
|
|
|
71
88
|
SURROGATE_PAIRED: "W_XGMML_SURROGATE_PAIRED",
|
|
72
89
|
/** An empty list whose element type nothing states; a list of strings is assumed. */
|
|
73
90
|
EMPTY_LIST_TYPE: "W_XGMML_EMPTY_LIST_TYPE",
|
|
74
|
-
/**
|
|
91
|
+
/**
|
|
92
|
+
* An attribute holds a structure a single column cannot (a list of records, a list of lists, a Cytoscape 2.x map
|
|
93
|
+
* or XML from another tool). Its value is kept as a JSON value, which a save as XGMML writes back.
|
|
94
|
+
*/
|
|
75
95
|
RECORD_LIST: "W_XGMML_RECORD_LIST",
|
|
76
96
|
/** A pointer into another file (`file.xgmml#id`); kept as text. */
|
|
77
97
|
CROSS_FILE_REFERENCE: "W_XGMML_CROSS_FILE_REFERENCE",
|
|
78
98
|
/** A graph nested in an edge's att; there is no model for it. */
|
|
79
99
|
EDGE_NESTED_GRAPH: "W_XGMML_EDGE_NESTED_GRAPH",
|
|
80
|
-
/**
|
|
100
|
+
/**
|
|
101
|
+
* Some nodes or edges of a Cytoscape session belong to none of its networks (Cytoscape keeps group meta-edges and
|
|
102
|
+
* the members of collapsed groups this way). They are not read; the message counts them.
|
|
103
|
+
*/
|
|
81
104
|
ROOT_ONLY_ELEMENTS: "W_XGMML_ROOT_ONLY_ELEMENTS",
|
|
82
105
|
/** A value that does not parse as its declared type; the cell is unset. */
|
|
83
106
|
BAD_VALUE: BAD_VALUE_CODE,
|
|
84
|
-
/**
|
|
107
|
+
/**
|
|
108
|
+
* An attribute's type was widened because a later value did not fit: an integer above 2^31 in an integer column,
|
|
109
|
+
* or two declared types for one attribute.
|
|
110
|
+
*/
|
|
85
111
|
WIDENED: WIDENED_CODE,
|
|
86
|
-
/**
|
|
112
|
+
/** An integer beyond 2^53 was stored as the nearest 64-bit float; pass `long: "string"` to keep every digit. */
|
|
87
113
|
PRECISION: PRECISION_CODE,
|
|
88
114
|
/** A reference (xlink:href, nested-network pointer) that names nothing. */
|
|
89
115
|
DANGLING_REFERENCE: DANGLING_REFERENCE_CODE,
|
|
@@ -101,49 +127,73 @@ const XGMML_ISSUE = Object.freeze({
|
|
|
101
127
|
UNKNOWN_ELEMENT: UNKNOWN_ELEMENT_CODE,
|
|
102
128
|
/** Character data where XGMML allows only elements, or inside an att. */
|
|
103
129
|
STRAY_TEXT: STRAY_TEXT_CODE,
|
|
104
|
-
/**
|
|
130
|
+
/**
|
|
131
|
+
* The file holds several graphs and only the first was read. It is not added when `graphIndex` or `graphName` chose the graph.
|
|
132
|
+
* `importAllGraphs()` reads every one.
|
|
133
|
+
*/
|
|
105
134
|
MULTIPLE_GRAPHS: MULTIPLE_GRAPHS_CODE,
|
|
106
|
-
/** graphIndex
|
|
135
|
+
/** `graphIndex` or `graphName` matches no network in the session. The import stops. */
|
|
107
136
|
GRAPH_NOT_FOUND: GRAPH_NOT_FOUND_CODE,
|
|
108
|
-
/** graphName
|
|
137
|
+
/** `graphName` matches several networks in the session. The import stops. */
|
|
109
138
|
AMBIGUOUS_GRAPH_NAME: AMBIGUOUS_GRAPH_NAME_CODE,
|
|
110
|
-
/**
|
|
139
|
+
/**
|
|
140
|
+
* An attribute was renamed `<name>#<suffix>` because another attribute already has its name, for example
|
|
141
|
+
* two attributes declared with the same name.
|
|
142
|
+
*/
|
|
111
143
|
COLUMN_RENAMED: COLUMN_RENAMED_CODE,
|
|
112
|
-
/**
|
|
144
|
+
/**
|
|
145
|
+
* You read into a graph builder that already has an id, label or position attribute, so this file's one is kept as
|
|
146
|
+
* a plain attribute.
|
|
147
|
+
*/
|
|
113
148
|
ROLE_TAKEN: ROLE_TAKEN_CODE,
|
|
114
|
-
/** Two id texts
|
|
149
|
+
/** Two different id texts became the same number because `ids` is "number", so their nodes were merged. */
|
|
115
150
|
ID_MERGED: ID_MERGED_CODE,
|
|
116
|
-
/**
|
|
151
|
+
/** You set an option this format does not use; it had no effect. The message names the option. */
|
|
117
152
|
OPTION_IGNORED: OPTION_IGNORED_CODE,
|
|
118
|
-
/**
|
|
153
|
+
/**
|
|
154
|
+
* You read into your own graph builder, which was created with a different `addMissingNodes`, `duplicateEdges`,
|
|
155
|
+
* `selfLoops` or `weightDtype` than the option you passed; the builder's setting applies.
|
|
156
|
+
*/
|
|
119
157
|
SINK_OPTION: SINK_OPTION_CODE,
|
|
120
|
-
/**
|
|
158
|
+
/**
|
|
159
|
+
* You read into a graph builder whose direction is already set, or which already holds edges, so the file is read
|
|
160
|
+
* with the builder's direction instead of its own.
|
|
161
|
+
*/
|
|
121
162
|
DIRECTION_REFUSED: DIRECTION_REFUSED_CODE,
|
|
122
|
-
/** Edges
|
|
163
|
+
/** Edges of the other direction were read with the direction `onMixedDirection` chose. */
|
|
123
164
|
DIRECTION_FORCED: DIRECTION_FORCED_CODE,
|
|
124
|
-
/**
|
|
165
|
+
/**
|
|
166
|
+
* The graph has both directed and undirected edges and `onMixedDirection` is "error". An import stops; a save to a
|
|
167
|
+
* format that holds one direction per file fails with E_DIRECTED. Pass "directed" or "undirected" to read or write
|
|
168
|
+
* it anyway.
|
|
169
|
+
*/
|
|
125
170
|
MIXED_DIRECTION: MIXED_DIRECTION_CODE
|
|
126
171
|
});
|
|
127
172
|
const XGMML_LOSS = Object.freeze({
|
|
128
173
|
/** A json or nested-list column written as a string att. */
|
|
129
174
|
JSON_AS_STRING: "W_XGMML_JSON_AS_STRING",
|
|
130
|
-
/**
|
|
175
|
+
/**
|
|
176
|
+
* An attribute type Cytoscape does not have is written as a wider one (a 32-bit float as Double, a large unsigned
|
|
177
|
+
* integer as Long, a byte as Integer, a dictionary as String).
|
|
178
|
+
*/
|
|
131
179
|
WIDENED_TYPE: "W_XGMML_WIDENED_TYPE",
|
|
132
|
-
/** A
|
|
180
|
+
/** A text value holds a character XML 1.0 forbids (most control characters); the save fails with E_COLUMN_TYPE. */
|
|
133
181
|
XML_ILLEGAL_CHAR: XML_ILLEGAL_CHAR_CODE,
|
|
134
182
|
/** A temporal column written as plain numbers. */
|
|
135
183
|
TEMPORAL_DROPPED: TEMPORAL_DROPPED_CODE,
|
|
136
184
|
/** A temporal text companion written as a plain string att. */
|
|
137
185
|
TEMPORAL_TEXT_DROPPED: TEMPORAL_TEXT_DROPPED_CODE,
|
|
138
|
-
/**
|
|
186
|
+
/** An attribute with a role the format has no place for is written as a plain attribute; the role is lost. */
|
|
139
187
|
ROLE_DROPPED: ROLE_DROPPED_CODE,
|
|
140
|
-
/**
|
|
188
|
+
/**
|
|
189
|
+
* A `parents` attribute (several parents per node) is not written because the graph also has a `parent` attribute.
|
|
190
|
+
*/
|
|
141
191
|
PARENTS_DROPPED: PARENTS_DROPPED_CODE,
|
|
142
192
|
/** A mutual pair written as two directed edges. */
|
|
143
193
|
MUTUAL_EXPANDED: MUTUAL_EXPANDED_CODE,
|
|
144
194
|
/** Node ids whose text reads back as the other type. */
|
|
145
195
|
ID_TEXT_TYPE: ID_TEXT_TYPE_CODE,
|
|
146
|
-
/**
|
|
196
|
+
/** Edge ids that are not text are written as text and read back as text. */
|
|
147
197
|
EDGE_ID_TEXT: "W_XGMML_EDGE_ID_TEXT",
|
|
148
198
|
/** Strings holding a literal backslash-n or backslash-t read back as newline / tab (Cytoscape's escapes). */
|
|
149
199
|
BACKSLASH_ESCAPE: "W_XGMML_BACKSLASH_ESCAPE",
|
|
@@ -151,13 +201,22 @@ const XGMML_LOSS = Object.freeze({
|
|
|
151
201
|
POSITION: "W_XGMML_POSITION",
|
|
152
202
|
/** Nodes whose parent chain never reaches a root are written at the top level. */
|
|
153
203
|
PARENT_CYCLE: "W_XGMML_PARENT_CYCLE",
|
|
154
|
-
/**
|
|
204
|
+
/**
|
|
205
|
+
* An attribute with a role (for example, the label) is written where the format keeps that role, and reads back under the
|
|
206
|
+
* name the format's importer gives it.
|
|
207
|
+
*/
|
|
155
208
|
COLUMN_NAME_CHANGED: COLUMN_RENAMED_LOSS_CODE,
|
|
156
|
-
/**
|
|
209
|
+
/**
|
|
210
|
+
* An attribute without a role is written where the format keeps a role (for example, a `name` column as the label), and
|
|
211
|
+
* reads back with that role.
|
|
212
|
+
*/
|
|
157
213
|
ROLE_ASSUMED: ROLE_ASSUMED_CODE,
|
|
158
|
-
/**
|
|
214
|
+
/** An attribute named `weight` without the weight role reads back as the edge weight. */
|
|
159
215
|
WEIGHT_KEY_CLASH: WEIGHT_KEY_CLASH_CODE,
|
|
160
|
-
/**
|
|
216
|
+
/**
|
|
217
|
+
* A text attribute reads back as a dictionary attribute, or the reverse, because the importer chooses by how often
|
|
218
|
+
* its values repeat. The values are the same.
|
|
219
|
+
*/
|
|
161
220
|
STORAGE_CLASS_CHANGED: STORAGE_CLASS_CODE,
|
|
162
221
|
/** Edge labels shaped `a (i) b` read back with an `interaction` column (Cytoscape's label alias). */
|
|
163
222
|
INTERACTION_FROM_LABEL: "W_XGMML_INTERACTION_FROM_LABEL"
|
|
@@ -189,13 +248,18 @@ const TRUE_TEXT = /^(1|true|yes)$/i;
|
|
|
189
248
|
function isCyTrue(text) {
|
|
190
249
|
return text !== null && text !== void 0 && TRUE_TEXT.test(text.trim());
|
|
191
250
|
}
|
|
192
|
-
function normaliseName(name,
|
|
251
|
+
function normaliseName(name, scope) {
|
|
193
252
|
const colon = name.indexOf(":");
|
|
194
|
-
if (colon
|
|
253
|
+
if (colon <= 0) {
|
|
254
|
+
return name;
|
|
255
|
+
}
|
|
256
|
+
const prefix = name.slice(0, colon);
|
|
257
|
+
if (prefix === "xlink" || scope.get(prefix) === XLINK_NAMESPACE) {
|
|
195
258
|
return `xlink:${name.slice(colon + 1)}`;
|
|
196
259
|
}
|
|
197
260
|
return name;
|
|
198
261
|
}
|
|
262
|
+
const NO_SCOPE = /* @__PURE__ */ new Map();
|
|
199
263
|
class XgmmlParser {
|
|
200
264
|
/**
|
|
201
265
|
* Create a parser.
|
|
@@ -203,7 +267,7 @@ class XgmmlParser {
|
|
|
203
267
|
*/
|
|
204
268
|
constructor(report) {
|
|
205
269
|
this.frames = [];
|
|
206
|
-
this.
|
|
270
|
+
this.scopes = [];
|
|
207
271
|
this.rootGraph = null;
|
|
208
272
|
this.nodes = [];
|
|
209
273
|
this.edges = [];
|
|
@@ -213,6 +277,7 @@ class XgmmlParser {
|
|
|
213
277
|
this.rootPrefix = null;
|
|
214
278
|
this.rdf = {};
|
|
215
279
|
this.rdfXml = null;
|
|
280
|
+
this.doctypeText = null;
|
|
216
281
|
this.rdfElement = null;
|
|
217
282
|
this.report = report;
|
|
218
283
|
}
|
|
@@ -233,9 +298,17 @@ class XgmmlParser {
|
|
|
233
298
|
cytoscape: this.cytoscape,
|
|
234
299
|
xgmmlNamespace: this.xgmmlNamespace,
|
|
235
300
|
rdf: this.rdf,
|
|
236
|
-
rdfXml: this.rdfXml
|
|
301
|
+
rdfXml: this.rdfXml,
|
|
302
|
+
doctype: this.doctypeText
|
|
237
303
|
};
|
|
238
304
|
}
|
|
305
|
+
/**
|
|
306
|
+
* The DOCTYPE declaration.
|
|
307
|
+
* @param text - the declaration as written
|
|
308
|
+
*/
|
|
309
|
+
doctype(text) {
|
|
310
|
+
this.doctypeText ??= text;
|
|
311
|
+
}
|
|
239
312
|
/**
|
|
240
313
|
* An element starts.
|
|
241
314
|
* @param rawName - the element name as written
|
|
@@ -243,6 +316,7 @@ class XgmmlParser {
|
|
|
243
316
|
* @param line - the line
|
|
244
317
|
*/
|
|
245
318
|
start(rawName, rawAttrs, line) {
|
|
319
|
+
this.enterScope(rawAttrs);
|
|
246
320
|
const top = this.frames.length === 0 ? null : this.frames[this.frames.length - 1];
|
|
247
321
|
if (top === null) {
|
|
248
322
|
this.startRoot(rawName, rawAttrs, line);
|
|
@@ -256,8 +330,8 @@ class XgmmlParser {
|
|
|
256
330
|
this.capture(top, rawName, rawAttrs);
|
|
257
331
|
return;
|
|
258
332
|
}
|
|
259
|
-
const attrs = this.
|
|
260
|
-
const name = localName(rawName);
|
|
333
|
+
const attrs = this.normalize(rawAttrs);
|
|
334
|
+
const name = this.isXgmmlName(rawName) ? localName(rawName) : rawName;
|
|
261
335
|
switch (top.kind) {
|
|
262
336
|
case "graph":
|
|
263
337
|
this.startInGraph(top.graph, rawName, name, attrs, line);
|
|
@@ -294,6 +368,7 @@ class XgmmlParser {
|
|
|
294
368
|
* @param _line - the line
|
|
295
369
|
*/
|
|
296
370
|
end(name, _line) {
|
|
371
|
+
this.scopes.pop();
|
|
297
372
|
const frame = this.frames.pop();
|
|
298
373
|
const below = this.frames.length === 0 ? null : this.frames[this.frames.length - 1];
|
|
299
374
|
switch (frame?.kind) {
|
|
@@ -302,7 +377,11 @@ class XgmmlParser {
|
|
|
302
377
|
frame.depth--;
|
|
303
378
|
if (frame.depth > 0) {
|
|
304
379
|
this.frames.push(frame);
|
|
305
|
-
|
|
380
|
+
this.rdfElement = null;
|
|
381
|
+
return;
|
|
382
|
+
}
|
|
383
|
+
frame.att.xml = bindPrefixes(frame.att.xml, frame.start, frame.scope);
|
|
384
|
+
if (frame.att.name === "networkMetadata") {
|
|
306
385
|
this.rdfXml = frame.att.xml;
|
|
307
386
|
}
|
|
308
387
|
this.rdfElement = null;
|
|
@@ -348,15 +427,40 @@ class XgmmlParser {
|
|
|
348
427
|
);
|
|
349
428
|
}
|
|
350
429
|
// ------------------------------------------------------------------ structure
|
|
430
|
+
/**
|
|
431
|
+
* Open the namespace scope of an element: its parent's, plus the prefixes it declares.
|
|
432
|
+
* @param attrs - the element's attributes as written
|
|
433
|
+
*/
|
|
434
|
+
enterScope(attrs) {
|
|
435
|
+
const parent = this.scopes.at(-1) ?? NO_SCOPE;
|
|
436
|
+
let scope = parent;
|
|
437
|
+
for (const [key2, value] of attrs) {
|
|
438
|
+
if (key2 === "xmlns" || key2.startsWith("xmlns:")) {
|
|
439
|
+
if (scope === parent) {
|
|
440
|
+
scope = new Map(parent);
|
|
441
|
+
}
|
|
442
|
+
scope.set(key2 === "xmlns" ? "" : key2.slice(6), value);
|
|
443
|
+
}
|
|
444
|
+
}
|
|
445
|
+
this.scopes.push(scope);
|
|
446
|
+
}
|
|
447
|
+
/**
|
|
448
|
+
* The namespace prefixes in scope at the innermost open element.
|
|
449
|
+
* @returns prefix to URI
|
|
450
|
+
*/
|
|
451
|
+
get scope() {
|
|
452
|
+
return this.scopes.at(-1) ?? NO_SCOPE;
|
|
453
|
+
}
|
|
351
454
|
/**
|
|
352
455
|
* The XML attribute map with every XLink prefix written `xlink:`.
|
|
353
456
|
* @param attrs - the attributes as written
|
|
354
|
-
* @returns the
|
|
457
|
+
* @returns the normalized map
|
|
355
458
|
*/
|
|
356
|
-
|
|
459
|
+
normalize(attrs) {
|
|
357
460
|
const out = /* @__PURE__ */ new Map();
|
|
461
|
+
const { scope } = this;
|
|
358
462
|
for (const [key2, value] of attrs) {
|
|
359
|
-
out.set(normaliseName(key2,
|
|
463
|
+
out.set(normaliseName(key2, scope), value);
|
|
360
464
|
}
|
|
361
465
|
return out;
|
|
362
466
|
}
|
|
@@ -369,10 +473,7 @@ class XgmmlParser {
|
|
|
369
473
|
startRoot(rawName, rawAttrs, line) {
|
|
370
474
|
const local = localName(rawName);
|
|
371
475
|
const prefix = rawName.includes(":") ? rawName.slice(0, rawName.indexOf(":")) : null;
|
|
372
|
-
for (const
|
|
373
|
-
if (key2.startsWith("xmlns:") && value === "http://www.w3.org/1999/xlink") {
|
|
374
|
-
this.xlinkPrefixes.add(key2.slice(6));
|
|
375
|
-
}
|
|
476
|
+
for (const key2 of rawAttrs.keys()) {
|
|
376
477
|
if (key2 === "xmlns:cy" || key2.startsWith("cy:")) {
|
|
377
478
|
this.cytoscape = true;
|
|
378
479
|
}
|
|
@@ -387,7 +488,7 @@ class XgmmlParser {
|
|
|
387
488
|
{ line }
|
|
388
489
|
);
|
|
389
490
|
}
|
|
390
|
-
const graph = this.newGraph(this.
|
|
491
|
+
const graph = this.newGraph(this.normalize(rawAttrs), line, null, null);
|
|
391
492
|
this.rootGraph = graph;
|
|
392
493
|
this.frames.push({ kind: "graph", graph });
|
|
393
494
|
}
|
|
@@ -447,7 +548,7 @@ class XgmmlParser {
|
|
|
447
548
|
return;
|
|
448
549
|
}
|
|
449
550
|
case "graphics":
|
|
450
|
-
this.beginGraphics(graph, attrs);
|
|
551
|
+
this.beginGraphics(graph, attrs, line);
|
|
451
552
|
return;
|
|
452
553
|
default:
|
|
453
554
|
this.unknownElement(rawName, line);
|
|
@@ -470,7 +571,7 @@ class XgmmlParser {
|
|
|
470
571
|
return;
|
|
471
572
|
}
|
|
472
573
|
case "graphics":
|
|
473
|
-
this.beginGraphics(element, attrs);
|
|
574
|
+
this.beginGraphics(element, attrs, line);
|
|
474
575
|
return;
|
|
475
576
|
default:
|
|
476
577
|
this.unknownElement(rawName, line);
|
|
@@ -499,19 +600,30 @@ class XgmmlParser {
|
|
|
499
600
|
return;
|
|
500
601
|
}
|
|
501
602
|
att.xml ??= "";
|
|
502
|
-
const capture = {
|
|
603
|
+
const capture = {
|
|
604
|
+
kind: "capture",
|
|
605
|
+
att,
|
|
606
|
+
depth: 0,
|
|
607
|
+
start: att.xml.length,
|
|
608
|
+
scope: this.scope
|
|
609
|
+
};
|
|
503
610
|
this.frames.push(capture);
|
|
504
611
|
this.capture(capture, rawName, attrs);
|
|
505
612
|
}
|
|
506
613
|
/**
|
|
507
|
-
* Whether an element name
|
|
508
|
-
*
|
|
614
|
+
* Whether an element name is XGMML's own (unprefixed, with the root's prefix as in a document
|
|
615
|
+
* whose root is `<xgmml:graph>`, or with any prefix bound to the XGMML namespace) rather than
|
|
616
|
+
* foreign XML such as `rdf:RDF` or `svg:node`.
|
|
509
617
|
* @param rawName - the name as written
|
|
510
618
|
* @returns true for an XGMML element name
|
|
511
619
|
*/
|
|
512
620
|
isXgmmlName(rawName) {
|
|
513
621
|
const colon = rawName.indexOf(":");
|
|
514
|
-
|
|
622
|
+
if (colon < 0) {
|
|
623
|
+
return true;
|
|
624
|
+
}
|
|
625
|
+
const prefix = rawName.slice(0, colon);
|
|
626
|
+
return prefix === this.rootPrefix || this.scope.get(prefix) === XGMML_NAMESPACE;
|
|
515
627
|
}
|
|
516
628
|
/**
|
|
517
629
|
* A `<graph>` inside an `<att>`: a subnetwork of the root, a group or nested-network pointer
|
|
@@ -583,6 +695,9 @@ class XgmmlParser {
|
|
|
583
695
|
const labelAttr = attrs.get("label") ?? null;
|
|
584
696
|
const nameAttr = attrs.get("name") ?? null;
|
|
585
697
|
const label = labelAttr ?? nameAttr;
|
|
698
|
+
if (href !== null && id !== null) {
|
|
699
|
+
this.idAndHref("node", id, href, line);
|
|
700
|
+
}
|
|
586
701
|
if (href === null && id === null) {
|
|
587
702
|
if (label === null || label.length === 0) {
|
|
588
703
|
this.report.counts.skippedNodes++;
|
|
@@ -631,9 +746,13 @@ class XgmmlParser {
|
|
|
631
746
|
*/
|
|
632
747
|
beginEdge(graph, attrs, line) {
|
|
633
748
|
const href = attrs.get("xlink:href") ?? null;
|
|
749
|
+
const id = attrs.get("id") ?? null;
|
|
750
|
+
if (href !== null && id !== null) {
|
|
751
|
+
this.idAndHref("edge", id, href, line);
|
|
752
|
+
}
|
|
634
753
|
const edge = {
|
|
635
754
|
kind: "edge",
|
|
636
|
-
id: href === null ?
|
|
755
|
+
id: href === null ? id : null,
|
|
637
756
|
href,
|
|
638
757
|
source: attrs.get("source") ?? null,
|
|
639
758
|
target: attrs.get("target") ?? null,
|
|
@@ -654,6 +773,21 @@ class XgmmlParser {
|
|
|
654
773
|
}
|
|
655
774
|
this.frames.push({ kind: "edge", edge });
|
|
656
775
|
}
|
|
776
|
+
/**
|
|
777
|
+
* W_XGMML_ID_AND_HREF: an element that both declares an id and references another element.
|
|
778
|
+
* @param kind - node or edge
|
|
779
|
+
* @param id - the id
|
|
780
|
+
* @param href - the reference
|
|
781
|
+
* @param line - the line
|
|
782
|
+
*/
|
|
783
|
+
idAndHref(kind, id, href, line) {
|
|
784
|
+
this.report.warning(
|
|
785
|
+
"validation-error",
|
|
786
|
+
XGMML_ISSUE.ID_AND_HREF,
|
|
787
|
+
`<${kind}> has both id "${id}" and xlink:href "${href}"; it is read as a reference to ${href} and the id is not used`,
|
|
788
|
+
{ line, element: id }
|
|
789
|
+
);
|
|
790
|
+
}
|
|
657
791
|
// ------------------------------------------------------------------ atts
|
|
658
792
|
/**
|
|
659
793
|
* An att record from its XML attributes.
|
|
@@ -707,7 +841,17 @@ class XgmmlParser {
|
|
|
707
841
|
frame.att.xml = `${frame.att.xml ?? ""}${tag}>`;
|
|
708
842
|
frame.depth++;
|
|
709
843
|
if (frame.att.name === "networkMetadata") {
|
|
710
|
-
|
|
844
|
+
const field = localName(rawName);
|
|
845
|
+
this.rdfElement = field;
|
|
846
|
+
if (this.rdf[field] !== void 0) {
|
|
847
|
+
this.rdfElement = null;
|
|
848
|
+
this.report.warning(
|
|
849
|
+
"validation-error",
|
|
850
|
+
XGMML_ISSUE.DUPLICATE_ATTRIBUTE,
|
|
851
|
+
`the network metadata gives <${rawName}> twice; the first ("${this.rdf[field]}") is kept`,
|
|
852
|
+
{ line: frame.att.line, element: field }
|
|
853
|
+
);
|
|
854
|
+
}
|
|
711
855
|
}
|
|
712
856
|
}
|
|
713
857
|
/**
|
|
@@ -725,13 +869,20 @@ class XgmmlParser {
|
|
|
725
869
|
* attribute is kept as written, merged key by key with an earlier `<graphics>`.
|
|
726
870
|
* @param target - the node, edge or graph
|
|
727
871
|
* @param attrs - its attributes
|
|
872
|
+
* @param line - the line
|
|
728
873
|
*/
|
|
729
|
-
beginGraphics(target, attrs) {
|
|
874
|
+
beginGraphics(target, attrs, line) {
|
|
730
875
|
const graphics = { ...target.graphics ?? {} };
|
|
731
876
|
for (const [key2, value] of attrs) {
|
|
732
877
|
if ("x" in target && (key2 === "x" || key2 === "y" || key2 === "z")) {
|
|
878
|
+
if (target[key2] !== null && target[key2] !== void 0) {
|
|
879
|
+
this.duplicateGraphics(key2, line);
|
|
880
|
+
}
|
|
733
881
|
target[key2] = value;
|
|
734
882
|
} else if (key2 !== "xmlns" && !key2.startsWith("xmlns:")) {
|
|
883
|
+
if (key2 in graphics) {
|
|
884
|
+
this.duplicateGraphics(key2, line);
|
|
885
|
+
}
|
|
735
886
|
graphics[key2] = value;
|
|
736
887
|
}
|
|
737
888
|
}
|
|
@@ -789,8 +940,25 @@ class XgmmlParser {
|
|
|
789
940
|
);
|
|
790
941
|
return;
|
|
791
942
|
}
|
|
943
|
+
if (target.graphics !== null && att.name in target.graphics) {
|
|
944
|
+
this.duplicateGraphics(att.name, att.line);
|
|
945
|
+
}
|
|
792
946
|
target.graphics = { ...target.graphics ?? {}, [att.name]: attJson(att) };
|
|
793
947
|
}
|
|
948
|
+
/**
|
|
949
|
+
* W_DUPLICATE_ATTRIBUTE for a graphics property given twice on one element (once per name).
|
|
950
|
+
* @param key - the property
|
|
951
|
+
* @param line - the line
|
|
952
|
+
*/
|
|
953
|
+
duplicateGraphics(key2, line) {
|
|
954
|
+
this.report.warnOnce(
|
|
955
|
+
"validation-error",
|
|
956
|
+
XGMML_ISSUE.DUPLICATE_ATTRIBUTE,
|
|
957
|
+
`the graphics property "${key2}" is given twice on one element; the later value is kept`,
|
|
958
|
+
{ line, element: key2 },
|
|
959
|
+
`${XGMML_ISSUE.DUPLICATE_ATTRIBUTE}:graphics:${key2}`
|
|
960
|
+
);
|
|
961
|
+
}
|
|
794
962
|
}
|
|
795
963
|
function isListLike(att) {
|
|
796
964
|
const names = new Set(att.children.map((c) => c.name));
|
|
@@ -816,6 +984,26 @@ function attJson(att) {
|
|
|
816
984
|
}
|
|
817
985
|
return out;
|
|
818
986
|
}
|
|
987
|
+
function bindPrefixes(xml, start, scope) {
|
|
988
|
+
const segment = xml.slice(start);
|
|
989
|
+
const used = /* @__PURE__ */ new Set();
|
|
990
|
+
for (const match of segment.matchAll(/<\/?([A-Za-z_][\w.-]*):|\s([A-Za-z_][\w.-]*):[\w.-]+="/g)) {
|
|
991
|
+
used.add(match[1] ?? match[2]);
|
|
992
|
+
}
|
|
993
|
+
let declarations = "";
|
|
994
|
+
for (const prefix of used) {
|
|
995
|
+
const uri = scope.get(prefix);
|
|
996
|
+
if (prefix !== "xmlns" && prefix !== "xml" && uri !== void 0 && !segment.includes(` xmlns:${prefix}="`)) {
|
|
997
|
+
declarations += ` xmlns:${prefix}="${escapeXmlAttribute(uri)}"`;
|
|
998
|
+
}
|
|
999
|
+
}
|
|
1000
|
+
if (declarations.length === 0) {
|
|
1001
|
+
return xml;
|
|
1002
|
+
}
|
|
1003
|
+
const nameEnd = xml.slice(start).search(/[\s>]/);
|
|
1004
|
+
const at = start + (nameEnd < 0 ? segment.length : nameEnd);
|
|
1005
|
+
return `${xml.slice(0, at)}${declarations}${xml.slice(at)}`;
|
|
1006
|
+
}
|
|
819
1007
|
function otherAttributes(attrs, read) {
|
|
820
1008
|
const out = [];
|
|
821
1009
|
for (const [key2, value] of attrs) {
|
|
@@ -881,7 +1069,8 @@ function widenScalar(a, b) {
|
|
|
881
1069
|
return "long";
|
|
882
1070
|
}
|
|
883
1071
|
const INTEGER_TEXT = /^[+-]?[0-9]+$/;
|
|
884
|
-
const REAL_TEXT = /^[+-]?(
|
|
1072
|
+
const REAL_TEXT = /^[+-]?(?:\d+(?:\.\d*)?|\.\d+)(?:[eE][+-]?\d+)?$/;
|
|
1073
|
+
const NON_FINITE_TEXT = /^[+-]?(?:NaN|Infinity)$/;
|
|
885
1074
|
const I32_MIN = -2147483648;
|
|
886
1075
|
const I32_MAX = 2147483647;
|
|
887
1076
|
function parseScalar(text, kind, unescape) {
|
|
@@ -912,7 +1101,7 @@ function parseScalar(text, kind, unescape) {
|
|
|
912
1101
|
}
|
|
913
1102
|
case "real": {
|
|
914
1103
|
const t = text.trim();
|
|
915
|
-
if (!REAL_TEXT.test(t)) {
|
|
1104
|
+
if (!REAL_TEXT.test(t) && !NON_FINITE_TEXT.test(t)) {
|
|
916
1105
|
return null;
|
|
917
1106
|
}
|
|
918
1107
|
const n = Number(t);
|
|
@@ -1167,6 +1356,15 @@ class ColumnSet {
|
|
|
1167
1356
|
return jsonCell(names.size > 1 ? recordOf(att) : children.map(jsonOfAtt));
|
|
1168
1357
|
}
|
|
1169
1358
|
let itemKind = elementKind(att.elementType);
|
|
1359
|
+
if (itemKind === null && att.elementType !== null && att.elementType.trim().length > 0) {
|
|
1360
|
+
this.report.warnOnce(
|
|
1361
|
+
"unsupported",
|
|
1362
|
+
XGMML_ISSUE.UNKNOWN_ATTR_TYPE,
|
|
1363
|
+
`list element type "${att.elementType}" of "${name}" is not a Cytoscape type; the items are read by their own types`,
|
|
1364
|
+
at,
|
|
1365
|
+
`${XGMML_ISSUE.UNKNOWN_ATTR_TYPE}:${this.domain}:${name}:items`
|
|
1366
|
+
);
|
|
1367
|
+
}
|
|
1170
1368
|
if (itemKind === null) {
|
|
1171
1369
|
const kinds = /* @__PURE__ */ new Set();
|
|
1172
1370
|
for (const child of children) {
|
|
@@ -1519,7 +1717,7 @@ function dialectOf(doc, report) {
|
|
|
1519
1717
|
let version = 0;
|
|
1520
1718
|
if (versionText !== null) {
|
|
1521
1719
|
version = Number(versionText.trim());
|
|
1522
|
-
if (!Number.isFinite(version) || versionText.trim().length === 0) {
|
|
1720
|
+
if (!Number.isFinite(version) || version < 0 || versionText.trim().length === 0) {
|
|
1523
1721
|
report.warning(
|
|
1524
1722
|
"validation-error",
|
|
1525
1723
|
XGMML_ISSUE.DOCUMENT_VERSION,
|
|
@@ -1542,6 +1740,10 @@ function dialectOf(doc, report) {
|
|
|
1542
1740
|
function graphsOf(doc, dialect) {
|
|
1543
1741
|
return dialect.session ? doc.root.subgraphs.filter((g) => isCyTrue(g.registered)) : [doc.root];
|
|
1544
1742
|
}
|
|
1743
|
+
function parseCoordinate(text) {
|
|
1744
|
+
const parsed = parseScalar(text, "real", false);
|
|
1745
|
+
return parsed === null || !Number.isFinite(parsed.value) ? null : parsed.value;
|
|
1746
|
+
}
|
|
1545
1747
|
function localRef(href) {
|
|
1546
1748
|
return href.startsWith("#") ? href.slice(1) : null;
|
|
1547
1749
|
}
|
|
@@ -1607,6 +1809,7 @@ class XgmmlEmitter {
|
|
|
1607
1809
|
this.aliasInteractions = 0;
|
|
1608
1810
|
this.weighted = false;
|
|
1609
1811
|
this.directions = /* @__PURE__ */ new Map();
|
|
1812
|
+
this.nameLabel = { node: false, edge: false };
|
|
1610
1813
|
this.labelRows = null;
|
|
1611
1814
|
this.doc = doc;
|
|
1612
1815
|
this.dialect = dialect;
|
|
@@ -1618,10 +1821,11 @@ class XgmmlEmitter {
|
|
|
1618
1821
|
this.coercer = new IdCoercer(options.ids);
|
|
1619
1822
|
this.direction = new DirectionResolver(sink, report, options.onMixedDirection);
|
|
1620
1823
|
const base = { unescape: settings.cytoscapeEscapes, long: options.long };
|
|
1824
|
+
const label = extras.labelFromName === true ? [] : [LABEL_COLUMN];
|
|
1621
1825
|
this.nodeColumns = new ColumnSet("node", report, {
|
|
1622
1826
|
...base,
|
|
1623
1827
|
reserved: /* @__PURE__ */ new Set([
|
|
1624
|
-
|
|
1828
|
+
...label,
|
|
1625
1829
|
POSITION_COLUMN,
|
|
1626
1830
|
Z_COLUMN,
|
|
1627
1831
|
GRAPHICS_COLUMN,
|
|
@@ -1635,7 +1839,7 @@ class XgmmlEmitter {
|
|
|
1635
1839
|
});
|
|
1636
1840
|
this.edgeColumns = new ColumnSet("edge", report, {
|
|
1637
1841
|
...base,
|
|
1638
|
-
reserved: /* @__PURE__ */ new Set([EDGE_ID_COLUMN,
|
|
1842
|
+
reserved: /* @__PURE__ */ new Set([EDGE_ID_COLUMN, ...label, GRAPHICS_COLUMN])
|
|
1639
1843
|
});
|
|
1640
1844
|
this.graphColumns = new ColumnSet("graph", report, { ...base, reserved: /* @__PURE__ */ new Set([GRAPHICS_COLUMN]) });
|
|
1641
1845
|
}
|
|
@@ -1649,7 +1853,7 @@ class XgmmlEmitter {
|
|
|
1649
1853
|
this.report.warning(
|
|
1650
1854
|
"validation-error",
|
|
1651
1855
|
XGMML_ISSUE.DANGLING_REFERENCE,
|
|
1652
|
-
`${this.prefix()}${members.dangling} xlink:href member reference(
|
|
1856
|
+
`${this.prefix()}${members.dangling} xlink:href member reference${plural(members.dangling)} ${agree(members.dangling, "names", "name")} no node or edge of the document`,
|
|
1653
1857
|
{ line: graph?.line ?? null }
|
|
1654
1858
|
);
|
|
1655
1859
|
}
|
|
@@ -1775,11 +1979,28 @@ class XgmmlEmitter {
|
|
|
1775
1979
|
edgeDirection(record, header) {
|
|
1776
1980
|
let directed = this.directions.get(record);
|
|
1777
1981
|
if (directed === void 0) {
|
|
1778
|
-
|
|
1982
|
+
const fallback = this.graphDirected(record.graph, header);
|
|
1983
|
+
directed = record.directed === null ? fallback : this.flag(record.directed, fallback, { line: record.line, element: record.id ?? record.label });
|
|
1779
1984
|
this.directions.set(record, directed);
|
|
1780
1985
|
}
|
|
1781
1986
|
return directed;
|
|
1782
1987
|
}
|
|
1988
|
+
/**
|
|
1989
|
+
* The default direction of the edges of a graph: the `directed` attribute of the graph or of
|
|
1990
|
+
* the nearest graph it is nested in that has one, else the header.
|
|
1991
|
+
* @param graph - the graph that holds the edge
|
|
1992
|
+
* @param header - the header direction
|
|
1993
|
+
* @returns whether the graph's edges are directed by default
|
|
1994
|
+
*/
|
|
1995
|
+
graphDirected(graph, header) {
|
|
1996
|
+
for (let g = graph; g !== null && g !== this.doc.root; g = g.parent) {
|
|
1997
|
+
const text = g.attrs.get("directed");
|
|
1998
|
+
if (text !== void 0) {
|
|
1999
|
+
return this.flag(text, header, { line: g.line, element: "directed" });
|
|
2000
|
+
}
|
|
2001
|
+
}
|
|
2002
|
+
return header;
|
|
2003
|
+
}
|
|
1783
2004
|
/**
|
|
1784
2005
|
* The direction the sink starts with: the one every edge has when they all agree (a
|
|
1785
2006
|
* Cytoscape file writes cy:directed on every edge and may omit the root attribute), else the
|
|
@@ -1858,6 +2079,33 @@ class XgmmlEmitter {
|
|
|
1858
2079
|
this.checkAbort();
|
|
1859
2080
|
}
|
|
1860
2081
|
}
|
|
2082
|
+
/**
|
|
2083
|
+
* The sink id of a node's written id: the restored original, else the written id, coerced.
|
|
2084
|
+
* @param text - the written id
|
|
2085
|
+
* @returns the id
|
|
2086
|
+
*/
|
|
2087
|
+
idOf(text) {
|
|
2088
|
+
return this.coercer.text(this.extras.restoredIds?.get(text) ?? text);
|
|
2089
|
+
}
|
|
2090
|
+
/**
|
|
2091
|
+
* Decide whether a table's label comes from its `name` atts.
|
|
2092
|
+
* @param domain - node or edge
|
|
2093
|
+
* @param records - the table's records
|
|
2094
|
+
*/
|
|
2095
|
+
decideNameLabel(domain, records) {
|
|
2096
|
+
this.nameLabel[domain] = this.extras.labelFromName === true && records.some((r) => r.atts.some(isNameAtt));
|
|
2097
|
+
}
|
|
2098
|
+
/**
|
|
2099
|
+
* The label of a record: its `name` att, or its XGMML label.
|
|
2100
|
+
* @param record - the node or edge
|
|
2101
|
+
* @returns the label, or undefined
|
|
2102
|
+
*/
|
|
2103
|
+
labelOf(record) {
|
|
2104
|
+
if (this.nameLabel[record.kind]) {
|
|
2105
|
+
return record.atts.find(isNameAtt)?.value ?? void 0;
|
|
2106
|
+
}
|
|
2107
|
+
return record.label ?? void 0;
|
|
2108
|
+
}
|
|
1861
2109
|
/**
|
|
1862
2110
|
* The coerced id of a node text.
|
|
1863
2111
|
* @param text - the id text
|
|
@@ -1865,7 +2113,7 @@ class XgmmlEmitter {
|
|
|
1865
2113
|
* @returns the id
|
|
1866
2114
|
*/
|
|
1867
2115
|
nodeId(text, line) {
|
|
1868
|
-
const id = this.
|
|
2116
|
+
const id = this.idOf(text);
|
|
1869
2117
|
const merge = this.coercer.lastMerge;
|
|
1870
2118
|
if (merge !== null) {
|
|
1871
2119
|
this.report.warning(
|
|
@@ -1923,7 +2171,7 @@ class XgmmlEmitter {
|
|
|
1923
2171
|
this.report.warning(
|
|
1924
2172
|
"validation-error",
|
|
1925
2173
|
XGMML_ISSUE.DANGLING_REFERENCE,
|
|
1926
|
-
`${this.prefix()}${dangling} xlink:href reference(
|
|
2174
|
+
`${this.prefix()}${dangling} xlink:href reference${plural(dangling)} ${agree(dangling, "names", "name")} no node or edge of the document`
|
|
1927
2175
|
);
|
|
1928
2176
|
}
|
|
1929
2177
|
}
|
|
@@ -1937,11 +2185,15 @@ class XgmmlEmitter {
|
|
|
1937
2185
|
const positions = new Positions(this, this.dialect.cytoscape ? this.settings.zAs : "position");
|
|
1938
2186
|
const graphics = new JsonColumn(this, "node", GRAPHICS_COLUMN, XGMML_ORIGIN_NAMESPACE, "graphics");
|
|
1939
2187
|
const pointers = new Pointers(this, this.groupTest());
|
|
2188
|
+
this.decideNameLabel(
|
|
2189
|
+
"node",
|
|
2190
|
+
this.rowList.flatMap((r) => r.records)
|
|
2191
|
+
);
|
|
1940
2192
|
for (const row of this.rowList) {
|
|
1941
2193
|
const where = { line: row.records[0].line, element: row.id };
|
|
1942
2194
|
const seen = /* @__PURE__ */ new Set();
|
|
1943
2195
|
for (const record of row.records) {
|
|
1944
|
-
labels[row.row] ??= record
|
|
2196
|
+
labels[row.row] ??= this.labelOf(record);
|
|
1945
2197
|
this.addElementColumns(this.nodeColumns, row.row, record, seen, where);
|
|
1946
2198
|
positions.add(row, record);
|
|
1947
2199
|
if (record.graphics !== null && Object.keys(record.graphics).length > 0) {
|
|
@@ -1983,7 +2235,7 @@ class XgmmlEmitter {
|
|
|
1983
2235
|
names.add(key2);
|
|
1984
2236
|
}
|
|
1985
2237
|
for (const att of record.atts) {
|
|
1986
|
-
if (this.skipAtt(record, att) || merging && att.name !== null && seen.has(att.name)) {
|
|
2238
|
+
if (this.skipAtt(record, att) || this.nameLabel[record.kind] && isNameAtt(att) || merging && att.name !== null && seen.has(att.name)) {
|
|
1987
2239
|
continue;
|
|
1988
2240
|
}
|
|
1989
2241
|
if (record.kind === "node" && att.name === "__isGroup" && record.nested.length > 0 && isCyTrue(att.value)) {
|
|
@@ -2008,7 +2260,19 @@ class XgmmlEmitter {
|
|
|
2008
2260
|
* @returns true to skip it
|
|
2009
2261
|
*/
|
|
2010
2262
|
skipAtt(record, att) {
|
|
2011
|
-
|
|
2263
|
+
if (record.kind !== "edge" || att.name !== this.options.weightFrom) {
|
|
2264
|
+
return false;
|
|
2265
|
+
}
|
|
2266
|
+
if (record.weight === null || att.name !== "weight" || att.children.length > 0) {
|
|
2267
|
+
return record.weight === null;
|
|
2268
|
+
}
|
|
2269
|
+
this.report.warning(
|
|
2270
|
+
"validation-error",
|
|
2271
|
+
XGMML_ISSUE.DUPLICATE_ATTRIBUTE,
|
|
2272
|
+
`${this.prefix()}an edge has weight="${record.weight}" and a weight att "${att.value ?? ""}"; the weight attribute is the weight and the att is not read`,
|
|
2273
|
+
{ line: att.line, element: record.id ?? record.label ?? "weight" }
|
|
2274
|
+
);
|
|
2275
|
+
return true;
|
|
2012
2276
|
}
|
|
2013
2277
|
/**
|
|
2014
2278
|
* Write a label column (role label).
|
|
@@ -2021,7 +2285,7 @@ class XgmmlEmitter {
|
|
|
2021
2285
|
return;
|
|
2022
2286
|
}
|
|
2023
2287
|
const handle = this.declare(domain, {
|
|
2024
|
-
name: LABEL_COLUMN,
|
|
2288
|
+
name: this.nameLabel[domain] ? "name" : LABEL_COLUMN,
|
|
2025
2289
|
dtype: "string",
|
|
2026
2290
|
role: "label",
|
|
2027
2291
|
nullable: true,
|
|
@@ -2085,21 +2349,20 @@ class XgmmlEmitter {
|
|
|
2085
2349
|
addEdges(records, header) {
|
|
2086
2350
|
const ids = /* @__PURE__ */ new Set();
|
|
2087
2351
|
const dedupe = this.dialect.cy2 && this.doc.nodes.some((n) => n.nested.length > 0) ? /* @__PURE__ */ new Set() : null;
|
|
2352
|
+
let repeats = 0;
|
|
2353
|
+
let firstRepeat = null;
|
|
2088
2354
|
const labels = [];
|
|
2089
2355
|
const edgeIds = [];
|
|
2090
2356
|
const graphics = [];
|
|
2091
2357
|
let row = 0;
|
|
2358
|
+
this.decideNameLabel("edge", records);
|
|
2092
2359
|
for (const record of records) {
|
|
2093
2360
|
const where = { line: record.line, element: record.id ?? record.label };
|
|
2094
|
-
const key2 = record.id ?? record.label;
|
|
2361
|
+
const key2 = record.id ?? (record.label === null ? null : JSON.stringify([record.label, record.source, record.target]));
|
|
2095
2362
|
if (dedupe !== null && key2 !== null) {
|
|
2096
2363
|
if (dedupe.has(key2)) {
|
|
2097
|
-
|
|
2098
|
-
|
|
2099
|
-
XGMML_ISSUE.GROUP_DUPLICATE_EDGE,
|
|
2100
|
-
`${this.prefix()}the Cytoscape 2.x writer repeats the edges of a group; each repeat is dropped`,
|
|
2101
|
-
where
|
|
2102
|
-
);
|
|
2364
|
+
repeats++;
|
|
2365
|
+
firstRepeat ??= where;
|
|
2103
2366
|
continue;
|
|
2104
2367
|
}
|
|
2105
2368
|
dedupe.add(key2);
|
|
@@ -2110,7 +2373,7 @@ class XgmmlEmitter {
|
|
|
2110
2373
|
continue;
|
|
2111
2374
|
}
|
|
2112
2375
|
this.edgeIndex[row] = index;
|
|
2113
|
-
labels[row] = record
|
|
2376
|
+
labels[row] = this.labelOf(record);
|
|
2114
2377
|
edgeIds[row] = record.id ?? void 0;
|
|
2115
2378
|
this.addElementColumns(this.edgeColumns, row, record, /* @__PURE__ */ new Set(), where);
|
|
2116
2379
|
this.fillInteraction(record, row, where);
|
|
@@ -2119,6 +2382,14 @@ class XgmmlEmitter {
|
|
|
2119
2382
|
}
|
|
2120
2383
|
row++;
|
|
2121
2384
|
}
|
|
2385
|
+
if (repeats > 0) {
|
|
2386
|
+
this.report.warning(
|
|
2387
|
+
"merged",
|
|
2388
|
+
XGMML_ISSUE.GROUP_DUPLICATE_EDGE,
|
|
2389
|
+
`${this.prefix()}the Cytoscape 2.x writer repeats the edges of a group; ${repeats} repeat${plural(repeats)} ${agree(repeats, "was", "were")} dropped`,
|
|
2390
|
+
firstRepeat ?? void 0
|
|
2391
|
+
);
|
|
2392
|
+
}
|
|
2122
2393
|
this.writeEdgeIds(edgeIds);
|
|
2123
2394
|
this.writeLabels("edge", labels, (r) => this.edgeIndex[r] ?? -1);
|
|
2124
2395
|
const column = new JsonColumn(this, "edge", GRAPHICS_COLUMN, XGMML_ORIGIN_NAMESPACE, "graphics");
|
|
@@ -2195,7 +2466,7 @@ class XgmmlEmitter {
|
|
|
2195
2466
|
if (text === null) {
|
|
2196
2467
|
return void 0;
|
|
2197
2468
|
}
|
|
2198
|
-
const weight = parseWeightText(text);
|
|
2469
|
+
const weight = parseWeightText(text, this.report);
|
|
2199
2470
|
this.weighted ||= weight !== void 0;
|
|
2200
2471
|
return weight;
|
|
2201
2472
|
}
|
|
@@ -2213,21 +2484,22 @@ class XgmmlEmitter {
|
|
|
2213
2484
|
if (text !== null) {
|
|
2214
2485
|
const row = this.rows.get(text);
|
|
2215
2486
|
if (row !== void 0 && row.index >= 0) {
|
|
2216
|
-
return this.
|
|
2487
|
+
return this.idOf(text);
|
|
2217
2488
|
}
|
|
2218
2489
|
}
|
|
2219
2490
|
if (alias !== null) {
|
|
2220
2491
|
const resolved = this.aliasRow(alias);
|
|
2221
2492
|
if (resolved !== null) {
|
|
2222
2493
|
this.aliasResolved++;
|
|
2223
|
-
return this.
|
|
2494
|
+
return this.idOf(resolved.id);
|
|
2224
2495
|
}
|
|
2225
2496
|
}
|
|
2226
2497
|
if (text === null) {
|
|
2498
|
+
const ambiguous = alias !== null && this.aliasRow(alias) === null && this.labelRows?.get(alias) === null;
|
|
2227
2499
|
this.report.error(
|
|
2228
2500
|
"missing-value",
|
|
2229
2501
|
XGMML_ISSUE.MISSING_ENDPOINT,
|
|
2230
|
-
`${this.prefix()}<edge> without a ${side}`,
|
|
2502
|
+
ambiguous ? `${this.prefix()}<edge> without a ${side}: its label alias "${alias}" is ambiguous (several nodes have that label); the edge is skipped` : `${this.prefix()}<edge> without a ${side}`,
|
|
2231
2503
|
where
|
|
2232
2504
|
);
|
|
2233
2505
|
return null;
|
|
@@ -2293,7 +2565,7 @@ class XgmmlEmitter {
|
|
|
2293
2565
|
this.report.warning(
|
|
2294
2566
|
"coercion",
|
|
2295
2567
|
XGMML_ISSUE.LABEL_ALIAS,
|
|
2296
|
-
`${this.prefix()}Cytoscape label aliases ("a (pp) b"): ${this.aliasResolved} endpoint(
|
|
2568
|
+
`${this.prefix()}Cytoscape label aliases ("a (pp) b"): ${this.aliasResolved} endpoint${plural(this.aliasResolved)} resolved, ${this.aliasInteractions} interaction${plural(this.aliasInteractions)} filled from edge labels`
|
|
2297
2569
|
);
|
|
2298
2570
|
}
|
|
2299
2571
|
/**
|
|
@@ -2391,6 +2663,9 @@ class XgmmlEmitter {
|
|
|
2391
2663
|
});
|
|
2392
2664
|
}
|
|
2393
2665
|
}
|
|
2666
|
+
function isNameAtt(att) {
|
|
2667
|
+
return att.name === "name" && (att.namespace ?? null) === null && att.value !== null && att.children.length === 0 && (att.cyType ?? "String") === "String";
|
|
2668
|
+
}
|
|
2394
2669
|
function aliasesOf(label) {
|
|
2395
2670
|
if (label === null) {
|
|
2396
2671
|
return null;
|
|
@@ -2491,8 +2766,8 @@ class Positions {
|
|
|
2491
2766
|
if (text === null) {
|
|
2492
2767
|
return null;
|
|
2493
2768
|
}
|
|
2494
|
-
const n =
|
|
2495
|
-
if (
|
|
2769
|
+
const n = parseCoordinate(text);
|
|
2770
|
+
if (n === null) {
|
|
2496
2771
|
this.emitter.issues.error(
|
|
2497
2772
|
"validation-error",
|
|
2498
2773
|
XGMML_ISSUE.BAD_VALUE,
|
|
@@ -2595,7 +2870,7 @@ class Pointers {
|
|
|
2595
2870
|
this.emitter.issues.warning(
|
|
2596
2871
|
"validation-error",
|
|
2597
2872
|
XGMML_ISSUE.DANGLING_REFERENCE,
|
|
2598
|
-
`${prefix}${this.dangling} nested-network pointer(
|
|
2873
|
+
`${prefix}${this.dangling} nested-network pointer${plural(this.dangling)} ${agree(this.dangling, "names", "name")} no graph of the document`
|
|
2599
2874
|
);
|
|
2600
2875
|
}
|
|
2601
2876
|
const names = new JsonColumn(
|
|
@@ -2613,7 +2888,7 @@ class Pointers {
|
|
|
2613
2888
|
this.emitter.issues.warning(
|
|
2614
2889
|
"unsupported",
|
|
2615
2890
|
XGMML_ISSUE.CROSS_FILE_REFERENCE,
|
|
2616
|
-
`${prefix}${this.crossFile.size} nested-network pointer(
|
|
2891
|
+
`${prefix}${this.crossFile.size} nested-network pointer${plural(this.crossFile.size)} ${agree(this.crossFile.size, "points", "point")} into another file; each is kept as text in ${NETWORK_POINTER_COLUMN}`
|
|
2617
2892
|
);
|
|
2618
2893
|
const column = new JsonColumn(
|
|
2619
2894
|
this.emitter,
|
|
@@ -2638,6 +2913,7 @@ class Containment {
|
|
|
2638
2913
|
this.emitter = emitter;
|
|
2639
2914
|
this.parents = /* @__PURE__ */ new Map();
|
|
2640
2915
|
this.subgraphs = /* @__PURE__ */ new Map();
|
|
2916
|
+
this.groups = /* @__PURE__ */ new Set();
|
|
2641
2917
|
}
|
|
2642
2918
|
/**
|
|
2643
2919
|
* Collect the memberships of every group node of the graph.
|
|
@@ -2683,7 +2959,7 @@ class Containment {
|
|
|
2683
2959
|
this.emitter.issues.error(
|
|
2684
2960
|
"missing-value",
|
|
2685
2961
|
XGMML_ISSUE.UNKNOWN_PARENT,
|
|
2686
|
-
`${this.emitter.prefix()}${unknown} group member(
|
|
2962
|
+
`${this.emitter.prefix()}${unknown} group member${plural(unknown)} ${agree(unknown, "names", "name")} no node of this graph`
|
|
2687
2963
|
);
|
|
2688
2964
|
}
|
|
2689
2965
|
}
|
|
@@ -2694,7 +2970,7 @@ class Containment {
|
|
|
2694
2970
|
* @param line - the line
|
|
2695
2971
|
*/
|
|
2696
2972
|
link(child, parent, line) {
|
|
2697
|
-
if (child === parent || this.isAncestor(child, parent)) {
|
|
2973
|
+
if (child === parent || this.groups.has(child) && this.isAncestor(child, parent)) {
|
|
2698
2974
|
this.emitter.issues.error(
|
|
2699
2975
|
"validation-error",
|
|
2700
2976
|
XGMML_ISSUE.PARENT_CYCLE,
|
|
@@ -2708,6 +2984,7 @@ class Containment {
|
|
|
2708
2984
|
list.push(parent);
|
|
2709
2985
|
}
|
|
2710
2986
|
this.parents.set(child, list);
|
|
2987
|
+
this.groups.add(parent);
|
|
2711
2988
|
}
|
|
2712
2989
|
/**
|
|
2713
2990
|
* Whether a node is an ancestor of another through the memberships so far.
|
|
@@ -2780,8 +3057,6 @@ const USED_OPTIONS = /* @__PURE__ */ new Set([
|
|
|
2780
3057
|
"onProgress",
|
|
2781
3058
|
"encoding"
|
|
2782
3059
|
]);
|
|
2783
|
-
const SNIFF_BYTES = 4096;
|
|
2784
|
-
const HEAD_CHARS = 2048;
|
|
2785
3060
|
const XGMML_DOCTYPE = /<!DOCTYPE\s+graph\s[^<>]*xgmml\.dtd/i;
|
|
2786
3061
|
function resolveSettings(options, cytoscape) {
|
|
2787
3062
|
const zAs = options?.zAs ?? "column";
|
|
@@ -2828,10 +3103,10 @@ async function parseXgmml(input, report, common, options) {
|
|
|
2828
3103
|
} : void 0
|
|
2829
3104
|
};
|
|
2830
3105
|
const parser = new XgmmlParser(report);
|
|
2831
|
-
const seen = {
|
|
3106
|
+
const seen = { content: false };
|
|
2832
3107
|
try {
|
|
2833
3108
|
await tokenizeXml(
|
|
2834
|
-
watch(textChunks(input, report, { ...common, declaredEncoding: xmlDeclaredEncoding }), seen),
|
|
3109
|
+
watch(textChunks(input, report, { ...common, declaredEncoding: xmlDeclaredEncoding, xml: true }), seen),
|
|
2835
3110
|
parser,
|
|
2836
3111
|
repairs
|
|
2837
3112
|
);
|
|
@@ -2845,7 +3120,7 @@ async function parseXgmml(input, report, common, options) {
|
|
|
2845
3120
|
throw err;
|
|
2846
3121
|
}
|
|
2847
3122
|
const doc = parser.document();
|
|
2848
|
-
if (!doc.xgmmlNamespace && !XGMML_DOCTYPE.test(
|
|
3123
|
+
if (!doc.xgmmlNamespace && !XGMML_DOCTYPE.test(doc.doctype ?? "")) {
|
|
2849
3124
|
report.warning(
|
|
2850
3125
|
"validation-error",
|
|
2851
3126
|
XGMML_ISSUE.NO_NAMESPACE,
|
|
@@ -2857,9 +3132,6 @@ async function parseXgmml(input, report, common, options) {
|
|
|
2857
3132
|
}
|
|
2858
3133
|
async function* watch(chunks, seen) {
|
|
2859
3134
|
for await (const chunk of chunks) {
|
|
2860
|
-
if (seen.head.length < HEAD_CHARS) {
|
|
2861
|
-
seen.head += chunk.slice(0, HEAD_CHARS - seen.head.length);
|
|
2862
|
-
}
|
|
2863
3135
|
seen.content ||= !isWhitespace(chunk);
|
|
2864
3136
|
yield chunk;
|
|
2865
3137
|
}
|
|
@@ -2913,7 +3185,7 @@ function reportRootOnly(prepared) {
|
|
|
2913
3185
|
prepared.report.warning(
|
|
2914
3186
|
"unsupported",
|
|
2915
3187
|
XGMML_ISSUE.ROOT_ONLY_ELEMENTS,
|
|
2916
|
-
`${nodes}
|
|
3188
|
+
`${elementCount(nodes, edges)} ${agree(nodes + edges, "belongs", "belong")} to none of the file's networks (group meta-edges or collapsed group members) and ${agree(nodes + edges, "was", "were")} not read`
|
|
2917
3189
|
);
|
|
2918
3190
|
}
|
|
2919
3191
|
}
|
|
@@ -2924,22 +3196,22 @@ async function importXgmml(input, sink, options) {
|
|
|
2924
3196
|
options,
|
|
2925
3197
|
prepared.report
|
|
2926
3198
|
);
|
|
2927
|
-
if (prepared.graphs.length > 1) {
|
|
3199
|
+
if (prepared.graphs.length > 1 && !graphChosen(options)) {
|
|
2928
3200
|
prepared.report.warning(
|
|
2929
3201
|
"unsupported",
|
|
2930
3202
|
XGMML_ISSUE.MULTIPLE_GRAPHS,
|
|
2931
|
-
`the session network document holds ${prepared.graphs.length} registered networks;
|
|
3203
|
+
`the session network document holds ${prepared.graphs.length} registered networks; only the first is read (importAllGraphs() reads every one; graphIndex or graphName chooses one)`
|
|
2932
3204
|
);
|
|
2933
3205
|
}
|
|
2934
3206
|
return emitOne(prepared, prepared.graphs[index], sink);
|
|
2935
3207
|
}
|
|
2936
3208
|
async function importAllXgmml(input, sinkFor, options) {
|
|
2937
|
-
const
|
|
2938
|
-
const
|
|
3209
|
+
const first = await prepare(input, null, options);
|
|
3210
|
+
const parsed = first.report.fork();
|
|
2939
3211
|
const reports = [];
|
|
2940
3212
|
for (let i = 0; i < first.graphs.length; i++) {
|
|
2941
3213
|
const sink = sinkFor(i);
|
|
2942
|
-
const prepared = i === 0 ? first :
|
|
3214
|
+
const prepared = i === 0 ? first : { ...first, report: parsed.fork() };
|
|
2943
3215
|
reportSinkOptions(sink, options, prepared.report, true);
|
|
2944
3216
|
reportUnusedOptions(options, prepared.report, USED_OPTIONS);
|
|
2945
3217
|
reports.push(emitOne(prepared, prepared.graphs[i], sink));
|
|
@@ -2961,50 +3233,23 @@ async function listXgmmlGraphs(input, options) {
|
|
|
2961
3233
|
function graphName(graph, doc) {
|
|
2962
3234
|
return graph.label ?? (graph === doc.root ? doc.rdf.title ?? null : null) ?? graph.id ?? null;
|
|
2963
3235
|
}
|
|
2964
|
-
async function reread(input) {
|
|
2965
|
-
if (typeof input === "string" || input instanceof Uint8Array) {
|
|
2966
|
-
return input;
|
|
2967
|
-
}
|
|
2968
|
-
const parts = [];
|
|
2969
|
-
const iterable = typeof input.getReader === "function" ? streamIterable(input) : input;
|
|
2970
|
-
for await (const chunk of iterable) {
|
|
2971
|
-
parts.push(chunk);
|
|
2972
|
-
}
|
|
2973
|
-
if (parts.every((p) => typeof p === "string")) {
|
|
2974
|
-
return parts.join("");
|
|
2975
|
-
}
|
|
2976
|
-
const bytes = parts.map((p) => typeof p === "string" ? new TextEncoder().encode(p) : p);
|
|
2977
|
-
const out = new Uint8Array(bytes.reduce((n, b) => n + b.byteLength, 0));
|
|
2978
|
-
let at = 0;
|
|
2979
|
-
for (const b of bytes) {
|
|
2980
|
-
out.set(b, at);
|
|
2981
|
-
at += b.byteLength;
|
|
2982
|
-
}
|
|
2983
|
-
return out;
|
|
2984
|
-
}
|
|
2985
|
-
async function* streamIterable(stream) {
|
|
2986
|
-
const reader = stream.getReader();
|
|
2987
|
-
try {
|
|
2988
|
-
for (; ; ) {
|
|
2989
|
-
const { done, value } = await reader.read();
|
|
2990
|
-
if (done) {
|
|
2991
|
-
return;
|
|
2992
|
-
}
|
|
2993
|
-
yield value;
|
|
2994
|
-
}
|
|
2995
|
-
} finally {
|
|
2996
|
-
reader.releaseLock();
|
|
2997
|
-
}
|
|
2998
|
-
}
|
|
2999
3236
|
function sniffXgmml(head) {
|
|
3000
|
-
|
|
3237
|
+
let encoding = "utf-8";
|
|
3238
|
+
if (head[0] === 255 && head[1] === 254 || head[0] === 60 && head[1] === 0 && head[2] === 63) {
|
|
3239
|
+
encoding = "utf-16le";
|
|
3240
|
+
} else if (head[0] === 254 && head[1] === 255 || head[0] === 0 && head[1] === 60 && head[2] === 0) {
|
|
3241
|
+
encoding = "utf-16be";
|
|
3242
|
+
}
|
|
3243
|
+
const text = new TextDecoder(encoding, { fatal: false }).decode(head);
|
|
3001
3244
|
if (!/^\uFEFF?\s*</.test(text)) {
|
|
3002
3245
|
return 0;
|
|
3003
3246
|
}
|
|
3004
3247
|
if (XGMML_DOCTYPE.test(text)) {
|
|
3005
3248
|
return 0.95;
|
|
3006
3249
|
}
|
|
3007
|
-
const root = /<(
|
|
3250
|
+
const root = /<(?![?!])([A-Za-z_][\w.-]*:)?([A-Za-z_][\w.-]*)[\s/>]/.exec(
|
|
3251
|
+
text.replaceAll(/<!--[\s\S]*?(-->|$)/g, "")
|
|
3252
|
+
);
|
|
3008
3253
|
if (root === null || root[2] !== "graph") {
|
|
3009
3254
|
return 0;
|
|
3010
3255
|
}
|
|
@@ -3014,6 +3259,13 @@ function sniffXgmml(head) {
|
|
|
3014
3259
|
}
|
|
3015
3260
|
const xgmmlImporter = Object.freeze({
|
|
3016
3261
|
format: FORMAT,
|
|
3262
|
+
options: Object.freeze([
|
|
3263
|
+
"cytoscapeEscapes",
|
|
3264
|
+
"labelAliases",
|
|
3265
|
+
"pairSurrogateReferences",
|
|
3266
|
+
"repairBareAmpersands",
|
|
3267
|
+
"zAs"
|
|
3268
|
+
]),
|
|
3017
3269
|
extensions: EXTENSIONS,
|
|
3018
3270
|
mimeTypes: MIME_TYPES,
|
|
3019
3271
|
sniff: sniffXgmml,
|
|
@@ -3044,12 +3296,13 @@ export {
|
|
|
3044
3296
|
PARENTS_COLUMN as h,
|
|
3045
3297
|
XGMML_ORIGIN_NAMESPACE as i,
|
|
3046
3298
|
CYTOSCAPE_ORIGIN_NAMESPACE as j,
|
|
3047
|
-
|
|
3048
|
-
|
|
3299
|
+
XgmmlEmitter as k,
|
|
3300
|
+
isCyTrue as l,
|
|
3049
3301
|
membersOf as m,
|
|
3050
3302
|
dialectOf as n,
|
|
3303
|
+
parseCoordinate as o,
|
|
3051
3304
|
parseXgmml as p,
|
|
3052
3305
|
resolveSettings as r,
|
|
3053
3306
|
xgmmlImporter as x
|
|
3054
3307
|
};
|
|
3055
|
-
//# sourceMappingURL=importer-
|
|
3308
|
+
//# sourceMappingURL=importer-Bcl1d4xH.js.map
|