forked from dnbard/dou-black-list
-
Notifications
You must be signed in to change notification settings - Fork 0
/
settings.ts
127 lines (114 loc) · 3.42 KB
/
settings.ts
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
const SETTINGS_SELECTORS = {
userProfile: ".min-profile",
aboutUser: ".b-user-info",
};
const exportId = STORAGE_KEY + "export";
const importId = STORAGE_KEY + "import";
const importIdFile = STORAGE_KEY + "import_file";
function getSettingsHtml(settings) {
// language=HTML
return `
<h3>Dou Block List Settings</h3>
<p>
Currently, there are ${
Object.keys(settings).length
} folks in the ban list.
</p>
<p>
<label>
<button type="button" id="${exportId}">📩</button>
Export block list as json file
</label>
</p>
<p>
<input type="file" style="display: none" id="${importIdFile}">
<label>
<button type="button" id="${importId}">📤</button>
Import block list from json file
</label>
</p>
`;
}
function isOnSettingsPage() {
const minProfile = document.querySelectorAll(
SETTINGS_SELECTORS.userProfile
)[0] as HTMLAnchorElement;
return (
minProfile.tagName === "A" && minProfile.href === document.location.href
);
}
function getOnFileUpload(importFileInput) {
return () => {
const fr = new FileReader();
fr.onload = function (e) {
const result = JSON.parse(e.target.result.toString());
updateStorageWithSettings(result);
};
fr.readAsText(importFileInput.files.item(0));
};
}
function attachEventListeners(injectElement) {
const exportButton: HTMLButtonElement = injectElement.querySelector(
`#${exportId}`
);
const importButton: HTMLButtonElement = injectElement.querySelector(
`#${importId}`
);
const importFileInput: HTMLInputElement = injectElement.querySelector(
`#${importIdFile}`
);
exportButton.onclick = downloadSettings;
importButton.onclick = openUploadDialog;
importFileInput.onchange = getOnFileUpload(importFileInput);
}
function getInjectElement() {
const aboutUser = document.querySelectorAll(SETTINGS_SELECTORS.aboutUser)[0];
return aboutUser.parentElement;
}
function renderSettings(settings) {
const settingsElement = document.createElement("article");
settingsElement.className = "b-typo";
settingsElement.id = STORAGE_KEY;
settingsElement.innerHTML = getSettingsHtml(settings);
const injectElement = getInjectElement();
const existingSettings = injectElement.querySelectorAll(`#${STORAGE_KEY}`)[0];
if (existingSettings) {
injectElement.removeChild(existingSettings);
}
injectElement.appendChild(settingsElement);
attachEventListeners(injectElement);
}
function openUploadDialog() {
document.getElementById(importIdFile).click();
}
function updateStorageWithSettings(settings) {
if (!ensureSettings(settings)) {
return;
}
localStorage.setItem(STORAGE_KEY, JSON.stringify(settings));
renderSettings(getStorage());
}
function ensureSettings(settings) {
return (
!Array.isArray(settings) &&
typeof settings === "object" &&
Object.keys(settings).every((key) => key !== "undefined")
);
}
function downloadSettings() {
const storage = getStorage();
const json: string = JSON.stringify(storage, null, 2);
const blob = new Blob([json], { type: "octet/stream" });
const a = document.createElement("a");
a.href = window.URL.createObjectURL(blob);
a.download = `dou-block-list-${Object.keys(storage).length}-items.json`;
a.setAttribute("style", "display: none;");
a.rel = "noopener noreferrer";
a.click();
}
(() => {
if (!isOnSettingsPage()) {
return;
}
renderSettings(getStorage());
})();