Laravel Echo library for beautiful Pusher and Socket.IO integration
—
Pending
Does it follow best practices?
Impact
Pending
No eval scenarios have been run
Pending
The risk profile of this skill
Comprehensive channel system supporting public, private, encrypted private, and presence channels with event listening and broadcasting capabilities.
Abstract base class providing common channel functionality for all channel types.
/**
* Base class representing a broadcasting channel
*/
abstract class Channel {
/** Listen for an event on the channel instance */
abstract listen(event: string, callback: CallableFunction): this;
/** Stop listening to an event on the channel instance */
abstract stopListening(event: string, callback?: CallableFunction): this;
/** Register a callback to be called anytime a subscription succeeds */
abstract subscribed(callback: CallableFunction): this;
/** Register a callback to be called anytime an error occurs */
abstract error(callback: CallableFunction): this;
/** Listen for a whisper event on the channel instance */
listenForWhisper(event: string, callback: CallableFunction): this;
/** Stop listening for a whisper event on the channel instance */
stopListeningForWhisper(event: string, callback?: CallableFunction): this;
/** Listen for Laravel notifications on the channel */
notification(callback: CallableFunction): this;
}Usage Examples:
// Basic event listening
channel.listen("OrderShipped", (e) => {
console.log("Order shipped:", e.order);
});
// Listen for whispers (client-to-client events)
channel.listenForWhisper("typing", (e) => {
console.log(`${e.user.name} is typing...`);
});
// Listen for Laravel notifications
channel.notification((notification) => {
console.log("Notification received:", notification);
});
// Handle subscription success
channel.subscribed(() => {
console.log("Successfully subscribed to channel");
});
// Handle errors
channel.error((error) => {
console.error("Channel error:", error);
});Interface extending Channel for presence channels with member tracking capabilities.
/**
* Interface representing a presence channel with member tracking
*/
interface PresenceChannel extends Channel {
/** Register a callback to be called with current channel members */
here(callback: CallableFunction): this;
/** Listen for someone joining the channel */
joining(callback: CallableFunction): this;
/** Listen for someone leaving the channel */
leaving(callback: CallableFunction): this;
/** Send a whisper event to other clients in the channel */
whisper(eventName: string, data: Record<any, any>): this;
}Usage Examples:
const presenceChannel = echo.join("chat.1");
// Get current members when joining
presenceChannel.here((users) => {
console.log("Current users in chat:", users);
users.forEach(user => {
console.log(`- ${user.name} (${user.id})`);
});
});
// Listen for new members joining
presenceChannel.joining((user) => {
console.log(`${user.name} joined the chat`);
displayMessage(`${user.name} joined the chat`);
});
// Listen for members leaving
presenceChannel.leaving((user) => {
console.log(`${user.name} left the chat`);
displayMessage(`${user.name} left the chat`);
});
// Send whisper to other clients
presenceChannel.whisper("typing", {
user: { id: 1, name: "John" },
timestamp: Date.now()
});Channel implementations for Pusher-based broadcasters (Pusher, Reverb, Ably).
/**
* Basic Pusher channel for public events
*/
class PusherChannel<T extends BroadcastDriver> extends Channel {
pusher: Pusher;
name: string;
eventFormatter: EventFormatter;
subscription: PusherChannelInstance;
constructor(pusher: Pusher, name: string, options: EchoOptionsWithDefaults<T>);
listen(event: string, callback: CallableFunction): this;
stopListening(event: string, callback?: CallableFunction): this;
subscribed(callback: CallableFunction): this;
error(callback: CallableFunction): this;
}
/**
* Private Pusher channel requiring authentication
*/
class PusherPrivateChannel<T extends BroadcastDriver> extends PusherChannel<T> {
whisper(eventName: string, data: Record<any, any>): this;
}
/**
* Encrypted private Pusher channel with end-to-end encryption
*/
class PusherEncryptedPrivateChannel<T extends BroadcastDriver> extends PusherPrivateChannel<T> {
// Inherits all private channel functionality with encryption
}
/**
* Presence Pusher channel with member tracking
*/
class PusherPresenceChannel<T extends BroadcastDriver> extends PusherPrivateChannel<T> implements PresenceChannel {
here(callback: CallableFunction): this;
joining(callback: CallableFunction): this;
leaving(callback: CallableFunction): this;
}Channel implementations for Socket.IO broadcaster.
import type { Socket } from "socket.io-client";
/**
* Basic Socket.IO channel for public events
*/
class SocketIoChannel extends Channel {
socket: Socket;
name: string;
eventFormatter: EventFormatter;
constructor(socket: Socket, name: string, options: EchoOptionsWithDefaults<"socket.io">);
listen(event: string, callback: CallableFunction): this;
stopListening(event: string, callback?: CallableFunction): this;
subscribed(callback: CallableFunction): this;
error(callback: CallableFunction): this;
}
/**
* Private Socket.IO channel requiring authentication
*/
class SocketIoPrivateChannel extends SocketIoChannel {
whisper(eventName: string, data: Record<any, any>): this;
}
/**
* Presence Socket.IO channel with member tracking
*/
class SocketIoPresenceChannel extends SocketIoPrivateChannel implements PresenceChannel {
here(callback: CallableFunction): this;
joining(callback: CallableFunction): this;
leaving(callback: CallableFunction): this;
}Mock channel implementations for testing and development.
/**
* Null/mock channel for testing purposes
*/
class NullChannel extends Channel {
name: string;
constructor(name: string);
listen(event: string, callback: CallableFunction): this;
stopListening(event: string, callback?: CallableFunction): this;
subscribed(callback: CallableFunction): this;
error(callback: CallableFunction): this;
}
/**
* Null/mock private channel for testing
*/
class NullPrivateChannel extends NullChannel {
whisper(eventName: string, data: Record<any, any>): this;
}
/**
* Null/mock encrypted private channel for testing
*/
class NullEncryptedPrivateChannel extends NullPrivateChannel {
// Inherits private channel functionality
}
/**
* Null/mock presence channel for testing
*/
class NullPresenceChannel extends NullPrivateChannel implements PresenceChannel {
here(callback: CallableFunction): this;
joining(callback: CallableFunction): this;
leaving(callback: CallableFunction): this;
}Public channels are accessible to all users without authentication.
// Listen to public events
echo.channel("orders")
.listen("OrderShipped", (e) => {
console.log("Order shipped:", e.order);
})
.subscribed(() => {
console.log("Successfully subscribed to orders channel");
});Private channels require authentication and are typically user or resource-specific.
// Listen to private events
echo.private("user.1")
.listen("MessageReceived", (e) => {
console.log("New message:", e.message);
})
.error((error) => {
console.error("Private channel error:", error);
});Encrypted private channels provide end-to-end encryption (Pusher/Reverb only).
// Only available with Pusher/Reverb
echo.encryptedPrivate("sensitive-data.1")
.listen("ConfidentialUpdate", (e) => {
console.log("Encrypted data:", e.data);
});Presence channels track who is currently subscribed to the channel.
// Full presence channel example
const chatChannel = echo.join("chat.general");
chatChannel
.here((users) => {
console.log("Current users:", users);
updateUserList(users);
})
.joining((user) => {
console.log(`${user.name} joined`);
addUserToList(user);
showNotification(`${user.name} joined the chat`);
})
.leaving((user) => {
console.log(`${user.name} left`);
removeUserFromList(user);
showNotification(`${user.name} left the chat`);
})
.listen("MessageSent", (e) => {
displayMessage(e.message);
})
.listenForWhisper("typing", (e) => {
showTypingIndicator(e.user);
});
// Send typing indicator to other users
function handleTyping() {
chatChannel.whisper("typing", {
user: getCurrentUser(),
timestamp: Date.now()
});
}