@freqhole/reliquary 0.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/automerge/acl-filtering.d.ts +87 -0
- package/dist/automerge/acl-filtering.d.ts.map +1 -0
- package/dist/automerge/acl-filtering.js +138 -0
- package/dist/automerge/acl-filtering.test.d.ts +2 -0
- package/dist/automerge/acl-filtering.test.d.ts.map +1 -0
- package/dist/automerge/acl-filtering.test.js +302 -0
- package/dist/automerge/index.d.ts +5 -0
- package/dist/automerge/index.d.ts.map +1 -0
- package/dist/automerge/index.js +7 -0
- package/dist/automerge/iroh-network-adapter.d.ts +178 -0
- package/dist/automerge/iroh-network-adapter.d.ts.map +1 -0
- package/dist/automerge/iroh-network-adapter.js +691 -0
- package/dist/automerge/iroh-network-adapter.test.d.ts +2 -0
- package/dist/automerge/iroh-network-adapter.test.d.ts.map +1 -0
- package/dist/automerge/iroh-network-adapter.test.js +818 -0
- package/dist/automerge/types.d.ts +66 -0
- package/dist/automerge/types.d.ts.map +1 -0
- package/dist/automerge/types.js +10 -0
- package/dist/blobs/bytes-backend.d.ts +41 -0
- package/dist/blobs/bytes-backend.d.ts.map +1 -0
- package/dist/blobs/bytes-backend.js +252 -0
- package/dist/blobs/bytes-backend.test.d.ts +2 -0
- package/dist/blobs/bytes-backend.test.d.ts.map +1 -0
- package/dist/blobs/bytes-backend.test.js +241 -0
- package/dist/blobs/db.d.ts +8 -0
- package/dist/blobs/db.d.ts.map +1 -0
- package/dist/blobs/db.js +141 -0
- package/dist/blobs/db.test.d.ts +2 -0
- package/dist/blobs/db.test.d.ts.map +1 -0
- package/dist/blobs/db.test.js +120 -0
- package/dist/blobs/index.d.ts +5 -0
- package/dist/blobs/index.d.ts.map +1 -0
- package/dist/blobs/index.js +2 -0
- package/dist/blobs/store.d.ts +47 -0
- package/dist/blobs/store.d.ts.map +1 -0
- package/dist/blobs/store.js +263 -0
- package/dist/blobs/store.test.d.ts +2 -0
- package/dist/blobs/store.test.d.ts.map +1 -0
- package/dist/blobs/store.test.js +377 -0
- package/dist/blobs/types.d.ts +55 -0
- package/dist/blobs/types.d.ts.map +1 -0
- package/dist/blobs/types.js +8 -0
- package/dist/ensure/client.d.ts +19 -0
- package/dist/ensure/client.d.ts.map +1 -0
- package/dist/ensure/client.js +74 -0
- package/dist/ensure/client.test.d.ts +2 -0
- package/dist/ensure/client.test.d.ts.map +1 -0
- package/dist/ensure/client.test.js +133 -0
- package/dist/ensure/index.d.ts +4 -0
- package/dist/ensure/index.d.ts.map +1 -0
- package/dist/ensure/index.js +4 -0
- package/dist/ensure/responder.d.ts +20 -0
- package/dist/ensure/responder.d.ts.map +1 -0
- package/dist/ensure/responder.js +100 -0
- package/dist/ensure/responder.test.d.ts +2 -0
- package/dist/ensure/responder.test.d.ts.map +1 -0
- package/dist/ensure/responder.test.js +191 -0
- package/dist/ensure/types.d.ts +19 -0
- package/dist/ensure/types.d.ts.map +1 -0
- package/dist/ensure/types.js +4 -0
- package/dist/ensure/types.test.d.ts +2 -0
- package/dist/ensure/types.test.d.ts.map +1 -0
- package/dist/ensure/types.test.js +81 -0
- package/dist/index.d.ts +2 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +3 -0
- package/dist/index.test.d.ts +2 -0
- package/dist/index.test.d.ts.map +1 -0
- package/dist/index.test.js +7 -0
- package/dist/solid/blob-url.d.ts +10 -0
- package/dist/solid/blob-url.d.ts.map +1 -0
- package/dist/solid/blob-url.js +34 -0
- package/dist/solid/blob-url.test.d.ts +2 -0
- package/dist/solid/blob-url.test.d.ts.map +1 -0
- package/dist/solid/blob-url.test.js +62 -0
- package/dist/solid/connection-summary.d.ts +25 -0
- package/dist/solid/connection-summary.d.ts.map +1 -0
- package/dist/solid/connection-summary.js +29 -0
- package/dist/solid/connection-summary.test.d.ts +2 -0
- package/dist/solid/connection-summary.test.d.ts.map +1 -0
- package/dist/solid/connection-summary.test.js +57 -0
- package/dist/solid/doc-store.d.ts +29 -0
- package/dist/solid/doc-store.d.ts.map +1 -0
- package/dist/solid/doc-store.js +79 -0
- package/dist/solid/doc-store.test.d.ts +2 -0
- package/dist/solid/doc-store.test.d.ts.map +1 -0
- package/dist/solid/doc-store.test.js +234 -0
- package/dist/solid/index.d.ts +4 -0
- package/dist/solid/index.d.ts.map +1 -0
- package/dist/solid/index.js +9 -0
- package/dist/solid/transfer-progress.d.ts +21 -0
- package/dist/solid/transfer-progress.d.ts.map +1 -0
- package/dist/solid/transfer-progress.js +32 -0
- package/dist/solid/transfer-progress.test.d.ts +2 -0
- package/dist/solid/transfer-progress.test.d.ts.map +1 -0
- package/dist/solid/transfer-progress.test.js +76 -0
- package/dist/testing/blob-fixtures.d.ts +19 -0
- package/dist/testing/blob-fixtures.d.ts.map +1 -0
- package/dist/testing/blob-fixtures.js +46 -0
- package/dist/testing/blob-fixtures.test.d.ts +2 -0
- package/dist/testing/blob-fixtures.test.d.ts.map +1 -0
- package/dist/testing/blob-fixtures.test.js +46 -0
- package/dist/testing/idb-harness.d.ts +10 -0
- package/dist/testing/idb-harness.d.ts.map +1 -0
- package/dist/testing/idb-harness.js +17 -0
- package/dist/testing/idb-harness.test.d.ts +2 -0
- package/dist/testing/idb-harness.test.d.ts.map +1 -0
- package/dist/testing/idb-harness.test.js +48 -0
- package/dist/testing/index.d.ts +7 -0
- package/dist/testing/index.d.ts.map +1 -0
- package/dist/testing/index.js +11 -0
- package/dist/testing/media.d.ts +15 -0
- package/dist/testing/media.d.ts.map +1 -0
- package/dist/testing/media.js +37 -0
- package/dist/testing/media.test.d.ts +2 -0
- package/dist/testing/media.test.d.ts.map +1 -0
- package/dist/testing/media.test.js +47 -0
- package/dist/testing/mock-blob-fetch.d.ts +33 -0
- package/dist/testing/mock-blob-fetch.d.ts.map +1 -0
- package/dist/testing/mock-blob-fetch.js +39 -0
- package/dist/testing/mock-blob-fetch.test.d.ts +2 -0
- package/dist/testing/mock-blob-fetch.test.d.ts.map +1 -0
- package/dist/testing/mock-blob-fetch.test.js +65 -0
- package/dist/testing/mock-node.d.ts +36 -0
- package/dist/testing/mock-node.d.ts.map +1 -0
- package/dist/testing/mock-node.js +97 -0
- package/dist/testing/mock-node.test.d.ts +2 -0
- package/dist/testing/mock-node.test.d.ts.map +1 -0
- package/dist/testing/mock-node.test.js +66 -0
- package/dist/testing/streams.d.ts +68 -0
- package/dist/testing/streams.d.ts.map +1 -0
- package/dist/testing/streams.js +99 -0
- package/dist/testing/streams.test.d.ts +2 -0
- package/dist/testing/streams.test.d.ts.map +1 -0
- package/dist/testing/streams.test.js +82 -0
- package/dist/transfer/cancellation.d.ts +8 -0
- package/dist/transfer/cancellation.d.ts.map +1 -0
- package/dist/transfer/cancellation.js +19 -0
- package/dist/transfer/index.d.ts +8 -0
- package/dist/transfer/index.d.ts.map +1 -0
- package/dist/transfer/index.js +4 -0
- package/dist/transfer/prefetch.d.ts +38 -0
- package/dist/transfer/prefetch.d.ts.map +1 -0
- package/dist/transfer/prefetch.js +61 -0
- package/dist/transfer/prefetch.test.d.ts +2 -0
- package/dist/transfer/prefetch.test.d.ts.map +1 -0
- package/dist/transfer/prefetch.test.js +136 -0
- package/dist/transfer/serve.d.ts +66 -0
- package/dist/transfer/serve.d.ts.map +1 -0
- package/dist/transfer/serve.js +126 -0
- package/dist/transfer/serve.test.d.ts +2 -0
- package/dist/transfer/serve.test.d.ts.map +1 -0
- package/dist/transfer/serve.test.js +101 -0
- package/dist/transfer/snatch.d.ts +39 -0
- package/dist/transfer/snatch.d.ts.map +1 -0
- package/dist/transfer/snatch.js +289 -0
- package/dist/transfer/snatch.test.d.ts +2 -0
- package/dist/transfer/snatch.test.d.ts.map +1 -0
- package/dist/transfer/snatch.test.js +337 -0
- package/dist/transfer/types.d.ts +85 -0
- package/dist/transfer/types.d.ts.map +1 -0
- package/dist/transfer/types.js +15 -0
- package/dist/utils/hash.d.ts +13 -0
- package/dist/utils/hash.d.ts.map +1 -0
- package/dist/utils/hash.js +31 -0
- package/dist/utils/hash.test.d.ts +2 -0
- package/dist/utils/hash.test.d.ts.map +1 -0
- package/dist/utils/hash.test.js +56 -0
- package/dist/utils/image-utils.d.ts +28 -0
- package/dist/utils/image-utils.d.ts.map +1 -0
- package/dist/utils/image-utils.js +113 -0
- package/dist/utils/image-utils.test.d.ts +2 -0
- package/dist/utils/image-utils.test.d.ts.map +1 -0
- package/dist/utils/image-utils.test.js +181 -0
- package/dist/utils/index.d.ts +4 -0
- package/dist/utils/index.d.ts.map +1 -0
- package/dist/utils/index.js +3 -0
- package/dist/utils/log.d.ts +22 -0
- package/dist/utils/log.d.ts.map +1 -0
- package/dist/utils/log.js +100 -0
- package/dist/utils/log.test.d.ts +2 -0
- package/dist/utils/log.test.d.ts.map +1 -0
- package/dist/utils/log.test.js +113 -0
- package/dist/worker/blob-worker-client.d.ts +118 -0
- package/dist/worker/blob-worker-client.d.ts.map +1 -0
- package/dist/worker/blob-worker-client.js +361 -0
- package/dist/worker/blob-worker-client.test.d.ts +2 -0
- package/dist/worker/blob-worker-client.test.d.ts.map +1 -0
- package/dist/worker/blob-worker-client.test.js +137 -0
- package/dist/worker/blob-worker-logic.d.ts +120 -0
- package/dist/worker/blob-worker-logic.d.ts.map +1 -0
- package/dist/worker/blob-worker-logic.js +368 -0
- package/dist/worker/blob-worker-logic.test.d.ts +2 -0
- package/dist/worker/blob-worker-logic.test.d.ts.map +1 -0
- package/dist/worker/blob-worker-logic.test.js +191 -0
- package/dist/worker/blob-worker.d.ts +21 -0
- package/dist/worker/blob-worker.d.ts.map +1 -0
- package/dist/worker/blob-worker.js +44 -0
- package/dist/worker/index.d.ts +12 -0
- package/dist/worker/index.d.ts.map +1 -0
- package/dist/worker/index.js +6 -0
- package/dist/worker/midden-blake3.d.ts +23 -0
- package/dist/worker/midden-blake3.d.ts.map +1 -0
- package/dist/worker/midden-blake3.js +47 -0
- package/dist/worker/midden-blake3.test.d.ts +2 -0
- package/dist/worker/midden-blake3.test.d.ts.map +1 -0
- package/dist/worker/midden-blake3.test.js +25 -0
- package/dist/worker/midden-not-bundled.stub.d.ts +1 -0
- package/dist/worker/midden-not-bundled.stub.d.ts.map +1 -0
- package/dist/worker/midden-not-bundled.stub.js +10 -0
- package/dist/worker/midden-stub.d.ts +10 -0
- package/dist/worker/midden-stub.d.ts.map +1 -0
- package/dist/worker/midden-stub.js +31 -0
- package/dist/worker/midden-stub.test.d.ts +2 -0
- package/dist/worker/midden-stub.test.d.ts.map +1 -0
- package/dist/worker/midden-stub.test.js +25 -0
- package/dist/worker/midden-worker-client.d.ts +103 -0
- package/dist/worker/midden-worker-client.d.ts.map +1 -0
- package/dist/worker/midden-worker-client.js +246 -0
- package/dist/worker/midden-worker-client.test.d.ts +2 -0
- package/dist/worker/midden-worker-client.test.d.ts.map +1 -0
- package/dist/worker/midden-worker-client.test.js +151 -0
- package/dist/worker/midden-worker-contract.d.ts +87 -0
- package/dist/worker/midden-worker-contract.d.ts.map +1 -0
- package/dist/worker/midden-worker-contract.js +30 -0
- package/package.json +90 -0
|
@@ -0,0 +1,100 @@
|
|
|
1
|
+
// lightweight logger with level + tag filtering.
|
|
2
|
+
// level order: trace < debug < info < warn < error
|
|
3
|
+
//
|
|
4
|
+
// configuration precedence (highest wins):
|
|
5
|
+
// 1. localStorage overrides (browser devtools, no rebuild needed):
|
|
6
|
+
// localStorage.logLevel = "trace";
|
|
7
|
+
// localStorage.logFilter = "automerge.repo,idb.docindex";
|
|
8
|
+
// location.reload();
|
|
9
|
+
// 2. configureLogging({ level, filter }) - call this once at app startup.
|
|
10
|
+
// this is the hook a consuming app uses to wire up its own build-time env
|
|
11
|
+
// vars (e.g. `configureLogging({ level: import.meta.env.VITE_LOG_LEVEL })`
|
|
12
|
+
// in a vite app) without this package hard-depending on any bundler's env
|
|
13
|
+
// injection.
|
|
14
|
+
// 3. default: "warn", no tag filter.
|
|
15
|
+
//
|
|
16
|
+
// trace is off by default even when a lower level is configured - enable it
|
|
17
|
+
// explicitly when needed. it's useful for detailed call-by-call tracing of
|
|
18
|
+
// services without adding noise to normal debug output.
|
|
19
|
+
//
|
|
20
|
+
// tags use dotted namespaces, e.g. "p2p.transfer", "audio.player", "idb.service".
|
|
21
|
+
// filter prefix matching: "p2p" matches "p2p", "p2p.transfer", "p2p.knock", etc.
|
|
22
|
+
//
|
|
23
|
+
// usage:
|
|
24
|
+
// import { log } from "@freqhole/reliquary/utils";
|
|
25
|
+
// log.warn("share.panel", "could not build share link:", err);
|
|
26
|
+
// log.debug("playlist.sync", "syncPlaylists #", syncId, "entries:", entries.length);
|
|
27
|
+
// log.trace("automerge.repo", "findPlaylistDoc call #", n, docId);
|
|
28
|
+
const LEVEL_NUM = {
|
|
29
|
+
trace: -1,
|
|
30
|
+
debug: 0,
|
|
31
|
+
info: 1,
|
|
32
|
+
warn: 2,
|
|
33
|
+
error: 3,
|
|
34
|
+
};
|
|
35
|
+
const DEFAULT_LEVEL = "warn";
|
|
36
|
+
let configuredLevel;
|
|
37
|
+
let configuredFilter;
|
|
38
|
+
/**
|
|
39
|
+
* set the default log level and/or tag filter. intended to be called once at
|
|
40
|
+
* app startup; localStorage overrides (if present) still take priority so
|
|
41
|
+
* logging can be adjusted at runtime without a rebuild.
|
|
42
|
+
*/
|
|
43
|
+
export function configureLogging(config) {
|
|
44
|
+
if (config.level !== undefined)
|
|
45
|
+
configuredLevel = config.level;
|
|
46
|
+
if (config.filter !== undefined)
|
|
47
|
+
configuredFilter = config.filter;
|
|
48
|
+
}
|
|
49
|
+
/** clear any configureLogging() overrides, restoring the built-in default. */
|
|
50
|
+
export function resetLoggingConfig() {
|
|
51
|
+
configuredLevel = undefined;
|
|
52
|
+
configuredFilter = undefined;
|
|
53
|
+
}
|
|
54
|
+
function readLocalStorage(key) {
|
|
55
|
+
return typeof localStorage !== "undefined" && typeof localStorage.getItem === "function"
|
|
56
|
+
? localStorage.getItem(key)
|
|
57
|
+
: null;
|
|
58
|
+
}
|
|
59
|
+
function resolveLevel() {
|
|
60
|
+
const override = readLocalStorage("logLevel");
|
|
61
|
+
const raw = override ?? configuredLevel ?? DEFAULT_LEVEL;
|
|
62
|
+
return LEVEL_NUM[raw] ?? LEVEL_NUM.warn;
|
|
63
|
+
}
|
|
64
|
+
function resolveFilter() {
|
|
65
|
+
const override = readLocalStorage("logFilter");
|
|
66
|
+
if (override !== null) {
|
|
67
|
+
return override
|
|
68
|
+
.split(",")
|
|
69
|
+
.map((s) => s.trim())
|
|
70
|
+
.filter(Boolean);
|
|
71
|
+
}
|
|
72
|
+
return configuredFilter ?? [];
|
|
73
|
+
}
|
|
74
|
+
function allowed(tag) {
|
|
75
|
+
const filter = resolveFilter();
|
|
76
|
+
if (filter.length === 0)
|
|
77
|
+
return true;
|
|
78
|
+
return filter.some((prefix) => tag === prefix || tag.startsWith(prefix + "."));
|
|
79
|
+
}
|
|
80
|
+
function emit(level, tag, msg, ...args) {
|
|
81
|
+
if (LEVEL_NUM[level] < resolveLevel())
|
|
82
|
+
return;
|
|
83
|
+
if (!allowed(tag))
|
|
84
|
+
return;
|
|
85
|
+
const prefix = `[${tag}]`;
|
|
86
|
+
if (level === "error")
|
|
87
|
+
console.error(prefix, msg, ...args);
|
|
88
|
+
else if (level === "warn")
|
|
89
|
+
console.warn(prefix, msg, ...args);
|
|
90
|
+
// eslint-disable-next-line no-console -- this IS the logger implementation
|
|
91
|
+
else
|
|
92
|
+
console.log(prefix, msg, ...args);
|
|
93
|
+
}
|
|
94
|
+
export const log = {
|
|
95
|
+
trace: (tag, msg, ...args) => emit("trace", tag, msg, ...args),
|
|
96
|
+
debug: (tag, msg, ...args) => emit("debug", tag, msg, ...args),
|
|
97
|
+
info: (tag, msg, ...args) => emit("info", tag, msg, ...args),
|
|
98
|
+
warn: (tag, msg, ...args) => emit("warn", tag, msg, ...args),
|
|
99
|
+
error: (tag, msg, ...args) => emit("error", tag, msg, ...args),
|
|
100
|
+
};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"log.test.d.ts","sourceRoot":"","sources":["../../src/utils/log.test.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,113 @@
|
|
|
1
|
+
import { afterEach, beforeEach, describe, expect, it, vi } from "vitest";
|
|
2
|
+
import { configureLogging, log, resetLoggingConfig } from "./log.js";
|
|
3
|
+
// minimal in-memory localStorage stand-in so these tests don't depend on a DOM
|
|
4
|
+
// environment; log.ts only touches localStorage.getItem.
|
|
5
|
+
class FakeLocalStorage {
|
|
6
|
+
store = new Map();
|
|
7
|
+
getItem(key) {
|
|
8
|
+
return this.store.get(key) ?? null;
|
|
9
|
+
}
|
|
10
|
+
setItem(key, value) {
|
|
11
|
+
this.store.set(key, value);
|
|
12
|
+
}
|
|
13
|
+
removeItem(key) {
|
|
14
|
+
this.store.delete(key);
|
|
15
|
+
}
|
|
16
|
+
clear() {
|
|
17
|
+
this.store.clear();
|
|
18
|
+
}
|
|
19
|
+
}
|
|
20
|
+
describe("log", () => {
|
|
21
|
+
let consoleLog;
|
|
22
|
+
let consoleWarn;
|
|
23
|
+
let consoleError;
|
|
24
|
+
beforeEach(() => {
|
|
25
|
+
consoleLog = vi.spyOn(console, "log").mockImplementation(() => { });
|
|
26
|
+
consoleWarn = vi.spyOn(console, "warn").mockImplementation(() => { });
|
|
27
|
+
consoleError = vi.spyOn(console, "error").mockImplementation(() => { });
|
|
28
|
+
});
|
|
29
|
+
afterEach(() => {
|
|
30
|
+
resetLoggingConfig();
|
|
31
|
+
vi.unstubAllGlobals();
|
|
32
|
+
consoleLog.mockRestore();
|
|
33
|
+
consoleWarn.mockRestore();
|
|
34
|
+
consoleError.mockRestore();
|
|
35
|
+
});
|
|
36
|
+
it("defaults to the warn level: debug/info/trace are suppressed, warn/error are not", () => {
|
|
37
|
+
log.trace("app", "trace msg");
|
|
38
|
+
log.debug("app", "debug msg");
|
|
39
|
+
log.info("app", "info msg");
|
|
40
|
+
log.warn("app", "warn msg");
|
|
41
|
+
log.error("app", "error msg");
|
|
42
|
+
expect(consoleLog).not.toHaveBeenCalled();
|
|
43
|
+
expect(consoleWarn).toHaveBeenCalledTimes(1);
|
|
44
|
+
expect(consoleError).toHaveBeenCalledTimes(1);
|
|
45
|
+
});
|
|
46
|
+
it("configureLogging lowers the level so debug/info start emitting", () => {
|
|
47
|
+
configureLogging({ level: "debug" });
|
|
48
|
+
log.trace("app", "trace msg");
|
|
49
|
+
log.debug("app", "debug msg");
|
|
50
|
+
log.info("app", "info msg");
|
|
51
|
+
expect(consoleLog).toHaveBeenCalledTimes(2); // debug + info, both route through console.log
|
|
52
|
+
});
|
|
53
|
+
it("trace stays off even when the configured level is debug", () => {
|
|
54
|
+
configureLogging({ level: "debug" });
|
|
55
|
+
log.trace("app", "trace msg");
|
|
56
|
+
expect(consoleLog).not.toHaveBeenCalled();
|
|
57
|
+
});
|
|
58
|
+
it("trace only emits when explicitly configured", () => {
|
|
59
|
+
configureLogging({ level: "trace" });
|
|
60
|
+
log.trace("app", "trace msg");
|
|
61
|
+
expect(consoleLog).toHaveBeenCalledTimes(1);
|
|
62
|
+
});
|
|
63
|
+
it("resetLoggingConfig restores the default level", () => {
|
|
64
|
+
configureLogging({ level: "trace" });
|
|
65
|
+
resetLoggingConfig();
|
|
66
|
+
log.debug("app", "debug msg");
|
|
67
|
+
expect(consoleLog).not.toHaveBeenCalled();
|
|
68
|
+
});
|
|
69
|
+
it("configureLogging's filter allows only matching tag prefixes", () => {
|
|
70
|
+
configureLogging({ level: "debug", filter: ["p2p"] });
|
|
71
|
+
log.debug("p2p.transfer", "in filter");
|
|
72
|
+
log.debug("audio.player", "not in filter");
|
|
73
|
+
expect(consoleLog).toHaveBeenCalledTimes(1);
|
|
74
|
+
expect(consoleLog).toHaveBeenCalledWith("[p2p.transfer]", "in filter");
|
|
75
|
+
});
|
|
76
|
+
it("an empty filter (or none configured) allows every tag", () => {
|
|
77
|
+
configureLogging({ level: "debug" });
|
|
78
|
+
log.debug("anything.goes", "msg");
|
|
79
|
+
expect(consoleLog).toHaveBeenCalledTimes(1);
|
|
80
|
+
});
|
|
81
|
+
it("prefixes emitted messages with [tag]", () => {
|
|
82
|
+
log.error("share.panel", "could not build link", { reason: "boom" });
|
|
83
|
+
expect(consoleError).toHaveBeenCalledWith("[share.panel]", "could not build link", {
|
|
84
|
+
reason: "boom",
|
|
85
|
+
});
|
|
86
|
+
});
|
|
87
|
+
describe("localStorage overrides", () => {
|
|
88
|
+
beforeEach(() => {
|
|
89
|
+
vi.stubGlobal("localStorage", new FakeLocalStorage());
|
|
90
|
+
});
|
|
91
|
+
it("localStorage.logLevel overrides configureLogging's level", () => {
|
|
92
|
+
configureLogging({ level: "warn" });
|
|
93
|
+
localStorage.setItem("logLevel", "debug");
|
|
94
|
+
log.debug("app", "debug msg");
|
|
95
|
+
expect(consoleLog).toHaveBeenCalledTimes(1);
|
|
96
|
+
});
|
|
97
|
+
it("localStorage.logFilter overrides configureLogging's filter", () => {
|
|
98
|
+
configureLogging({ level: "debug", filter: ["p2p"] });
|
|
99
|
+
localStorage.setItem("logFilter", "audio");
|
|
100
|
+
log.debug("audio.player", "now allowed");
|
|
101
|
+
log.debug("p2p.transfer", "no longer allowed");
|
|
102
|
+
expect(consoleLog).toHaveBeenCalledTimes(1);
|
|
103
|
+
expect(consoleLog).toHaveBeenCalledWith("[audio.player]", "now allowed");
|
|
104
|
+
});
|
|
105
|
+
it("an empty localStorage.logFilter value means no filter (allow every tag)", () => {
|
|
106
|
+
configureLogging({ level: "debug", filter: ["p2p"] });
|
|
107
|
+
localStorage.setItem("logFilter", "");
|
|
108
|
+
log.debug("p2p.transfer", "allowed");
|
|
109
|
+
log.debug("audio.player", "also allowed, since an explicit empty override clears the filter");
|
|
110
|
+
expect(consoleLog).toHaveBeenCalledTimes(2);
|
|
111
|
+
});
|
|
112
|
+
});
|
|
113
|
+
});
|
|
@@ -0,0 +1,118 @@
|
|
|
1
|
+
import * as Comlink from "comlink";
|
|
2
|
+
import type { BlobWorkerApi } from "./blob-worker.js";
|
|
3
|
+
/**
|
|
4
|
+
* get (and lazily spawn) the comlink-wrapped blob worker proxy.
|
|
5
|
+
*
|
|
6
|
+
* returns null if Worker isn't available, or if the worker doesn't signal
|
|
7
|
+
* readiness within `WORKER_READY_TIMEOUT_MS` - callers should branch and use
|
|
8
|
+
* a main-thread fallback (every exported helper below already does this).
|
|
9
|
+
*
|
|
10
|
+
* waits for an explicit "ready" postMessage from the worker before handing
|
|
11
|
+
* out the Comlink proxy. this avoids a real race: the worker's module top
|
|
12
|
+
* level may await a wasm module's instantiation before calling
|
|
13
|
+
* `Comlink.expose()` (which registers the "message" listener). an RPC call
|
|
14
|
+
* sent before that listener exists fires with no listener attached and is
|
|
15
|
+
* silently dropped forever - the caller's promise then never resolves.
|
|
16
|
+
* waiting for the ready signal (sent immediately after `Comlink.expose()`
|
|
17
|
+
* in blob-worker.ts) guarantees the listener is registered before any real
|
|
18
|
+
* RPC call goes out.
|
|
19
|
+
*/
|
|
20
|
+
export declare function getBlobWorker(): Promise<Comlink.Remote<BlobWorkerApi> | null>;
|
|
21
|
+
/**
|
|
22
|
+
* tear down the worker. mainly useful for tests; production code can leave
|
|
23
|
+
* the worker alive for the page lifetime.
|
|
24
|
+
*/
|
|
25
|
+
export declare function shutdownBlobWorker(): void;
|
|
26
|
+
/**
|
|
27
|
+
* hash bytes with blake3, preferring the worker. accepts a Uint8Array.
|
|
28
|
+
* note: this DOES copy across the worker boundary (Uint8Array isn't
|
|
29
|
+
* transferable directly without giving up the underlying ArrayBuffer);
|
|
30
|
+
* for upload pipelines, prefer `processBlobBytes` which transfers the
|
|
31
|
+
* underlying buffer.
|
|
32
|
+
*/
|
|
33
|
+
export declare function hashBlake3(data: Uint8Array): Promise<string>;
|
|
34
|
+
/**
|
|
35
|
+
* sha256 hash of an ArrayBuffer.
|
|
36
|
+
*/
|
|
37
|
+
export declare function hashSha256(data: ArrayBuffer): Promise<string>;
|
|
38
|
+
/**
|
|
39
|
+
* base64-encode an ArrayBuffer.
|
|
40
|
+
*
|
|
41
|
+
* NOTE: the buffer is structured-cloned (copied) across the worker
|
|
42
|
+
* boundary so callers can safely reuse it afterwards. if you have a
|
|
43
|
+
* dedicated buffer that won't be touched again, you can transfer
|
|
44
|
+
* ownership manually for a small perf win.
|
|
45
|
+
*/
|
|
46
|
+
export declare function base64Encode(buffer: ArrayBuffer): Promise<string>;
|
|
47
|
+
/**
|
|
48
|
+
* one-shot upload pipeline: hash + write to OPFS in the worker, return
|
|
49
|
+
* metadata. transfers the buffer.
|
|
50
|
+
*/
|
|
51
|
+
export declare function processBlobBytes(buffer: ArrayBuffer, filename: string, mime: string): Promise<{
|
|
52
|
+
blob_id: string;
|
|
53
|
+
sha256: string;
|
|
54
|
+
blake3: string;
|
|
55
|
+
size: number;
|
|
56
|
+
mime: string;
|
|
57
|
+
filename: string;
|
|
58
|
+
}>;
|
|
59
|
+
/**
|
|
60
|
+
* write a blob to OPFS via the worker (uses `FileSystemSyncAccessHandle`
|
|
61
|
+
* for max throughput).
|
|
62
|
+
*
|
|
63
|
+
* NOTE: the buffer is structured-cloned (copied) across the worker
|
|
64
|
+
* boundary so callers can safely reuse it afterwards - important for
|
|
65
|
+
* code paths that read or return the buffer after kicking off an OPFS
|
|
66
|
+
* write (e.g. a snatch/download cache-back-fill). for the upload pipeline
|
|
67
|
+
* use `processBlobBytes` instead, which transfers.
|
|
68
|
+
*/
|
|
69
|
+
export declare function writeBlobToOpfs(blobId: string, buffer: ArrayBuffer): Promise<void>;
|
|
70
|
+
/**
|
|
71
|
+
* stream a File into OPFS via the worker's chunked upload session:
|
|
72
|
+
* incremental blake3 + incremental sync-access-handle writes, so neither
|
|
73
|
+
* thread ever holds the whole payload. each chunk buffer is transferred
|
|
74
|
+
* (zero-copy) across the worker boundary.
|
|
75
|
+
*
|
|
76
|
+
* `onProgress` reports bytes pushed / file size (0..1) per chunk.
|
|
77
|
+
* `signal` cancels between chunks: the worker session is aborted (temp
|
|
78
|
+
* file cleaned up) and a DOMException AbortError is thrown.
|
|
79
|
+
*
|
|
80
|
+
* returns { blake3, size } - the file lands in OPFS under its blake3
|
|
81
|
+
* content address. throws when streaming isn't available (no worker, no
|
|
82
|
+
* OPFS sync handles, no midden module bundled); callers should fall back
|
|
83
|
+
* to the one-shot processBlobBytes path.
|
|
84
|
+
*/
|
|
85
|
+
export declare function streamFileToOpfs(file: File, options?: {
|
|
86
|
+
onProgress?: (fraction: number) => void;
|
|
87
|
+
signal?: AbortSignal;
|
|
88
|
+
}): Promise<{
|
|
89
|
+
blake3: string;
|
|
90
|
+
size: number;
|
|
91
|
+
}>;
|
|
92
|
+
export interface ResizeImageOptions {
|
|
93
|
+
maxWidth?: number;
|
|
94
|
+
maxHeight?: number;
|
|
95
|
+
quality?: number;
|
|
96
|
+
cropSquare?: boolean;
|
|
97
|
+
mime?: string;
|
|
98
|
+
}
|
|
99
|
+
/**
|
|
100
|
+
* resize an image Blob to a (default WebP) data URL.
|
|
101
|
+
* prefers the blob worker (keeps the decode/encode work off the main
|
|
102
|
+
* thread); falls back to a main-thread `OffscreenCanvas` path if the
|
|
103
|
+
* worker isn't available. returns null on failure (non-image input,
|
|
104
|
+
* decode failure, etc.).
|
|
105
|
+
*/
|
|
106
|
+
export declare function resizeImageToWebpDataUrl(blob: Blob, options?: ResizeImageOptions): Promise<string | null>;
|
|
107
|
+
/**
|
|
108
|
+
* generate a thumbnail data URL (default 200x200 WebP @ q=0.75) for an
|
|
109
|
+
* image Blob. delegates to the worker.
|
|
110
|
+
*/
|
|
111
|
+
export declare function generateThumbnailDataUrl(blob: Blob, maxSize?: number): Promise<string | null>;
|
|
112
|
+
/**
|
|
113
|
+
* decode a base64 string into a Uint8Array via the worker. for large
|
|
114
|
+
* payloads (megabyte-scale snatch responses) this avoids blocking the
|
|
115
|
+
* main thread on a tight `String.charCodeAt` loop.
|
|
116
|
+
*/
|
|
117
|
+
export declare function base64Decode(b64: string): Promise<Uint8Array>;
|
|
118
|
+
//# sourceMappingURL=blob-worker-client.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"blob-worker-client.d.ts","sourceRoot":"","sources":["../../src/worker/blob-worker-client.ts"],"names":[],"mappings":"AAUA,OAAO,KAAK,OAAO,MAAM,SAAS,CAAC;AACnC,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,kBAAkB,CAAC;AAsBtD;;;;;;;;;;;;;;;;GAgBG;AACH,wBAAsB,aAAa,IAAI,OAAO,CAAC,OAAO,CAAC,MAAM,CAAC,aAAa,CAAC,GAAG,IAAI,CAAC,CAuDnF;AAED;;;GAGG;AACH,wBAAgB,kBAAkB,IAAI,IAAI,CAOzC;AAiCD;;;;;;GAMG;AACH,wBAAsB,UAAU,CAAC,IAAI,EAAE,UAAU,GAAG,OAAO,CAAC,MAAM,CAAC,CAIlE;AAED;;GAEG;AACH,wBAAsB,UAAU,CAAC,IAAI,EAAE,WAAW,GAAG,OAAO,CAAC,MAAM,CAAC,CAInE;AAED;;;;;;;GAOG;AACH,wBAAsB,YAAY,CAAC,MAAM,EAAE,WAAW,GAAG,OAAO,CAAC,MAAM,CAAC,CAIvE;AAED;;;GAGG;AACH,wBAAsB,gBAAgB,CACpC,MAAM,EAAE,WAAW,EACnB,QAAQ,EAAE,MAAM,EAChB,IAAI,EAAE,MAAM,GACX,OAAO,CAAC;IACT,OAAO,EAAE,MAAM,CAAC;IAChB,MAAM,EAAE,MAAM,CAAC;IACf,MAAM,EAAE,MAAM,CAAC;IACf,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,EAAE,MAAM,CAAC;IACb,QAAQ,EAAE,MAAM,CAAC;CAClB,CAAC,CAeD;AAED;;;;;;;;;GASG;AACH,wBAAsB,eAAe,CAAC,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,WAAW,GAAG,OAAO,CAAC,IAAI,CAAC,CAQxF;AAED;;;;;;;;;;;;;;GAcG;AACH,wBAAsB,gBAAgB,CACpC,IAAI,EAAE,IAAI,EACV,OAAO,CAAC,EAAE;IAAE,UAAU,CAAC,EAAE,CAAC,QAAQ,EAAE,MAAM,KAAK,IAAI,CAAC;IAAC,MAAM,CAAC,EAAE,WAAW,CAAA;CAAE,GAC1E,OAAO,CAAC;IAAE,MAAM,EAAE,MAAM,CAAC;IAAC,IAAI,EAAE,MAAM,CAAA;CAAE,CAAC,CAkC3C;AAID,MAAM,WAAW,kBAAkB;IACjC,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,UAAU,CAAC,EAAE,OAAO,CAAC;IACrB,IAAI,CAAC,EAAE,MAAM,CAAC;CACf;AAED;;;;;;GAMG;AACH,wBAAsB,wBAAwB,CAC5C,IAAI,EAAE,IAAI,EACV,OAAO,CAAC,EAAE,kBAAkB,GAC3B,OAAO,CAAC,MAAM,GAAG,IAAI,CAAC,CAIxB;AAED;;;GAGG;AACH,wBAAsB,wBAAwB,CAAC,IAAI,EAAE,IAAI,EAAE,OAAO,SAAM,GAAG,OAAO,CAAC,MAAM,GAAG,IAAI,CAAC,CAOhG;AAED;;;;GAIG;AACH,wBAAsB,YAAY,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,UAAU,CAAC,CAQnE"}
|