eyevinn-channel-engine 4.3.6 → 4.3.7
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/engine/preflight.d.ts +1 -0
- package/dist/engine/preflight.js +43 -0
- package/dist/engine/server.d.ts +2 -0
- package/dist/engine/server.js +15 -24
- package/dist/examples/default.js +2 -1
- package/dist/package.json +1 -1
- package/engine/preflight.js +44 -0
- package/engine/server.ts +18 -18
- package/examples/default.ts +2 -1
- package/package.json +1 -1
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export function handler(req: any, res: any, next: any): any;
|
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
var constants = {
|
|
2
|
+
ALLOW_HEADERS: [
|
|
3
|
+
'accept',
|
|
4
|
+
'accept-version',
|
|
5
|
+
'content-type',
|
|
6
|
+
'request-id',
|
|
7
|
+
'origin',
|
|
8
|
+
'x-api-version',
|
|
9
|
+
'x-request-id',
|
|
10
|
+
'x-requested-with'
|
|
11
|
+
],
|
|
12
|
+
EXPOSE_HEADERS: [
|
|
13
|
+
'api-version',
|
|
14
|
+
'content-length',
|
|
15
|
+
'content-md5',
|
|
16
|
+
'content-type',
|
|
17
|
+
'date',
|
|
18
|
+
'request-id',
|
|
19
|
+
'response-time'
|
|
20
|
+
],
|
|
21
|
+
AC_REQ_METHOD: 'access-control-request-method',
|
|
22
|
+
AC_REQ_HEADERS: 'access-control-request-headers',
|
|
23
|
+
AC_ALLOW_CREDS: 'access-control-allow-credentials',
|
|
24
|
+
AC_ALLOW_ORIGIN: 'access-control-allow-origin',
|
|
25
|
+
AC_ALLOW_HEADERS: 'access-control-allow-headers',
|
|
26
|
+
AC_ALLOW_METHODS: 'access-control-allow-methods',
|
|
27
|
+
AC_EXPOSE_HEADERS: 'access-control-expose-headers',
|
|
28
|
+
AC_MAX_AGE: 'access-control-max-age',
|
|
29
|
+
STR_VARY: 'vary',
|
|
30
|
+
STR_ORIGIN: 'origin',
|
|
31
|
+
HTTP_NO_CONTENT: 204
|
|
32
|
+
};
|
|
33
|
+
exports.handler = function (req, res, next) {
|
|
34
|
+
if (req.method !== 'OPTIONS')
|
|
35
|
+
return next();
|
|
36
|
+
res.once('header', function () {
|
|
37
|
+
res.header(constants.AC_ALLOW_ORIGIN, '*');
|
|
38
|
+
res.header(constants.AC_ALLOW_CREDS, true);
|
|
39
|
+
res.header(constants.AC_ALLOW_METHODS, ['GET', 'OPTIONS']);
|
|
40
|
+
res.header(constants.AC_ALLOW_HEADERS, ['x-health-key']);
|
|
41
|
+
});
|
|
42
|
+
res.send(constants.HTTP_NO_CONTENT);
|
|
43
|
+
};
|
package/dist/engine/server.d.ts
CHANGED
|
@@ -33,6 +33,7 @@ export interface ChannelEngineOpts {
|
|
|
33
33
|
sessionResetKey?: string;
|
|
34
34
|
keepAliveTimeout?: number;
|
|
35
35
|
sessionEventStream?: boolean;
|
|
36
|
+
sessionHealthKey?: string;
|
|
36
37
|
}
|
|
37
38
|
export interface VodRequest {
|
|
38
39
|
sessionId: string;
|
|
@@ -153,6 +154,7 @@ export declare class ChannelEngine {
|
|
|
153
154
|
private autoCreateSession;
|
|
154
155
|
private sessionResetKey;
|
|
155
156
|
private sessionEventStream;
|
|
157
|
+
private sessionHealthKey;
|
|
156
158
|
constructor(assetMgr: IAssetManager, options?: ChannelEngineOpts);
|
|
157
159
|
updateStreamSwitchAsync(): Promise<void>;
|
|
158
160
|
updateChannelsAsync(channelMgr: any, options: any): Promise<void>;
|
package/dist/engine/server.js
CHANGED
|
@@ -52,6 +52,7 @@ var SessionStateStore = require('./session_state.js').SessionStateStore;
|
|
|
52
52
|
var SessionLiveStateStore = require('./session_live_state.js').SessionLiveStateStore;
|
|
53
53
|
var PlayheadStateStore = require('./playhead_state.js').PlayheadStateStore;
|
|
54
54
|
var _a = require('./util.js'), filterQueryParser = _a.filterQueryParser, toHHMMSS = _a.toHHMMSS, WaitTimeGenerator = _a.WaitTimeGenerator;
|
|
55
|
+
var preflight = require('./preflight.js');
|
|
55
56
|
var version = require('../package.json').version;
|
|
56
57
|
var AUTO_CREATE_CHANNEL_TIMEOUT = 3000;
|
|
57
58
|
var sessions = {}; // Should be a persistent store...
|
|
@@ -73,6 +74,7 @@ var ChannelEngine = /** @class */ (function () {
|
|
|
73
74
|
this.autoCreateSession = false;
|
|
74
75
|
this.sessionResetKey = "";
|
|
75
76
|
this.sessionEventStream = false;
|
|
77
|
+
this.sessionHealthKey = "";
|
|
76
78
|
this.options = options;
|
|
77
79
|
if (options && options.adCopyMgrUri) {
|
|
78
80
|
this.adCopyMgrUri = options.adCopyMgrUri;
|
|
@@ -92,6 +94,9 @@ var ChannelEngine = /** @class */ (function () {
|
|
|
92
94
|
if (options && options.sessionResetKey) {
|
|
93
95
|
this.sessionResetKey = options.sessionResetKey;
|
|
94
96
|
}
|
|
97
|
+
if (options && options.sessionHealthKey) {
|
|
98
|
+
this.sessionHealthKey = options.sessionHealthKey;
|
|
99
|
+
}
|
|
95
100
|
this.alwaysNewSegments = false;
|
|
96
101
|
if (options && options.alwaysNewSegments) {
|
|
97
102
|
this.alwaysNewSegments = true;
|
|
@@ -245,30 +250,7 @@ var ChannelEngine = /** @class */ (function () {
|
|
|
245
250
|
}
|
|
246
251
|
});
|
|
247
252
|
}); });
|
|
248
|
-
this.server.
|
|
249
|
-
return __generator(this, function (_a) {
|
|
250
|
-
res.sendRaw(204, "", {
|
|
251
|
-
headers: {
|
|
252
|
-
"Access-Control-Allow-Origin": "*",
|
|
253
|
-
"Access-Control-Allow-Methods": "GET, OPTIONS",
|
|
254
|
-
},
|
|
255
|
-
});
|
|
256
|
-
next();
|
|
257
|
-
return [2 /*return*/];
|
|
258
|
-
});
|
|
259
|
-
}); });
|
|
260
|
-
this.server.opts('/channels/:channelId/:file', function (req, res, next) { return __awaiter(_this, void 0, void 0, function () {
|
|
261
|
-
return __generator(this, function (_a) {
|
|
262
|
-
res.sendRaw(204, "", {
|
|
263
|
-
headers: {
|
|
264
|
-
"Access-Control-Allow-Origin": "*",
|
|
265
|
-
"Access-Control-Allow-Methods": "GET, OPTIONS",
|
|
266
|
-
},
|
|
267
|
-
});
|
|
268
|
-
next();
|
|
269
|
-
return [2 /*return*/];
|
|
270
|
-
});
|
|
271
|
-
}); });
|
|
253
|
+
this.server.pre(preflight.handler);
|
|
272
254
|
this.server.get('/eventstream/:sessionId', this._handleEventStream.bind(this));
|
|
273
255
|
this.server.get('/status/:sessionId', this._handleStatus.bind(this));
|
|
274
256
|
this.server.get('/health', this._handleAggregatedSessionHealth.bind(this));
|
|
@@ -1203,6 +1185,15 @@ var ChannelEngine = /** @class */ (function () {
|
|
|
1203
1185
|
switch (_b.label) {
|
|
1204
1186
|
case 0:
|
|
1205
1187
|
debug("req.url=".concat(req.url));
|
|
1188
|
+
if (this.sessionHealthKey && this.sessionHealthKey !== req.headers['x-health-key']) {
|
|
1189
|
+
res.sendRaw(403, JSON.stringify({ "message": "Invalid Session-Health-Key" }), {
|
|
1190
|
+
"Content-Type": "application/json",
|
|
1191
|
+
"Access-Control-Allow-Origin": "*",
|
|
1192
|
+
"Cache-Control": "no-cache",
|
|
1193
|
+
});
|
|
1194
|
+
next();
|
|
1195
|
+
return [2 /*return*/];
|
|
1196
|
+
}
|
|
1206
1197
|
failingSessions = [];
|
|
1207
1198
|
endpoints = [];
|
|
1208
1199
|
_i = 0, _a = Object.keys(sessions);
|
package/dist/examples/default.js
CHANGED
|
@@ -94,7 +94,8 @@ var engineOptions = {
|
|
|
94
94
|
defaultSlateUri: "https://maitv-vod.lab.eyevinn.technology/slate-consuo.mp4/master.m3u8",
|
|
95
95
|
slateRepetitions: 10,
|
|
96
96
|
redisUrl: process.env.REDIS_URL,
|
|
97
|
-
keepAliveTimeout: process.env.KEEP_ALIVE_TIMEOUT ? parseInt(process.env.KEEP_ALIVE_TIMEOUT) * 1000 : undefined
|
|
97
|
+
keepAliveTimeout: process.env.KEEP_ALIVE_TIMEOUT ? parseInt(process.env.KEEP_ALIVE_TIMEOUT) * 1000 : undefined,
|
|
98
|
+
sessionHealthKey: 'eyevinn'
|
|
98
99
|
};
|
|
99
100
|
var engine = new index_1.ChannelEngine(refAssetManager, engineOptions);
|
|
100
101
|
engine.start();
|
package/dist/package.json
CHANGED
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
const constants = {
|
|
2
|
+
ALLOW_HEADERS: [
|
|
3
|
+
'accept',
|
|
4
|
+
'accept-version',
|
|
5
|
+
'content-type',
|
|
6
|
+
'request-id',
|
|
7
|
+
'origin',
|
|
8
|
+
'x-api-version',
|
|
9
|
+
'x-request-id',
|
|
10
|
+
'x-requested-with'
|
|
11
|
+
],
|
|
12
|
+
EXPOSE_HEADERS: [
|
|
13
|
+
'api-version',
|
|
14
|
+
'content-length',
|
|
15
|
+
'content-md5',
|
|
16
|
+
'content-type',
|
|
17
|
+
'date',
|
|
18
|
+
'request-id',
|
|
19
|
+
'response-time'
|
|
20
|
+
],
|
|
21
|
+
AC_REQ_METHOD: 'access-control-request-method',
|
|
22
|
+
AC_REQ_HEADERS: 'access-control-request-headers',
|
|
23
|
+
AC_ALLOW_CREDS: 'access-control-allow-credentials',
|
|
24
|
+
AC_ALLOW_ORIGIN: 'access-control-allow-origin',
|
|
25
|
+
AC_ALLOW_HEADERS: 'access-control-allow-headers',
|
|
26
|
+
AC_ALLOW_METHODS: 'access-control-allow-methods',
|
|
27
|
+
AC_EXPOSE_HEADERS: 'access-control-expose-headers',
|
|
28
|
+
AC_MAX_AGE: 'access-control-max-age',
|
|
29
|
+
STR_VARY: 'vary',
|
|
30
|
+
STR_ORIGIN: 'origin',
|
|
31
|
+
HTTP_NO_CONTENT: 204
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
exports.handler = function (req, res, next) {
|
|
35
|
+
if (req.method !== 'OPTIONS') return next();
|
|
36
|
+
res.once('header', function () {
|
|
37
|
+
res.header(constants.AC_ALLOW_ORIGIN, '*');
|
|
38
|
+
res.header(constants.AC_ALLOW_CREDS, true);
|
|
39
|
+
res.header(constants.AC_ALLOW_METHODS, ['GET', 'OPTIONS']);
|
|
40
|
+
res.header(constants.AC_ALLOW_HEADERS, ['x-health-key']);
|
|
41
|
+
});
|
|
42
|
+
|
|
43
|
+
res.send(constants.HTTP_NO_CONTENT);
|
|
44
|
+
}
|
package/engine/server.ts
CHANGED
|
@@ -15,6 +15,8 @@ const { SessionLiveStateStore } = require('./session_live_state.js');
|
|
|
15
15
|
const { PlayheadStateStore } = require('./playhead_state.js');
|
|
16
16
|
|
|
17
17
|
const { filterQueryParser, toHHMMSS, WaitTimeGenerator } = require('./util.js');
|
|
18
|
+
const preflight = require('./preflight.js');
|
|
19
|
+
|
|
18
20
|
const { version } = require('../package.json');
|
|
19
21
|
|
|
20
22
|
const AUTO_CREATE_CHANNEL_TIMEOUT = 3000;
|
|
@@ -62,6 +64,7 @@ export interface ChannelEngineOpts {
|
|
|
62
64
|
sessionResetKey?: string;
|
|
63
65
|
keepAliveTimeout?: number;
|
|
64
66
|
sessionEventStream?: boolean;
|
|
67
|
+
sessionHealthKey?: string;
|
|
65
68
|
}
|
|
66
69
|
|
|
67
70
|
interface StreamerOpts {
|
|
@@ -209,6 +212,7 @@ export class ChannelEngine {
|
|
|
209
212
|
private autoCreateSession: boolean = false;
|
|
210
213
|
private sessionResetKey: string = "";
|
|
211
214
|
private sessionEventStream: boolean = false;
|
|
215
|
+
private sessionHealthKey: string = "";
|
|
212
216
|
|
|
213
217
|
constructor(assetMgr: IAssetManager, options?: ChannelEngineOpts) {
|
|
214
218
|
this.options = options;
|
|
@@ -232,6 +236,9 @@ export class ChannelEngine {
|
|
|
232
236
|
if (options && options.sessionResetKey) {
|
|
233
237
|
this.sessionResetKey = options.sessionResetKey;
|
|
234
238
|
}
|
|
239
|
+
if (options && options.sessionHealthKey) {
|
|
240
|
+
this.sessionHealthKey = options.sessionHealthKey;
|
|
241
|
+
}
|
|
235
242
|
this.alwaysNewSegments = false;
|
|
236
243
|
if (options && options.alwaysNewSegments) {
|
|
237
244
|
this.alwaysNewSegments = true;
|
|
@@ -353,25 +360,8 @@ export class ChannelEngine {
|
|
|
353
360
|
this.server.get('/channels/:channelId/:file', async (req, res, next) => {
|
|
354
361
|
req.query['channel'] = req.params.channelId;
|
|
355
362
|
await handleMasterRoute(req, res, next);
|
|
356
|
-
});
|
|
357
|
-
this.server.opts('/live/:file', async (req, res, next) => {
|
|
358
|
-
res.sendRaw(204, "", {
|
|
359
|
-
headers: {
|
|
360
|
-
"Access-Control-Allow-Origin": "*",
|
|
361
|
-
"Access-Control-Allow-Methods": "GET, OPTIONS",
|
|
362
|
-
},
|
|
363
|
-
});
|
|
364
|
-
next();
|
|
365
|
-
});
|
|
366
|
-
this.server.opts('/channels/:channelId/:file', async (req, res, next) => {
|
|
367
|
-
res.sendRaw(204, "", {
|
|
368
|
-
headers: {
|
|
369
|
-
"Access-Control-Allow-Origin": "*",
|
|
370
|
-
"Access-Control-Allow-Methods": "GET, OPTIONS",
|
|
371
|
-
},
|
|
372
|
-
});
|
|
373
|
-
next();
|
|
374
363
|
});
|
|
364
|
+
this.server.pre(preflight.handler);
|
|
375
365
|
this.server.get('/eventstream/:sessionId', this._handleEventStream.bind(this));
|
|
376
366
|
this.server.get('/status/:sessionId', this._handleStatus.bind(this));
|
|
377
367
|
this.server.get('/health', this._handleAggregatedSessionHealth.bind(this));
|
|
@@ -957,6 +947,16 @@ export class ChannelEngine {
|
|
|
957
947
|
|
|
958
948
|
async _handleAggregatedSessionHealth(req, res, next) {
|
|
959
949
|
debug(`req.url=${req.url}`);
|
|
950
|
+
if (this.sessionHealthKey && this.sessionHealthKey !== req.headers['x-health-key']) {
|
|
951
|
+
res.sendRaw(403, JSON.stringify({ "message": "Invalid Session-Health-Key" }),
|
|
952
|
+
{
|
|
953
|
+
"Content-Type": "application/json",
|
|
954
|
+
"Access-Control-Allow-Origin": "*",
|
|
955
|
+
"Cache-Control": "no-cache",
|
|
956
|
+
});
|
|
957
|
+
next();
|
|
958
|
+
return;
|
|
959
|
+
}
|
|
960
960
|
let failingSessions = [];
|
|
961
961
|
let endpoints = [];
|
|
962
962
|
for (const sessionId of Object.keys(sessions)) {
|
package/examples/default.ts
CHANGED
|
@@ -106,7 +106,8 @@ const engineOptions: ChannelEngineOpts = {
|
|
|
106
106
|
"https://maitv-vod.lab.eyevinn.technology/slate-consuo.mp4/master.m3u8",
|
|
107
107
|
slateRepetitions: 10,
|
|
108
108
|
redisUrl: process.env.REDIS_URL,
|
|
109
|
-
keepAliveTimeout: process.env.KEEP_ALIVE_TIMEOUT ? parseInt(process.env.KEEP_ALIVE_TIMEOUT) * 1000: undefined
|
|
109
|
+
keepAliveTimeout: process.env.KEEP_ALIVE_TIMEOUT ? parseInt(process.env.KEEP_ALIVE_TIMEOUT) * 1000: undefined,
|
|
110
|
+
sessionHealthKey: 'eyevinn'
|
|
110
111
|
};
|
|
111
112
|
|
|
112
113
|
const engine = new ChannelEngine(refAssetManager, engineOptions);
|