@gmod/bbi 2.0.4 → 2.0.5
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/CHANGELOG.md +6 -0
- package/README.md +1 -1
- package/dist/bbi.js +157 -266
- package/dist/bbi.js.map +1 -1
- package/dist/bigbed.js +146 -259
- package/dist/bigbed.js.map +1 -1
- package/dist/bigint-polyfill/polyfill.js +1 -1
- package/dist/bigint-polyfill/polyfill.js.map +1 -1
- package/dist/bigint-polyfill/pure.js +11 -11
- package/dist/bigint-polyfill/pure.js.map +1 -1
- package/dist/bigwig.js +21 -75
- package/dist/bigwig.js.map +1 -1
- package/dist/blockView.js +207 -302
- package/dist/blockView.js.map +1 -1
- package/dist/range.js +49 -50
- package/dist/range.js.map +1 -1
- package/dist/unzip-pako.js +1 -1
- package/dist/unzip-pako.js.map +1 -1
- package/dist/unzip.js +1 -1
- package/dist/unzip.js.map +1 -1
- package/dist/util.js +14 -66
- package/dist/util.js.map +1 -1
- package/package.json +2 -2
package/dist/blockView.js
CHANGED
|
@@ -1,15 +1,4 @@
|
|
|
1
1
|
"use strict";
|
|
2
|
-
var __assign = (this && this.__assign) || function () {
|
|
3
|
-
__assign = Object.assign || function(t) {
|
|
4
|
-
for (var s, i = 1, n = arguments.length; i < n; i++) {
|
|
5
|
-
s = arguments[i];
|
|
6
|
-
for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p))
|
|
7
|
-
t[p] = s[p];
|
|
8
|
-
}
|
|
9
|
-
return t;
|
|
10
|
-
};
|
|
11
|
-
return __assign.apply(this, arguments);
|
|
12
|
-
};
|
|
13
2
|
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
|
|
14
3
|
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
|
|
15
4
|
return new (P || (P = Promise))(function (resolve, reject) {
|
|
@@ -19,55 +8,27 @@ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, ge
|
|
|
19
8
|
step((generator = generator.apply(thisArg, _arguments || [])).next());
|
|
20
9
|
});
|
|
21
10
|
};
|
|
22
|
-
var __generator = (this && this.__generator) || function (thisArg, body) {
|
|
23
|
-
var _ = { label: 0, sent: function() { if (t[0] & 1) throw t[1]; return t[1]; }, trys: [], ops: [] }, f, y, t, g;
|
|
24
|
-
return g = { next: verb(0), "throw": verb(1), "return": verb(2) }, typeof Symbol === "function" && (g[Symbol.iterator] = function() { return this; }), g;
|
|
25
|
-
function verb(n) { return function (v) { return step([n, v]); }; }
|
|
26
|
-
function step(op) {
|
|
27
|
-
if (f) throw new TypeError("Generator is already executing.");
|
|
28
|
-
while (_) try {
|
|
29
|
-
if (f = 1, y && (t = op[0] & 2 ? y["return"] : op[0] ? y["throw"] || ((t = y["return"]) && t.call(y), 0) : y.next) && !(t = t.call(y, op[1])).done) return t;
|
|
30
|
-
if (y = 0, t) op = [op[0] & 2, t.value];
|
|
31
|
-
switch (op[0]) {
|
|
32
|
-
case 0: case 1: t = op; break;
|
|
33
|
-
case 4: _.label++; return { value: op[1], done: false };
|
|
34
|
-
case 5: _.label++; y = op[1]; op = [0]; continue;
|
|
35
|
-
case 7: op = _.ops.pop(); _.trys.pop(); continue;
|
|
36
|
-
default:
|
|
37
|
-
if (!(t = _.trys, t = t.length > 0 && t[t.length - 1]) && (op[0] === 6 || op[0] === 2)) { _ = 0; continue; }
|
|
38
|
-
if (op[0] === 3 && (!t || (op[1] > t[0] && op[1] < t[3]))) { _.label = op[1]; break; }
|
|
39
|
-
if (op[0] === 6 && _.label < t[1]) { _.label = t[1]; t = op; break; }
|
|
40
|
-
if (t && _.label < t[2]) { _.label = t[2]; _.ops.push(op); break; }
|
|
41
|
-
if (t[2]) _.ops.pop();
|
|
42
|
-
_.trys.pop(); continue;
|
|
43
|
-
}
|
|
44
|
-
op = body.call(thisArg, _);
|
|
45
|
-
} catch (e) { op = [6, e]; y = 0; } finally { f = t = 0; }
|
|
46
|
-
if (op[0] & 5) throw op[1]; return { value: op[0] ? op[1] : void 0, done: true };
|
|
47
|
-
}
|
|
48
|
-
};
|
|
49
11
|
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
50
12
|
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
51
13
|
};
|
|
52
14
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
53
15
|
exports.BlockView = void 0;
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
16
|
+
const binary_parser_1 = require("binary-parser");
|
|
17
|
+
const abortable_promise_cache_1 = __importDefault(require("abortable-promise-cache"));
|
|
18
|
+
const quick_lru_1 = __importDefault(require("quick-lru"));
|
|
57
19
|
// locals
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
20
|
+
const range_1 = __importDefault(require("./range"));
|
|
21
|
+
const unzip_1 = require("./unzip");
|
|
22
|
+
const util_1 = require("./util");
|
|
23
|
+
const BIG_WIG_TYPE_GRAPH = 1;
|
|
24
|
+
const BIG_WIG_TYPE_VSTEP = 2;
|
|
25
|
+
const BIG_WIG_TYPE_FSTEP = 3;
|
|
64
26
|
function coordFilter(s1, e1, s2, e2) {
|
|
65
27
|
return s1 < e2 && e1 >= s2;
|
|
66
28
|
}
|
|
67
29
|
function getParsers(isBigEndian) {
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
var summaryParser = new binary_parser_1.Parser()
|
|
30
|
+
const le = isBigEndian ? 'big' : 'little';
|
|
31
|
+
const summaryParser = new binary_parser_1.Parser()
|
|
71
32
|
.endianess(le)
|
|
72
33
|
.uint32('chromId')
|
|
73
34
|
.uint32('start')
|
|
@@ -78,7 +39,7 @@ function getParsers(isBigEndian) {
|
|
|
78
39
|
.floatle('sumData')
|
|
79
40
|
.floatle('sumSqData')
|
|
80
41
|
.saveOffset('offset');
|
|
81
|
-
|
|
42
|
+
const leafParser = new binary_parser_1.Parser()
|
|
82
43
|
.endianess(le)
|
|
83
44
|
.uint8('isLeaf')
|
|
84
45
|
.skip(1)
|
|
@@ -111,7 +72,7 @@ function getParsers(isBigEndian) {
|
|
|
111
72
|
}),
|
|
112
73
|
},
|
|
113
74
|
});
|
|
114
|
-
|
|
75
|
+
const bigBedParser = new binary_parser_1.Parser()
|
|
115
76
|
.endianess(le)
|
|
116
77
|
.uint32('chromId')
|
|
117
78
|
.int32('start')
|
|
@@ -120,7 +81,7 @@ function getParsers(isBigEndian) {
|
|
|
120
81
|
zeroTerminated: true,
|
|
121
82
|
})
|
|
122
83
|
.saveOffset('offset');
|
|
123
|
-
|
|
84
|
+
const bigWigParser = new binary_parser_1.Parser()
|
|
124
85
|
.endianess(le)
|
|
125
86
|
.skip(4)
|
|
126
87
|
.int32('blockStart')
|
|
@@ -132,16 +93,16 @@ function getParsers(isBigEndian) {
|
|
|
132
93
|
.uint16('itemCount')
|
|
133
94
|
.choice({
|
|
134
95
|
tag: 'blockType',
|
|
135
|
-
choices:
|
|
136
|
-
|
|
96
|
+
choices: {
|
|
97
|
+
[BIG_WIG_TYPE_FSTEP]: new binary_parser_1.Parser().array('items', {
|
|
137
98
|
length: 'itemCount',
|
|
138
99
|
type: new binary_parser_1.Parser().floatle('score'),
|
|
139
100
|
}),
|
|
140
|
-
|
|
101
|
+
[BIG_WIG_TYPE_VSTEP]: new binary_parser_1.Parser().array('items', {
|
|
141
102
|
length: 'itemCount',
|
|
142
103
|
type: new binary_parser_1.Parser().endianess(le).int32('start').floatle('score'),
|
|
143
104
|
}),
|
|
144
|
-
|
|
105
|
+
[BIG_WIG_TYPE_GRAPH]: new binary_parser_1.Parser().array('items', {
|
|
145
106
|
length: 'itemCount',
|
|
146
107
|
type: new binary_parser_1.Parser()
|
|
147
108
|
.endianess(le)
|
|
@@ -149,13 +110,13 @@ function getParsers(isBigEndian) {
|
|
|
149
110
|
.int32('end')
|
|
150
111
|
.floatle('score'),
|
|
151
112
|
}),
|
|
152
|
-
|
|
113
|
+
},
|
|
153
114
|
});
|
|
154
115
|
return {
|
|
155
|
-
bigWigParser
|
|
156
|
-
bigBedParser
|
|
157
|
-
summaryParser
|
|
158
|
-
leafParser
|
|
116
|
+
bigWigParser,
|
|
117
|
+
bigBedParser,
|
|
118
|
+
summaryParser,
|
|
119
|
+
leafParser,
|
|
159
120
|
};
|
|
160
121
|
}
|
|
161
122
|
/**
|
|
@@ -165,9 +126,8 @@ function getParsers(isBigEndian) {
|
|
|
165
126
|
* Explorer by Thomas Down.
|
|
166
127
|
* @constructs
|
|
167
128
|
*/
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
var _this = this;
|
|
129
|
+
class BlockView {
|
|
130
|
+
constructor(bbi, refsByName, cirTreeOffset, isBigEndian, isCompressed, blockType) {
|
|
171
131
|
this.bbi = bbi;
|
|
172
132
|
this.refsByName = refsByName;
|
|
173
133
|
this.cirTreeOffset = cirTreeOffset;
|
|
@@ -176,159 +136,131 @@ var BlockView = /** @class */ (function () {
|
|
|
176
136
|
this.blockType = blockType;
|
|
177
137
|
this.featureCache = new abortable_promise_cache_1.default({
|
|
178
138
|
cache: new quick_lru_1.default({ maxSize: 1000 }),
|
|
179
|
-
fill:
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
len = Number(requestData.length);
|
|
185
|
-
off = Number(requestData.offset);
|
|
186
|
-
return [4 /*yield*/, this.bbi.read(Buffer.alloc(len), 0, len, off, {
|
|
187
|
-
signal: signal,
|
|
188
|
-
})];
|
|
189
|
-
case 1:
|
|
190
|
-
buffer = (_a.sent()).buffer;
|
|
191
|
-
return [2 /*return*/, buffer];
|
|
192
|
-
}
|
|
139
|
+
fill: (requestData, signal) => __awaiter(this, void 0, void 0, function* () {
|
|
140
|
+
const len = Number(requestData.length);
|
|
141
|
+
const off = Number(requestData.offset);
|
|
142
|
+
const { buffer } = yield this.bbi.read(Buffer.alloc(len), 0, len, off, {
|
|
143
|
+
signal,
|
|
193
144
|
});
|
|
194
|
-
|
|
145
|
+
return buffer;
|
|
146
|
+
}),
|
|
195
147
|
});
|
|
196
148
|
if (!(cirTreeOffset >= 0)) {
|
|
197
149
|
throw new Error('invalid cirTreeOffset!');
|
|
198
150
|
}
|
|
199
|
-
|
|
151
|
+
const parsers = getParsers(isBigEndian);
|
|
200
152
|
this.leafParser = parsers.leafParser;
|
|
201
153
|
this.bigBedParser = parsers.bigBedParser;
|
|
202
154
|
}
|
|
203
|
-
|
|
204
|
-
return __awaiter(this, void 0, void 0, function () {
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
|
|
211
|
-
|
|
212
|
-
|
|
213
|
-
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
|
|
155
|
+
readWigData(chrName, start, end, observer, opts) {
|
|
156
|
+
return __awaiter(this, void 0, void 0, function* () {
|
|
157
|
+
try {
|
|
158
|
+
const { refsByName, bbi, cirTreeOffset, isBigEndian } = this;
|
|
159
|
+
const chrId = refsByName[chrName];
|
|
160
|
+
if (chrId === undefined) {
|
|
161
|
+
observer.complete();
|
|
162
|
+
}
|
|
163
|
+
const request = { chrId, start, end };
|
|
164
|
+
if (!this.cirTreePromise) {
|
|
165
|
+
this.cirTreePromise = bbi.read(Buffer.alloc(48), 0, 48, Number(cirTreeOffset), opts);
|
|
166
|
+
}
|
|
167
|
+
const { buffer } = yield this.cirTreePromise;
|
|
168
|
+
const cirBlockSize = isBigEndian
|
|
169
|
+
? buffer.readUInt32BE(4)
|
|
170
|
+
: buffer.readUInt32LE(4);
|
|
171
|
+
let blocksToFetch = [];
|
|
172
|
+
let outstanding = 0;
|
|
173
|
+
const cirFobRecur2 = (cirBlockData, offset, level) => {
|
|
174
|
+
try {
|
|
175
|
+
const data = cirBlockData.subarray(offset);
|
|
176
|
+
const p = this.leafParser.parse(data);
|
|
177
|
+
if (p.blocksToFetch) {
|
|
178
|
+
blocksToFetch = blocksToFetch.concat(p.blocksToFetch
|
|
179
|
+
.filter(filterFeats)
|
|
180
|
+
.map((l) => ({
|
|
181
|
+
offset: l.blockOffset,
|
|
182
|
+
length: l.blockSize,
|
|
183
|
+
})));
|
|
219
184
|
}
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
blocksToFetch_1 = [];
|
|
227
|
-
outstanding_1 = 0;
|
|
228
|
-
cirFobRecur2_1 = function (cirBlockData, offset, level) {
|
|
229
|
-
try {
|
|
230
|
-
var data = cirBlockData.subarray(offset);
|
|
231
|
-
var p = _this.leafParser.parse(data);
|
|
232
|
-
if (p.blocksToFetch) {
|
|
233
|
-
blocksToFetch_1 = blocksToFetch_1.concat(p.blocksToFetch
|
|
234
|
-
.filter(filterFeats_1)
|
|
235
|
-
.map(function (l) { return ({
|
|
236
|
-
offset: l.blockOffset,
|
|
237
|
-
length: l.blockSize,
|
|
238
|
-
}); }));
|
|
239
|
-
}
|
|
240
|
-
if (p.recurOffsets) {
|
|
241
|
-
var recurOffsets = p.recurOffsets
|
|
242
|
-
.filter(filterFeats_1)
|
|
243
|
-
.map(function (l) { return Number(l.blockOffset); });
|
|
244
|
-
if (recurOffsets.length > 0) {
|
|
245
|
-
cirFobRecur_1(recurOffsets, level + 1);
|
|
246
|
-
}
|
|
247
|
-
}
|
|
185
|
+
if (p.recurOffsets) {
|
|
186
|
+
const recurOffsets = p.recurOffsets
|
|
187
|
+
.filter(filterFeats)
|
|
188
|
+
.map(l => Number(l.blockOffset));
|
|
189
|
+
if (recurOffsets.length > 0) {
|
|
190
|
+
cirFobRecur(recurOffsets, level + 1);
|
|
248
191
|
}
|
|
249
|
-
|
|
250
|
-
|
|
251
|
-
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
|
|
270
|
-
|
|
271
|
-
cirFobRecur2_1(resultBuffer, off[i] - offset, level);
|
|
272
|
-
outstanding_1 -= 1;
|
|
273
|
-
if (outstanding_1 === 0) {
|
|
274
|
-
this.readFeatures(observer, blocksToFetch_1, __assign(__assign({}, opts), { request: request_1 }));
|
|
275
|
-
}
|
|
276
|
-
}
|
|
277
|
-
}
|
|
278
|
-
return [3 /*break*/, 3];
|
|
279
|
-
case 2:
|
|
280
|
-
e_2 = _a.sent();
|
|
281
|
-
observer.error(e_2);
|
|
282
|
-
return [3 /*break*/, 3];
|
|
283
|
-
case 3: return [2 /*return*/];
|
|
284
|
-
}
|
|
285
|
-
});
|
|
286
|
-
}); };
|
|
287
|
-
cirFobRecur_1 = function (offset, level) {
|
|
288
|
-
try {
|
|
289
|
-
outstanding_1 += offset.length;
|
|
290
|
-
var maxCirBlockSpan = 4 + Number(cirBlockSize_1) * 32; // Upper bound on size, based on a completely full leaf node.
|
|
291
|
-
var spans = new range_1.default(offset[0], offset[0] + maxCirBlockSpan);
|
|
292
|
-
for (var i = 1; i < offset.length; i += 1) {
|
|
293
|
-
var blockSpan = new range_1.default(offset[i], offset[i] + maxCirBlockSpan);
|
|
294
|
-
spans = spans.union(blockSpan);
|
|
192
|
+
}
|
|
193
|
+
}
|
|
194
|
+
catch (e) {
|
|
195
|
+
observer.error(e);
|
|
196
|
+
}
|
|
197
|
+
};
|
|
198
|
+
const filterFeats = (b) => {
|
|
199
|
+
const { startChrom, startBase, endChrom, endBase } = b;
|
|
200
|
+
return ((startChrom < chrId || (startChrom === chrId && startBase <= end)) &&
|
|
201
|
+
(endChrom > chrId || (endChrom === chrId && endBase >= start)));
|
|
202
|
+
};
|
|
203
|
+
const cirFobStartFetch = (off, fr, level) => __awaiter(this, void 0, void 0, function* () {
|
|
204
|
+
try {
|
|
205
|
+
const length = fr.max() - fr.min();
|
|
206
|
+
const offset = fr.min();
|
|
207
|
+
const resultBuffer = yield this.featureCache.get(`${length}_${offset}`, { length, offset }, opts.signal);
|
|
208
|
+
for (let i = 0; i < off.length; i += 1) {
|
|
209
|
+
if (fr.contains(off[i])) {
|
|
210
|
+
cirFobRecur2(resultBuffer, off[i] - offset, level);
|
|
211
|
+
outstanding -= 1;
|
|
212
|
+
if (outstanding === 0) {
|
|
213
|
+
this.readFeatures(observer, blocksToFetch, Object.assign(Object.assign({}, opts), { request }));
|
|
295
214
|
}
|
|
296
|
-
spans.getRanges().map(function (fr) { return cirFobStartFetch_1(offset, fr, level); });
|
|
297
|
-
}
|
|
298
|
-
catch (e) {
|
|
299
|
-
observer.error(e);
|
|
300
215
|
}
|
|
301
|
-
}
|
|
302
|
-
|
|
303
|
-
|
|
304
|
-
|
|
305
|
-
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
|
|
309
|
-
|
|
216
|
+
}
|
|
217
|
+
}
|
|
218
|
+
catch (e) {
|
|
219
|
+
observer.error(e);
|
|
220
|
+
}
|
|
221
|
+
});
|
|
222
|
+
const cirFobRecur = (offset, level) => {
|
|
223
|
+
try {
|
|
224
|
+
outstanding += offset.length;
|
|
225
|
+
const maxCirBlockSpan = 4 + Number(cirBlockSize) * 32; // Upper bound on size, based on a completely full leaf node.
|
|
226
|
+
let spans = new range_1.default(offset[0], offset[0] + maxCirBlockSpan);
|
|
227
|
+
for (let i = 1; i < offset.length; i += 1) {
|
|
228
|
+
const blockSpan = new range_1.default(offset[i], offset[i] + maxCirBlockSpan);
|
|
229
|
+
spans = spans.union(blockSpan);
|
|
230
|
+
}
|
|
231
|
+
spans.getRanges().map(fr => cirFobStartFetch(offset, fr, level));
|
|
232
|
+
}
|
|
233
|
+
catch (e) {
|
|
234
|
+
observer.error(e);
|
|
235
|
+
}
|
|
236
|
+
};
|
|
237
|
+
return cirFobRecur([Number(cirTreeOffset) + 48], 1);
|
|
238
|
+
}
|
|
239
|
+
catch (e) {
|
|
240
|
+
observer.error(e);
|
|
241
|
+
}
|
|
310
242
|
});
|
|
311
|
-
}
|
|
312
|
-
|
|
313
|
-
|
|
314
|
-
|
|
315
|
-
|
|
243
|
+
}
|
|
244
|
+
parseSummaryBlock(buffer, startOffset, request) {
|
|
245
|
+
const features = [];
|
|
246
|
+
let offset = startOffset;
|
|
247
|
+
const dataView = new DataView(buffer.buffer, buffer.byteOffset, buffer.length);
|
|
316
248
|
while (offset < buffer.byteLength) {
|
|
317
249
|
// this was extracted from looking at the runtime code generated by
|
|
318
250
|
// binary-parser
|
|
319
|
-
|
|
251
|
+
const chromId = dataView.getUint32(offset, true);
|
|
320
252
|
offset += 4;
|
|
321
|
-
|
|
253
|
+
const start = dataView.getUint32(offset, true);
|
|
322
254
|
offset += 4;
|
|
323
|
-
|
|
255
|
+
const end = dataView.getUint32(offset, true);
|
|
324
256
|
offset += 4;
|
|
325
|
-
|
|
257
|
+
const validCnt = dataView.getUint32(offset, true);
|
|
326
258
|
offset += 4;
|
|
327
|
-
|
|
259
|
+
const minScore = dataView.getFloat32(offset, true);
|
|
328
260
|
offset += 4;
|
|
329
|
-
|
|
261
|
+
const maxScore = dataView.getFloat32(offset, true);
|
|
330
262
|
offset += 4;
|
|
331
|
-
|
|
263
|
+
const sumData = dataView.getFloat32(offset, true);
|
|
332
264
|
offset += 4;
|
|
333
265
|
// unused
|
|
334
266
|
// const sumSqData = dataView.getFloat32(offset, true)
|
|
@@ -338,148 +270,121 @@ var BlockView = /** @class */ (function () {
|
|
|
338
270
|
coordFilter(start, end, request.start, request.end)
|
|
339
271
|
: true) {
|
|
340
272
|
features.push({
|
|
341
|
-
start
|
|
342
|
-
end
|
|
343
|
-
maxScore
|
|
344
|
-
minScore
|
|
273
|
+
start,
|
|
274
|
+
end,
|
|
275
|
+
maxScore,
|
|
276
|
+
minScore,
|
|
345
277
|
summary: true,
|
|
346
278
|
score: sumData / (validCnt || 1),
|
|
347
279
|
});
|
|
348
280
|
}
|
|
349
281
|
}
|
|
350
282
|
return features;
|
|
351
|
-
}
|
|
352
|
-
|
|
353
|
-
|
|
354
|
-
|
|
283
|
+
}
|
|
284
|
+
parseBigBedBlock(data, startOffset, offset, request) {
|
|
285
|
+
const items = [];
|
|
286
|
+
let currOffset = startOffset;
|
|
355
287
|
while (currOffset < data.byteLength) {
|
|
356
|
-
|
|
357
|
-
items.push(
|
|
288
|
+
const res = this.bigBedParser.parse(data.subarray(currOffset));
|
|
289
|
+
items.push(Object.assign(Object.assign({}, res), { uniqueId: `bb-${offset + currOffset}` }));
|
|
358
290
|
currOffset += res.offset;
|
|
359
291
|
}
|
|
360
292
|
return request
|
|
361
|
-
? items.filter(
|
|
362
|
-
return coordFilter(f.start, f.end, request.start, request.end);
|
|
363
|
-
})
|
|
293
|
+
? items.filter((f) => coordFilter(f.start, f.end, request.start, request.end))
|
|
364
294
|
: items;
|
|
365
|
-
}
|
|
366
|
-
|
|
367
|
-
|
|
368
|
-
|
|
369
|
-
|
|
295
|
+
}
|
|
296
|
+
parseBigWigBlock(buffer, startOffset, request) {
|
|
297
|
+
const b = buffer.subarray(startOffset);
|
|
298
|
+
const dataView = new DataView(b.buffer, b.byteOffset, b.length);
|
|
299
|
+
let offset = 0;
|
|
370
300
|
offset += 4;
|
|
371
|
-
|
|
301
|
+
const blockStart = dataView.getInt32(offset, true);
|
|
372
302
|
offset += 8;
|
|
373
|
-
|
|
303
|
+
const itemStep = dataView.getUint32(offset, true);
|
|
374
304
|
offset += 4;
|
|
375
|
-
|
|
305
|
+
const itemSpan = dataView.getUint32(offset, true);
|
|
376
306
|
offset += 4;
|
|
377
|
-
|
|
307
|
+
const blockType = dataView.getUint8(offset);
|
|
378
308
|
offset += 2;
|
|
379
|
-
|
|
309
|
+
const itemCount = dataView.getUint16(offset, true);
|
|
380
310
|
offset += 2;
|
|
381
|
-
|
|
311
|
+
const items = new Array(itemCount);
|
|
382
312
|
switch (blockType) {
|
|
383
313
|
case 1:
|
|
384
|
-
for (
|
|
385
|
-
|
|
314
|
+
for (let i = 0; i < itemCount; i++) {
|
|
315
|
+
const start = dataView.getInt32(offset, true);
|
|
386
316
|
offset += 4;
|
|
387
|
-
|
|
317
|
+
const end = dataView.getInt32(offset, true);
|
|
388
318
|
offset += 4;
|
|
389
|
-
|
|
319
|
+
const score = dataView.getFloat32(offset, true);
|
|
390
320
|
offset += 4;
|
|
391
|
-
items[i] = { start
|
|
321
|
+
items[i] = { start, end, score };
|
|
392
322
|
}
|
|
393
323
|
break;
|
|
394
324
|
case 2:
|
|
395
|
-
for (
|
|
396
|
-
|
|
325
|
+
for (let i = 0; i < itemCount; i++) {
|
|
326
|
+
const start = dataView.getInt32(offset, true);
|
|
397
327
|
offset += 4;
|
|
398
|
-
|
|
328
|
+
const score = dataView.getFloat32(offset, true);
|
|
399
329
|
offset += 4;
|
|
400
|
-
items[i] = { score
|
|
330
|
+
items[i] = { score, start, end: start + itemSpan };
|
|
401
331
|
}
|
|
402
332
|
break;
|
|
403
333
|
case 3:
|
|
404
|
-
for (
|
|
405
|
-
|
|
334
|
+
for (let i = 0; i < itemCount; i++) {
|
|
335
|
+
const score = dataView.getFloat32(offset, true);
|
|
406
336
|
offset += 4;
|
|
407
|
-
|
|
408
|
-
items[i] = { score
|
|
337
|
+
const start = blockStart + i * itemStep;
|
|
338
|
+
items[i] = { score, start, end: start + itemSpan };
|
|
409
339
|
}
|
|
410
340
|
break;
|
|
411
341
|
}
|
|
412
342
|
return request
|
|
413
|
-
? items.filter(
|
|
414
|
-
return coordFilter(f.start, f.end, request.start, request.end);
|
|
415
|
-
})
|
|
343
|
+
? items.filter((f) => coordFilter(f.start, f.end, request.start, request.end))
|
|
416
344
|
: items;
|
|
417
|
-
}
|
|
418
|
-
|
|
419
|
-
|
|
420
|
-
|
|
421
|
-
|
|
422
|
-
|
|
423
|
-
|
|
424
|
-
|
|
425
|
-
|
|
426
|
-
|
|
427
|
-
|
|
428
|
-
|
|
429
|
-
|
|
430
|
-
(0, util_1.checkAbortSignal)(
|
|
431
|
-
|
|
432
|
-
|
|
433
|
-
|
|
434
|
-
|
|
435
|
-
|
|
436
|
-
|
|
437
|
-
|
|
438
|
-
|
|
439
|
-
|
|
440
|
-
|
|
441
|
-
|
|
442
|
-
|
|
443
|
-
|
|
444
|
-
|
|
445
|
-
|
|
446
|
-
|
|
447
|
-
|
|
448
|
-
|
|
449
|
-
|
|
450
|
-
|
|
451
|
-
|
|
452
|
-
|
|
453
|
-
|
|
454
|
-
|
|
455
|
-
|
|
456
|
-
|
|
457
|
-
|
|
458
|
-
case 'bigbed':
|
|
459
|
-
observer.next(_this.parseBigBedBlock(resultData, blockOffset, Number(block.offset) * (1 << 8), request_2));
|
|
460
|
-
break;
|
|
461
|
-
default:
|
|
462
|
-
console.warn("Don't know what to do with ".concat(blockType_1));
|
|
463
|
-
}
|
|
464
|
-
});
|
|
465
|
-
return [2 /*return*/];
|
|
466
|
-
}
|
|
467
|
-
});
|
|
468
|
-
}); }))];
|
|
469
|
-
case 1:
|
|
470
|
-
_b.sent();
|
|
471
|
-
observer.complete();
|
|
472
|
-
return [3 /*break*/, 3];
|
|
473
|
-
case 2:
|
|
474
|
-
e_3 = _b.sent();
|
|
475
|
-
observer.error(e_3);
|
|
476
|
-
return [3 /*break*/, 3];
|
|
477
|
-
case 3: return [2 /*return*/];
|
|
478
|
-
}
|
|
479
|
-
});
|
|
345
|
+
}
|
|
346
|
+
readFeatures(observer, blocks, opts = {}) {
|
|
347
|
+
return __awaiter(this, void 0, void 0, function* () {
|
|
348
|
+
try {
|
|
349
|
+
const { blockType, isCompressed } = this;
|
|
350
|
+
const { signal, request } = opts;
|
|
351
|
+
const blockGroupsToFetch = (0, util_1.groupBlocks)(blocks);
|
|
352
|
+
(0, util_1.checkAbortSignal)(signal);
|
|
353
|
+
yield Promise.all(blockGroupsToFetch.map((blockGroup) => __awaiter(this, void 0, void 0, function* () {
|
|
354
|
+
(0, util_1.checkAbortSignal)(signal);
|
|
355
|
+
const { length, offset } = blockGroup;
|
|
356
|
+
const data = yield this.featureCache.get(`${length}_${offset}`, blockGroup, signal);
|
|
357
|
+
blockGroup.blocks.forEach(block => {
|
|
358
|
+
(0, util_1.checkAbortSignal)(signal);
|
|
359
|
+
let blockOffset = Number(block.offset) - Number(blockGroup.offset);
|
|
360
|
+
let resultData = data;
|
|
361
|
+
if (isCompressed) {
|
|
362
|
+
resultData = (0, unzip_1.unzip)(data.subarray(blockOffset));
|
|
363
|
+
blockOffset = 0;
|
|
364
|
+
}
|
|
365
|
+
(0, util_1.checkAbortSignal)(signal);
|
|
366
|
+
switch (blockType) {
|
|
367
|
+
case 'summary':
|
|
368
|
+
observer.next(this.parseSummaryBlock(resultData, blockOffset, request));
|
|
369
|
+
break;
|
|
370
|
+
case 'bigwig':
|
|
371
|
+
observer.next(this.parseBigWigBlock(resultData, blockOffset, request));
|
|
372
|
+
break;
|
|
373
|
+
case 'bigbed':
|
|
374
|
+
observer.next(this.parseBigBedBlock(resultData, blockOffset, Number(block.offset) * (1 << 8), request));
|
|
375
|
+
break;
|
|
376
|
+
default:
|
|
377
|
+
console.warn(`Don't know what to do with ${blockType}`);
|
|
378
|
+
}
|
|
379
|
+
});
|
|
380
|
+
})));
|
|
381
|
+
observer.complete();
|
|
382
|
+
}
|
|
383
|
+
catch (e) {
|
|
384
|
+
observer.error(e);
|
|
385
|
+
}
|
|
480
386
|
});
|
|
481
|
-
}
|
|
482
|
-
|
|
483
|
-
}());
|
|
387
|
+
}
|
|
388
|
+
}
|
|
484
389
|
exports.BlockView = BlockView;
|
|
485
390
|
//# sourceMappingURL=blockView.js.map
|