From e3aeb0caa19fa0fea6705fde96352b912ce99130 Mon Sep 17 00:00:00 2001 From: Ajay Ramachandran Date: Tue, 30 Jul 2019 18:38:07 -0400 Subject: [PATCH 01/27] Update LICENSE --- LICENSE | 11 ++++++++--- 1 file changed, 8 insertions(+), 3 deletions(-) diff --git a/LICENSE b/LICENSE index ce167a86..61e854aa 100644 --- a/LICENSE +++ b/LICENSE @@ -1,4 +1,8 @@ - GNU GENERAL PUBLIC LICENSE +SponsorBlock Copyright (C) 2019 Ajay Ramachandran and other SponsorBlock contributors. + +Please refer to the license below. + + GNU GENERAL PUBLIC LICENSE Version 3, 29 June 2007 Copyright (C) 2007 Free Software Foundation, Inc. @@ -651,8 +655,9 @@ Also add information on how to contact you by electronic and paper mail. If the program does terminal interaction, make it output a short notice like this when it starts in an interactive mode: - - SponsorBlock Copyright (C) 2019 Ajay Ramachandran and other SponsorBlock contributors + + Copyright (C) + This program comes with ABSOLUTELY NO WARRANTY; for details type `show w'. This is free software, and you are welcome to redistribute it under certain conditions; type `show c' for details. From 3b3653af67469e13ec0acd3167a6b42e09e7dc17 Mon Sep 17 00:00:00 2001 From: Ajay Ramachandran Date: Sat, 3 Aug 2019 22:38:21 -0400 Subject: [PATCH 02/27] Update README.md --- README.md | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/README.md b/README.md index 74fbcac5..ce8c9e8a 100644 --- a/README.md +++ b/README.md @@ -21,6 +21,10 @@ To make sure that this project doesn't die, I have made the database publicly do Hopefully this project can be combined with projects like [this](https://github.com/Sponsoff/sponsorship_remover) and use this data to create a neural network to predict when sponsored segments happen. That project is sadly abandoned now, so I have decided to attempt to revive this idea. +# API + +You can read the API docs [here](https://github.com/ajayyy/SponsorBlockServer#api-docs) + # Previous extension This project is partially based off of [this experimental extension](https://github.com/OfficialNoob/YTSponsorSkip). That extension has the basic video skipping functionality. From 3a037818a89b63d75567edf823d107c6a4949591 Mon Sep 17 00:00:00 2001 From: Mario Ortiz Manero Date: Sun, 4 Aug 2019 13:29:43 +0200 Subject: [PATCH 03/27] Grammar and phrasing fixes --- README.md | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/README.md b/README.md index ce8c9e8a..6ca1eb4c 100644 --- a/README.md +++ b/README.md @@ -3,7 +3,7 @@ # SponsorBlock -SponsorBlock is an extension that will skip over sponsored segments of YouTube videos. SponsorBlock is a crowdsourced browser extension that let's anyone submit the start and end time's of sponsored segments of YouTube videos. Once one person submits this information, everyone else with this extension will skip right over the sponsored segment. +SponsorBlock is an extension that will skip over sponsored segments of YouTube videos. SponsorBlock is a crowdsourced browser extension that lets anyone submit the start and end times of sponsored segments of YouTube videos. Once one person submits this information, everyone else with this extension will skip right over the sponsored segment. # Available for Chrome and Firefox @@ -23,11 +23,11 @@ Hopefully this project can be combined with projects like [this](https://github. # API -You can read the API docs [here](https://github.com/ajayyy/SponsorBlockServer#api-docs) +You can read the API docs [here](https://github.com/ajayyy/SponsorBlockServer#api-docs). # Previous extension -This project is partially based off of [this experimental extension](https://github.com/OfficialNoob/YTSponsorSkip). That extension has the basic video skipping functionality. +This project is partially based off of [this experimental extension](https://github.com/OfficialNoob/YTSponsorSkip), which has the basic video skipping functionality. # Build Yourself @@ -39,4 +39,4 @@ The awesome [Invidious API](https://github.com/omarroth/invidious/wiki/API) is u Some icons made by Gregor Cresnar from www.flaticon.com and are licensed by CC 3.0 BY -Some icons made by Freepik from www.flaticon.com is licensed by CC 3.0 BY +Some icons made by Freepik from www.flaticon.com are licensed by CC 3.0 BY From f6c9e8e235bfdaa3d1c89c584aaa40fa3897a41f Mon Sep 17 00:00:00 2001 From: Official Noob <31563761+OfficialNoob@users.noreply.github.com> Date: Sun, 4 Aug 2019 18:47:07 +0100 Subject: [PATCH 04/27] Added getYouTubeVideoID --- utils.js | 11 +++++++++++ 1 file changed, 11 insertions(+) create mode 100644 utils.js diff --git a/utils.js b/utils.js new file mode 100644 index 00000000..c2803729 --- /dev/null +++ b/utils.js @@ -0,0 +1,11 @@ +function getYouTubeVideoID(url) { // Returns with video id else returns false + var regExp = /^.*((youtu.be\/)|(v\/)|(\/u\/\w\/)|(embed\/)|(watch\?))\??v?=?([^#\&\?]*).*/; + var match = url.match(regExp); + var id = new URL(url).searchParams.get("v"); + if (url.includes("/embed/")) { + //it is an embed, don't search for v + id = match[7]; + } + + return (match && match[7].length == 11) ? id : false; +} From aae099842663eb200e4939f5c53cb0411baad59d Mon Sep 17 00:00:00 2001 From: Official Noob <31563761+OfficialNoob@users.noreply.github.com> Date: Sun, 4 Aug 2019 18:59:08 +0100 Subject: [PATCH 05/27] Added utils.js --- manifest.json | 2 ++ 1 file changed, 2 insertions(+) diff --git a/manifest.json b/manifest.json index 1fe36a7c..be3a2dc7 100644 --- a/manifest.json +++ b/manifest.json @@ -11,6 +11,7 @@ "all_frames": true, "js": [ "config.js", + "utils.js", "content.js", "popup.js" ], @@ -48,6 +49,7 @@ }, "background": { "scripts":[ + "utils.js", "config.js", "background.js" ] From 5425c54fca2889fba9e59f862e869f492512195c Mon Sep 17 00:00:00 2001 From: Official Noob <31563761+OfficialNoob@users.noreply.github.com> Date: Sun, 4 Aug 2019 18:59:51 +0100 Subject: [PATCH 06/27] Added utils.js --- popup.html | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/popup.html b/popup.html index be45142b..30195294 100644 --- a/popup.html +++ b/popup.html @@ -193,5 +193,6 @@ + - \ No newline at end of file + From 64befaebfcaee74d36de58dbcd2cba5c0fc4c9b0 Mon Sep 17 00:00:00 2001 From: Official Noob <31563761+OfficialNoob@users.noreply.github.com> Date: Sun, 4 Aug 2019 19:00:54 +0100 Subject: [PATCH 07/27] Removed getYouTubeVideoID as in utils --- background.js | 8 +------- 1 file changed, 1 insertion(+), 7 deletions(-) diff --git a/background.js b/background.js index cbd45531..3ab8f8e9 100644 --- a/background.js +++ b/background.js @@ -263,11 +263,5 @@ function sendRequestToServer(type, address, callback) { xmlhttp.send(); } -function getYouTubeVideoID(url) { // Return video id or false - var regExp = /^.*((youtu.be\/)|(v\/)|(\/u\/\w\/)|(embed\/)|(watch\?))\??v?=?([^#\&\?]*).*/; - var match = url.match(regExp); - return (match && match[7].length == 11) ? match[7] : false; -} - //uuid generator function from https://gist.github.com/jed/982883 -function generateUUID(a){return a?(a^Math.random()*16>>a/4).toString(16):([1e7]+-1e3+-4e3+-8e3+-1e11).replace(/[018]/g,generateUUID)} \ No newline at end of file +function generateUUID(a){return a?(a^Math.random()*16>>a/4).toString(16):([1e7]+-1e3+-4e3+-8e3+-1e11).replace(/[018]/g,generateUUID)} From e6fa832cb86593499f4c9d3f219d776710d8fd3a Mon Sep 17 00:00:00 2001 From: Official Noob <31563761+OfficialNoob@users.noreply.github.com> Date: Sun, 4 Aug 2019 19:04:43 +0100 Subject: [PATCH 08/27] Removed getYouTubeVideoID as in utils --- content.js | 14 +------------- 1 file changed, 1 insertion(+), 13 deletions(-) diff --git a/content.js b/content.js index 73348973..77260012 100644 --- a/content.js +++ b/content.js @@ -1144,18 +1144,6 @@ function sendRequestToCustomServer(type, fullAddress, callback) { xmlhttp.send(); } -function getYouTubeVideoID(url) { // Returns with video id else returns false - var regExp = /^.*((youtu.be\/)|(v\/)|(\/u\/\w\/)|(embed\/)|(watch\?))\??v?=?([^#\&\?]*).*/; - var match = url.match(regExp); - var id = new URL(url).searchParams.get("v"); - if (url.includes("/embed/")) { - //it is an embed, don't search for v - id = match[7]; - } - - return (match && match[7].length == 11) ? id : false; -} - //returns the start time of the video if there was one specified (ex. ?t=5s) function getYouTubeVideoStartTime(url) { let searchParams = new URL(url).searchParams; @@ -1165,4 +1153,4 @@ function getYouTubeVideoStartTime(url) { } return startTime; -} \ No newline at end of file +} From 5ee279dec7d074dd266c23892ff27b118f5bb504 Mon Sep 17 00:00:00 2001 From: Official Noob <31563761+OfficialNoob@users.noreply.github.com> Date: Sun, 4 Aug 2019 19:06:07 +0100 Subject: [PATCH 09/27] Added getYouTubeVideoStartTime --- utils.js | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/utils.js b/utils.js index c2803729..1e4da828 100644 --- a/utils.js +++ b/utils.js @@ -9,3 +9,14 @@ function getYouTubeVideoID(url) { // Returns with video id else returns false return (match && match[7].length == 11) ? id : false; } + +//returns the start time of the video if there was one specified (ex. ?t=5s) +function getYouTubeVideoStartTime(url) { + let searchParams = new URL(url).searchParams; + var startTime = searchParams.get("t"); + if (startTime == null) { + startTime = searchParams.get("time_continue"); + } + + return startTime; +} From d25792f39a86017529746338436efb10c7bab444 Mon Sep 17 00:00:00 2001 From: Official Noob <31563761+OfficialNoob@users.noreply.github.com> Date: Sun, 4 Aug 2019 19:07:00 +0100 Subject: [PATCH 10/27] Removed getYouTubeVideoID --- popup.js | 9 +-------- 1 file changed, 1 insertion(+), 8 deletions(-) diff --git a/popup.js b/popup.js index 8368f274..d1186984 100644 --- a/popup.js +++ b/popup.js @@ -1127,13 +1127,6 @@ function runThePopup() { xmlhttp.send(); } - function getYouTubeVideoID(url) { // Returns with video id else returns false - var regExp = /^.*((youtu.be\/)|(v\/)|(\/u\/\w\/)|(embed\/)|(watch\?))\??v?=?([^#\&\?]*).*/; - var match = url.match(regExp); - var id = new URL(url).searchParams.get("v"); - return (match && match[7].length == 11) ? id : false; - } - //end of function } @@ -1143,4 +1136,4 @@ if (chrome.tabs != undefined) { //this means it is actually opened in the popup runThePopup(); -} \ No newline at end of file +} From 9a32710ef84161e73146ccaa17610c9462433fef Mon Sep 17 00:00:00 2001 From: Official Noob <31563761+OfficialNoob@users.noreply.github.com> Date: Sun, 4 Aug 2019 19:09:46 +0100 Subject: [PATCH 11/27] Removed getYouTubeVideoStartTime --- content.js | 11 ----------- 1 file changed, 11 deletions(-) diff --git a/content.js b/content.js index 77260012..656b0e83 100644 --- a/content.js +++ b/content.js @@ -1143,14 +1143,3 @@ function sendRequestToCustomServer(type, fullAddress, callback) { //submit this request xmlhttp.send(); } - -//returns the start time of the video if there was one specified (ex. ?t=5s) -function getYouTubeVideoStartTime(url) { - let searchParams = new URL(url).searchParams; - var startTime = searchParams.get("t"); - if (startTime == null) { - startTime = searchParams.get("time_continue"); - } - - return startTime; -} From 7ad5e426fb965d4a06575377704244bd3c4dd2f3 Mon Sep 17 00:00:00 2001 From: Official Noob <31563761+OfficialNoob@users.noreply.github.com> Date: Tue, 6 Aug 2019 10:27:13 +0100 Subject: [PATCH 12/27] Improved Parser --- utils.js | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/utils.js b/utils.js index 1e4da828..c12fb6cb 100644 --- a/utils.js +++ b/utils.js @@ -2,12 +2,10 @@ function getYouTubeVideoID(url) { // Returns with video id else returns false var regExp = /^.*((youtu.be\/)|(v\/)|(\/u\/\w\/)|(embed\/)|(watch\?))\??v?=?([^#\&\?]*).*/; var match = url.match(regExp); var id = new URL(url).searchParams.get("v"); - if (url.includes("/embed/")) { - //it is an embed, don't search for v + if (url.includes("/embed/")) { //it is an embed, don't search for v id = match[7]; } - - return (match && match[7].length == 11) ? id : false; + return (match) ? id : false; } //returns the start time of the video if there was one specified (ex. ?t=5s) From 2b5402fa5797f95e53ffd98647c758791de1dfe1 Mon Sep 17 00:00:00 2001 From: Official Noob <31563761+OfficialNoob@users.noreply.github.com> Date: Tue, 6 Aug 2019 14:08:46 +0100 Subject: [PATCH 13/27] Added sanity check --- utils.js | 7 ++----- 1 file changed, 2 insertions(+), 5 deletions(-) diff --git a/utils.js b/utils.js index c12fb6cb..916c2c73 100644 --- a/utils.js +++ b/utils.js @@ -1,11 +1,8 @@ function getYouTubeVideoID(url) { // Returns with video id else returns false var regExp = /^.*((youtu.be\/)|(v\/)|(\/u\/\w\/)|(embed\/)|(watch\?))\??v?=?([^#\&\?]*).*/; var match = url.match(regExp); - var id = new URL(url).searchParams.get("v"); - if (url.includes("/embed/")) { //it is an embed, don't search for v - id = match[7]; - } - return (match) ? id : false; + var id = url.includes("/embed/") ? match[7] : new URL(url).searchParams.get("v"); + return (match && id.length === 11) ? id : false; } //returns the start time of the video if there was one specified (ex. ?t=5s) From 02e11503cba1ee420a338e200e1a873ff71d081e Mon Sep 17 00:00:00 2001 From: Official Noob <31563761+OfficialNoob@users.noreply.github.com> Date: Tue, 6 Aug 2019 22:06:23 +0100 Subject: [PATCH 14/27] Removed Regex as "looks bad" --- utils.js | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-) diff --git a/utils.js b/utils.js index 916c2c73..c1d6c23d 100644 --- a/utils.js +++ b/utils.js @@ -1,8 +1,9 @@ -function getYouTubeVideoID(url) { // Returns with video id else returns false - var regExp = /^.*((youtu.be\/)|(v\/)|(\/u\/\w\/)|(embed\/)|(watch\?))\??v?=?([^#\&\?]*).*/; - var match = url.match(regExp); - var id = url.includes("/embed/") ? match[7] : new URL(url).searchParams.get("v"); - return (match && id.length === 11) ? id : false; +function getYouTubeVideoID(url) { + let obj = new URL(url); + if(obj.host !== "www.youtube.com" || "www.youtube-nocookie.com") return false // Check if valid hostname + if (obj.pathname == "/watch") id = obj.searchParams.get("v"); // Get ID from searchParam + if (obj.pathname.startsWith("/embed/")) id = obj.pathname.slice("/embed/".length); // Get ID from end or URL + return id.length == 11 ? id : false; } //returns the start time of the video if there was one specified (ex. ?t=5s) From c6c8d7de491281e38d21c0d9124bdb0e6c1d7644 Mon Sep 17 00:00:00 2001 From: Official Noob <31563761+OfficialNoob@users.noreply.github.com> Date: Wed, 7 Aug 2019 15:34:21 +0100 Subject: [PATCH 15/27] Update utils.js --- utils.js | 22 +++++++++++++++++----- 1 file changed, 17 insertions(+), 5 deletions(-) diff --git a/utils.js b/utils.js index c1d6c23d..5e470e27 100644 --- a/utils.js +++ b/utils.js @@ -1,9 +1,21 @@ function getYouTubeVideoID(url) { - let obj = new URL(url); - if(obj.host !== "www.youtube.com" || "www.youtube-nocookie.com") return false // Check if valid hostname - if (obj.pathname == "/watch") id = obj.searchParams.get("v"); // Get ID from searchParam - if (obj.pathname.startsWith("/embed/")) id = obj.pathname.slice("/embed/".length); // Get ID from end or URL - return id.length == 11 ? id : false; + + try { // Attempt to parse url + let obj = new URL(url); + } catch (e) { + return false + console.error("[SB] Unable to parser URL"); + } + + if(!["www.youtube.com","www.youtube-nocookie.com"].includes(obj.host)) return false // Check if valid hostname + + if (obj.pathname == "/watch" && obj.searchParams.has("v")) { + id = obj.searchParams.get("v"); // Get ID from searchParam + } else if (obj.pathname.startsWith("/embed/")) { + id = obj.pathname.slice("/embed/".length); // Get ID from end or URL + } + + return id.length == 11 ? id : false; // If ID is not 11 in length return false } //returns the start time of the video if there was one specified (ex. ?t=5s) From dce036b0e6bc7a5347b41665c55eb3e77202ca8f Mon Sep 17 00:00:00 2001 From: Official Noob <31563761+OfficialNoob@users.noreply.github.com> Date: Wed, 7 Aug 2019 15:46:07 +0100 Subject: [PATCH 16/27] Update utils.js --- utils.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/utils.js b/utils.js index 5e470e27..117c1e61 100644 --- a/utils.js +++ b/utils.js @@ -2,9 +2,9 @@ function getYouTubeVideoID(url) { try { // Attempt to parse url let obj = new URL(url); - } catch (e) { - return false + } catch (e) { console.error("[SB] Unable to parser URL"); + return false } if(!["www.youtube.com","www.youtube-nocookie.com"].includes(obj.host)) return false // Check if valid hostname From baba619fe74fd750dc0c65cf191b5ea0251ad596 Mon Sep 17 00:00:00 2001 From: Official Noob <31563761+OfficialNoob@users.noreply.github.com> Date: Wed, 7 Aug 2019 16:20:07 +0100 Subject: [PATCH 17/27] Fixed scope --- utils.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/utils.js b/utils.js index 117c1e61..f7fb6ecf 100644 --- a/utils.js +++ b/utils.js @@ -1,7 +1,7 @@ function getYouTubeVideoID(url) { try { // Attempt to parse url - let obj = new URL(url); + var obj = new URL(url); } catch (e) { console.error("[SB] Unable to parser URL"); return false From b964d93ea948b94515a7a93dc573c5ab5a52be3c Mon Sep 17 00:00:00 2001 From: Official Noob <31563761+OfficialNoob@users.noreply.github.com> Date: Wed, 7 Aug 2019 16:35:29 +0100 Subject: [PATCH 18/27] Update utils.js --- utils.js | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/utils.js b/utils.js index f7fb6ecf..80b4a1f3 100644 --- a/utils.js +++ b/utils.js @@ -11,11 +11,15 @@ function getYouTubeVideoID(url) { if (obj.pathname == "/watch" && obj.searchParams.has("v")) { id = obj.searchParams.get("v"); // Get ID from searchParam + return id.length == 11 ? id : false; } else if (obj.pathname.startsWith("/embed/")) { - id = obj.pathname.slice("/embed/".length); // Get ID from end or URL + try { + return obj.pathname.substr(7, 11); + } catch (e) { + console.error("[SB] Video ID not valid"); + return false + } } - - return id.length == 11 ? id : false; // If ID is not 11 in length return false } //returns the start time of the video if there was one specified (ex. ?t=5s) From 7e2925a1e35ff9aa2514d7a82fb78812282bd413 Mon Sep 17 00:00:00 2001 From: Anton Bershanskiy Date: Thu, 8 Aug 2019 00:24:30 -0500 Subject: [PATCH 19/27] Refactor: make background non-persistent --- background.js | 132 +++++++++++++++++++++------------------------- config.js.example | 2 +- manifest.json | 7 ++- 3 files changed, 63 insertions(+), 78 deletions(-) diff --git a/background.js b/background.js index cbd45531..b7069994 100644 --- a/background.js +++ b/background.js @@ -1,11 +1,3 @@ -var previousVideoID = null - -//the id of this user, randomly generated once per install -var userID = null; - -//the last video id loaded, to make sure it is a video id change -var sponsorVideoID = null; - //when a new tab is highlighted chrome.tabs.onActivated.addListener( function(activeInfo) { @@ -62,14 +54,23 @@ chrome.runtime.onMessage.addListener(function (request, sender, callback) { //add help page on install chrome.runtime.onInstalled.addListener(function (object) { - chrome.storage.sync.get(["shownInstallPage"], function(result) { - let shownInstallPage = result.shownInstallPage; - if (shownInstallPage == undefined || !shownInstallPage) { + chrome.storage.sync.get(["userID"], function(result) { + const userID = result.userID; + // If there is no userID, then it is the first install. + if (!userID){ //open up the install page chrome.tabs.create({url: chrome.extension.getURL("/help/index.html")}); - //save that this happened - chrome.storage.sync.set({shownInstallPage: true}); + //generate a userID + const newUserID = generateUUID(); + //save this UUID + chrome.storage.sync.set({ + "userID": newUserID, + "serverAddress": serverAddress, + //the last video id loaded, to make sure it is a video id change + "sponsorVideoID": null, + "previousVideoID": null + }); } }); }); @@ -109,9 +110,12 @@ function addSponsorTime(time, videoID, callback) { } function submitVote(type, UUID, callback) { - getUserID(function(userID) { + chrome.storage.sync.get(["serverAddress", "userID"], function(result) { + const serverAddress = result.serverAddress; + const userID = result.userID; + //publish this vote - sendRequestToServer('GET', "/api/voteOnSponsorTime?UUID=" + UUID + "&userID=" + userID + "&type=" + type, function(xmlhttp, error) { + sendRequestToServer("GET", serverAddress + "/api/voteOnSponsorTime?UUID=" + UUID + "&userID=" + userID + "&type=" + type, function(xmlhttp, error) { if (xmlhttp.readyState == 4 && xmlhttp.status == 200) { callback({ successType: 1 @@ -136,16 +140,17 @@ function submitVote(type, UUID, callback) { function submitTimes(videoID, callback) { //get the video times from storage let sponsorTimeKey = 'sponsorTimes' + videoID; - chrome.storage.sync.get([sponsorTimeKey], function(result) { + chrome.storage.sync.get([sponsorTimeKey, "serverAddress"], function(result) { let sponsorTimes = result[sponsorTimeKey]; + const serverAddress = result.serverAddress; + const userID = result.userID; if (sponsorTimes != undefined && sponsorTimes.length > 0) { //submit these times for (let i = 0; i < sponsorTimes.length; i++) { - getUserID(function(userIDStorage) { //submit the sponsorTime - sendRequestToServer('GET', "/api/postVideoSponsorTimes?videoID=" + videoID + "&startTime=" + sponsorTimes[i][0] + "&endTime=" + sponsorTimes[i][1] - + "&userID=" + userIDStorage, function(xmlhttp, error) { + sendRequestToServer("GET", serverAddress + "/api/postVideoSponsorTimes?videoID=" + videoID + "&startTime=" + sponsorTimes[i][0] + "&endTime=" + sponsorTimes[i][1] + + "&userID=" + userID, function(xmlhttp, error) { if (xmlhttp.readyState == 4 && !error) { callback({ statusCode: xmlhttp.status @@ -169,7 +174,6 @@ function submitTimes(videoID, callback) { statusCode: -1 }); } - }); }); } } @@ -183,63 +187,45 @@ function videoIDChange(currentVideoID, tabId) { id: currentVideoID }); - //not a url change - if (sponsorVideoID == currentVideoID){ - return; - } - sponsorVideoID = currentVideoID; + chrome.storage.sync.get(["sponsorVideoID", "previousVideoID"], function(result) { + const sponsorVideoID = result.sponsorVideoID; + const previousVideoID = result.previousVideoID; - //warn them if they had unsubmitted times - if (previousVideoID != null) { - //get the sponsor times from storage - let sponsorTimeKey = 'sponsorTimes' + previousVideoID; - chrome.storage.sync.get([sponsorTimeKey], function(result) { - let sponsorTimes = result[sponsorTimeKey]; + //not a url change + if (sponsorVideoID == currentVideoID){ + return; + } - if (sponsorTimes != undefined && sponsorTimes.length > 0) { - //warn them that they have unsubmitted sponsor times - chrome.notifications.create("stillThere" + Math.random(), { - type: "basic", - title: "Do you want to submit the sponsor times for watch?v=" + previousVideoID + "?", - message: "You seem to have left some sponsor times unsubmitted. Go back to that page to submit them (they are not deleted).", - iconUrl: "./icons/LogoSponsorBlocker256px.png" - }); - } - - //set the previous video id to the currentID - previousVideoID = currentVideoID; + chrome.storage.sync.set({ + "sponsorVideoID": currentVideoID }); - } else { - previousVideoID = currentVideoID; - } -} -function getUserID(callback) { - if (userID != null) { - callback(userID); - return; - } + //warn them if they had unsubmitted times + if (previousVideoID != null) { + //get the sponsor times from storage + let sponsorTimeKey = 'sponsorTimes' + previousVideoID; + chrome.storage.sync.get([sponsorTimeKey], function(result) { + let sponsorTimes = result[sponsorTimeKey]; - //if it is not cached yet, grab it from storage - chrome.storage.sync.get(["userID"], function(result) { - let userIDStorage = result.userID; - if (userIDStorage != undefined) { - userID = userIDStorage; - callback(userID); + if (sponsorTimes != undefined && sponsorTimes.length > 0) { + //warn them that they have unsubmitted sponsor times + chrome.notifications.create("stillThere" + Math.random(), { + type: "basic", + title: "Do you want to submit the sponsor times for watch?v=" + previousVideoID + "?", + message: "You seem to have left some sponsor times unsubmitted. Go back to that page to submit them (they are not deleted).", + iconUrl: "./icons/LogoSponsorBlocker256px.png" + }); + } + + //set the previous video id to the currentID + chrome.storage.sync.set({ + "previousVideoID": currentVideoID + }); + }); } else { - //double check if a UUID hasn't been created since this was first called - if (userID != null) { - callback(userID); - return; - } - - //generate a userID - userID = generateUUID(); - - //save this UUID - chrome.storage.sync.set({"userID": userID}); - - callback(userID); + chrome.storage.sync.set({ + "previousVideoID": currentVideoID + }); } }); } @@ -247,7 +233,7 @@ function getUserID(callback) { function sendRequestToServer(type, address, callback) { let xmlhttp = new XMLHttpRequest(); - xmlhttp.open(type, serverAddress + address, true); + xmlhttp.open(type, address, true); if (callback != undefined) { xmlhttp.onreadystatechange = function () { @@ -270,4 +256,4 @@ function getYouTubeVideoID(url) { // Return video id or false } //uuid generator function from https://gist.github.com/jed/982883 -function generateUUID(a){return a?(a^Math.random()*16>>a/4).toString(16):([1e7]+-1e3+-4e3+-8e3+-1e11).replace(/[018]/g,generateUUID)} \ No newline at end of file +function generateUUID(a){return a?(a^Math.random()*16>>a/4).toString(16):([1e7]+-1e3+-4e3+-8e3+-1e11).replace(/[018]/g,generateUUID)} diff --git a/config.js.example b/config.js.example index 23cc0be3..399153ea 100644 --- a/config.js.example +++ b/config.js.example @@ -1,3 +1,3 @@ //this file is loaded along iwth content.js //this file sets the server to connect to, and is gitignored -var serverAddress = "https://sponsor.ajay.app"; \ No newline at end of file +var serverAddress = "https://sponsor.ajay.app"; diff --git a/manifest.json b/manifest.json index 1fe36a7c..2391ccb5 100644 --- a/manifest.json +++ b/manifest.json @@ -32,9 +32,7 @@ "icons/downvote.png", "icons/PlayerInfoIconSponsorBlocker256px.png", "icons/PlayerDeleteIconSponsorBlocker256px.png", - "popup.html", - "help/index.html", - "help/style.css" + "popup.html" ], "permissions": [ "tabs", @@ -50,7 +48,8 @@ "scripts":[ "config.js", "background.js" - ] + ], + "persistent": false }, "icons": { "16": "icons/IconSponsorBlocker16px.png", From 0c669d6b8301669a1f427e872898cc34b1556b17 Mon Sep 17 00:00:00 2001 From: Anton Bershanskiy Date: Thu, 8 Aug 2019 13:29:09 -0500 Subject: [PATCH 20/27] Fix: add migration path away from shownInstallPage --- background.js | 22 +++++++++++++++++++--- 1 file changed, 19 insertions(+), 3 deletions(-) diff --git a/background.js b/background.js index b7069994..d60dfb84 100644 --- a/background.js +++ b/background.js @@ -54,12 +54,28 @@ chrome.runtime.onMessage.addListener(function (request, sender, callback) { //add help page on install chrome.runtime.onInstalled.addListener(function (object) { - chrome.storage.sync.get(["userID"], function(result) { + // TODO (shownInstallPage): remove shownInstallPage logic after sufficient amount of time, + // so that people have time to upgrade and move to shownInstallPage-free code. + chrome.storage.sync.get(["userID", "shownInstallPage"], function(result) { const userID = result.userID; + // TODO (shownInstallPage): delete row below + const shownInstallPage = result.shownInstallPage; + // If there is no userID, then it is the first install. if (!userID){ - //open up the install page - chrome.tabs.create({url: chrome.extension.getURL("/help/index.html")}); + // Show install page, if there is no user id + // and there is no shownInstallPage. + // TODO (shownInstallPage): remove this if statement, but leave contents + if (!shownInstallPage){ + //open up the install page + chrome.tabs.create({url: chrome.extension.getURL("/help/index.html")}); + } + + // TODO (shownInstallPage): delete if statement and contents + // If shownInstallPage is set, remove it. + if (!!shownInstallPage){ + chrome.storage.sync.remove("shownInstallPage"); + } //generate a userID const newUserID = generateUUID(); From 7c787b77e869a7c0a5354e5f82f5a0b443f93eee Mon Sep 17 00:00:00 2001 From: Anton Bershanskiy Date: Thu, 8 Aug 2019 14:17:33 -0500 Subject: [PATCH 21/27] Remove unnecessary changes --- config.js.example | 2 +- manifest.json | 4 +++- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/config.js.example b/config.js.example index 399153ea..23cc0be3 100644 --- a/config.js.example +++ b/config.js.example @@ -1,3 +1,3 @@ //this file is loaded along iwth content.js //this file sets the server to connect to, and is gitignored -var serverAddress = "https://sponsor.ajay.app"; +var serverAddress = "https://sponsor.ajay.app"; \ No newline at end of file diff --git a/manifest.json b/manifest.json index 2391ccb5..e84bfac2 100644 --- a/manifest.json +++ b/manifest.json @@ -32,7 +32,9 @@ "icons/downvote.png", "icons/PlayerInfoIconSponsorBlocker256px.png", "icons/PlayerDeleteIconSponsorBlocker256px.png", - "popup.html" + "popup.html", + "help/index.html", + "help/style.css" ], "permissions": [ "tabs", From b34b3f565172d1587be41514e359c4a235566d9b Mon Sep 17 00:00:00 2001 From: Anton Bershanskiy <45960703+bershanskiy@users.noreply.github.com> Date: Thu, 8 Aug 2019 14:21:42 -0500 Subject: [PATCH 22/27] Remove help/* from web_accessible_resources Remove files in help/ directory from web_accessible_resources in manifest.json because the help page opens in context of the extension (no need to expose it to other contexts). --- manifest.json | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/manifest.json b/manifest.json index 1fe36a7c..8c713b64 100644 --- a/manifest.json +++ b/manifest.json @@ -32,9 +32,7 @@ "icons/downvote.png", "icons/PlayerInfoIconSponsorBlocker256px.png", "icons/PlayerDeleteIconSponsorBlocker256px.png", - "popup.html", - "help/index.html", - "help/style.css" + "popup.html" ], "permissions": [ "tabs", From ccafbf663c0cd3c3800a7fd70ece4b65a39a3cda Mon Sep 17 00:00:00 2001 From: Ajay Ramachandran Date: Sat, 10 Aug 2019 19:51:08 -0400 Subject: [PATCH 23/27] Fixed typos. Co-author worked on creating this url parser. Co-Authored-By: Giacomo Rossetto --- utils.js | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/utils.js b/utils.js index 80b4a1f3..2134c1af 100644 --- a/utils.js +++ b/utils.js @@ -1,13 +1,15 @@ function getYouTubeVideoID(url) { - try { // Attempt to parse url + //Attempt to parse url + try { var obj = new URL(url); } catch (e) { console.error("[SB] Unable to parser URL"); return false } - if(!["www.youtube.com","www.youtube-nocookie.com"].includes(obj.host)) return false // Check if valid hostname + //Check if valid hostname + if(!["www.youtube.com","www.youtube-nocookie.com"].includes(obj.host)) return false; if (obj.pathname == "/watch" && obj.searchParams.has("v")) { id = obj.searchParams.get("v"); // Get ID from searchParam @@ -17,7 +19,7 @@ function getYouTubeVideoID(url) { return obj.pathname.substr(7, 11); } catch (e) { console.error("[SB] Video ID not valid"); - return false + return false; } } } From 5be8ecb32b3a69ebd083686d3b711f5e38131c2d Mon Sep 17 00:00:00 2001 From: Ajay Ramachandran Date: Sat, 10 Aug 2019 19:55:39 -0400 Subject: [PATCH 24/27] Fixed up formatting and style. Added more detailed error messages. Changed from var to let. Co-author worked on creating this url parser. Co-Authored-By: Giacomo Rossetto --- utils.js | 20 ++++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-) diff --git a/utils.js b/utils.js index 2134c1af..1a2374b7 100644 --- a/utils.js +++ b/utils.js @@ -1,24 +1,24 @@ function getYouTubeVideoID(url) { - //Attempt to parse url try { - var obj = new URL(url); + let urlObject = new URL(url); } catch (e) { - console.error("[SB] Unable to parser URL"); + console.error("[SB] Unable to parse URL: " + url); return false } //Check if valid hostname - if(!["www.youtube.com","www.youtube-nocookie.com"].includes(obj.host)) return false; + if(!["www.youtube.com","www.youtube-nocookie.com"].includes(urlObject.host)) return false; - if (obj.pathname == "/watch" && obj.searchParams.has("v")) { - id = obj.searchParams.get("v"); // Get ID from searchParam + //Get ID from searchParam + if ((urlObject.pathname == "/watch" || urlObject.pathname == "/watch/") && urlObject.searchParams.has("v")) { + id = urlObject.searchParams.get("v"); return id.length == 11 ? id : false; - } else if (obj.pathname.startsWith("/embed/")) { + } else if (urlObject.pathname.startsWith("/embed/")) { try { - return obj.pathname.substr(7, 11); + return urlObject.pathname.substr(7, 11); } catch (e) { - console.error("[SB] Video ID not valid"); + console.error("[SB] Video ID not valid for " + url); return false; } } @@ -27,7 +27,7 @@ function getYouTubeVideoID(url) { //returns the start time of the video if there was one specified (ex. ?t=5s) function getYouTubeVideoStartTime(url) { let searchParams = new URL(url).searchParams; - var startTime = searchParams.get("t"); + let startTime = searchParams.get("t"); if (startTime == null) { startTime = searchParams.get("time_continue"); } From 15d6a48359926aadc9e769760889bc9db7b673ba Mon Sep 17 00:00:00 2001 From: Ajay Ramachandran Date: Sat, 10 Aug 2019 20:53:43 -0400 Subject: [PATCH 25/27] Fixed url object not being properly defined. --- utils.js | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/utils.js b/utils.js index 1a2374b7..178d4e81 100644 --- a/utils.js +++ b/utils.js @@ -1,7 +1,8 @@ function getYouTubeVideoID(url) { //Attempt to parse url + let urlObject = null; try { - let urlObject = new URL(url); + urlObject = new URL(url); } catch (e) { console.error("[SB] Unable to parse URL: " + url); return false From 30c12e398371eda8c3496d87a3d8a063dbbf83ab Mon Sep 17 00:00:00 2001 From: Ajay Ramachandran Date: Sat, 10 Aug 2019 20:57:11 -0400 Subject: [PATCH 26/27] Reduced errors by getting if the channel is whitelisted after checking it is is a YouTube tab. --- popup.js | 40 ++++++++++++++++++++-------------------- 1 file changed, 20 insertions(+), 20 deletions(-) diff --git a/popup.js b/popup.js index d1186984..96302742 100644 --- a/popup.js +++ b/popup.js @@ -123,26 +123,6 @@ function runThePopup() { } }); - //see if whitelist button should be swapped - chrome.tabs.query({ - active: true, - currentWindow: true - }, tabs => { - chrome.tabs.sendMessage( - tabs[0].id, - {message: 'isChannelWhitelisted'}, - function(response) { - if (response.value) { - SB.whitelistChannel.style.display = "none"; - SB.unwhitelistChannel.style.display = "unset"; - - SB.downloadedSponsorMessageTimes.innerText = "Channel Whitelisted!"; - SB.downloadedSponsorMessageTimes.style.fontWeight = "bold"; - } - }); - } - ); - //if the don't show notice again letiable is true, an option to // disable should be available chrome.storage.sync.get(["dontShowNoticeAgain"], function(result) { @@ -292,6 +272,26 @@ function runThePopup() { SB.videoFound.innerHTML = "No sponsors found" } } + + //see if whitelist button should be swapped + chrome.tabs.query({ + active: true, + currentWindow: true + }, tabs => { + chrome.tabs.sendMessage( + tabs[0].id, + {message: 'isChannelWhitelisted'}, + function(response) { + if (response.value) { + SB.whitelistChannel.style.display = "none"; + SB.unwhitelistChannel.style.display = "unset"; + + SB.downloadedSponsorMessageTimes.innerText = "Channel Whitelisted!"; + SB.downloadedSponsorMessageTimes.style.fontWeight = "bold"; + } + }); + } + ); } function setVideoID(request) { From 699ca91a9430f6715f966533fdb5eceb0a57e7a3 Mon Sep 17 00:00:00 2001 From: Ajay Ramachandran Date: Sat, 10 Aug 2019 22:04:32 -0400 Subject: [PATCH 27/27] Made channel whitelisting properly work on first loaded video. --- content.js | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/content.js b/content.js index 656b0e83..07dae739 100644 --- a/content.js +++ b/content.js @@ -10,10 +10,6 @@ var sponsorVideoID = null; //the time this video is starting at when first played, if not zero var youtubeVideoStartTime = null; -if(id = getYouTubeVideoID(document.URL)){ // Direct Links - videoIDChange(id); -} - //the video var v; @@ -23,6 +19,10 @@ var channelURL; //is this channel whitelised from getting sponsors skipped var channelWhitelisted = false; +if(id = getYouTubeVideoID(document.URL)){ // Direct Links + videoIDChange(id); +} + //the last time looked at (used to see if this time is in the interval) var lastTime = -1;