@peerbit/program 1.0.5 → 2.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.
@@ -4,17 +4,9 @@ import { PubSub } from "@peerbit/pubsub-interface";
4
4
  import { Ed25519PublicKey, Identity, Keychain } from "@peerbit/crypto";
5
5
  import type { SimpleLevel } from "@peerbit/lazy-level";
6
6
  import { Multiaddr } from "@multiformats/multiaddr";
7
- import { Address } from "./address";
8
- export type WithArgs<Args> = {
9
- args?: Args;
10
- };
11
- export type WithParent<T> = {
12
- parent?: T;
13
- };
14
- export type CanOpen<Args> = {
15
- open(args?: Args): Promise<void>;
16
- };
17
- export interface Client<T extends P, P> {
7
+ import { Address } from "./address.js";
8
+ import { CanOpen, Manageable, OpenOptions } from "./handler.js";
9
+ export interface Client<T extends Manageable<any>> {
18
10
  peerId: Libp2pPeerId;
19
11
  identity: Identity<Ed25519PublicKey>;
20
12
  getMultiaddrs: () => Multiaddr[];
@@ -23,9 +15,9 @@ export interface Client<T extends P, P> {
23
15
  pubsub: PubSub;
24
16
  blocks: Blocks;
25
17
  };
26
- memory?: SimpleLevel;
27
- keychain?: Keychain;
18
+ memory: SimpleLevel;
19
+ keychain: Keychain;
28
20
  start(): Promise<void>;
29
21
  stop(): Promise<void>;
30
- open<TExt extends T & CanOpen<Args>, Args = any>(program: TExt | Address, options?: WithArgs<Args> & WithParent<P>): Promise<TExt>;
22
+ open<S extends T & CanOpen<Args>, Args = any>(program: S | Address, options?: OpenOptions<Args, S>): Promise<S>;
31
23
  }
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=client.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"client.js","sourceRoot":"","sources":["../../src/client.ts"],"names":[],"mappings":""}
@@ -0,0 +1,81 @@
1
+ import { Blocks } from "@peerbit/blocks-interface";
2
+ import { Address } from "./address.js";
3
+ export declare const logger: import("pino").Logger<import("pino").LoggerOptions | import("pino").DestinationStream>;
4
+ type ProgramMergeStrategy = "replace" | "reject" | "reuse";
5
+ export type EventOptions = {
6
+ onBeforeOpen?: (program: Manageable<any>) => Promise<void> | void;
7
+ onOpen?: (program: Manageable<any>) => Promise<void> | void;
8
+ onDrop?: (program: Manageable<any>) => Promise<void> | void;
9
+ onClose?: (program: Manageable<any>) => Promise<void> | void;
10
+ };
11
+ export type OpenOptions<Args, T extends Manageable<Args>> = {
12
+ timeout?: number;
13
+ existing?: ProgramMergeStrategy;
14
+ } & ProgramInitializationOptions<Args, T>;
15
+ export type WithArgs<Args> = {
16
+ args?: Args;
17
+ };
18
+ export type WithParent<T> = {
19
+ parent?: T;
20
+ };
21
+ export type Closeable = {
22
+ closed: boolean;
23
+ close(): Promise<boolean>;
24
+ };
25
+ export type Addressable = {
26
+ address: Address;
27
+ };
28
+ export interface Saveable {
29
+ save(store: Blocks, options?: {
30
+ format?: string;
31
+ timeout?: number;
32
+ }): Promise<Address>;
33
+ delete(): Promise<void>;
34
+ }
35
+ export type CanEmit = {
36
+ emitEvent: (event: CustomEvent) => void;
37
+ };
38
+ export type CanOpen<Args> = {
39
+ beforeOpen: (client: any, options?: EventOptions) => Promise<void>;
40
+ open(args?: Args): Promise<void>;
41
+ afterOpen: () => Promise<void>;
42
+ };
43
+ export type Manageable<Args> = Closeable & Addressable & CanOpen<Args> & Saveable & CanEmit & {
44
+ children: Manageable<any>[];
45
+ parents: (Manageable<any> | undefined)[];
46
+ };
47
+ export type ProgramInitializationOptions<Args, T extends Manageable<Args>> = {} & WithArgs<Args> & WithParent<T> & EventOptions;
48
+ export declare class Handler<T extends Manageable<any>> {
49
+ readonly properties: {
50
+ client: {
51
+ services: {
52
+ blocks: Blocks;
53
+ };
54
+ stop: () => Promise<void>;
55
+ };
56
+ load: (address: Address, blocks: Blocks, options?: {
57
+ timeout?: number;
58
+ }) => Promise<T | undefined>;
59
+ shouldMonitor: (thing: any) => boolean;
60
+ };
61
+ items: Map<string, Manageable<any>>;
62
+ private _openQueue;
63
+ constructor(properties: {
64
+ client: {
65
+ services: {
66
+ blocks: Blocks;
67
+ };
68
+ stop: () => Promise<void>;
69
+ };
70
+ load: (address: Address, blocks: Blocks, options?: {
71
+ timeout?: number;
72
+ }) => Promise<T | undefined>;
73
+ shouldMonitor: (thing: any) => boolean;
74
+ });
75
+ stop(): Promise<void>;
76
+ private _onProgamClose;
77
+ private _onProgramOpen;
78
+ private checkProcessExisting;
79
+ open<S extends T, Args = any>(storeOrAddress: S | Address | string, options?: OpenOptions<Args, S>): Promise<S>;
80
+ }
81
+ export {};
@@ -0,0 +1,133 @@
1
+ import PQueue from "p-queue";
2
+ import { logger as loggerFn } from "@peerbit/logger";
3
+ export const logger = loggerFn({ module: "program-handler" });
4
+ export class Handler {
5
+ properties;
6
+ items;
7
+ _openQueue;
8
+ constructor(properties) {
9
+ this.properties = properties;
10
+ this._openQueue = new PQueue({ concurrency: 1 });
11
+ this.items = new Map();
12
+ }
13
+ async stop() {
14
+ this._openQueue.clear();
15
+ await this._openQueue.onIdle();
16
+ // Close all open databases
17
+ await Promise.all([...this.items.values()].map((program) => program.close()));
18
+ // Remove all databases from the state
19
+ this.items = new Map();
20
+ }
21
+ _onProgamClose(program) {
22
+ this.items.delete(program.address.toString());
23
+ }
24
+ async _onProgramOpen(program, mergeSrategy) {
25
+ const programAddress = program.address?.toString();
26
+ if (!programAddress) {
27
+ throw new Error("Missing program address");
28
+ }
29
+ if (this.items.has(programAddress)) {
30
+ // second condition only makes this throw error if we are to add a new instance with the same address
31
+ const existing = await this.checkProcessExisting(programAddress, program, mergeSrategy);
32
+ if (!existing) {
33
+ throw new Error("Unexpected");
34
+ }
35
+ this.items.set(programAddress, program);
36
+ }
37
+ else {
38
+ this.items.set(programAddress, program);
39
+ }
40
+ }
41
+ async checkProcessExisting(address, toOpen, mergeSrategy = "reject") {
42
+ const prev = this.items.get(address);
43
+ if (mergeSrategy === "reject") {
44
+ if (prev) {
45
+ throw new Error(`Program at ${address} is already open`);
46
+ }
47
+ }
48
+ else if (mergeSrategy === "replace") {
49
+ if (prev && prev !== toOpen) {
50
+ await prev.close(); // clouse previous
51
+ }
52
+ }
53
+ else if (mergeSrategy === "reuse") {
54
+ return prev;
55
+ }
56
+ }
57
+ async open(storeOrAddress, options = {}) {
58
+ const fn = async () => {
59
+ // TODO add locks for store lifecycle, e.g. what happens if we try to open and close a store at the same time?
60
+ let program = storeOrAddress;
61
+ if (typeof storeOrAddress === "string") {
62
+ try {
63
+ if (this.items?.has(storeOrAddress.toString())) {
64
+ const existing = await this.checkProcessExisting(storeOrAddress.toString(), program, options?.existing);
65
+ if (existing) {
66
+ return existing;
67
+ }
68
+ }
69
+ else {
70
+ program = (await this.properties.load(storeOrAddress, this.properties.client.services.blocks, options)); // TODO fix typings
71
+ if (!this.properties.shouldMonitor(program)) {
72
+ throw new Error(`Failed to open program because program is of type ${program?.constructor.name} `);
73
+ }
74
+ }
75
+ }
76
+ catch (error) {
77
+ logger.error("Failed to load store with address: " + storeOrAddress.toString());
78
+ throw error;
79
+ }
80
+ }
81
+ else if (!program.closed) {
82
+ const existing = this.items.get(program.address);
83
+ if (existing === program) {
84
+ return program;
85
+ }
86
+ else if (existing) {
87
+ const existing = await this.checkProcessExisting(program.address, program, options?.existing);
88
+ if (existing) {
89
+ return existing;
90
+ }
91
+ }
92
+ }
93
+ logger.debug(`Open database '${program.constructor.name}`);
94
+ const address = await program.save(this.properties.client.services.blocks);
95
+ const existing = await this.checkProcessExisting(address, program, options?.existing);
96
+ if (existing) {
97
+ return existing;
98
+ }
99
+ await program.beforeOpen(this.properties.client, {
100
+ onBeforeOpen: async (p) => {
101
+ if (this.properties.shouldMonitor(p) &&
102
+ p.parents.length === 1 &&
103
+ !p.parents[0]) {
104
+ return this._onProgramOpen(p, options?.existing);
105
+ }
106
+ },
107
+ onClose: (p) => {
108
+ if (this.properties.shouldMonitor(p)) {
109
+ return this._onProgamClose(p);
110
+ }
111
+ },
112
+ onDrop: (p) => {
113
+ if (this.properties.shouldMonitor(p)) {
114
+ return this._onProgamClose(p);
115
+ }
116
+ },
117
+ ...options,
118
+ // If the program opens more programs
119
+ // reset: options.reset,
120
+ });
121
+ await program.open(options.args);
122
+ await program.afterOpen();
123
+ return program;
124
+ };
125
+ // Prevent deadlocks when a program is opened by another program
126
+ // TODO make proper deduplciation behaviour
127
+ if (options?.parent) {
128
+ return fn();
129
+ }
130
+ return this._openQueue.add(fn); // TODO p-queue seem to return void type ;
131
+ }
132
+ }
133
+ //# sourceMappingURL=handler.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"handler.js","sourceRoot":"","sources":["../../src/handler.ts"],"names":[],"mappings":"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"}
@@ -1,101 +1,4 @@
1
- import { PublicSignKey } from "@peerbit/crypto";
2
- import { Constructor } from "@dao-xyz/borsh";
3
- import { EventEmitter } from "@libp2p/interfaces/events";
4
- import { Client } from "./node.js";
5
- import { Blocks } from "@peerbit/blocks-interface";
6
- import { PeerId as Libp2pPeerId } from "@libp2p/interface-peer-id";
7
- import { Address } from "./address.js";
8
- export type { Address };
9
- export interface Addressable {
10
- address?: Address | undefined;
11
- }
12
- export interface Saveable {
13
- save(store: Blocks, options?: {
14
- format?: string;
15
- timeout?: number;
16
- }): Promise<Address>;
17
- delete(): Promise<void>;
18
- }
19
- export type OpenProgram = (program: Program) => Promise<Program>;
20
- export interface NetworkEvents {
21
- join: CustomEvent<PublicSignKey>;
22
- leave: CustomEvent<PublicSignKey>;
23
- }
24
- export interface LifeCycleEvents {
25
- drop: CustomEvent<Program>;
26
- open: CustomEvent<Program>;
27
- close: CustomEvent<Program>;
28
- }
29
- export interface ProgramEvents extends NetworkEvents, LifeCycleEvents {
30
- }
31
- type EventOptions = {
32
- onBeforeOpen?: (program: AbstractProgram<any>) => Promise<void> | void;
33
- onOpen?: (program: AbstractProgram<any>) => Promise<void> | void;
34
- onDrop?: (program: AbstractProgram<any>) => Promise<void> | void;
35
- onClose?: (program: AbstractProgram<any>) => Promise<void> | void;
36
- };
37
- export type ProgramInitializationOptions<Args> = {
38
- args?: Args;
39
- parent?: AbstractProgram;
40
- } & EventOptions;
41
- export type ProgramClient = Client<Program, AbstractProgram>;
42
- export declare abstract class AbstractProgram<Args = any, Events extends ProgramEvents = ProgramEvents> {
43
- private _node;
44
- private _allPrograms;
45
- private _events;
46
- private _closed;
47
- parents: (AbstractProgram | undefined)[];
48
- children: AbstractProgram[];
49
- addParent(program: AbstractProgram | undefined): void;
50
- get events(): EventEmitter<Events>;
51
- get closed(): boolean;
52
- set closed(closed: boolean);
53
- get node(): ProgramClient;
54
- set node(node: ProgramClient);
55
- private _eventOptions;
56
- beforeOpen(node: ProgramClient, options?: ProgramInitializationOptions<Args>): Promise<this>;
57
- afterOpen(): Promise<this>;
58
- abstract open(args?: Args): Promise<void>;
59
- private _clear;
60
- private _emitJoinNetworkEvents;
61
- private _emitLeaveNetworkEvents;
62
- private _subscriptionEventListener;
63
- private _unsubscriptionEventListener;
64
- private processEnd;
65
- private end;
66
- close(from?: AbstractProgram): Promise<boolean>;
67
- drop(from?: AbstractProgram): Promise<boolean>;
68
- emitEvent(event: CustomEvent, parents?: boolean): void;
69
- /**
70
- * Wait for another peer to be 'ready' to talk with you for this particular program
71
- * @param other
72
- */
73
- waitFor(...other: (PublicSignKey | Libp2pPeerId)[]): Promise<void>;
74
- getReady(): Promise<Set<string>>;
75
- get allPrograms(): AbstractProgram[];
76
- get programs(): AbstractProgram[];
77
- clone(): this;
78
- getTopics?(): string[];
79
- }
80
- export interface CanTrust {
81
- isTrusted(keyHash: string): Promise<boolean> | boolean;
82
- }
83
- export declare abstract class Program<Args = any, Events extends ProgramEvents = ProgramEvents> extends AbstractProgram<Args, Events> implements Addressable, Saveable {
84
- private _address?;
85
- constructor();
86
- get address(): Address;
87
- set address(address: Address);
88
- beforeOpen(node: ProgramClient, options?: ProgramInitializationOptions<Args>): Promise<this>;
89
- static open<T extends Program<Args>, Args = any>(this: Constructor<T>, address: Address, node: ProgramClient, options?: ProgramInitializationOptions<Args>): Promise<T>;
90
- save(store?: Blocks): Promise<Address>;
91
- delete(): Promise<void>;
92
- static load<P extends Program<any>>(address: Address, store: Blocks, options?: {
93
- timeout?: number;
94
- }): Promise<P | undefined>;
95
- drop(from?: AbstractProgram): Promise<boolean>;
96
- }
97
- /**eve
98
- * Building block, but not something you use as a standalone
99
- */
100
- export declare abstract class ComposableProgram<Args = any, Events extends ProgramEvents = ProgramEvents> extends AbstractProgram<Args, Events> {
101
- }
1
+ export { type ProgramInitializationOptions, type OpenOptions, } from "./handler.js";
2
+ export * from "./client.js";
3
+ export * from "./program.js";
4
+ export * from "./address.js";