@interncom/diplomatic 0.0.13 → 0.0.15
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/client.d.ts +4 -3
- package/dist/idbStore.d.ts +2 -0
- package/dist/index.d.ts +4 -3
- package/dist/index.mjs +66 -18
- package/dist/localStorageStore.d.ts +2 -0
- package/dist/memoryStore.d.ts +2 -0
- package/dist/types.d.ts +9 -1
- package/dist/useClient.d.ts +3 -2
- package/package.json +1 -1
package/dist/client.d.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import type { IOp, KeyPair } from "./shared/types";
|
|
2
|
-
import type { IClientStateStore,
|
|
2
|
+
import type { IClientStateStore, Applier, IDiplomaticClientState } from "./types";
|
|
3
3
|
import type { StateManager } from "./state";
|
|
4
4
|
export interface IDiplomaticClientParams {
|
|
5
5
|
store: IClientStateStore;
|
|
@@ -11,7 +11,7 @@ export interface IDiplomaticClientParams {
|
|
|
11
11
|
export default class DiplomaticClient {
|
|
12
12
|
store: IClientStateStore;
|
|
13
13
|
applier: Applier;
|
|
14
|
-
listener?: (state:
|
|
14
|
+
listener?: (state: IDiplomaticClientState) => void;
|
|
15
15
|
seed?: Uint8Array;
|
|
16
16
|
encKey?: Uint8Array;
|
|
17
17
|
hostURL?: URL;
|
|
@@ -25,7 +25,8 @@ export default class DiplomaticClient {
|
|
|
25
25
|
setSeed(seed: Uint8Array): Promise<void>;
|
|
26
26
|
loadHost(): Promise<void>;
|
|
27
27
|
register(hostURL: string): Promise<void>;
|
|
28
|
-
|
|
28
|
+
emitUpdate(): Promise<void>;
|
|
29
|
+
getState(): Promise<IDiplomaticClientState>;
|
|
29
30
|
processOps(): Promise<void>;
|
|
30
31
|
pullOpPaths(): Promise<never[] | undefined>;
|
|
31
32
|
fetchAndExecQueuedOps(): Promise<never[] | undefined>;
|
package/dist/idbStore.d.ts
CHANGED
|
@@ -15,10 +15,12 @@ declare class IDBStore implements IClientStateStore {
|
|
|
15
15
|
dequeueUpload: (sha256: string) => Promise<void>;
|
|
16
16
|
peekUpload: (sha256: string) => Promise<Uint8Array | undefined>;
|
|
17
17
|
listUploads: () => Promise<string[]>;
|
|
18
|
+
numUploads: () => Promise<number>;
|
|
18
19
|
downloadQueue: Set<string>;
|
|
19
20
|
enqueueDownload: (path: string) => Promise<void>;
|
|
20
21
|
dequeueDownload: (path: string) => Promise<void>;
|
|
21
22
|
listDownloads: () => Promise<string[]>;
|
|
23
|
+
numDownloads: () => Promise<number>;
|
|
22
24
|
}
|
|
23
25
|
export declare const idbStore: IDBStore;
|
|
24
26
|
export {};
|
package/dist/index.d.ts
CHANGED
|
@@ -1,10 +1,11 @@
|
|
|
1
|
-
import { useClientState } from "./useClient";
|
|
1
|
+
import { useClientState, useSyncOnResume } from "./useClient";
|
|
2
2
|
import { StateManager, useStateWatcher } from './state';
|
|
3
3
|
import { localStorageStore } from "./localStorageStore";
|
|
4
4
|
import { idbStore } from "./idbStore";
|
|
5
|
+
import type { IDiplomaticClientState } from "./types";
|
|
5
6
|
import DiplomaticClient from "./client";
|
|
6
7
|
import libsodiumCrypto from "./crypto";
|
|
7
8
|
import { btoh, htob } from "./shared/lib";
|
|
8
9
|
import { type IOp, Verb } from "./shared/types";
|
|
9
|
-
export { useClientState, StateManager, useStateWatcher, localStorageStore, idbStore, DiplomaticClient, libsodiumCrypto, btoh, htob, Verb, };
|
|
10
|
-
export type { IOp, };
|
|
10
|
+
export { useClientState, useSyncOnResume, StateManager, useStateWatcher, localStorageStore, idbStore, DiplomaticClient, libsodiumCrypto, btoh, htob, Verb, };
|
|
11
|
+
export type { IOp, IDiplomaticClientState, };
|
package/dist/index.mjs
CHANGED
|
@@ -12,15 +12,32 @@ var __export = (target, all) => {
|
|
|
12
12
|
|
|
13
13
|
// src/useClient.ts
|
|
14
14
|
import { useState, useEffect } from "react";
|
|
15
|
-
var initialState = "loading";
|
|
16
15
|
function useClientState(client) {
|
|
17
|
-
const [state, setState] = useState(
|
|
16
|
+
const [state, setState] = useState();
|
|
18
17
|
useEffect(() => {
|
|
19
|
-
|
|
20
|
-
|
|
18
|
+
async function updateState() {
|
|
19
|
+
const state2 = await client.getState();
|
|
20
|
+
setState(state2);
|
|
21
|
+
}
|
|
22
|
+
client.listener = updateState;
|
|
23
|
+
updateState();
|
|
24
|
+
return () => {
|
|
25
|
+
client.listener = void 0;
|
|
26
|
+
};
|
|
21
27
|
}, [client]);
|
|
22
28
|
return state;
|
|
23
29
|
}
|
|
30
|
+
function useSyncOnResume(client) {
|
|
31
|
+
useEffect(() => {
|
|
32
|
+
function handleOnline() {
|
|
33
|
+
client.sync();
|
|
34
|
+
}
|
|
35
|
+
window.addEventListener("online", handleOnline);
|
|
36
|
+
return () => {
|
|
37
|
+
window.removeEventListener("online", handleOnline);
|
|
38
|
+
};
|
|
39
|
+
}, [client]);
|
|
40
|
+
}
|
|
24
41
|
|
|
25
42
|
// src/state.ts
|
|
26
43
|
import { useEffect as useEffect2, useState as useState2 } from "react";
|
|
@@ -140,6 +157,9 @@ var LocalStorageStore = class {
|
|
|
140
157
|
listUploads = async () => {
|
|
141
158
|
return Array.from(this.uploadQueue.keys());
|
|
142
159
|
};
|
|
160
|
+
numUploads = async () => {
|
|
161
|
+
return this.uploadQueue.size;
|
|
162
|
+
};
|
|
143
163
|
downloadQueue = /* @__PURE__ */ new Set();
|
|
144
164
|
enqueueDownload = async (path) => {
|
|
145
165
|
this.downloadQueue.add(path);
|
|
@@ -150,6 +170,9 @@ var LocalStorageStore = class {
|
|
|
150
170
|
listDownloads = async () => {
|
|
151
171
|
return Array.from(this.downloadQueue.keys());
|
|
152
172
|
};
|
|
173
|
+
numDownloads = async () => {
|
|
174
|
+
return this.downloadQueue.size;
|
|
175
|
+
};
|
|
153
176
|
};
|
|
154
177
|
var localStorageStore = new LocalStorageStore();
|
|
155
178
|
|
|
@@ -470,6 +493,10 @@ var IDBStore = class {
|
|
|
470
493
|
const sha256s = await db.getAllKeys("uploadQueue");
|
|
471
494
|
return sha256s;
|
|
472
495
|
};
|
|
496
|
+
numUploads = async () => {
|
|
497
|
+
const db = await dbPromise;
|
|
498
|
+
return db.count("uploadQueue");
|
|
499
|
+
};
|
|
473
500
|
downloadQueue = /* @__PURE__ */ new Set();
|
|
474
501
|
enqueueDownload = async (path) => {
|
|
475
502
|
const db = await dbPromise;
|
|
@@ -484,6 +511,10 @@ var IDBStore = class {
|
|
|
484
511
|
const paths = await db.getAllKeys("downloadQueue");
|
|
485
512
|
return paths;
|
|
486
513
|
};
|
|
514
|
+
numDownloads = async () => {
|
|
515
|
+
const db = await dbPromise;
|
|
516
|
+
return db.count("downloadQueue");
|
|
517
|
+
};
|
|
487
518
|
};
|
|
488
519
|
var idbStore = new IDBStore();
|
|
489
520
|
|
|
@@ -8795,10 +8826,12 @@ var DiplomaticClient = class {
|
|
|
8795
8826
|
this.websocket = new WebSocket(url);
|
|
8796
8827
|
this.websocket.onopen = (e) => {
|
|
8797
8828
|
console.log("CONNECTED");
|
|
8829
|
+
this.emitUpdate();
|
|
8798
8830
|
};
|
|
8799
8831
|
this.websocket.onclose = (e) => {
|
|
8800
8832
|
console.log("DISCONNECTED");
|
|
8801
8833
|
this.connect(hostURL);
|
|
8834
|
+
this.emitUpdate();
|
|
8802
8835
|
};
|
|
8803
8836
|
this.websocket.onmessage = (e) => {
|
|
8804
8837
|
console.log(`RECEIVED: ${e.data}`);
|
|
@@ -8826,7 +8859,7 @@ var DiplomaticClient = class {
|
|
|
8826
8859
|
await this.connect(this.hostURL);
|
|
8827
8860
|
}
|
|
8828
8861
|
await this.sync();
|
|
8829
|
-
this.
|
|
8862
|
+
this.emitUpdate();
|
|
8830
8863
|
}
|
|
8831
8864
|
async loadSeed() {
|
|
8832
8865
|
const seed = await this.store.getSeed();
|
|
@@ -8839,7 +8872,7 @@ var DiplomaticClient = class {
|
|
|
8839
8872
|
this.seed = seed;
|
|
8840
8873
|
this.encKey = await crypto_default.deriveXSalsa20Poly1305Key(seed);
|
|
8841
8874
|
await this.store.setSeed(seed);
|
|
8842
|
-
this.
|
|
8875
|
+
this.emitUpdate();
|
|
8843
8876
|
}
|
|
8844
8877
|
async loadHost() {
|
|
8845
8878
|
if (!this.seed) {
|
|
@@ -8864,16 +8897,20 @@ var DiplomaticClient = class {
|
|
|
8864
8897
|
await api_default.register(this.hostURL, this.hostKeyPair.publicKey, "tok123");
|
|
8865
8898
|
await this.store.setHostURL(hostURL);
|
|
8866
8899
|
await this.store.setHostID(hostID);
|
|
8867
|
-
this.
|
|
8868
|
-
}
|
|
8869
|
-
|
|
8870
|
-
|
|
8871
|
-
|
|
8872
|
-
|
|
8873
|
-
|
|
8874
|
-
|
|
8875
|
-
|
|
8876
|
-
|
|
8900
|
+
this.emitUpdate();
|
|
8901
|
+
}
|
|
8902
|
+
async emitUpdate() {
|
|
8903
|
+
const state = await this.getState();
|
|
8904
|
+
this.listener?.(state);
|
|
8905
|
+
}
|
|
8906
|
+
async getState() {
|
|
8907
|
+
return {
|
|
8908
|
+
hasSeed: this.seed !== void 0 && this.encKey !== void 0,
|
|
8909
|
+
hasHost: this.hostURL !== void 0 && this.hostKeyPair !== void 0,
|
|
8910
|
+
connected: this.websocket?.readyState === WebSocket.OPEN,
|
|
8911
|
+
numUploads: await this.store.numUploads(),
|
|
8912
|
+
numDownloads: await this.store.numDownloads()
|
|
8913
|
+
};
|
|
8877
8914
|
}
|
|
8878
8915
|
async processOps() {
|
|
8879
8916
|
await this.pullOpPaths();
|
|
@@ -8889,6 +8926,7 @@ var DiplomaticClient = class {
|
|
|
8889
8926
|
const paths = pathResp.paths;
|
|
8890
8927
|
for (const path of paths) {
|
|
8891
8928
|
await this.store.enqueueDownload(path);
|
|
8929
|
+
this.emitUpdate();
|
|
8892
8930
|
}
|
|
8893
8931
|
this.lastFetchedAt = pathResp.fetchedAt;
|
|
8894
8932
|
}
|
|
@@ -8906,10 +8944,12 @@ var DiplomaticClient = class {
|
|
|
8906
8944
|
try {
|
|
8907
8945
|
await this.applier(op);
|
|
8908
8946
|
await this.store.dequeueDownload(path);
|
|
8947
|
+
this.emitUpdate();
|
|
8909
8948
|
} catch {
|
|
8910
8949
|
const transient = true;
|
|
8911
8950
|
if (!transient) {
|
|
8912
8951
|
await this.store.dequeueDownload(path);
|
|
8952
|
+
this.emitUpdate();
|
|
8913
8953
|
}
|
|
8914
8954
|
}
|
|
8915
8955
|
}
|
|
@@ -8923,6 +8963,7 @@ var DiplomaticClient = class {
|
|
|
8923
8963
|
await api_default.putDelta(this.hostURL, cipherOp, this.hostKeyPair);
|
|
8924
8964
|
}
|
|
8925
8965
|
await this.store.dequeueUpload(sha256);
|
|
8966
|
+
this.emitUpdate();
|
|
8926
8967
|
}
|
|
8927
8968
|
async pushQueuedOps() {
|
|
8928
8969
|
for (const sha256 of await this.store.listUploads()) {
|
|
@@ -8942,12 +8983,18 @@ var DiplomaticClient = class {
|
|
|
8942
8983
|
const sha256 = await crypto_default.sha256Hash(cipherOp);
|
|
8943
8984
|
const shaHex = btoh(sha256);
|
|
8944
8985
|
await this.store.enqueueUpload(shaHex, cipherOp);
|
|
8986
|
+
this.emitUpdate();
|
|
8945
8987
|
try {
|
|
8946
8988
|
await this.applier(op);
|
|
8947
8989
|
} catch {
|
|
8948
8990
|
await this.store.dequeueUpload(shaHex);
|
|
8991
|
+
this.emitUpdate();
|
|
8992
|
+
}
|
|
8993
|
+
try {
|
|
8994
|
+
await this.pushQueuedOp(shaHex);
|
|
8995
|
+
} catch (err) {
|
|
8996
|
+
console.info("failed to push");
|
|
8949
8997
|
}
|
|
8950
|
-
await this.pushQueuedOp(shaHex);
|
|
8951
8998
|
}
|
|
8952
8999
|
async upsert(type, body, version = 0) {
|
|
8953
9000
|
const op = genUpsertOp(type, body, version);
|
|
@@ -8964,5 +9011,6 @@ export {
|
|
|
8964
9011
|
crypto_default as libsodiumCrypto,
|
|
8965
9012
|
localStorageStore,
|
|
8966
9013
|
useClientState,
|
|
8967
|
-
useStateWatcher
|
|
9014
|
+
useStateWatcher,
|
|
9015
|
+
useSyncOnResume
|
|
8968
9016
|
};
|
|
@@ -12,10 +12,12 @@ declare class LocalStorageStore implements IClientStateStore {
|
|
|
12
12
|
dequeueUpload: (sha256: string) => Promise<void>;
|
|
13
13
|
peekUpload: (sha256: string) => Promise<Uint8Array | undefined>;
|
|
14
14
|
listUploads: () => Promise<string[]>;
|
|
15
|
+
numUploads: () => Promise<number>;
|
|
15
16
|
downloadQueue: Set<string>;
|
|
16
17
|
enqueueDownload: (path: string) => Promise<void>;
|
|
17
18
|
dequeueDownload: (path: string) => Promise<void>;
|
|
18
19
|
listDownloads: () => Promise<string[]>;
|
|
20
|
+
numDownloads: () => Promise<number>;
|
|
19
21
|
}
|
|
20
22
|
export declare const localStorageStore: LocalStorageStore;
|
|
21
23
|
export {};
|
package/dist/memoryStore.d.ts
CHANGED
|
@@ -15,10 +15,12 @@ declare class MemoryStore implements IClientStateStore {
|
|
|
15
15
|
dequeueUpload: (sha256: string) => Promise<void>;
|
|
16
16
|
peekUpload: (sha256: string) => Promise<Uint8Array | undefined>;
|
|
17
17
|
listUploads: () => Promise<string[]>;
|
|
18
|
+
numUploads: () => Promise<number>;
|
|
18
19
|
downloadQueue: Set<string>;
|
|
19
20
|
enqueueDownload: (path: string) => Promise<void>;
|
|
20
21
|
dequeueDownload: (path: string) => Promise<void>;
|
|
21
22
|
listDownloads: () => Promise<string[]>;
|
|
23
|
+
numDownloads: () => Promise<number>;
|
|
22
24
|
}
|
|
23
25
|
export declare const memoryStore: MemoryStore;
|
|
24
26
|
export {};
|
package/dist/types.d.ts
CHANGED
|
@@ -11,9 +11,17 @@ export interface IClientStateStore {
|
|
|
11
11
|
dequeueUpload: (sha256: string) => Promise<void>;
|
|
12
12
|
peekUpload: (sha256: string) => Promise<Uint8Array | undefined>;
|
|
13
13
|
listUploads: () => Promise<string[]>;
|
|
14
|
+
numUploads: () => Promise<number>;
|
|
14
15
|
enqueueDownload: (path: string) => Promise<void>;
|
|
15
16
|
dequeueDownload: (path: string) => Promise<void>;
|
|
16
17
|
listDownloads: () => Promise<string[]>;
|
|
18
|
+
numDownloads: () => Promise<number>;
|
|
19
|
+
}
|
|
20
|
+
export interface IDiplomaticClientState {
|
|
21
|
+
hasSeed: boolean;
|
|
22
|
+
hasHost: boolean;
|
|
23
|
+
connected: boolean;
|
|
24
|
+
numUploads: number;
|
|
25
|
+
numDownloads: number;
|
|
17
26
|
}
|
|
18
|
-
export type DiplomaticClientState = "loading" | "seedless" | "hostless" | "ready";
|
|
19
27
|
export type Applier = (op: IOp) => Promise<void>;
|
package/dist/useClient.d.ts
CHANGED
|
@@ -1,3 +1,4 @@
|
|
|
1
|
-
import type {
|
|
1
|
+
import type { IDiplomaticClientState } from "./types";
|
|
2
2
|
import type DiplomaticClient from "./client";
|
|
3
|
-
export declare function useClientState(client: DiplomaticClient):
|
|
3
|
+
export declare function useClientState(client: DiplomaticClient): IDiplomaticClientState | undefined;
|
|
4
|
+
export declare function useSyncOnResume(client: DiplomaticClient): void;
|