mirror of
https://github.com/logos-messaging/js-waku.git
synced 2026-01-11 10:13:13 +00:00
* feat: implement LightPush v3 protocol support Add comprehensive LightPush v3 protocol implementation with: Core Features: - LightPush v3 protocol codec and multicodec detection - Status code-based error handling and validation - Protocol version inference and compatibility layers - Enhanced error types with detailed failure information Protocol Support: - Automatic v3/v2 protocol negotiation and fallback - Status code mapping to LightPush error types - Protocol version tracking in SDK results - Mixed protocol environment support Testing Infrastructure: - Comprehensive v3 error code handling tests - Mock functions for v3/v2 response scenarios - Protocol version detection and validation tests - Backward compatibility verification Implementation Details: - Clean separation between v2 and v3 response handling - Type-safe status code validation with isSuccess helper - Enhanced failure reporting with protocol version context - Proper error propagation through SDK layers This implementation maintains full backward compatibility with v2 while providing enhanced functionality for v3 protocol features. * feat: handle both light push protocols * fix: unsubscribe test * feat: consolidate lpv2/v3 types * feat(tests): bump nwaku to 0.36.0 * fix: remove extraneous exports * fix: add delay to tests * fix: remove protocol result types * feat: consolidate light push codec branching * fix: revert nwaku image * fix: remove multicodec * fix: remove protocolversion * feat: simplify v2/v3 branching logic to use two stream managers * fix: remove unused utils * fix: remove comments * fix: revert store test * fix: cleanup lightpush sdk * fix: remove unused util * fix: remove unused exports * fix: rename file from public to protocol_handler * fix: use proper type for sdk result * fix: update return types in filter * fix: rebase against latest master * fix: use both lightpush codecs when waiting for peer * fix: handle both lp codecs * fix: remove unused code * feat: use array for multicodec fields * fix: add timestamp if missing in v3 rpc * fix: resolve on either lp codec when waiting for peer * fix: remove unused util * fix: remove unnecessary abstraction * feat: accept nwaku docker image as arg, test lp backwards compat * fix: revert filter error * feat: add legacy flag to enable lightpushv2 only * Revert "feat: accept nwaku docker image as arg, test lp backwards compat" This reverts commit 857e12cbc73305e5c51abd057665bd34708b2737. * fix: remove unused test * feat: improve lp3 (#2597) * improve light push core * move back to singualar multicodec property, enable array prop only for light push * implement v2/v3 interop e2e test, re-add useLegacy flag, ensure e2e runs for v2 and v3 * fix v2 v3 condition * generate message package earlier * add log, fix condition --------- Co-authored-by: Sasha <118575614+weboko@users.noreply.github.com> Co-authored-by: Sasha <oleksandr@status.im>
253 lines
7.7 KiB
TypeScript
253 lines
7.7 KiB
TypeScript
import type { PeerId } from "@libp2p/interface";
|
|
|
|
import type { ConnectionManagerOptions } from "./connection_manager.js";
|
|
import type { DiscoveryOptions, PeerCache } from "./discovery.js";
|
|
import type { FilterProtocolOptions } from "./filter.js";
|
|
import type { CreateLibp2pOptions } from "./libp2p.js";
|
|
import type { LightPushProtocolOptions } from "./light_push.js";
|
|
import type { IDecodedMessage } from "./message.js";
|
|
import type { ThisAndThat, ThisOrThat } from "./misc.js";
|
|
import { NetworkConfig } from "./sharding.js";
|
|
import type { StoreProtocolOptions } from "./store.js";
|
|
|
|
export enum Protocols {
|
|
Relay = "relay",
|
|
Store = "store",
|
|
LightPush = "lightpush",
|
|
Filter = "filter"
|
|
}
|
|
|
|
export type CreateNodeOptions = {
|
|
/**
|
|
* Set the user agent string to be used in identification of the node.
|
|
*
|
|
* @default "js-waku"
|
|
*/
|
|
userAgent?: string;
|
|
|
|
/**
|
|
* Starts Waku node automatically upon creations.
|
|
* Calls {@link @waku/sdk!WakuNode.start} before returning {@link @waku/sdk!WakuNode}
|
|
*
|
|
* @default true
|
|
*/
|
|
autoStart?: boolean;
|
|
|
|
/**
|
|
* Configuration for determining the network in use.
|
|
* Network configuration refers to the shards and clusters used in the network.
|
|
*
|
|
* If using Static Sharding:
|
|
* Cluster ID and shards are specified in the format: clusterId: number, shards: number[]
|
|
* The default value is configured for The Waku Network => clusterId: 0, shards: [0, 1, 2, 3, 4, 5, 6, 7]
|
|
* To learn more about the sharding specification, see [Relay Sharding](https://rfc.vac.dev/spec/51/).
|
|
*
|
|
* If using Auto Sharding:
|
|
* Cluster ID and content topics are specified in the format: clusterId: number, contentTopics: string[]
|
|
* Content topics are used to determine the shards to be configured for the network.
|
|
* Cluster ID is optional, and defaults to The Waku Network's cluster ID => 0
|
|
* To specify content topics, see [Waku v2 Topic Usage Recommendations](https://github.com/vacp2p/rfc-index/blob/main/waku/informational/23/topics.md#content-topics) for details
|
|
*
|
|
* @default { clusterId: 1, shards: [0, 1, 2, 3, 4, 5, 6, 7] }
|
|
*/
|
|
networkConfig?: NetworkConfig;
|
|
|
|
/**
|
|
* You can pass options to the `Libp2p` instance used by {@link @waku/sdk!WakuNode} using the `libp2p` property.
|
|
* This property is the same type as the one passed to [`Libp2p.create`](https://github.com/libp2p/js-libp2p/blob/master/doc/API.md#create)
|
|
* apart that we made the `modules` property optional and partial,
|
|
* allowing its omission and letting Waku set good defaults.
|
|
* Notes that some values are overridden by {@link @waku/sdk!WakuNode} to ensure it implements the Waku protocol.
|
|
*/
|
|
libp2p?: Partial<CreateLibp2pOptions>;
|
|
|
|
/**
|
|
* Number of peers to connect to, for the usage of the protocol.
|
|
* This is used by Filter to retrieve messages.
|
|
*
|
|
* @default 2.
|
|
*/
|
|
numPeersToUse?: number;
|
|
|
|
/**
|
|
* Byte array used as key for the noise protocol used for connection encryption
|
|
* by [`Libp2p.create`](https://github.com/libp2p/js-libp2p/blob/master/doc/API.md#create)
|
|
* This is only used for test purposes to not run out of entropy during CI runs.
|
|
*/
|
|
staticNoiseKey?: Uint8Array;
|
|
|
|
/**
|
|
* Use recommended bootstrap method to discovery and connect to new nodes.
|
|
*/
|
|
defaultBootstrap?: boolean;
|
|
|
|
/**
|
|
* Enable or disable specific discovery methods.
|
|
*
|
|
* @default { peerExchange: true, dns: true, peerCache: true }
|
|
*/
|
|
discovery?: Partial<DiscoveryOptions>;
|
|
|
|
/**
|
|
* Peer cache to use for storing and retrieving peer information.
|
|
* If present, enables peer cache discovery.
|
|
*
|
|
* @default browser's localStorage
|
|
*/
|
|
peerCache?: PeerCache;
|
|
|
|
/**
|
|
* List of peers to use to bootstrap the node. Ignored if defaultBootstrap is set to true.
|
|
*/
|
|
bootstrapPeers?: string[];
|
|
|
|
/**
|
|
* Configuration for connection manager.
|
|
* If not specified - default values are applied.
|
|
*/
|
|
connectionManager?: Partial<ConnectionManagerOptions>;
|
|
|
|
/**
|
|
* Configuration for Filter protocol.
|
|
* If not specified - default values are applied.
|
|
*/
|
|
filter?: Partial<FilterProtocolOptions>;
|
|
|
|
/**
|
|
* Options for the Store protocol.
|
|
* If not specified - default values are applied.
|
|
*/
|
|
store?: Partial<StoreProtocolOptions>;
|
|
|
|
/**
|
|
* Options for the LightPush protocol.
|
|
* If not specified - default values are applied.
|
|
*/
|
|
lightPush?: Partial<LightPushProtocolOptions>;
|
|
};
|
|
|
|
export type Callback<T extends IDecodedMessage> = (
|
|
msg: T
|
|
) => void | Promise<void>;
|
|
|
|
export enum LightPushError {
|
|
GENERIC_FAIL = "Generic error",
|
|
DECODE_FAILED = "Failed to decode",
|
|
NO_PEER_AVAILABLE = "No peer available",
|
|
NO_STREAM_AVAILABLE = "No stream available",
|
|
NO_RESPONSE = "No response received",
|
|
STREAM_ABORTED = "Stream aborted",
|
|
|
|
ENCODE_FAILED = "Failed to encode",
|
|
EMPTY_PAYLOAD = "Payload is empty",
|
|
SIZE_TOO_BIG = "Size is too big",
|
|
TOPIC_NOT_CONFIGURED = "Topic not configured",
|
|
RLN_PROOF_GENERATION = "Proof generation failed",
|
|
REMOTE_PEER_REJECTED = "Remote peer rejected",
|
|
|
|
BAD_REQUEST = "Bad request format",
|
|
PAYLOAD_TOO_LARGE = "Message payload exceeds maximum size",
|
|
INVALID_MESSAGE = "Message validation failed",
|
|
UNSUPPORTED_TOPIC = "Unsupported pubsub topic",
|
|
TOO_MANY_REQUESTS = "Rate limit exceeded",
|
|
INTERNAL_ERROR = "Internal server error",
|
|
UNAVAILABLE = "Service temporarily unavailable",
|
|
NO_RLN_PROOF = "RLN proof generation failed",
|
|
NO_PEERS = "No relay peers available"
|
|
}
|
|
|
|
export enum FilterError {
|
|
// General errors
|
|
GENERIC_FAIL = "Generic error",
|
|
DECODE_FAILED = "Failed to decode",
|
|
NO_PEER_AVAILABLE = "No peer available",
|
|
NO_STREAM_AVAILABLE = "No stream available",
|
|
NO_RESPONSE = "No response received",
|
|
STREAM_ABORTED = "Stream aborted",
|
|
|
|
// Filter specific errors
|
|
REMOTE_PEER_REJECTED = "Remote peer rejected",
|
|
TOPIC_NOT_CONFIGURED = "Topic not configured",
|
|
SUBSCRIPTION_FAILED = "Subscription failed",
|
|
UNSUBSCRIBE_FAILED = "Unsubscribe failed",
|
|
PING_FAILED = "Ping failed",
|
|
TOPIC_DECODER_MISMATCH = "Topic decoder mismatch",
|
|
INVALID_DECODER_TOPICS = "Invalid decoder topics",
|
|
SUBSCRIPTION_LIMIT_EXCEEDED = "Subscription limit exceeded",
|
|
INVALID_CONTENT_TOPIC = "Invalid content topic",
|
|
PUSH_MESSAGE_FAILED = "Push message failed",
|
|
EMPTY_MESSAGE = "Empty message received",
|
|
MISSING_PUBSUB_TOPIC = "Pubsub topic missing from push message"
|
|
}
|
|
|
|
export interface LightPushFailure {
|
|
error: LightPushError;
|
|
peerId?: PeerId;
|
|
}
|
|
|
|
export interface FilterFailure {
|
|
error: FilterError;
|
|
peerId?: PeerId;
|
|
}
|
|
|
|
export type LightPushCoreResult = ThisOrThat<
|
|
"success",
|
|
PeerId,
|
|
"failure",
|
|
LightPushFailure
|
|
>;
|
|
|
|
export type FilterCoreResult = ThisOrThat<
|
|
"success",
|
|
PeerId,
|
|
"failure",
|
|
FilterFailure
|
|
>;
|
|
|
|
export type LightPushSDKResult = ThisAndThat<
|
|
"successes",
|
|
PeerId[],
|
|
"failures",
|
|
LightPushFailure[]
|
|
>;
|
|
|
|
export type FilterSDKResult = ThisAndThat<
|
|
"successes",
|
|
PeerId[],
|
|
"failures",
|
|
FilterFailure[]
|
|
>;
|
|
|
|
/**
|
|
* @deprecated replace usage by specific result types
|
|
*/
|
|
export type SDKProtocolResult = ThisAndThat<
|
|
"successes",
|
|
PeerId[],
|
|
"failures",
|
|
Array<{
|
|
error: ProtocolError;
|
|
peerId?: PeerId;
|
|
}>
|
|
>;
|
|
|
|
/**
|
|
* @deprecated replace usage by specific result types
|
|
*/
|
|
export enum ProtocolError {
|
|
GENERIC_FAIL = "Generic error",
|
|
REMOTE_PEER_REJECTED = "Remote peer rejected",
|
|
DECODE_FAILED = "Failed to decode",
|
|
NO_PEER_AVAILABLE = "No peer available",
|
|
NO_STREAM_AVAILABLE = "No stream available",
|
|
NO_RESPONSE = "No response received",
|
|
ENCODE_FAILED = "Failed to encode",
|
|
EMPTY_PAYLOAD = "Payload is empty",
|
|
SIZE_TOO_BIG = "Size is too big",
|
|
TOPIC_NOT_CONFIGURED = "Topic not configured",
|
|
STREAM_ABORTED = "Stream aborted",
|
|
RLN_PROOF_GENERATION = "Proof generation failed",
|
|
TOPIC_DECODER_MISMATCH = "Topic decoder mismatch",
|
|
INVALID_DECODER_TOPICS = "Invalid decoder topics"
|
|
}
|