From 70be35e3fa1da60b91d7e62a76d5436c1b2c76c0 Mon Sep 17 00:00:00 2001 From: Calvin Montgomery Date: Thu, 2 Mar 2017 18:47:47 -0800 Subject: [PATCH] Experimental ustream fix --- package.json | 2 +- player/ustream.coffee | 2 +- src/web/httpstatus.js | 1 + src/web/routes/ustream_bypass.js | 54 ++++++++++++++++++++++++++++++++ src/web/webserver.js | 1 + www/js/player.js | 2 +- 6 files changed, 59 insertions(+), 3 deletions(-) create mode 100644 src/web/routes/ustream_bypass.js diff --git a/package.json b/package.json index c04fbb5a..867dab14 100644 --- a/package.json +++ b/package.json @@ -2,7 +2,7 @@ "author": "Calvin Montgomery", "name": "CyTube", "description": "Online media synchronizer and chat", - "version": "3.30.1", + "version": "3.30.2", "repository": { "url": "http://github.com/calzoneman/sync" }, diff --git a/player/ustream.coffee b/player/ustream.coffee index 129f8558..f68ab142 100644 --- a/player/ustream.coffee +++ b/player/ustream.coffee @@ -8,5 +8,5 @@ window.UstreamPlayer = class UstreamPlayer extends EmbedPlayer load: (data) -> data.meta.embed = tag: 'iframe' - src: "https://www.ustream.tv/embed/#{data.id}?html5ui&autoplay=1" + src: "/ustream_bypass/embed/#{data.id}?html5ui&autoplay=1" super(data) diff --git a/src/web/httpstatus.js b/src/web/httpstatus.js index b2e2430d..7e40bb78 100644 --- a/src/web/httpstatus.js +++ b/src/web/httpstatus.js @@ -1,3 +1,4 @@ +export const OK = 200; export const BAD_REQUEST = 400; export const FORBIDDEN = 403; export const NOT_FOUND = 404; diff --git a/src/web/routes/ustream_bypass.js b/src/web/routes/ustream_bypass.js new file mode 100644 index 00000000..111ba8d2 --- /dev/null +++ b/src/web/routes/ustream_bypass.js @@ -0,0 +1,54 @@ +import { HTTPError } from '../../errors'; +import * as HTTPStatus from '../httpstatus'; +import https from 'https'; +import Promise from 'bluebird'; + +const INJECTION = ` + + `; + +function ustreamSucks(channelId) { + const url = `https://www.ustream.tv/embed/${channelId}`; + return new Promise((resolve, reject) => { + const req = https.get(url, (res) => { + if (res.statusCode !== HTTPStatus.OK) { + res.resume(); + return reject(new HTTPError(res.statusMessage, { status: res.statusCode })); + } + + res.setEncoding('utf8'); + let buffer = ''; + res.on('data', data => buffer += data); + res.on('end', () => { + buffer = buffer.replace(//, INJECTION); + resolve(buffer); + }); + }); + + req.on('error', error => { + reject(error); + }); + }); +} + +export default function initialize(app) { + app.get('/ustream_bypass/embed/:channelId', (req, res) => { + if (!req.params.channelId || !/^\d+$/.test(req.params.channelId)) { + throw new HTTPError(`Invalid channel ID "${req.params.channelId}".`, { + status: HTTPStatus.BAD_REQUEST + }); + } + + ustreamSucks(req.params.channelId).then(buffer => { + res.type('html').send(buffer); + }).catch(HTTPError, error => { + res.status(error.status).send(error.message); + }).catch(error => { + res.status(HTTPStatus.INTERNAL_SERVER_ERROR).send('Internal Server Error'); + }); + }); +}; diff --git a/src/web/webserver.js b/src/web/webserver.js index 5aac81ed..0d8fcf11 100644 --- a/src/web/webserver.js +++ b/src/web/webserver.js @@ -186,6 +186,7 @@ module.exports = { require('./acp').init(app); require('../google2vtt').attach(app); require('./routes/google_drive_userscript')(app); + require('./routes/ustream_bypass')(app); app.use(serveStatic(path.join(__dirname, '..', '..', 'www'), { maxAge: webConfig.getCacheTTL() })); diff --git a/www/js/player.js b/www/js/player.js index a30ee1b9..b4d8f257 100644 --- a/www/js/player.js +++ b/www/js/player.js @@ -1271,7 +1271,7 @@ UstreamPlayer.prototype.load = function(data) { data.meta.embed = { tag: 'iframe', - src: "https://www.ustream.tv/embed/" + data.id + "?html5ui&autoplay=1" + src: "/ustream_bypass/embed/" + data.id + "?html5ui&autoplay=1" }; return UstreamPlayer.__super__.load.call(this, data); };