-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Uses a browser action to communicate with the content script and extr…
…act and print a list, with ability to copy text. Don't think I actually need the browser action though!
- Loading branch information
1 parent
6708187
commit 1551fd6
Showing
6 changed files
with
298 additions
and
8 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,106 @@ | ||
(function() { | ||
/** | ||
* Check and set a global guard variable. | ||
* If this content script is injected into the same page again, | ||
* it will do nothing next time. | ||
*/ | ||
if (window.hasRun) { | ||
console.log('has already run, do nothing'); | ||
|
||
return; | ||
} | ||
window.hasRun = true; | ||
console.log('running for first time...'); | ||
|
||
/** | ||
* Given a URL to a beast image, remove all existing beasts, then | ||
* create and style an IMG node pointing to | ||
* that image, then insert the node into the document. | ||
*/ | ||
function insertBeast(beastURL) { | ||
removeExistingBeasts(); | ||
let beastImage = document.createElement("img"); | ||
beastImage.setAttribute("src", beastURL); | ||
beastImage.style.height = "100vh"; | ||
beastImage.className = "beastify-image"; | ||
document.body.appendChild(beastImage); | ||
} | ||
|
||
/** | ||
* Remove every beast from the page. | ||
*/ | ||
function removeExistingBeasts() { | ||
let existingBeasts = document.querySelectorAll(".beastify-image"); | ||
for (let beast of existingBeasts) { | ||
beast.remove(); | ||
} | ||
} | ||
|
||
function extractLinks() { | ||
// shopping basket items are in li tags with class "basket-item" | ||
|
||
//var all_links = document.getElementsByTagName('a'); | ||
var basket_items = document.querySelectorAll('li.basket-item'); | ||
var basket_items_links = document.querySelectorAll('li.basket-item > a'); | ||
//var basket_items = document.getElementsByClassName('basket-item'); | ||
console.log('basket_items: ') | ||
console.log(basket_items) | ||
console.log('basket_items_links') | ||
console.log(basket_items_links) | ||
var all_items = [] | ||
for (let bi of basket_items) { | ||
var link_in_title = bi.querySelector('.basket-item__title a'); | ||
var abs_url = link_in_title.href; | ||
var wine_desc = link_in_title.text; | ||
var stock_status_span = bi.querySelector('.badge-label'); | ||
try { | ||
var quantity_value_sel = bi.querySelector('.basket-item__quantity-select select'); | ||
var quantity_value = quantity_value_sel.value; | ||
var quantity_unit_sel = bi.querySelector('.basket-item__type select'); | ||
var quantity_unit = quantity_unit_sel.value; | ||
} catch (err) { | ||
var quantity_value = '?'; | ||
var quantity_unit = '?'; | ||
} | ||
//var links_in_item = bi.querySelectorAll('a'); | ||
//var links_in_item = bi.getElementsByTagName('a'); | ||
var item = { | ||
wine: wine_desc, | ||
url: abs_url, | ||
stock: stock_status_span.text, | ||
qty_val: quantity_value, | ||
qty_unit: quantity_unit | ||
}; | ||
all_items.push(item); | ||
//if (links_in_item.length > 0) { | ||
// all_items.push(links_in_item[0]); | ||
//} else { | ||
// console.log('No links in LI: ' + bi); | ||
//} | ||
} | ||
return all_items; | ||
//return [ | ||
//"flub", "flib" | ||
//]; | ||
} | ||
|
||
/** | ||
* Listen for messages from the background script. | ||
* Call "beastify()" or "reset()". | ||
*/ | ||
browser.runtime.onMessage.addListener((message) => { | ||
if (message.command === "beastify") { | ||
insertBeast(message.beastURL); | ||
} else if (message.command === "reset") { | ||
removeExistingBeasts(); | ||
} else if (message.command === "extractLinks") { | ||
links = extractLinks(); | ||
|
||
// will want to send this back as a message, but just log for now... | ||
console.log('links = ', links); | ||
return Promise.resolve(links); | ||
} | ||
}); | ||
|
||
})(); | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,30 @@ | ||
html, body { | ||
width: 800px; | ||
} | ||
|
||
.hidden { | ||
display: none; | ||
} | ||
|
||
button { | ||
border: none; | ||
width: 100%; | ||
margin: 3% auto; | ||
padding: 4px; | ||
text-align: center; | ||
font-size: 1.5em; | ||
cursor: pointer; | ||
background-color: #E5F2F2; | ||
} | ||
|
||
button:hover { | ||
background-color: #CFF2F2; | ||
} | ||
|
||
button[type="reset"] { | ||
background-color: #FBFBC9; | ||
} | ||
|
||
button[type="reset"]:hover { | ||
background-color: #EAEA9D; | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,20 @@ | ||
<!DOCTYPE html> | ||
|
||
<html> | ||
<head> | ||
<meta charset="utf-8"> | ||
<!-- why?? --> | ||
<meta http-equiv="Content-Security-Policy" content="default-src 'self'; style-src 'self';"/> | ||
<link rel="stylesheet" href="copy_wine.css"/> | ||
</head> | ||
|
||
<body> | ||
<div id="link-content"> | ||
</div> | ||
<div id="error-content" class="hidden"> | ||
<p>Couldn't find any links</p> | ||
</div> | ||
<script src="copy_wine.js"></script> | ||
</body> | ||
|
||
</html> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,130 @@ | ||
"use strict"; | ||
|
||
/** | ||
* CSS to hide everything on the page, | ||
* except for elements that have the "beastify-image" class. | ||
*/ | ||
const hidePage = `body > :not(.beastify-image) { | ||
display: none; | ||
}`; | ||
|
||
/** | ||
* Listen for clicks on the buttons, and send the appropriate message to | ||
* the content script in the page. | ||
*/ | ||
function listenForClicks() { | ||
console.log('listenForClicks addingeventlistener'); | ||
|
||
/** | ||
* Given the name of a beast, get the URL to the corresponding image. | ||
*/ | ||
function beastNameToURL(beastName) { | ||
switch (beastName) { | ||
case "Frog": | ||
return browser.runtime.getURL("beasts/frog.jpg"); | ||
case "Snake": | ||
return browser.runtime.getURL("beasts/snake.jpg"); | ||
case "Turtle": | ||
return browser.runtime.getURL("beasts/turtle.jpg"); | ||
} | ||
} | ||
|
||
/** | ||
* Insert the page-hiding CSS into the active tab, | ||
* then get the beast URL and | ||
* send a "beastify" message to the content script in the active tab. | ||
*/ | ||
function beastify(tabs) { | ||
browser.tabs.insertCSS({code: hidePage}).then(() => { | ||
const url = beastNameToURL(e.target.textContent); | ||
browser.tabs.sendMessage(tabs[0].id, { | ||
command: "beastify", | ||
beastURL: url | ||
}); | ||
}); | ||
} | ||
|
||
function requestLinks(tabs) { | ||
var promise = browser.tabs.sendMessage(tabs[0].id, { | ||
command: "extractLinks" | ||
}); | ||
promise.then((all_wines) => { | ||
console.log('got data back!' + all_wines); | ||
|
||
var table = document.createElement("TABLE"); | ||
|
||
for(var i = 0; i < all_wines.length; i++) { | ||
var trow = table.insertRow(i); | ||
var butt = document.createElement('BUTTON'); | ||
var copyString = 'yada yada ' + all_wines[i].wine; | ||
butt.onclick = () => { | ||
navigator.clipboard.writeText(copyString); | ||
} | ||
|
||
butt.innerHTML = 'Copy'; | ||
trow.insertCell().appendChild(butt); | ||
trow.insertCell().innerHTML = all_wines[i].wine; | ||
trow.insertCell().innerHTML = all_wines[i].url; | ||
trow.insertCell().innerHTML = all_wines[i].stock; | ||
trow.insertCell().innerHTML = 'val ' + all_wines[i].qty_val; | ||
trow.insertCell().innerHTML = 'unit ' + all_wines[i].qty_unit; | ||
} | ||
|
||
var theadRow = table.createTHead().insertRow(0); | ||
var headers = ['copy', 'wine', 'url', 'stock', 'qty_val', 'qty_unit']; | ||
for(var i = 0; i < headers.length; i++) { | ||
theadRow.insertCell(i).innerHTML = headers[i]; | ||
} | ||
|
||
var table_place = document.getElementById('link-content'); | ||
table_place.appendChild(table); | ||
}); | ||
} | ||
|
||
/** | ||
* Remove the page-hiding CSS from the active tab, | ||
* send a "reset" message to the content script in the active tab. | ||
*/ | ||
function reset(tabs) { | ||
browser.tabs.removeCSS({code: hidePage}).then(() => { | ||
browser.tabs.sendMessage(tabs[0].id, { | ||
command: "reset", | ||
}); | ||
}); | ||
} | ||
|
||
/** | ||
* Just log the error to the console. | ||
*/ | ||
function reportError(error) { | ||
console.error(`Could not beastify: ${error}`); | ||
} | ||
|
||
/** | ||
* Get the active tab and request it to extract links and send them | ||
* to us. | ||
*/ | ||
browser.tabs.query({active: true, currentWindow: true}) | ||
.then(requestLinks) | ||
.catch(reportError); | ||
} | ||
|
||
/** | ||
* There was an error executing the script. | ||
* Display the popup's error message, and hide the normal UI. | ||
*/ | ||
function reportExecuteScriptError(error) { | ||
document.querySelector("#popup-content").classList.add("hidden"); | ||
document.querySelector("#error-content").classList.remove("hidden"); | ||
console.error(`Failed to execute beastify content script: ${error.message}`); | ||
} | ||
|
||
/** | ||
* When the popup loads, inject a content script into the active tab, | ||
* and add a click handler. | ||
* If we couldn't inject the script, handle the error. | ||
*/ | ||
console.log('inject content script'); | ||
browser.tabs.executeScript({file: "/content_scripts/linkex.js"}) | ||
.then(listenForClicks) | ||
.catch(reportExecuteScriptError); |