create-test-data.js
3.33 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
/* global window */
const fs = require('fs');
const path = require('path');
const baseDir = path.join(__dirname, '..');
const manifestsDir = path.join(baseDir, 'test', 'manifests');
const segmentsDir = path.join(baseDir, 'test', 'segments');
const base64ToUint8Array = function(base64) {
const decoded = window.atob(base64);
const uint8Array = new Uint8Array(new ArrayBuffer(decoded.length));
for (let i = 0; i < decoded.length; i++) {
uint8Array[i] = decoded.charCodeAt(i);
}
return uint8Array;
};
const getManifests = () => (fs.readdirSync(manifestsDir) || [])
.filter((f) => ((/\.(m3u8|mpd)/).test(path.extname(f))))
.map((f) => path.resolve(manifestsDir, f));
const getSegments = () => (fs.readdirSync(segmentsDir) || [])
.filter((f) => ((/\.(ts|mp4|key|webm|aac|ac3)/).test(path.extname(f))))
.map((f) => path.resolve(segmentsDir, f));
const buildManifestString = function() {
let manifests = 'export default {\n';
getManifests().forEach((file) => {
// translate this manifest
manifests += ' \'' + path.basename(file, path.extname(file)) + '\': ';
manifests += fs.readFileSync(file, 'utf8')
.split(/\r\n|\n/)
// quote and concatenate
.map((line) => ' \'' + line + '\\n\' +\n')
.join('')
// strip leading spaces and the trailing '+'
.slice(4, -3);
manifests += ',\n';
});
// clean up and close the objects
manifests = manifests.slice(0, -2);
manifests += '\n};\n';
return manifests;
};
const buildSegmentString = function() {
const segmentData = {};
getSegments().forEach((file) => {
// read the file directly as a buffer before converting to base64
const base64Segment = fs.readFileSync(file).toString('base64');
segmentData[path.basename(file, path.extname(file))] = base64Segment;
});
const segmentDataExportStrings = Object.keys(segmentData).reduce((acc, key) => {
// use a function since the segment may be cleared out on usage
acc.push(`export const ${key} = () => {
cache.${key} = cache.${key} || base64ToUint8Array('${segmentData[key]}');
const dest = new Uint8Array(cache.${key}.byteLength);
dest.set(cache.${key});
return dest;
};`);
return acc;
}, []);
const segmentsFile =
'const cache = {};\n' +
`const base64ToUint8Array = ${base64ToUint8Array.toString()};\n` +
segmentDataExportStrings.join('\n');
return segmentsFile;
};
/* we refer to them as .js, so that babel and other plugins can work on them */
const segmentsKey = 'create-test-data!segments.js';
const manifestsKey = 'create-test-data!manifests.js';
module.exports = function() {
return {
name: 'createTestData',
buildStart() {
this.addWatchFile(segmentsDir);
this.addWatchFile(manifestsDir);
[].concat(getSegments())
.concat(getManifests())
.forEach((file) => this.addWatchFile(file));
},
resolveId(importee, importer) {
// if this is not an id we can resolve return
if (importee.indexOf('create-test-data!') !== 0) {
return;
}
const name = importee.split('!')[1];
return (name.indexOf('segments') === 0) ? segmentsKey : manifestsKey;
},
load(id) {
if (id === segmentsKey) {
return buildSegmentString.call(this);
}
if (id === manifestsKey) {
return buildManifestString.call(this);
}
}
};
};