parent
1af01856e1
commit
6282f54ac0
30
lib/i18n.ts
30
lib/i18n.ts
@ -4,7 +4,7 @@
|
||||
import {memoize} from "./memoize";
|
||||
import langs from "../_locales/all.json";
|
||||
import { sorted, naturalCaseCompare } from "./sorting";
|
||||
|
||||
import lf from "localforage";
|
||||
|
||||
export const ALL_LANGS = Object.freeze(new Map<string, string>(
|
||||
sorted(Object.entries(langs), e => {
|
||||
@ -123,14 +123,16 @@ async function fetchLanguage(code: string) {
|
||||
}
|
||||
|
||||
|
||||
function loadCached() {
|
||||
if (document.location.pathname.includes("/windows/")) {
|
||||
const cached = localStorage.getItem(CACHE_KEY);
|
||||
if (cached) {
|
||||
return JSON.parse(cached) as any[];
|
||||
}
|
||||
async function loadCached() {
|
||||
const cached = await lf.getItem<string>(CACHE_KEY);
|
||||
if (!cached) {
|
||||
return null;
|
||||
}
|
||||
return null;
|
||||
const parsed = JSON.parse(cached);
|
||||
if (Array.isArray(parsed)) {
|
||||
return null;
|
||||
}
|
||||
return parsed;
|
||||
}
|
||||
|
||||
async function loadRawLocales() {
|
||||
@ -187,16 +189,16 @@ async function load(): Promise<Localization> {
|
||||
}
|
||||
CURRENT = currentLang;
|
||||
// en is the base locale
|
||||
let valid = loadCached();
|
||||
let valid = await loadCached();
|
||||
if (!valid) {
|
||||
valid = await loadRawLocales();
|
||||
localStorage.setItem(CACHE_KEY, JSON.stringify(valid));
|
||||
await lf.setItem(CACHE_KEY, JSON.stringify(valid));
|
||||
}
|
||||
if (!valid.length) {
|
||||
throw new Error("Could not lood ANY of these locales");
|
||||
}
|
||||
|
||||
const custom = localStorage.getItem(CUSTOM_KEY);
|
||||
const custom = await lf.getItem<string>(CUSTOM_KEY);
|
||||
if (custom) {
|
||||
try {
|
||||
valid.push(JSON.parse(custom));
|
||||
@ -302,11 +304,11 @@ export async function localize<T extends HTMLElement | DocumentFragment>(
|
||||
return localize_(elem);
|
||||
}
|
||||
|
||||
export function saveCustomLocale(data?: string) {
|
||||
export async function saveCustomLocale(data?: string) {
|
||||
if (!data) {
|
||||
localStorage.removeItem(CUSTOM_KEY);
|
||||
await lf.removeItem(CUSTOM_KEY);
|
||||
return;
|
||||
}
|
||||
new Localization(JSON.parse(data));
|
||||
localStorage.setItem(CUSTOM_KEY, data);
|
||||
await localStorage.setItem(CUSTOM_KEY, data);
|
||||
}
|
||||
|
@ -4,9 +4,11 @@
|
||||
import { downloads, CHROME } from "./browser";
|
||||
import { EventEmitter } from "../uikit/lib/events";
|
||||
import { PromiseSerializer } from "./pserializer";
|
||||
import lf from "localforage";
|
||||
|
||||
|
||||
const VERSION = 1;
|
||||
const STORE = "iconcache";
|
||||
|
||||
// eslint-disable-next-line no-magic-numbers
|
||||
const CACHE_SIZES = CHROME ? [16, 32] : [16, 32, 64, 127];
|
||||
|
||||
@ -48,37 +50,17 @@ const SYNONYMS = Object.freeze(new Map<string, string>([
|
||||
]));
|
||||
|
||||
export const IconCache = new class IconCache extends EventEmitter {
|
||||
private db: Promise<IDBDatabase>;
|
||||
private db = lf.createInstance({name: STORE});
|
||||
|
||||
private cache: Map<string, string>;
|
||||
|
||||
constructor() {
|
||||
super();
|
||||
this.db = this.init();
|
||||
this.cache = new Map();
|
||||
this.get = PromiseSerializer.wrapNew(8, this, this.get);
|
||||
this.set = PromiseSerializer.wrapNew(1, this, this.set);
|
||||
}
|
||||
|
||||
private async init() {
|
||||
return await new Promise<IDBDatabase>((resolve, reject) => {
|
||||
const req = indexedDB.open(STORE, VERSION);
|
||||
req.onupgradeneeded = evt => {
|
||||
const db = req.result;
|
||||
switch (evt.oldVersion) {
|
||||
case 0: {
|
||||
db.createObjectStore(STORE);
|
||||
break;
|
||||
}
|
||||
}
|
||||
};
|
||||
req.onerror = ex => reject(ex);
|
||||
req.onsuccess = () => {
|
||||
resolve(req.result);
|
||||
};
|
||||
});
|
||||
}
|
||||
|
||||
private normalize(ext: string) {
|
||||
ext = ext.toLocaleLowerCase();
|
||||
return SYNONYMS.get(ext) || ext;
|
||||
@ -95,36 +77,25 @@ export const IconCache = new class IconCache extends EventEmitter {
|
||||
if (rv) {
|
||||
return rv;
|
||||
}
|
||||
const db = await this.db;
|
||||
rv = this.cache.get(sext);
|
||||
if (rv) {
|
||||
return rv;
|
||||
}
|
||||
return await new Promise<string | undefined>(resolve => {
|
||||
const trans = db.transaction(STORE, "readonly");
|
||||
trans.onerror = () => resolve(undefined);
|
||||
const store = trans.objectStore(STORE);
|
||||
const req = store.get(sext);
|
||||
req.onerror = () => resolve(undefined);
|
||||
req.onsuccess = () => {
|
||||
const rv = this.cache.get(sext);
|
||||
if (rv) {
|
||||
resolve(rv);
|
||||
return;
|
||||
}
|
||||
let {result} = req;
|
||||
if (!result) {
|
||||
resolve(undefined);
|
||||
return;
|
||||
}
|
||||
if (typeof req.result !== "string") {
|
||||
result = URL.createObjectURL(result).toString();
|
||||
}
|
||||
this.cache.set(sext, result);
|
||||
this.cache.set(ext, "");
|
||||
resolve(result);
|
||||
};
|
||||
});
|
||||
let result = await this.db.getItem<any>(sext);
|
||||
if (!result) {
|
||||
return this.cache.get(sext);
|
||||
}
|
||||
rv = this.cache.get(sext);
|
||||
if (rv) {
|
||||
return rv;
|
||||
}
|
||||
if (typeof result !== "string") {
|
||||
result = URL.createObjectURL(result).toString();
|
||||
}
|
||||
|
||||
this.cache.set(sext, result);
|
||||
this.cache.set(ext, "");
|
||||
return result;
|
||||
}
|
||||
|
||||
async set(ext: string, manId: number) {
|
||||
@ -145,18 +116,9 @@ export const IconCache = new class IconCache extends EventEmitter {
|
||||
}
|
||||
for (const {size, icon} of urls) {
|
||||
this.cache.set(`${ext}-${size}`, URL.createObjectURL(icon));
|
||||
await this.db.setItem(`${ext}-${size}`, icon);
|
||||
}
|
||||
this.cache.set(ext, "");
|
||||
const db = await this.db;
|
||||
await new Promise((resolve, reject) => {
|
||||
const trans = db.transaction(STORE, "readwrite");
|
||||
trans.onerror = reject;
|
||||
trans.oncomplete = resolve;
|
||||
const store = trans.objectStore(STORE);
|
||||
for (const {size, icon} of urls) {
|
||||
store.put(icon, `${ext}-${size}`);
|
||||
}
|
||||
});
|
||||
this.emit("cached", ext);
|
||||
}
|
||||
}();
|
||||
|
@ -35,6 +35,7 @@
|
||||
"dependencies": {
|
||||
"@types/psl": "^1.1.0",
|
||||
"@types/whatwg-mimetype": "^2.1.0",
|
||||
"localforage": "^1.9.0",
|
||||
"psl": "^1.4.0",
|
||||
"webextension-polyfill": "^0.5.0",
|
||||
"whatwg-mimetype": "^2.3.0"
|
||||
|
@ -641,10 +641,11 @@ addEventListener("DOMContentLoaded", async () => {
|
||||
$<HTMLInputElement>("#loadCustomLocale").addEventListener("click", () => {
|
||||
customLocale.click();
|
||||
});
|
||||
$<HTMLInputElement>("#clearCustomLocale").addEventListener("click", () => {
|
||||
saveCustomLocale(undefined);
|
||||
runtime.reload();
|
||||
});
|
||||
$<HTMLInputElement>("#clearCustomLocale").
|
||||
addEventListener("click", async () => {
|
||||
await saveCustomLocale(undefined);
|
||||
runtime.reload();
|
||||
});
|
||||
customLocale.addEventListener("change", async () => {
|
||||
if (!customLocale.files || !customLocale.files.length) {
|
||||
return;
|
||||
@ -662,7 +663,8 @@ addEventListener("DOMContentLoaded", async () => {
|
||||
reader.onerror = reject;
|
||||
reader.readAsText(file);
|
||||
});
|
||||
saveCustomLocale(text);
|
||||
await saveCustomLocale(text);
|
||||
|
||||
if (confirm("Imported your file.\nWant to relaod the extension now?")) {
|
||||
runtime.reload();
|
||||
}
|
||||
|
19
yarn.lock
19
yarn.lock
@ -1745,6 +1745,11 @@ ignore@^4.0.6:
|
||||
resolved "https://registry.yarnpkg.com/ignore/-/ignore-4.0.6.tgz#750e3db5862087b4737ebac8207ffd1ef27b25fc"
|
||||
integrity sha512-cyFDKrqc/YdcWFniJhzI42+AzS+gNwmUzOSFcRCQYwySuBBBy/KjuxWLZ/FHEH6Moq1NizMOBWyTcv8O4OZIMg==
|
||||
|
||||
immediate@~3.0.5:
|
||||
version "3.0.6"
|
||||
resolved "https://registry.yarnpkg.com/immediate/-/immediate-3.0.6.tgz#9db1dbd0faf8de6fbe0f5dd5e56bb606280de69b"
|
||||
integrity sha1-nbHb0Pr43m++D13V5Wu2BigN5ps=
|
||||
|
||||
import-fresh@^3.0.0:
|
||||
version "3.2.1"
|
||||
resolved "https://registry.yarnpkg.com/import-fresh/-/import-fresh-3.2.1.tgz#633ff618506e793af5ac91bf48b72677e15cbe66"
|
||||
@ -2084,6 +2089,13 @@ levn@^0.3.0, levn@~0.3.0:
|
||||
prelude-ls "~1.1.2"
|
||||
type-check "~0.3.2"
|
||||
|
||||
lie@3.1.1:
|
||||
version "3.1.1"
|
||||
resolved "https://registry.yarnpkg.com/lie/-/lie-3.1.1.tgz#9a436b2cc7746ca59de7a41fa469b3efb76bd87e"
|
||||
integrity sha1-mkNrLMd0bKWd56QfpGmz77dr2H4=
|
||||
dependencies:
|
||||
immediate "~3.0.5"
|
||||
|
||||
loader-runner@^2.4.0:
|
||||
version "2.4.0"
|
||||
resolved "https://registry.yarnpkg.com/loader-runner/-/loader-runner-2.4.0.tgz#ed47066bfe534d7e84c4c7b9998c2a75607d9357"
|
||||
@ -2098,6 +2110,13 @@ loader-utils@^1.0.2, loader-utils@^1.2.3, loader-utils@^1.4.0:
|
||||
emojis-list "^3.0.0"
|
||||
json5 "^1.0.1"
|
||||
|
||||
localforage@^1.9.0:
|
||||
version "1.9.0"
|
||||
resolved "https://registry.yarnpkg.com/localforage/-/localforage-1.9.0.tgz#f3e4d32a8300b362b4634cc4e066d9d00d2f09d1"
|
||||
integrity sha512-rR1oyNrKulpe+VM9cYmcFn6tsHuokyVHFaCM3+osEmxaHTbEk8oQu6eGDfS6DQLWi/N67XRmB8ECG37OES368g==
|
||||
dependencies:
|
||||
lie "3.1.1"
|
||||
|
||||
locate-path@^3.0.0:
|
||||
version "3.0.0"
|
||||
resolved "https://registry.yarnpkg.com/locate-path/-/locate-path-3.0.0.tgz#dbec3b3ab759758071b58fe59fc41871af21400e"
|
||||
|
Loading…
x
Reference in New Issue
Block a user