pump-chat-client
Version:
WebSocket client for connecting to pump.fun token chat rooms
319 lines • 11.1 kB
TypeScript
/**
* @fileoverview PumpChatClient - A WebSocket client for connecting to pump.fun token chat rooms.
* This client handles the socket.io protocol communication with pump.fun's chat servers,
* providing an easy-to-use interface for reading and sending chat messages.
*
* @module pump-chat-client
* @author codingbutter
* @license MIT
*/
import { EventEmitter } from "events";
/**
* Represents a chat message from pump.fun.
* @interface IMessage
* @property {string} id - Unique identifier for the message
* @property {string} roomId - The token address/room ID where the message was sent
* @property {string} username - Display name of the user who sent the message
* @property {string} userAddress - Wallet address of the user
* @property {string} message - The actual message content
* @property {string} profile_image - URL to the user's profile image
* @property {string} timestamp - ISO 8601 timestamp when the message was sent
* @property {string} messageType - Type of message (e.g., "REGULAR")
* @property {number} expiresAt - Unix timestamp when the message expires
*/
interface IMessage {
id: string;
roomId: string;
username: string;
userAddress: string;
message: string;
profile_image: string;
timestamp: string;
messageType: string;
expiresAt: number;
}
/**
* Configuration options for creating a PumpChatClient instance.
* @interface PumpChatClientOptions
* @property {string} roomId - The token address to connect to (required)
* @property {string} [username="anonymous"] - Username to display in chat (optional)
* @property {number} [messageHistoryLimit=100] - Maximum number of messages to store in memory (optional)
*/
interface PumpChatClientOptions {
roomId: string;
username?: string;
messageHistoryLimit?: number;
}
/**
* Event definitions for PumpChatClient
* @event PumpChatClient#connected - Emitted when successfully connected to the chat room
* @event PumpChatClient#disconnected - Emitted when disconnected from the chat room
* @event PumpChatClient#message - Emitted when a new message is received
* @event PumpChatClient#messageHistory - Emitted when message history is received
* @event PumpChatClient#error - Emitted when a connection or protocol error occurs
* @event PumpChatClient#serverError - Emitted when the server returns an error (e.g., authentication required)
* @event PumpChatClient#userLeft - Emitted when a user leaves the chat room
* @event PumpChatClient#maxReconnectAttemptsReached - Emitted after exhausting all reconnection attempts
*/
/**
* WebSocket client for connecting to pump.fun token chat rooms.
* Extends EventEmitter to provide event-driven communication.
*
* @class PumpChatClient
* @extends {EventEmitter}
* @example
* ```typescript
* const client = new PumpChatClient({
* roomId: 'YOUR_TOKEN_ADDRESS',
* username: 'myUsername',
* messageHistoryLimit: 50
* });
*
* client.on('message', (msg) => {
* console.log(`${msg.username}: ${msg.message}`);
* });
*
* client.connect();
* ```
*/
export declare class PumpChatClient extends EventEmitter {
/** WebSocket client instance from the 'websocket' library */
private client;
/** Active WebSocket connection, null when disconnected */
private connection;
/** The token address/room ID we're connected to */
private roomId;
/** Username displayed in chat messages */
private username;
/** In-memory storage of chat messages */
private messageHistory;
/** Maximum number of messages to keep in memory */
private messageHistoryLimit;
/** Current connection state */
private isConnected;
/** Interval timer for sending ping messages to keep connection alive */
private pingInterval;
/** Counter for reconnection attempts */
private reconnectAttempts;
/** Maximum number of times to attempt reconnection before giving up */
private maxReconnectAttempts;
/**
* Current acknowledgment ID for socket.io protocol.
* Cycles from 0-9 to match request/response pairs.
*/
private ackId;
/**
* Map of pending acknowledgments waiting for server responses.
* Key is the ack ID, value contains the event name and timestamp.
*/
private pendingAcks;
/**
* Creates a new PumpChatClient instance.
* @param {PumpChatClientOptions} options - Configuration options
* @param {string} options.roomId - The token address to connect to
* @param {string} [options.username="anonymous"] - Username for chat messages
* @param {number} [options.messageHistoryLimit=100] - Max messages to store
* @constructor
*/
constructor(options: PumpChatClientOptions);
/**
* Sets up event handlers for the WebSocket client.
* These handlers manage the initial connection establishment.
* @private
*/
private setupClientHandlers;
/**
* Sets up event handlers for an active WebSocket connection.
* These handlers manage the ongoing communication and lifecycle.
* @param {WebSocket.connection} connection - The active WebSocket connection
* @private
*/
private setupConnectionHandlers;
/**
* Main message handler that routes messages based on socket.io protocol type.
* Socket.io uses numeric prefixes to identify different message types.
* @param {string} data - Raw message data from the WebSocket
* @private
*/
private handleMessage;
/**
* Handles the initial connection message from the server.
* This message contains configuration like ping interval.
* @param {string} data - Raw message data starting with "0"
* @private
*/
private handleConnect;
/**
* Handles the server's acknowledgment of our handshake.
* After this, we can join the specific chat room.
* @param {string} data - Raw message data starting with "40"
* @private
*/
private handleConnectedAck;
/**
* Handles regular event messages that don't expect acknowledgments.
* These are typically server-initiated events.
* @param {string} data - Raw message data starting with "42"
* @private
*/
private handleEvent;
/**
* Handles acknowledgment messages without specific IDs.
* These are typically responses to requests without acknowledgment IDs.
* @param {string} data - Raw message data starting with "43"
* @private
*/
private handleEventWithAck;
/**
* Handles numbered acknowledgment messages (430-439).
* These correspond to our numbered requests (420-429).
* @param {string} data - Raw message data starting with "43X"
* @private
*/
private handleNumberedAck;
/**
* Handles new chat messages from the server.
* Adds the message to history and emits an event.
* @param {IMessage} message - The new message object
* @private
*/
private handleNewMessage;
/**
* Initializes the connection sequence.
* Currently a placeholder as the handshake is handled by message handlers.
* @private
*/
private initializeConnection;
/**
* Requests the chat message history from the server.
* Uses an acknowledgment ID to match the response.
* @private
*/
private requestMessageHistory;
/**
* Sends raw data through the WebSocket connection.
* Checks connection state before sending.
* @param {string} data - The data to send
* @private
*/
private send;
/**
* Starts sending periodic ping messages to keep the connection alive.
* The interval is usually specified by the server.
* @param {number} interval - Milliseconds between ping messages
* @private
*/
private startPing;
/**
* Stops sending ping messages.
* Called when disconnecting or before setting a new interval.
* @private
*/
private stopPing;
/**
* Sends a pong message in response to a server ping.
* This is part of the keep-alive mechanism.
* @private
*/
private sendPong;
/**
* Attempts to reconnect after a connection failure.
* Uses exponential backoff to avoid overwhelming the server.
* @private
*/
private attemptReconnect;
/**
* Connects to the pump.fun chat room.
* Sets up all required headers for the WebSocket handshake.
* @public
* @example
* ```typescript
* const client = new PumpChatClient({ roomId: 'token123' });
* client.connect();
* ```
*/
connect(): void;
/**
* Disconnects from the chat room.
* Stops all timers and closes the WebSocket connection.
* @public
* @example
* ```typescript
* client.disconnect();
* ```
*/
disconnect(): void;
/**
* Retrieves stored chat messages.
* @param {number} [limit] - Maximum number of messages to return (most recent)
* @returns {IMessage[]} Array of chat messages
* @public
* @example
* ```typescript
* // Get all stored messages
* const allMessages = client.getMessages();
*
* // Get last 10 messages
* const recentMessages = client.getMessages(10);
* ```
*/
getMessages(limit?: number): IMessage[];
/**
* Gets the most recent message from the chat.
* @returns {IMessage | null} The latest message or null if no messages
* @public
* @example
* ```typescript
* const latest = client.getLatestMessage();
* if (latest) {
* console.log(`Latest: ${latest.username}: ${latest.message}`);
* }
* ```
*/
getLatestMessage(): IMessage | null;
/**
* Sends a message to the chat room.
* Note: Requires authentication with pump.fun to work.
* @param {string} message - The message text to send
* @public
* @example
* ```typescript
* client.sendMessage('Hello everyone!');
* ```
* @remarks
* Sending messages requires being logged into pump.fun with valid session cookies.
* Without authentication, you'll receive a "Authentication required" error.
*/
sendMessage(message: string): void;
/**
* Gets the next acknowledgment ID for socket.io protocol.
* IDs cycle from 0 to 9 to match requests with responses.
* @returns {number} The next acknowledgment ID (0-9)
* @private
*/
private getNextAckId;
/**
* Cleans up acknowledgments that never received responses.
* This prevents memory leaks from accumulating pending acknowledgments.
* @private
*/
private cleanupStaleAcks;
/**
* Checks if the client is currently connected to the chat room.
* @returns {boolean} True if connected, false otherwise
* @public
* @example
* ```typescript
* if (client.isActive()) {
* client.sendMessage('Hello!');
* }
* ```
*/
isActive(): boolean;
}
/**
* Export the IMessage interface for external use
* @exports IMessage
*/
export type { IMessage };
//# sourceMappingURL=index.d.ts.map