laravel-echo
Version:
Laravel Echo library for beautiful Pusher and Socket.IO integration
506 lines (505 loc) • 14.2 kB
JavaScript
//#region src/channel/channel.ts
var e = class {
constructor() {
this.notificationCreatedEvent = ".Illuminate\\Notifications\\Events\\BroadcastNotificationCreated";
}
listenForWhisper(e, t) {
return this.listen(".client-" + e, t);
}
notification(e) {
return this.listen(this.notificationCreatedEvent, e);
}
stopListeningForNotification(e) {
return this.stopListening(this.notificationCreatedEvent, e);
}
stopListeningForWhisper(e, t) {
return this.stopListening(".client-" + e, t);
}
}, t = class {
constructor(e) {
this.namespace = e;
}
format(e) {
return [".", "\\"].includes(e.charAt(0)) ? e.substring(1) : (this.namespace && (e = this.namespace + "." + e), e.replace(/\./g, "\\"));
}
setNamespace(e) {
this.namespace = e;
}
};
//#endregion
//#region src/util/index.ts
function n(e) {
try {
return Reflect.construct(String, [], e), !0;
} catch {
return !1;
}
}
//#endregion
//#region src/channel/pusher-channel.ts
var r = class extends e {
constructor(e, n, r) {
super(), this.name = n, this.pusher = e, this.options = r, this.eventFormatter = new t(this.options.namespace), this.subscribe();
}
subscribe() {
this.subscription = this.pusher.subscribe(this.name);
}
unsubscribe() {
this.pusher.unsubscribe(this.name);
}
listen(e, t) {
return this.on(this.eventFormatter.format(e), t), this;
}
listenToAll(e) {
return this.subscription.bind_global((t, n) => {
if (t.startsWith("pusher:")) return;
let r = String(this.options.namespace ?? "").replace(/\./g, "\\");
e(t.startsWith(r) ? t.substring(r.length + 1) : "." + t, n);
}), this;
}
stopListening(e, t) {
return t ? this.subscription.unbind(this.eventFormatter.format(e), t) : this.subscription.unbind(this.eventFormatter.format(e)), this;
}
stopListeningToAll(e) {
return e ? this.subscription.unbind_global(e) : this.subscription.unbind_global(), this;
}
subscribed(e) {
return this.on("pusher:subscription_succeeded", () => {
e();
}), this;
}
error(e) {
return this.on("pusher:subscription_error", (t) => {
e(t);
}), this;
}
on(e, t) {
return this.subscription.bind(e, t), this;
}
}, i = class extends r {
whisper(e, t) {
return this.pusher.channels.channels[this.name].trigger(`client-${e}`, t), this;
}
}, a = class extends r {
whisper(e, t) {
return this.pusher.channels.channels[this.name].trigger(`client-${e}`, t), this;
}
}, o = class extends i {
here(e) {
return this.on("pusher:subscription_succeeded", (t) => {
e(Object.keys(t.members).map((e) => t.members[e]));
}), this;
}
joining(e) {
return this.on("pusher:member_added", (t) => {
e(t.info);
}), this;
}
whisper(e, t) {
return this.pusher.channels.channels[this.name].trigger(`client-${e}`, t), this;
}
leaving(e) {
return this.on("pusher:member_removed", (t) => {
e(t.info);
}), this;
}
}, s = class extends e {
constructor(e, n, r) {
super(), this.events = {}, this.listeners = {}, this.name = n, this.socket = e, this.options = r, this.eventFormatter = new t(this.options.namespace), this.subscribe();
}
subscribe() {
this.socket.emit("subscribe", {
channel: this.name,
auth: this.options.auth || {}
});
}
unsubscribe() {
this.unbind(), this.socket.emit("unsubscribe", {
channel: this.name,
auth: this.options.auth || {}
});
}
listen(e, t) {
return this.on(this.eventFormatter.format(e), t), this;
}
stopListening(e, t) {
return this.unbindEvent(this.eventFormatter.format(e), t), this;
}
subscribed(e) {
return this.on("connect", (t) => {
e(t);
}), this;
}
error(e) {
return this;
}
on(e, t) {
return this.listeners[e] = this.listeners[e] || [], this.events[e] || (this.events[e] = (t, n) => {
this.name === t && this.listeners[e] && this.listeners[e].forEach((e) => e(n));
}, this.socket.on(e, this.events[e])), this.listeners[e].push(t), this;
}
unbind() {
Object.keys(this.events).forEach((e) => {
this.unbindEvent(e);
});
}
unbindEvent(e, t) {
this.listeners[e] = this.listeners[e] || [], t && (this.listeners[e] = this.listeners[e].filter((e) => e !== t)), (!t || this.listeners[e].length === 0) && (this.events[e] && (this.socket.removeListener(e, this.events[e]), delete this.events[e]), delete this.listeners[e]);
}
}, c = class extends s {
whisper(e, t) {
return this.socket.emit("client event", {
channel: this.name,
event: `client-${e}`,
data: t
}), this;
}
}, l = class extends c {
here(e) {
return this.on("presence:subscribed", (t) => {
e(t.map((e) => e.user_info));
}), this;
}
joining(e) {
return this.on("presence:joining", (t) => e(t.user_info)), this;
}
whisper(e, t) {
return this.socket.emit("client event", {
channel: this.name,
event: `client-${e}`,
data: t
}), this;
}
leaving(e) {
return this.on("presence:leaving", (t) => e(t.user_info)), this;
}
}, u = class extends e {
subscribe() {}
unsubscribe() {}
listen(e, t) {
return this;
}
listenToAll(e) {
return this;
}
stopListening(e, t) {
return this;
}
subscribed(e) {
return this;
}
error(e) {
return this;
}
on(e, t) {
return this;
}
}, d = class extends u {
whisper(e, t) {
return this;
}
}, f = class extends u {
whisper(e, t) {
return this;
}
}, p = class extends d {
here(e) {
return this;
}
joining(e) {
return this;
}
whisper(e, t) {
return this;
}
leaving(e) {
return this;
}
}, m = class e {
static {
this._defaultOptions = {
auth: { headers: {} },
authEndpoint: "/broadcasting/auth",
userAuthentication: {
endpoint: "/broadcasting/user-auth",
headers: {}
},
csrfToken: null,
bearerToken: null,
host: null,
key: null,
namespace: "App.Events"
};
}
constructor(e) {
this.setOptions(e), this.connect();
}
setOptions(t) {
this.options = {
...e._defaultOptions,
...t,
broadcaster: t.broadcaster
};
let n = this.csrfToken();
n && (this.options.auth.headers["X-CSRF-TOKEN"] = n, this.options.userAuthentication.headers["X-CSRF-TOKEN"] = n), n = this.options.bearerToken, n && (this.options.auth.headers.Authorization = "Bearer " + n, this.options.userAuthentication.headers.Authorization = "Bearer " + n);
}
csrfToken() {
return typeof window < "u" && window.Laravel?.csrfToken ? window.Laravel.csrfToken : this.options.csrfToken ? this.options.csrfToken : typeof document < "u" && typeof document.querySelector == "function" ? document.querySelector("meta[name=\"csrf-token\"]")?.getAttribute("content") ?? null : null;
}
}, h = class extends m {
constructor(...e) {
super(...e), this.channels = {};
}
connect() {
if (this.options.client !== void 0) this.pusher = this.options.client;
else if (this.options.Pusher) this.pusher = new this.options.Pusher(this.options.key, this.options);
else if (typeof window < "u" && window.Pusher !== void 0) this.pusher = new window.Pusher(this.options.key, this.options);
else throw Error("Pusher client not found. Should be globally available or passed via options.client");
}
signin() {
this.pusher.signin();
}
listen(e, t, n) {
return this.channel(e).listen(t, n);
}
channel(e) {
return this.channels[e] || (this.channels[e] = new r(this.pusher, e, this.options)), this.channels[e];
}
privateChannel(e) {
return this.channels["private-" + e] || (this.channels["private-" + e] = new i(this.pusher, "private-" + e, this.options)), this.channels["private-" + e];
}
encryptedPrivateChannel(e) {
return this.channels["private-encrypted-" + e] || (this.channels["private-encrypted-" + e] = new a(this.pusher, "private-encrypted-" + e, this.options)), this.channels["private-encrypted-" + e];
}
presenceChannel(e) {
return this.channels["presence-" + e] || (this.channels["presence-" + e] = new o(this.pusher, "presence-" + e, this.options)), this.channels["presence-" + e];
}
leave(e) {
[
e,
"private-" + e,
"private-encrypted-" + e,
"presence-" + e
].forEach((e) => {
this.leaveChannel(e);
});
}
leaveChannel(e) {
this.channels[e] && (this.channels[e].unsubscribe(), delete this.channels[e]);
}
socketId() {
return this.pusher.connection.socket_id;
}
connectionStatus() {
let e = this.pusher.connection.state;
switch (e) {
case "connected":
case "connecting": return e;
case "failed":
case "unavailable": return "failed";
default: return "disconnected";
}
}
onConnectionChange(e) {
let t = () => {
e(this.connectionStatus());
}, n = [
"state_change",
"connected",
"disconnected"
];
return n.forEach((e) => {
this.pusher.connection.bind(e, t);
}), () => {
n.forEach((e) => {
this.pusher.connection.unbind(e, t);
});
};
}
disconnect() {
this.pusher.disconnect();
}
}, g = class extends m {
constructor(...e) {
super(...e), this.channels = {};
}
connect() {
let e = this.getSocketIO();
this.socket = e(this.options.host ?? void 0, this.options), this.socket.io.on("reconnect", () => {
Object.values(this.channels).forEach((e) => {
e.subscribe();
});
});
}
getSocketIO() {
if (this.options.client !== void 0) return this.options.client;
if (typeof window < "u" && window.io !== void 0) return window.io;
throw Error("Socket.io client not found. Should be globally available or passed via options.client");
}
listen(e, t, n) {
return this.channel(e).listen(t, n);
}
channel(e) {
return this.channels[e] || (this.channels[e] = new s(this.socket, e, this.options)), this.channels[e];
}
privateChannel(e) {
return this.channels["private-" + e] || (this.channels["private-" + e] = new c(this.socket, "private-" + e, this.options)), this.channels["private-" + e];
}
presenceChannel(e) {
return this.channels["presence-" + e] || (this.channels["presence-" + e] = new l(this.socket, "presence-" + e, this.options)), this.channels["presence-" + e];
}
leave(e) {
[
e,
"private-" + e,
"presence-" + e
].forEach((e) => {
this.leaveChannel(e);
});
}
leaveChannel(e) {
this.channels[e] && (this.channels[e].unsubscribe(), delete this.channels[e]);
}
socketId() {
return this.socket.id;
}
connectionStatus() {
return this.socket.connected ? "connected" : this.socket.io._reconnecting ? "reconnecting" : this.socket.id === void 0 ? "connecting" : "disconnected";
}
onConnectionChange(e) {
let t = () => {
e(this.connectionStatus());
}, n = [
"connect",
"disconnect",
"connect_error",
"reconnect_attempt",
"reconnect",
"reconnect_error",
"reconnect_failed"
];
return n.forEach((e) => {
this.socket.on(e, t);
}), () => {
n.forEach((e) => {
this.socket.off(e, t);
});
};
}
disconnect() {
this.socket.disconnect();
}
}, _ = class extends m {
constructor(...e) {
super(...e), this.channels = {};
}
connect() {}
listen(e, t, n) {
return new u();
}
channel(e) {
return new u();
}
privateChannel(e) {
return new d();
}
encryptedPrivateChannel(e) {
return new f();
}
presenceChannel(e) {
return new p();
}
leave(e) {}
leaveChannel(e) {}
socketId() {
return "fake-socket-id";
}
connectionStatus() {
return "connected";
}
onConnectionChange(e) {
return () => {};
}
disconnect() {}
}, v = class {
constructor(e) {
this.options = e, this.connect(), this.options.withoutInterceptors || this.registerInterceptors();
}
channel(e) {
return this.connector.channel(e);
}
connect() {
if (this.options.broadcaster === "reverb") this.connector = new h({
...this.options,
cluster: ""
});
else if (this.options.broadcaster === "pusher") this.connector = new h(this.options);
else if (this.options.broadcaster === "ably") this.connector = new h({
...this.options,
cluster: "",
broadcaster: "pusher"
});
else if (this.options.broadcaster === "socket.io") this.connector = new g(this.options);
else if (this.options.broadcaster === "null") this.connector = new _(this.options);
else if (typeof this.options.broadcaster == "function" && n(this.options.broadcaster)) this.connector = new this.options.broadcaster(this.options);
else throw Error(`Broadcaster ${typeof this.options.broadcaster} ${String(this.options.broadcaster)} is not supported.`);
}
disconnect() {
this.connector.disconnect();
}
join(e) {
return this.connector.presenceChannel(e);
}
leave(e) {
this.connector.leave(e);
}
leaveChannel(e) {
this.connector.leaveChannel(e);
}
leaveAllChannels() {
for (let e in this.connector.channels) this.leaveChannel(e);
}
listen(e, t, n) {
return this.connector.listen(e, t, n);
}
private(e) {
return this.connector.privateChannel(e);
}
encryptedPrivate(e) {
if (this.connectorSupportsEncryptedPrivateChannels(this.connector)) return this.connector.encryptedPrivateChannel(e);
throw Error(`Broadcaster ${typeof this.options.broadcaster} ${String(this.options.broadcaster)} does not support encrypted private channels.`);
}
connectorSupportsEncryptedPrivateChannels(e) {
return e instanceof h || e instanceof _;
}
socketId() {
return this.connector.socketId();
}
connectionStatus() {
return this.connector.connectionStatus();
}
registerInterceptors() {
typeof Vue < "u" && Vue?.http && this.registerVueRequestInterceptor(), typeof axios == "function" && this.registerAxiosRequestInterceptor(), typeof jQuery == "function" && this.registerjQueryAjaxSetup(), typeof Turbo == "object" && this.registerTurboRequestInterceptor();
}
registerVueRequestInterceptor() {
Vue.http.interceptors.push((e, t) => {
this.socketId() && e.headers.set("X-Socket-ID", this.socketId()), t();
});
}
registerAxiosRequestInterceptor() {
axios.interceptors.request.use((e) => (this.socketId() && (e.headers["X-Socket-Id"] = this.socketId()), e));
}
registerjQueryAjaxSetup() {
jQuery.ajax !== void 0 && jQuery.ajaxPrefilter((e, t, n) => {
this.socketId() && n.setRequestHeader("X-Socket-Id", this.socketId());
});
}
registerTurboRequestInterceptor() {
document.addEventListener("turbo:before-fetch-request", (e) => {
e.detail.fetchOptions.headers["X-Socket-Id"] = this.socketId();
});
}
};
//#endregion
export { e as Channel, m as Connector, t as EventFormatter, v as default };
//# sourceMappingURL=echo.js.map