@parcel/graph 2.0.2-nightly.2536 → 2.0.2-nightly.2549
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/lib/AdjacencyList.js +1165 -0
- package/lib/ContentGraph.js +1 -0
- package/lib/Graph.js +40 -213
- package/lib/index.js +3 -13
- package/package.json +2 -2
- package/src/AdjacencyList.js +1211 -0
- package/src/ContentGraph.js +9 -4
- package/src/Graph.js +77 -197
- package/src/index.js +4 -2
- package/test/AdjacencyList.test.js +280 -0
- package/test/Graph.test.js +9 -6
- package/test/integration/adjacency-list-shared-array.js +20 -0
package/lib/ContentGraph.js
CHANGED
package/lib/Graph.js
CHANGED
@@ -8,6 +8,8 @@ exports.default = exports.ALL_EDGE_TYPES = void 0;
|
|
8
8
|
|
9
9
|
var _types = require("./types");
|
10
10
|
|
11
|
+
var _AdjacencyList = _interopRequireDefault(require("./AdjacencyList"));
|
12
|
+
|
11
13
|
function _assert() {
|
12
14
|
const data = _interopRequireDefault(require("assert"));
|
13
15
|
|
@@ -30,35 +32,15 @@ function _nullthrows() {
|
|
30
32
|
|
31
33
|
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
|
32
34
|
|
33
|
-
const ALL_EDGE_TYPES =
|
35
|
+
const ALL_EDGE_TYPES = -1;
|
34
36
|
exports.ALL_EDGE_TYPES = ALL_EDGE_TYPES;
|
35
37
|
|
36
38
|
class Graph {
|
37
|
-
nextNodeId = 1;
|
38
|
-
|
39
39
|
constructor(opts) {
|
40
|
-
var _opts$nextNodeId;
|
41
|
-
|
42
40
|
this.nodes = (opts === null || opts === void 0 ? void 0 : opts.nodes) || new Map();
|
43
41
|
this.setRootNodeId(opts === null || opts === void 0 ? void 0 : opts.rootNodeId);
|
44
|
-
|
45
|
-
|
46
|
-
|
47
|
-
if (edges != null) {
|
48
|
-
this.inboundEdges = new AdjacencyList();
|
49
|
-
this.outboundEdges = new AdjacencyList(edges);
|
50
|
-
|
51
|
-
for (let [from, edgeList] of edges) {
|
52
|
-
for (let [type, toNodes] of edgeList) {
|
53
|
-
for (let to of toNodes) {
|
54
|
-
this.inboundEdges.addEdge(to, from, type);
|
55
|
-
}
|
56
|
-
}
|
57
|
-
}
|
58
|
-
} else {
|
59
|
-
this.inboundEdges = new AdjacencyList();
|
60
|
-
this.outboundEdges = new AdjacencyList();
|
61
|
-
}
|
42
|
+
let adjacencyList = opts === null || opts === void 0 ? void 0 : opts.adjacencyList;
|
43
|
+
this.adjacencyList = adjacencyList ? _AdjacencyList.default.deserialize(adjacencyList) : new _AdjacencyList.default();
|
62
44
|
}
|
63
45
|
|
64
46
|
setRootNodeId(id) {
|
@@ -68,43 +50,27 @@ class Graph {
|
|
68
50
|
static deserialize(opts) {
|
69
51
|
return new this({
|
70
52
|
nodes: opts.nodes,
|
71
|
-
|
72
|
-
rootNodeId: opts.rootNodeId
|
73
|
-
nextNodeId: opts.nextNodeId
|
53
|
+
adjacencyList: opts.adjacencyList,
|
54
|
+
rootNodeId: opts.rootNodeId
|
74
55
|
});
|
75
56
|
}
|
76
57
|
|
77
58
|
serialize() {
|
78
59
|
return {
|
79
60
|
nodes: this.nodes,
|
80
|
-
|
81
|
-
rootNodeId: this.rootNodeId
|
82
|
-
nextNodeId: this.nextNodeId
|
61
|
+
adjacencyList: this.adjacencyList.serialize(),
|
62
|
+
rootNodeId: this.rootNodeId
|
83
63
|
};
|
84
|
-
} // Returns
|
64
|
+
} // Returns an iterator of all edges in the graph. This can be large, so iterating
|
85
65
|
// the complete list can be costly in large graphs. Used when merging graphs.
|
86
66
|
|
87
67
|
|
88
68
|
getAllEdges() {
|
89
|
-
|
90
|
-
|
91
|
-
for (let [from, edgeList] of this.outboundEdges.getListMap()) {
|
92
|
-
for (let [type, toNodes] of edgeList) {
|
93
|
-
for (let to of toNodes) {
|
94
|
-
edges.push({
|
95
|
-
from,
|
96
|
-
to,
|
97
|
-
type
|
98
|
-
});
|
99
|
-
}
|
100
|
-
}
|
101
|
-
}
|
102
|
-
|
103
|
-
return edges;
|
69
|
+
return this.adjacencyList.getAllEdges();
|
104
70
|
}
|
105
71
|
|
106
72
|
addNode(node) {
|
107
|
-
let id =
|
73
|
+
let id = this.adjacencyList.addNode();
|
108
74
|
this.nodes.set(id, node);
|
109
75
|
return id;
|
110
76
|
}
|
@@ -118,6 +84,10 @@ class Graph {
|
|
118
84
|
}
|
119
85
|
|
120
86
|
addEdge(from, to, type = 1) {
|
87
|
+
if (Number(type) === 0) {
|
88
|
+
throw new Error(`Edge type "${type}" not allowed`);
|
89
|
+
}
|
90
|
+
|
121
91
|
if (!this.getNode(from)) {
|
122
92
|
throw new Error(`"from" node '${(0, _types.fromNodeId)(from)}' not found`);
|
123
93
|
}
|
@@ -126,108 +96,43 @@ class Graph {
|
|
126
96
|
throw new Error(`"to" node '${(0, _types.fromNodeId)(to)}' not found`);
|
127
97
|
}
|
128
98
|
|
129
|
-
this.
|
130
|
-
this.inboundEdges.addEdge(to, from, type);
|
99
|
+
return this.adjacencyList.addEdge(from, to, type);
|
131
100
|
}
|
132
101
|
|
133
102
|
hasEdge(from, to, type = 1) {
|
134
|
-
return this.
|
103
|
+
return this.adjacencyList.hasEdge(from, to, type);
|
135
104
|
}
|
136
105
|
|
137
106
|
getNodeIdsConnectedTo(nodeId, type = 1) {
|
138
107
|
this._assertHasNodeId(nodeId);
|
139
108
|
|
140
|
-
|
141
|
-
|
142
|
-
if (inboundByType == null) {
|
143
|
-
return [];
|
144
|
-
}
|
145
|
-
|
146
|
-
let nodes;
|
147
|
-
|
148
|
-
if (type === ALL_EDGE_TYPES) {
|
149
|
-
nodes = new Set();
|
150
|
-
|
151
|
-
for (let [, typeNodes] of inboundByType) {
|
152
|
-
for (let node of typeNodes) {
|
153
|
-
nodes.add(node);
|
154
|
-
}
|
155
|
-
}
|
156
|
-
} else if (Array.isArray(type)) {
|
157
|
-
nodes = new Set();
|
158
|
-
|
159
|
-
for (let typeName of type) {
|
160
|
-
for (let node of (_inboundByType$get$va = (_inboundByType$get = inboundByType.get(typeName)) === null || _inboundByType$get === void 0 ? void 0 : _inboundByType$get.values()) !== null && _inboundByType$get$va !== void 0 ? _inboundByType$get$va : []) {
|
161
|
-
var _inboundByType$get$va, _inboundByType$get;
|
162
|
-
|
163
|
-
nodes.add(node);
|
164
|
-
}
|
165
|
-
}
|
166
|
-
} else {
|
167
|
-
var _inboundByType$get$va2, _inboundByType$get2;
|
168
|
-
|
169
|
-
nodes = new Set((_inboundByType$get$va2 = (_inboundByType$get2 = inboundByType.get(type)) === null || _inboundByType$get2 === void 0 ? void 0 : _inboundByType$get2.values()) !== null && _inboundByType$get$va2 !== void 0 ? _inboundByType$get$va2 : []);
|
170
|
-
}
|
171
|
-
|
172
|
-
return [...nodes];
|
109
|
+
return this.adjacencyList.getNodeIdsConnectedTo(nodeId, type);
|
173
110
|
}
|
174
111
|
|
175
112
|
getNodeIdsConnectedFrom(nodeId, type = 1) {
|
176
113
|
this._assertHasNodeId(nodeId);
|
177
114
|
|
178
|
-
|
179
|
-
|
180
|
-
if (outboundByType == null) {
|
181
|
-
return [];
|
182
|
-
}
|
183
|
-
|
184
|
-
let nodes;
|
185
|
-
|
186
|
-
if (type === ALL_EDGE_TYPES) {
|
187
|
-
nodes = new Set();
|
188
|
-
|
189
|
-
for (let [, typeNodes] of outboundByType) {
|
190
|
-
for (let node of typeNodes) {
|
191
|
-
nodes.add(node);
|
192
|
-
}
|
193
|
-
}
|
194
|
-
} else if (Array.isArray(type)) {
|
195
|
-
nodes = new Set();
|
196
|
-
|
197
|
-
for (let typeName of type) {
|
198
|
-
for (let node of (_outboundByType$get$v = (_outboundByType$get = outboundByType.get(typeName)) === null || _outboundByType$get === void 0 ? void 0 : _outboundByType$get.values()) !== null && _outboundByType$get$v !== void 0 ? _outboundByType$get$v : []) {
|
199
|
-
var _outboundByType$get$v, _outboundByType$get;
|
200
|
-
|
201
|
-
nodes.add(node);
|
202
|
-
}
|
203
|
-
}
|
204
|
-
} else {
|
205
|
-
var _outboundByType$get$v2, _outboundByType$get2;
|
206
|
-
|
207
|
-
nodes = new Set((_outboundByType$get$v2 = (_outboundByType$get2 = outboundByType.get(type)) === null || _outboundByType$get2 === void 0 ? void 0 : _outboundByType$get2.values()) !== null && _outboundByType$get$v2 !== void 0 ? _outboundByType$get$v2 : []);
|
208
|
-
}
|
209
|
-
|
210
|
-
return [...nodes];
|
115
|
+
return this.adjacencyList.getNodeIdsConnectedFrom(nodeId, type);
|
211
116
|
} // Removes node and any edges coming from or to that node
|
212
117
|
|
213
118
|
|
214
119
|
removeNode(nodeId) {
|
215
120
|
this._assertHasNodeId(nodeId);
|
216
121
|
|
217
|
-
for (let
|
218
|
-
|
219
|
-
|
220
|
-
|
221
|
-
|
222
|
-
|
223
|
-
|
224
|
-
}
|
122
|
+
for (let {
|
123
|
+
type,
|
124
|
+
from
|
125
|
+
} of this.adjacencyList.getInboundEdgesByType(nodeId)) {
|
126
|
+
this.removeEdge(from, nodeId, type, // Do not allow orphans to be removed as this node could be one
|
127
|
+
// and is already being removed.
|
128
|
+
false);
|
225
129
|
}
|
226
130
|
|
227
|
-
for (let
|
228
|
-
|
229
|
-
|
230
|
-
|
131
|
+
for (let {
|
132
|
+
type,
|
133
|
+
to
|
134
|
+
} of this.adjacencyList.getOutboundEdgesByType(nodeId)) {
|
135
|
+
this.removeEdge(nodeId, to, type);
|
231
136
|
}
|
232
137
|
|
233
138
|
let wasRemoved = this.nodes.delete(nodeId);
|
@@ -237,23 +142,18 @@ class Graph {
|
|
237
142
|
removeEdges(nodeId, type = 1) {
|
238
143
|
this._assertHasNodeId(nodeId);
|
239
144
|
|
240
|
-
for (let to of this.
|
145
|
+
for (let to of this.getNodeIdsConnectedFrom(nodeId, type)) {
|
241
146
|
this.removeEdge(nodeId, to, type);
|
242
147
|
}
|
243
148
|
} // Removes edge and node the edge is to if the node is orphaned
|
244
149
|
|
245
150
|
|
246
151
|
removeEdge(from, to, type = 1, removeOrphans = true) {
|
247
|
-
if (!this.
|
248
|
-
throw new Error(`
|
152
|
+
if (!this.adjacencyList.hasEdge(from, to, type)) {
|
153
|
+
throw new Error(`Edge from ${(0, _types.fromNodeId)(from)} to ${(0, _types.fromNodeId)(to)} not found!`);
|
249
154
|
}
|
250
155
|
|
251
|
-
|
252
|
-
throw new Error(`Inbound edge from ${(0, _types.fromNodeId)(to)} to ${(0, _types.fromNodeId)(from)} not found!`);
|
253
|
-
}
|
254
|
-
|
255
|
-
this.outboundEdges.removeEdge(from, to, type);
|
256
|
-
this.inboundEdges.removeEdge(to, from, type);
|
156
|
+
this.adjacencyList.removeEdge(from, to, type);
|
257
157
|
|
258
158
|
if (removeOrphans && this.isOrphanedNode(to)) {
|
259
159
|
this.removeNode(to);
|
@@ -266,14 +166,7 @@ class Graph {
|
|
266
166
|
if (this.rootNodeId == null) {
|
267
167
|
// If the graph does not have a root, and there are inbound edges,
|
268
168
|
// this node should not be considered orphaned.
|
269
|
-
|
270
|
-
for (let [, inboundNodeIds] of this.inboundEdges.getEdgesByType(nodeId)) {
|
271
|
-
if (inboundNodeIds.size > 0) {
|
272
|
-
return false;
|
273
|
-
}
|
274
|
-
}
|
275
|
-
|
276
|
-
return true;
|
169
|
+
return !this.adjacencyList.hasInboundEdges(nodeId);
|
277
170
|
} // Otherwise, attempt to traverse backwards to the root. If there is a path,
|
278
171
|
// then this is not an orphaned node.
|
279
172
|
|
@@ -285,8 +178,7 @@ class Graph {
|
|
285
178
|
hasPathToRoot = true;
|
286
179
|
actions.stop();
|
287
180
|
}
|
288
|
-
},
|
289
|
-
ALL_EDGE_TYPES);
|
181
|
+
}, ALL_EDGE_TYPES);
|
290
182
|
|
291
183
|
if (hasPathToRoot) {
|
292
184
|
return false;
|
@@ -299,25 +191,14 @@ class Graph {
|
|
299
191
|
this._assertHasNodeId(nodeId);
|
300
192
|
|
301
193
|
this.nodes.set(nodeId, node);
|
302
|
-
}
|
303
|
-
|
304
|
-
replaceNode(fromNodeId, toNodeId, type = 1) {
|
305
|
-
this._assertHasNodeId(fromNodeId);
|
306
|
-
|
307
|
-
for (let parent of this.inboundEdges.getEdges(fromNodeId, type)) {
|
308
|
-
this.addEdge(parent, toNodeId, type);
|
309
|
-
this.removeEdge(parent, fromNodeId, type);
|
310
|
-
}
|
311
|
-
|
312
|
-
this.removeNode(fromNodeId);
|
313
194
|
} // Update a node's downstream nodes making sure to prune any orphaned branches
|
314
195
|
|
315
196
|
|
316
197
|
replaceNodeIdsConnectedTo(fromNodeId, toNodeIds, replaceFilter, type = 1) {
|
317
198
|
this._assertHasNodeId(fromNodeId);
|
318
199
|
|
319
|
-
let outboundEdges = this.
|
320
|
-
let childrenToRemove = new Set(replaceFilter ?
|
200
|
+
let outboundEdges = this.getNodeIdsConnectedFrom(fromNodeId, type);
|
201
|
+
let childrenToRemove = new Set(replaceFilter ? outboundEdges.filter(toNodeId => replaceFilter(toNodeId)) : outboundEdges);
|
321
202
|
|
322
203
|
for (let toNodeId of toNodeIds) {
|
323
204
|
childrenToRemove.delete(toNodeId);
|
@@ -549,58 +430,4 @@ function mapVisitor(filter, visit) {
|
|
549
430
|
}
|
550
431
|
|
551
432
|
return mapped;
|
552
|
-
}
|
553
|
-
|
554
|
-
class AdjacencyList {
|
555
|
-
constructor(listMap) {
|
556
|
-
this._listMap = listMap !== null && listMap !== void 0 ? listMap : new Map();
|
557
|
-
}
|
558
|
-
|
559
|
-
getListMap() {
|
560
|
-
return this._listMap;
|
561
|
-
}
|
562
|
-
|
563
|
-
getEdges(from, type) {
|
564
|
-
var _this$_listMap$get$ge, _this$_listMap$get;
|
565
|
-
|
566
|
-
return (_this$_listMap$get$ge = (_this$_listMap$get = this._listMap.get(from)) === null || _this$_listMap$get === void 0 ? void 0 : _this$_listMap$get.get(type)) !== null && _this$_listMap$get$ge !== void 0 ? _this$_listMap$get$ge : new Set();
|
567
|
-
}
|
568
|
-
|
569
|
-
getEdgesByType(from) {
|
570
|
-
var _this$_listMap$get2;
|
571
|
-
|
572
|
-
return (_this$_listMap$get2 = this._listMap.get(from)) !== null && _this$_listMap$get2 !== void 0 ? _this$_listMap$get2 : new Map();
|
573
|
-
}
|
574
|
-
|
575
|
-
hasEdge(from, to, type) {
|
576
|
-
var _this$_listMap$get3, _this$_listMap$get3$g;
|
577
|
-
|
578
|
-
return Boolean((_this$_listMap$get3 = this._listMap.get(from)) === null || _this$_listMap$get3 === void 0 ? void 0 : (_this$_listMap$get3$g = _this$_listMap$get3.get(type)) === null || _this$_listMap$get3$g === void 0 ? void 0 : _this$_listMap$get3$g.has(to));
|
579
|
-
}
|
580
|
-
|
581
|
-
addEdge(from, to, type) {
|
582
|
-
let types = this._listMap.get(from);
|
583
|
-
|
584
|
-
if (types == null) {
|
585
|
-
types = new Map();
|
586
|
-
|
587
|
-
this._listMap.set(from, types);
|
588
|
-
}
|
589
|
-
|
590
|
-
let adjacent = types.get(type);
|
591
|
-
|
592
|
-
if (adjacent == null) {
|
593
|
-
adjacent = new Set();
|
594
|
-
types.set(type, adjacent);
|
595
|
-
}
|
596
|
-
|
597
|
-
adjacent.add(to);
|
598
|
-
}
|
599
|
-
|
600
|
-
removeEdge(from, to, type) {
|
601
|
-
var _this$_listMap$get4, _this$_listMap$get4$g;
|
602
|
-
|
603
|
-
(_this$_listMap$get4 = this._listMap.get(from)) === null || _this$_listMap$get4 === void 0 ? void 0 : (_this$_listMap$get4$g = _this$_listMap$get4.get(type)) === null || _this$_listMap$get4$g === void 0 ? void 0 : _this$_listMap$get4$g.delete(to);
|
604
|
-
}
|
605
|
-
|
606
433
|
}
|
package/lib/index.js
CHANGED
@@ -27,12 +27,6 @@ Object.defineProperty(exports, "ALL_EDGE_TYPES", {
|
|
27
27
|
return _Graph.ALL_EDGE_TYPES;
|
28
28
|
}
|
29
29
|
});
|
30
|
-
Object.defineProperty(exports, "GraphOpts", {
|
31
|
-
enumerable: true,
|
32
|
-
get: function () {
|
33
|
-
return _Graph.GraphOpts;
|
34
|
-
}
|
35
|
-
});
|
36
30
|
Object.defineProperty(exports, "mapVisitor", {
|
37
31
|
enumerable: true,
|
38
32
|
get: function () {
|
@@ -45,18 +39,14 @@ Object.defineProperty(exports, "ContentGraph", {
|
|
45
39
|
return _ContentGraph.default;
|
46
40
|
}
|
47
41
|
});
|
48
|
-
Object.defineProperty(exports, "SerializedContentGraph", {
|
49
|
-
enumerable: true,
|
50
|
-
get: function () {
|
51
|
-
return _ContentGraph.SerializedContentGraph;
|
52
|
-
}
|
53
|
-
});
|
54
42
|
|
55
43
|
var _types = require("./types");
|
56
44
|
|
57
45
|
var _Graph = _interopRequireWildcard(require("./Graph"));
|
58
46
|
|
59
|
-
var _ContentGraph =
|
47
|
+
var _ContentGraph = _interopRequireDefault(require("./ContentGraph"));
|
48
|
+
|
49
|
+
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
|
60
50
|
|
61
51
|
function _getRequireWildcardCache() { if (typeof WeakMap !== "function") return null; var cache = new WeakMap(); _getRequireWildcardCache = function () { return cache; }; return cache; }
|
62
52
|
|
package/package.json
CHANGED
@@ -1,6 +1,6 @@
|
|
1
1
|
{
|
2
2
|
"name": "@parcel/graph",
|
3
|
-
"version": "2.0.2-nightly.
|
3
|
+
"version": "2.0.2-nightly.2549+b9426b83",
|
4
4
|
"description": "Blazing fast, zero configuration web application bundler",
|
5
5
|
"license": "MIT",
|
6
6
|
"publishConfig": {
|
@@ -22,5 +22,5 @@
|
|
22
22
|
"dependencies": {
|
23
23
|
"nullthrows": "^1.1.1"
|
24
24
|
},
|
25
|
-
"gitHead": "
|
25
|
+
"gitHead": "b9426b83f86809143ff122bde3ee217fb64a8d78"
|
26
26
|
}
|