summaryrefslogtreecommitdiff
path: root/extensions/chrome/common.js
diff options
context:
space:
mode:
Diffstat (limited to 'extensions/chrome/common.js')
-rw-r--r--extensions/chrome/common.js187
1 files changed, 187 insertions, 0 deletions
diff --git a/extensions/chrome/common.js b/extensions/chrome/common.js
new file mode 100644
index 0000000..30dc55a
--- /dev/null
+++ b/extensions/chrome/common.js
@@ -0,0 +1,187 @@
+function init() {
+ // receive messages from webpage
+ chrome.runtime.onMessageExternal.addListener(receiveMessage);
+}
+function receiveMessage(msg, sender, sendResponse) {
+ if (msg.cmd == "injection_result") {
+ var obj = Injections.get(msg.id);
+ if (obj) obj.addResponse(sender.tab.id, msg.data);
+ }
+}
+function extend(dest, source) {
+ for (var i in source) {
+ dest[i] = source[i];
+ }
+}
+function getWebSocket() {
+ return window.WebSocket || window.MozWebSocket;
+}
+function print() {
+ var msgs = [], i, tmp;
+ for (i = 0; i < arguments.length; i++) {
+ if (arguments[i] instanceof Error) tmp = [arguments[i], arguments[i].stack];
+ else tmp = arguments[i];
+ msgs.push(tmp);
+ }
+
+ try {
+ console.log.apply(console, msgs);
+ } catch(e) {}
+}
+function getExtensionId() {
+ return chrome.i18n.getMessage("@@extension_id");
+}
+function getVKTabs(callback) {
+ var vkTabs = [];
+ chrome.tabs.query({}, function(tabs) {
+ for (var i = 0; i < tabs.length; i++) {
+ var tab = tabs[i];
+ if (tab.url.match(new RegExp('https?://vk.com/.*', 'gi'))) {
+ vkTabs.push(tab);
+ }
+ }
+ callback(vkTabs);
+ });
+}
+function executeCommand(cmd) {
+ var injId = Injections.getNextId();
+ var code_inj = "var el = document.createElement('script'); el.src = chrome.extension.getURL('inject_and_return.js'); document.body.appendChild(el); var el1 = document.createElement('script'); el1.textContent = 'window.__vkpc_extid=\""+getExtensionId()+"\"; window.__vkpc_injid="+injId+"'; document.body.appendChild(el1)";
+ var code_exec = "var el = document.createElement('script'); el.src = chrome.extension.getURL('inject_exec.js'); document.body.appendChild(el); var el1 = document.createElement('script'); el1.textContent = 'window.__vkpc_cmd=\""+cmd+"\"'; document.body.appendChild(el1)";
+
+ getVKTabs(function(tabs) {
+ if (!tabs.length) return;
+
+ var injResponses, activeTabId = null;
+ var onDone = function() {
+ var ok = {nowPlaying: null, lsSource: null, recentlyPlayed: null, active: activeTabId, last: null};
+ var results = injResponses.results, lsSource = injResponses.lsSource;
+
+ for (var i = 0; i < results.length; i++) {
+ var data = results[i].data, id = results[i].tab;
+ ok.last = id;
+
+ if (data.havePlayer && (data.isPlaying || typeof data.trackId == 'string')) {
+ ok.recentlyPlayed = id;
+ }
+ if (data.isPlaying) {
+ ok.nowPlaying = id;
+ }
+ if (lsSource && lsSource == data.instanceId) {
+ ok.lsSource = id;
+ }
+ }
+ injResponses.unregister();
+
+ var rightId = ok.nowPlaying || ok.lsSource || ok.recentlyPlayed || ok.active || ok.last;
+ if (rightId) {
+ chrome.tabs.executeScript(rightId, {code: code_exec});
+ }
+ };
+ injResponses = new InjectionResponses(injId, tabs.length, onDone);
+
+ for (var i = 0; i < tabs.length; i++) {
+ if (tabs[i].active) activeTabId = tabs[i].id;
+ chrome.tabs.executeScript(tabs[i].id, {
+ code: code_inj
+ });
+ }
+ });
+}
+
+var Injections = {
+ id: 0,
+ objs: {},
+ getNextId: function() {
+ return ++this.id;
+ },
+ get: function(id) {
+ return this.objs[id] || false;
+ },
+ register: function(id, obj) {
+ this.objs[id] = obj;
+ },
+ unregister: function(id) {
+ if (this.objs[id] !== undefined) delete this.objs[id];
+ }
+};
+
+var WSClient = new function() {
+ var STATUS_NONE = 0, STATUS_OK = 1, STATUS_ERR = 2;
+ var _ws = getWebSocket(), ws;
+ var _status = STATUS_NONE;
+ var ping_timer, reconnect_timer;
+
+ if (!_ws) return;
+
+ function setTimers() {
+ ping_timer = setInterval(function() {
+ if (ws) ws.send("PING");
+ }, 30000);
+ }
+ function unsetTimers() {
+ clearInterval(ping_timer);
+ }
+
+ function connect() {
+ _status = STATUS_NONE;
+
+ print("[connect]");
+ ws = new _ws("ws://localhost:52178", "signaling-protocol");
+ ws.onopen = function() {
+ _status = STATUS_OK;
+ setTimers();
+ };
+ ws.onerror = function() {
+ unsetTimers();
+ if (_status != STATUS_ERR) {
+ _status = STATUS_ERR;
+ tryToReconnect();
+ }
+ }
+ ws.onclose = function() {
+ unsetTimers();
+ if (_status != STATUS_ERR) {
+ _status = STATUS_ERR;
+ tryToReconnect();
+ }
+ };
+ ws.onmessage = function(e) {
+ onCommand(e.data);
+ };
+ }
+ function tryToReconnect() {
+ print("[tryToReconnect]");
+
+ clearTimeout(reconnect_timer);
+ reconnect_timer = setTimeout(connect, 5000);
+ }
+ function onCommand(msg) {
+ executeCommand(msg);
+ }
+
+ connect();
+};
+
+function InjectionResponses(id, count, callback) {
+ this.id = id;
+ this.results = [];
+ this.lsSource = null;
+ this.maxCount = count;
+ this.callback = callback || function() {};
+
+ Injections.register(this.id, this);
+}
+extend(InjectionResponses.prototype, {
+ addResponse: function(id, response) {
+ this.results.push({tab: id, data: response});
+ if (!this.lsSource && response && response.lastInstanceId) this.lsSource = response.lastInstanceId;
+ if (this.results.length == this.maxCount) {
+ this.callback();
+ }
+ },
+ unregister: function() {
+ Injections.unregister(this.id);
+ }
+});
+
+init();