@warren-bank/hls-proxy 3.6.0 → 3.6.2
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/hls-proxy/acl_pass.js +4 -6
- package/hls-proxy/expressjs_utils.js +6 -7
- package/hls-proxy/manifest_parser.js +26 -12
- package/hls-proxy/proxy.js +1 -1
- package/hls-proxy/url.js +17 -1
- package/hls-proxy/utils.js +4 -4
- package/package.json +1 -1
package/hls-proxy/acl_pass.js
CHANGED
|
@@ -1,17 +1,15 @@
|
|
|
1
1
|
const expressjs = require('./expressjs_utils')
|
|
2
2
|
const {URL} = require('./url')
|
|
3
3
|
|
|
4
|
-
const
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
return req_url.searchParams.get('password') || ''
|
|
4
|
+
const get_decoded_qs_password = function(req) {
|
|
5
|
+
return expressjs.get_proxy_req_query(req, 'password', false)
|
|
8
6
|
}
|
|
9
7
|
|
|
10
8
|
const is_allowed = function(params, req) {
|
|
11
9
|
const {acl_pass} = params
|
|
12
10
|
|
|
13
11
|
if (acl_pass && Array.isArray(acl_pass) && acl_pass.length) {
|
|
14
|
-
const password =
|
|
12
|
+
const password = get_decoded_qs_password(req)
|
|
15
13
|
|
|
16
14
|
return (acl_pass.indexOf(password) >= 0)
|
|
17
15
|
}
|
|
@@ -20,6 +18,6 @@ const is_allowed = function(params, req) {
|
|
|
20
18
|
}
|
|
21
19
|
|
|
22
20
|
module.exports = {
|
|
23
|
-
|
|
21
|
+
get_decoded_qs_password,
|
|
24
22
|
is_allowed
|
|
25
23
|
}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
const {URL} = require('./url')
|
|
1
|
+
const {URL, decode_component_value} = require('./url')
|
|
2
2
|
|
|
3
3
|
const get_full_req_url = function(req) {
|
|
4
4
|
return req.originalUrl || req.url
|
|
@@ -19,16 +19,15 @@ const get_proxy_req_url = function(req) {
|
|
|
19
19
|
: req.url
|
|
20
20
|
}
|
|
21
21
|
|
|
22
|
-
const get_proxy_req_query = function(req, key) {
|
|
22
|
+
const get_proxy_req_query = function(req, key, is_base64) {
|
|
23
23
|
if (has_req_param(req, key))
|
|
24
|
-
return req.params[key]
|
|
24
|
+
return decode_component_value(req.params[key], false, is_base64, is_base64)
|
|
25
25
|
|
|
26
26
|
if (has_req_query(req, key))
|
|
27
|
-
return req.query[key]
|
|
27
|
+
return decode_component_value(req.query[key], false, is_base64, is_base64)
|
|
28
28
|
|
|
29
|
-
const
|
|
30
|
-
|
|
31
|
-
return qs.get(key)
|
|
29
|
+
const req_url = new URL(get_full_req_url(req))
|
|
30
|
+
return decode_component_value(req_url.searchParams.get(key), true, is_base64, is_base64)
|
|
32
31
|
}
|
|
33
32
|
|
|
34
33
|
const get_base_req_url = function(req) {
|
|
@@ -118,15 +118,16 @@ const parse_manifest = function(m3u8_content, m3u8_url, referer_url, querystring
|
|
|
118
118
|
|
|
119
119
|
const meta_data = {}
|
|
120
120
|
const embedded_urls = extract_embedded_urls(m3u8_lines, m3u8_url, referer_url, (cache_segments ? meta_data : null))
|
|
121
|
-
const qs_headers = !!querystring_req_headers ? utils.base64_encode(JSON.stringify(querystring_req_headers)) : null
|
|
122
121
|
const prefetch_urls = []
|
|
123
122
|
|
|
124
123
|
if (embedded_urls && Array.isArray(embedded_urls) && embedded_urls.length) {
|
|
124
|
+
const querystring = get_querystring(querystring_req_headers, qs_password)
|
|
125
|
+
|
|
125
126
|
embedded_urls.forEach(embedded_url => {
|
|
126
127
|
redirect_embedded_url(embedded_url, hooks, m3u8_url, debug)
|
|
127
128
|
if (validate_embedded_url(embedded_url)) {
|
|
128
129
|
finalize_embedded_url(embedded_url, vod_start_at_ms, debug)
|
|
129
|
-
encode_embedded_url(embedded_url, hooks, redirected_base_url, debug, manifest_extension, segment_extension,
|
|
130
|
+
encode_embedded_url(embedded_url, hooks, redirected_base_url, debug, manifest_extension, segment_extension, querystring)
|
|
130
131
|
get_prefetch_url(embedded_url, should_prefetch_url, prefetch_urls)
|
|
131
132
|
modify_m3u8_line(embedded_url, m3u8_lines)
|
|
132
133
|
}
|
|
@@ -234,6 +235,26 @@ const extract_meta_data = function(meta_data, m3u8_line, matching_landmark) {
|
|
|
234
235
|
}
|
|
235
236
|
}
|
|
236
237
|
|
|
238
|
+
const get_querystring = function(querystring_req_headers, qs_password) {
|
|
239
|
+
const qs_headers = !!querystring_req_headers ? utils.base64_encode(JSON.stringify(querystring_req_headers)) : null
|
|
240
|
+
let qs_pairs = []
|
|
241
|
+
let querystring = ''
|
|
242
|
+
|
|
243
|
+
if (qs_headers)
|
|
244
|
+
qs_pairs.push(['headers', qs_headers])
|
|
245
|
+
|
|
246
|
+
if (qs_password)
|
|
247
|
+
qs_pairs.push(['password', qs_password])
|
|
248
|
+
|
|
249
|
+
if (qs_pairs.length) {
|
|
250
|
+
qs_pairs = qs_pairs.map(pair => `${pair[0]}=${encodeURIComponent(pair[1])}`)
|
|
251
|
+
|
|
252
|
+
querystring = '?' + qs_pairs.join('&')
|
|
253
|
+
}
|
|
254
|
+
|
|
255
|
+
return querystring
|
|
256
|
+
}
|
|
257
|
+
|
|
237
258
|
const redirect_embedded_url = function(embedded_url, hooks, m3u8_url, debug) {
|
|
238
259
|
if (hooks && (hooks instanceof Object) && hooks.redirect && (typeof hooks.redirect === 'function')) {
|
|
239
260
|
let url, url_type, referer_url, result
|
|
@@ -333,7 +354,7 @@ const finalize_embedded_url = function(embedded_url, vod_start_at_ms, debug) {
|
|
|
333
354
|
}
|
|
334
355
|
}
|
|
335
356
|
|
|
336
|
-
const encode_embedded_url = function(embedded_url, hooks, redirected_base_url, debug, manifest_extension, segment_extension,
|
|
357
|
+
const encode_embedded_url = function(embedded_url, hooks, redirected_base_url, debug, manifest_extension, segment_extension, querystring) {
|
|
337
358
|
if (embedded_url.unencoded_url) {
|
|
338
359
|
let file_extension = embedded_url.url_type
|
|
339
360
|
if (file_extension) {
|
|
@@ -353,15 +374,8 @@ const encode_embedded_url = function(embedded_url, hooks, redirected_base_url, d
|
|
|
353
374
|
debug(3, 'redirecting (proxied, post-hook):', embedded_url.encoded_url)
|
|
354
375
|
}
|
|
355
376
|
|
|
356
|
-
|
|
357
|
-
|
|
358
|
-
qs_pairs.push(['headers', qs_headers])
|
|
359
|
-
if (qs_password)
|
|
360
|
-
qs_pairs.push(['password', qs_password])
|
|
361
|
-
if (qs_pairs.length) {
|
|
362
|
-
qs_pairs = qs_pairs.map(pair => `${pair[0]}=${encodeURIComponent(pair[1])}`)
|
|
363
|
-
|
|
364
|
-
embedded_url.encoded_url += '?' + qs_pairs.join('&')
|
|
377
|
+
if (querystring) {
|
|
378
|
+
embedded_url.encoded_url += querystring
|
|
365
379
|
debug(3, 'redirecting (proxied, with querystring):', embedded_url.encoded_url)
|
|
366
380
|
}
|
|
367
381
|
}
|
package/hls-proxy/proxy.js
CHANGED
|
@@ -55,7 +55,7 @@ const get_middleware = function(params) {
|
|
|
55
55
|
return
|
|
56
56
|
}
|
|
57
57
|
|
|
58
|
-
const qs_password = acl_pass.
|
|
58
|
+
const qs_password = acl_pass.get_decoded_qs_password(req)
|
|
59
59
|
const is_m3u8 = (url_type === 'm3u8')
|
|
60
60
|
|
|
61
61
|
const send_cache_segment = function(segment, type) {
|
package/hls-proxy/url.js
CHANGED
|
@@ -25,7 +25,23 @@ if (!parse || !URL) {
|
|
|
25
25
|
throw new Error('URL class is not supported')
|
|
26
26
|
}
|
|
27
27
|
|
|
28
|
+
const decode_component_value = function(value, decode = true, fix_unsafe_url_base64_encoding = false, fix_safe_url_base64_encoding = false) {
|
|
29
|
+
value = value || ''
|
|
30
|
+
|
|
31
|
+
if (decode)
|
|
32
|
+
value = decodeURIComponent(value)
|
|
33
|
+
|
|
34
|
+
if (fix_unsafe_url_base64_encoding)
|
|
35
|
+
value = value.replace(/ /g, '+')
|
|
36
|
+
|
|
37
|
+
if (fix_safe_url_base64_encoding)
|
|
38
|
+
value = value.replace(/-/g, '+').replace(/_/g, '/')
|
|
39
|
+
|
|
40
|
+
return value
|
|
41
|
+
}
|
|
42
|
+
|
|
28
43
|
module.exports = {
|
|
29
44
|
parse,
|
|
30
|
-
URL
|
|
45
|
+
URL,
|
|
46
|
+
decode_component_value
|
|
31
47
|
}
|
package/hls-proxy/utils.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
const expressjs = require('./expressjs_utils')
|
|
2
|
-
const parse_url = require('./url')
|
|
2
|
+
const {parse: parse_url, decode_component_value: decode_url_component_value} = require('./url')
|
|
3
3
|
|
|
4
4
|
const regexs = {
|
|
5
5
|
req_url: new RegExp('^(.*?)/([a-zA-Z0-9\\+/=%]+)(?:[\\._]([^/\\?#]*))?(?:[\\?#].*)?$'),
|
|
@@ -38,7 +38,7 @@ const parse_req_url = function(params, req) {
|
|
|
38
38
|
|
|
39
39
|
let url, url_lc, index
|
|
40
40
|
|
|
41
|
-
url = base64_decode(
|
|
41
|
+
url = base64_decode( decode_url_component_value( matches[2], true, true, true ) ).trim()
|
|
42
42
|
url_lc = url.toLowerCase()
|
|
43
43
|
index = url_lc.indexOf('http')
|
|
44
44
|
|
|
@@ -57,10 +57,10 @@ const parse_req_url = function(params, req) {
|
|
|
57
57
|
result.url = url
|
|
58
58
|
}
|
|
59
59
|
|
|
60
|
-
let qs_headers = expressjs.get_proxy_req_query(req, 'headers')
|
|
60
|
+
let qs_headers = expressjs.get_proxy_req_query(req, 'headers', true)
|
|
61
61
|
if (qs_headers) {
|
|
62
62
|
try {
|
|
63
|
-
qs_headers = base64_decode(
|
|
63
|
+
qs_headers = base64_decode( qs_headers ).trim()
|
|
64
64
|
qs_headers = JSON.parse(qs_headers)
|
|
65
65
|
|
|
66
66
|
if (qs_headers && (qs_headers instanceof Object))
|
package/package.json
CHANGED