Skip to content

Commit e0f89ba

Browse files
authored
Reduce the number of permissions required (#17)
* Reduce the number of permissions required * Update package-lock.json
1 parent 4d46194 commit e0f89ba

File tree

7 files changed

+151
-127
lines changed

7 files changed

+151
-127
lines changed

.eslintrc.json

Lines changed: 11 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,11 @@
1-
{
2-
"env": {
3-
"browser": true,
4-
"es6": true,
5-
"amd": true,
6-
"webextensions": true
7-
}
8-
}
1+
{
2+
"env": {
3+
"browser": true,
4+
"es6": true,
5+
"amd": true,
6+
"webextensions": true
7+
},
8+
"parserOptions": {
9+
"sourceType": "module"
10+
}
11+
}

addon/manifest.json

Lines changed: 28 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -1,29 +1,31 @@
11
{
2-
"manifest_version": 2,
3-
"name": "Advent of Code to Markdown",
4-
"version": "1.0.11",
5-
"description": "Converts a given Advent of Code page to a GitHub-compatible Markdown file.",
6-
"icons": {
7-
"16": "icons/aoc-to-markdown-16.png",
8-
"32": "icons/aoc-to-markdown-32.png",
9-
"48": "icons/aoc-to-markdown-48.png",
10-
"128": "icons/aoc-to-markdown-128.png"
2+
"manifest_version": 2,
3+
"name": "Advent of Code to Markdown",
4+
"version": "1.0.11",
5+
"description": "Converts a given Advent of Code page to a GitHub-compatible Markdown file.",
6+
"icons": {
7+
"16": "icons/aoc-to-markdown-16.png",
8+
"32": "icons/aoc-to-markdown-32.png",
9+
"48": "icons/aoc-to-markdown-48.png",
10+
"128": "icons/aoc-to-markdown-128.png"
11+
},
12+
"background": {
13+
"scripts": ["background_scripts/index.js"]
14+
},
15+
"content_scripts": [
16+
{
17+
"js": ["/content_scripts/index.js"],
18+
"matches": ["*://adventofcode.com/*/day/*"]
19+
}
20+
],
21+
"page_action": {
22+
"default_icon": {
23+
"16": "icons/aoc-to-markdown-16.png",
24+
"32": "icons/aoc-to-markdown-32.png",
25+
"48": "icons/aoc-to-markdown-48.png",
26+
"128": "icons/aoc-to-markdown-128.png"
1127
},
12-
"page_action": {
13-
"default_icon": {
14-
"16": "icons/aoc-to-markdown-16.png",
15-
"32": "icons/aoc-to-markdown-32.png",
16-
"48": "icons/aoc-to-markdown-48.png",
17-
"128": "icons/aoc-to-markdown-128.png"
18-
},
19-
"default_title": "Advent of Code to Markdown"
20-
},
21-
"background": {
22-
"scripts": ["background_scripts/index.js"]
23-
},
24-
"permissions": [
25-
"activeTab",
26-
"tabs",
27-
"downloads"
28-
]
28+
"default_title": "Advent of Code to Markdown"
29+
},
30+
"permissions": ["downloads"]
2931
}

background_scripts/background.js

Lines changed: 36 additions & 38 deletions
Original file line numberDiff line numberDiff line change
@@ -1,47 +1,45 @@
1-
const browser = require("webextension-polyfill");
1+
import {
2+
downloads,
3+
runtime,
4+
pageAction,
5+
tabs as _tabs,
6+
} from "webextension-polyfill";
27

3-
function urlIsApplicable(url) {
4-
const regex = /^https:\/\/adventofcode.com\/\d{4}\/day\/\d{1,2}/;
5-
return regex.test(url);
6-
}
8+
function saveAs(text) {
9+
const blob = new Blob([text], { type: "text/markdown;charset=utf-8" });
710

8-
function initializePageAction(tab) {
9-
if (urlIsApplicable(tab.url)) {
10-
browser.pageAction.show(tab.id);
11-
} else {
12-
browser.pageAction.hide(tab.id);
13-
}
11+
return downloads.download({
12+
url: URL.createObjectURL(blob),
13+
filename: "README.md",
14+
saveAs: true,
15+
});
1416
}
1517

16-
browser.tabs.onUpdated.addListener((id, changeInfo, tab) => {
17-
initializePageAction(tab);
18-
});
19-
20-
browser.runtime.onMessage.addListener((message) => {
21-
if (message.action === "saveAs") {
22-
const blob = new Blob([message.text], { type: "text/markdown;charset=utf-8" });
18+
runtime.onMessage.addListener((data, sender) => {
19+
switch (data.action) {
20+
case "saveAs":
21+
saveAs(data.text).catch((err) => {
22+
console.error('Failed to save content', err);
23+
});
24+
break;
2325

24-
browser.downloads.download({
25-
url: URL.createObjectURL(blob),
26-
filename: "README.md",
27-
saveAs: true,
28-
}).catch((e) => {
29-
console.error(e);
30-
});
31-
} else {
32-
console.warn(`Unknown action: ${message.action}`);
33-
}
34-
});
26+
case "showPageAction":
27+
pageAction.show(sender.tab.id);
28+
break;
3529

36-
browser.pageAction.onClicked.addListener(() => {
37-
browser.tabs.executeScript({file: "/content_scripts/index.js"})
38-
.catch((e) => {
39-
console.error(e);
40-
});
30+
default:
31+
console.warn("Unknown action", data.action);
32+
break;
33+
}
4134
});
4235

43-
browser.tabs.query({}).then((tabs) => {
44-
for (const tab of tabs) {
45-
initializePageAction(tab);
46-
}
36+
pageAction.onClicked.addListener(() => {
37+
_tabs
38+
.query({ active: true, currentWindow: true })
39+
.then((tabs) => {
40+
return _tabs.sendMessage(tabs[0].id, { action: "capturePage" });
41+
})
42+
.catch((e) => {
43+
console.error("Failed to send 'capturePage' message", e);
44+
});
4745
});

content_scripts/on-loaded.js

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
import { runtime } from "webextension-polyfill";
2+
3+
runtime
4+
.sendMessage({
5+
action: "showPageAction",
6+
})
7+
.catch((err) =>
8+
console.error("Failed to send 'showPageAction' message", err)
9+
);

content_scripts/to-markdown.js

Lines changed: 46 additions & 37 deletions
Original file line numberDiff line numberDiff line change
@@ -1,56 +1,65 @@
1-
const browser = require("webextension-polyfill");
2-
const gfm = require('turndown-plugin-gfm').gfm;
3-
const TurndownService = require('turndown').default;
4-
5-
function stripHyphens (str) {
6-
const regex = /^--- (.+) ---$/;
7-
return str.replace(regex, (match, p1) => {
8-
return p1;
9-
});
1+
import { runtime } from "webextension-polyfill";
2+
import { gfm } from "turndown-plugin-gfm";
3+
import TurndownService from "turndown";
4+
5+
function stripHyphens(str) {
6+
const regex = /^--- (.+) ---$/;
7+
return str.replace(regex, (match, p1) => {
8+
return p1;
9+
});
1010
}
1111

12-
const newDoc = document.createDocumentFragment();
13-
const titleElement = document.createElement('h1');
14-
newDoc.appendChild(titleElement);
12+
function capturePage() {
13+
const newDoc = document.createDocumentFragment();
14+
const titleElement = document.createElement("h1");
15+
newDoc.appendChild(titleElement);
1516

16-
const link = document.createElement('a');
17-
const href = window.location.origin + window.location.pathname
18-
link.href = href;
19-
link.innerText = href;
20-
newDoc.appendChild(link);
17+
const link = document.createElement("a");
18+
const href = window.location.origin + window.location.pathname;
19+
link.href = href;
20+
link.innerText = href;
21+
newDoc.appendChild(link);
2122

22-
const descriptionHeader = document.createElement('h2');
23-
descriptionHeader.innerText = 'Description';
24-
newDoc.appendChild(descriptionHeader);
23+
const descriptionHeader = document.createElement("h2");
24+
descriptionHeader.innerText = "Description";
25+
newDoc.appendChild(descriptionHeader);
2526

26-
const articleElements = document.querySelectorAll('article');
27-
const articleElementsLength = articleElements.length;
28-
for (let index = 0; index < articleElementsLength; ++index) {
27+
const articleElements = document.querySelectorAll("article");
28+
const articleElementsLength = articleElements.length;
29+
for (let index = 0; index < articleElementsLength; ++index) {
2930
const article = articleElements[index].cloneNode(true);
30-
const headingElement = article.querySelector('h2');
31+
const headingElement = article.querySelector("h2");
3132
let heading = stripHyphens(headingElement.innerText);
3233

3334
if (index === 0) {
34-
titleElement.innerText = heading;
35-
heading = 'Part One';
35+
titleElement.innerText = heading;
36+
heading = "Part One";
3637
}
3738

38-
const newHeadingElement = document.createElement('h3');
39+
const newHeadingElement = document.createElement("h3");
3940
newHeadingElement.innerText = heading;
4041
headingElement.replaceWith(newHeadingElement);
4142

4243
newDoc.appendChild(article);
43-
}
44+
}
4445

45-
const turndownService = new TurndownService({
46-
headingStyle: 'atx'
47-
});
48-
turndownService.use(gfm);
49-
turndownService.keep(['span']);
46+
const turndownService = new TurndownService({
47+
headingStyle: "atx",
48+
});
49+
turndownService.use(gfm);
50+
turndownService.keep(["span"]);
5051

51-
const markdown = turndownService.turndown(newDoc).concat('\n');
52+
return turndownService.turndown(newDoc).concat("\n");
53+
}
5254

53-
browser.runtime.sendMessage({
54-
action: "saveAs",
55-
text: markdown,
55+
runtime.onMessage.addListener((data) => {
56+
if (data.action === "capturePage") {
57+
const markdown = capturePage();
58+
return runtime
59+
.sendMessage({
60+
action: "saveAs",
61+
text: markdown,
62+
})
63+
.catch((err) => console.error("Failed to send 'saveAs' message", err));
64+
}
5665
});

package-lock.json

Lines changed: 5 additions & 5 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

webpack.config.js

Lines changed: 16 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,16 @@
1-
const path = require("path");
2-
3-
module.exports = {
4-
mode: "production",
5-
entry: {
6-
background_scripts: "./background_scripts/background.js",
7-
content_scripts: "./content_scripts/to-markdown.js"
8-
},
9-
output: {
10-
path: path.resolve(__dirname, "addon"),
11-
filename: "[name]/index.js"
12-
}
13-
};
1+
const path = require("path");
2+
3+
module.exports = {
4+
mode: "production",
5+
entry: {
6+
background_scripts: ["./background_scripts/background.js"],
7+
content_scripts: [
8+
"./content_scripts/on-loaded.js",
9+
"./content_scripts/to-markdown.js",
10+
],
11+
},
12+
output: {
13+
path: path.resolve(__dirname, "addon"),
14+
filename: "[name]/index.js",
15+
},
16+
};

0 commit comments

Comments
 (0)