{"version":3,"sources":["webpack://avo/./node_modules/@rails/actioncable/src/adapters.js","webpack://avo/./node_modules/@rails/actioncable/src/logger.js","webpack://avo/./node_modules/@rails/actioncable/src/connection_monitor.js","webpack://avo/./node_modules/@rails/actioncable/src/internal.js","webpack://avo/./node_modules/@rails/actioncable/src/connection.js","webpack://avo/./node_modules/@rails/actioncable/src/subscription.js","webpack://avo/./node_modules/@rails/actioncable/src/subscription_guarantor.js","webpack://avo/./node_modules/@rails/actioncable/src/subscriptions.js","webpack://avo/./node_modules/@rails/actioncable/src/consumer.js","webpack://avo/./node_modules/@rails/actioncable/src/index.js"],"names":["logger","self","console","WebSocket","messages","this","enabled","push","Date","now","adapters","log","getTime","secondsSince","time","ConnectionMonitor","connection","visibilityDidChange","bind","reconnectAttempts","isRunning","startedAt","stoppedAt","startPolling","addEventListener","constructor","staleThreshold","stopPolling","removeEventListener","pingedAt","recordPing","disconnectedAt","poll","clearTimeout","pollTimeout","setTimeout","reconnectIfStale","getPollInterval","reconnectionBackoffRate","Math","pow","min","random","connectionIsStale","refreshedAt","disconnectedRecently","reopen","document","visibilityState","isOpen","message_types","protocols","supportedProtocols","slice","length","indexOf","Connection","consumer","open","subscriptions","monitor","disconnected","data","webSocket","send","JSON","stringify","isActive","getState","uninstallEventHandlers","url","installEventHandlers","start","allowReconnect","stop","close","error","reopenDelay","protocol","isState","call","getProtocol","states","state","readyState","toLowerCase","eventName","events","handler","prototype","event","isProtocolSupported","identifier","message","reason","reconnect","type","parse","welcome","recordConnect","reload","disconnect","ping","confirmation","confirmSubscription","notify","rejection","reject","recordDisconnect","notifyAll","willAttemptReconnect","Subscription","params","mixin","object","properties","key","value","extend","action","command","remove","pendingSubscriptions","subscription","startGuaranteeing","filter","s","stopGuaranteeing","retrySubscribing","retryTimeout","map","subscribe","Subscriptions","guarantor","channelName","channel","add","ensureActiveConnection","forget","findAll","sendCommand","callbackName","args","undefined","guarantee","Consumer","_url","createWebSocketURL","test","a","createElement","href","replace","createConsumer","getConfig","name","element","head","querySelector","getAttribute"],"mappings":"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","file":"js/actioncable-7119dbc1a908641fb263.chunk.js","sourcesContent":["export default {\n logger: self.console,\n WebSocket: self.WebSocket\n}\n","import adapters from \"./adapters\"\n\n// The logger is disabled by default. You can enable it with:\n//\n// ActionCable.logger.enabled = true\n//\n// Example:\n//\n// import * as ActionCable from '@rails/actioncable'\n//\n// ActionCable.logger.enabled = true\n// ActionCable.logger.log('Connection Established.')\n//\n\nexport default {\n log(...messages) {\n if (this.enabled) {\n messages.push(Date.now())\n adapters.logger.log(\"[ActionCable]\", ...messages)\n }\n },\n}\n","import logger from \"./logger\"\n\n// Responsible for ensuring the cable connection is in good health by validating the heartbeat pings sent from the server, and attempting\n// revival reconnections if things go astray. Internal class, not intended for direct user manipulation.\n\nconst now = () => new Date().getTime()\n\nconst secondsSince = time => (now() - time) / 1000\n\nclass ConnectionMonitor {\n constructor(connection) {\n this.visibilityDidChange = this.visibilityDidChange.bind(this)\n this.connection = connection\n this.reconnectAttempts = 0\n }\n\n start() {\n if (!this.isRunning()) {\n this.startedAt = now()\n delete this.stoppedAt\n this.startPolling()\n addEventListener(\"visibilitychange\", this.visibilityDidChange)\n logger.log(`ConnectionMonitor started. stale threshold = ${this.constructor.staleThreshold} s`)\n }\n }\n\n stop() {\n if (this.isRunning()) {\n this.stoppedAt = now()\n this.stopPolling()\n removeEventListener(\"visibilitychange\", this.visibilityDidChange)\n logger.log(\"ConnectionMonitor stopped\")\n }\n }\n\n isRunning() {\n return this.startedAt && !this.stoppedAt\n }\n\n recordPing() {\n this.pingedAt = now()\n }\n\n recordConnect() {\n this.reconnectAttempts = 0\n this.recordPing()\n delete this.disconnectedAt\n logger.log(\"ConnectionMonitor recorded connect\")\n }\n\n recordDisconnect() {\n this.disconnectedAt = now()\n logger.log(\"ConnectionMonitor recorded disconnect\")\n }\n\n // Private\n\n startPolling() {\n this.stopPolling()\n this.poll()\n }\n\n stopPolling() {\n clearTimeout(this.pollTimeout)\n }\n\n poll() {\n this.pollTimeout = setTimeout(() => {\n this.reconnectIfStale()\n this.poll()\n }\n , this.getPollInterval())\n }\n\n getPollInterval() {\n const { staleThreshold, reconnectionBackoffRate } = this.constructor\n const backoff = Math.pow(1 + reconnectionBackoffRate, Math.min(this.reconnectAttempts, 10))\n const jitterMax = this.reconnectAttempts === 0 ? 1.0 : reconnectionBackoffRate\n const jitter = jitterMax * Math.random()\n return staleThreshold * 1000 * backoff * (1 + jitter)\n }\n\n reconnectIfStale() {\n if (this.connectionIsStale()) {\n logger.log(`ConnectionMonitor detected stale connection. reconnectAttempts = ${this.reconnectAttempts}, time stale = ${secondsSince(this.refreshedAt)} s, stale threshold = ${this.constructor.staleThreshold} s`)\n this.reconnectAttempts++\n if (this.disconnectedRecently()) {\n logger.log(`ConnectionMonitor skipping reopening recent disconnect. time disconnected = ${secondsSince(this.disconnectedAt)} s`)\n } else {\n logger.log(\"ConnectionMonitor reopening\")\n this.connection.reopen()\n }\n }\n }\n\n get refreshedAt() {\n return this.pingedAt ? this.pingedAt : this.startedAt\n }\n\n connectionIsStale() {\n return secondsSince(this.refreshedAt) > this.constructor.staleThreshold\n }\n\n disconnectedRecently() {\n return this.disconnectedAt && (secondsSince(this.disconnectedAt) < this.constructor.staleThreshold)\n }\n\n visibilityDidChange() {\n if (document.visibilityState === \"visible\") {\n setTimeout(() => {\n if (this.connectionIsStale() || !this.connection.isOpen()) {\n logger.log(`ConnectionMonitor reopening stale connection on visibilitychange. visibilityState = ${document.visibilityState}`)\n this.connection.reopen()\n }\n }\n , 200)\n }\n }\n\n}\n\nConnectionMonitor.staleThreshold = 6 // Server::Connections::BEAT_INTERVAL * 2 (missed two pings)\nConnectionMonitor.reconnectionBackoffRate = 0.15\n\nexport default ConnectionMonitor\n","export default {\n \"message_types\": {\n \"welcome\": \"welcome\",\n \"disconnect\": \"disconnect\",\n \"ping\": \"ping\",\n \"confirmation\": \"confirm_subscription\",\n \"rejection\": \"reject_subscription\"\n },\n \"disconnect_reasons\": {\n \"unauthorized\": \"unauthorized\",\n \"invalid_request\": \"invalid_request\",\n \"server_restart\": \"server_restart\"\n },\n \"default_mount_path\": \"/cable\",\n \"protocols\": [\n \"actioncable-v1-json\",\n \"actioncable-unsupported\"\n ]\n}\n","import adapters from \"./adapters\"\nimport ConnectionMonitor from \"./connection_monitor\"\nimport INTERNAL from \"./internal\"\nimport logger from \"./logger\"\n\n// Encapsulate the cable connection held by the consumer. This is an internal class not intended for direct user manipulation.\n\nconst {message_types, protocols} = INTERNAL\nconst supportedProtocols = protocols.slice(0, protocols.length - 1)\n\nconst indexOf = [].indexOf\n\nclass Connection {\n constructor(consumer) {\n this.open = this.open.bind(this)\n this.consumer = consumer\n this.subscriptions = this.consumer.subscriptions\n this.monitor = new ConnectionMonitor(this)\n this.disconnected = true\n }\n\n send(data) {\n if (this.isOpen()) {\n this.webSocket.send(JSON.stringify(data))\n return true\n } else {\n return false\n }\n }\n\n open() {\n if (this.isActive()) {\n logger.log(`Attempted to open WebSocket, but existing socket is ${this.getState()}`)\n return false\n } else {\n logger.log(`Opening WebSocket, current state is ${this.getState()}, subprotocols: ${protocols}`)\n if (this.webSocket) { this.uninstallEventHandlers() }\n this.webSocket = new adapters.WebSocket(this.consumer.url, protocols)\n this.installEventHandlers()\n this.monitor.start()\n return true\n }\n }\n\n close({allowReconnect} = {allowReconnect: true}) {\n if (!allowReconnect) { this.monitor.stop() }\n if (this.isActive()) {\n return this.webSocket.close()\n }\n }\n\n reopen() {\n logger.log(`Reopening WebSocket, current state is ${this.getState()}`)\n if (this.isActive()) {\n try {\n return this.close()\n } catch (error) {\n logger.log(\"Failed to reopen WebSocket\", error)\n }\n finally {\n logger.log(`Reopening WebSocket in ${this.constructor.reopenDelay}ms`)\n setTimeout(this.open, this.constructor.reopenDelay)\n }\n } else {\n return this.open()\n }\n }\n\n getProtocol() {\n if (this.webSocket) {\n return this.webSocket.protocol\n }\n }\n\n isOpen() {\n return this.isState(\"open\")\n }\n\n isActive() {\n return this.isState(\"open\", \"connecting\")\n }\n\n // Private\n\n isProtocolSupported() {\n return indexOf.call(supportedProtocols, this.getProtocol()) >= 0\n }\n\n isState(...states) {\n return indexOf.call(states, this.getState()) >= 0\n }\n\n getState() {\n if (this.webSocket) {\n for (let state in adapters.WebSocket) {\n if (adapters.WebSocket[state] === this.webSocket.readyState) {\n return state.toLowerCase()\n }\n }\n }\n return null\n }\n\n installEventHandlers() {\n for (let eventName in this.events) {\n const handler = this.events[eventName].bind(this)\n this.webSocket[`on${eventName}`] = handler\n }\n }\n\n uninstallEventHandlers() {\n for (let eventName in this.events) {\n this.webSocket[`on${eventName}`] = function() {}\n }\n }\n\n}\n\nConnection.reopenDelay = 500\n\nConnection.prototype.events = {\n message(event) {\n if (!this.isProtocolSupported()) { return }\n const {identifier, message, reason, reconnect, type} = JSON.parse(event.data)\n switch (type) {\n case message_types.welcome:\n this.monitor.recordConnect()\n return this.subscriptions.reload()\n case message_types.disconnect:\n logger.log(`Disconnecting. Reason: ${reason}`)\n return this.close({allowReconnect: reconnect})\n case message_types.ping:\n return this.monitor.recordPing()\n case message_types.confirmation:\n this.subscriptions.confirmSubscription(identifier)\n return this.subscriptions.notify(identifier, \"connected\")\n case message_types.rejection:\n return this.subscriptions.reject(identifier)\n default:\n return this.subscriptions.notify(identifier, \"received\", message)\n }\n },\n\n open() {\n logger.log(`WebSocket onopen event, using '${this.getProtocol()}' subprotocol`)\n this.disconnected = false\n if (!this.isProtocolSupported()) {\n logger.log(\"Protocol is unsupported. Stopping monitor and disconnecting.\")\n return this.close({allowReconnect: false})\n }\n },\n\n close(event) {\n logger.log(\"WebSocket onclose event\")\n if (this.disconnected) { return }\n this.disconnected = true\n this.monitor.recordDisconnect()\n return this.subscriptions.notifyAll(\"disconnected\", {willAttemptReconnect: this.monitor.isRunning()})\n },\n\n error() {\n logger.log(\"WebSocket onerror event\")\n }\n}\n\nexport default Connection\n","// A new subscription is created through the ActionCable.Subscriptions instance available on the consumer.\n// It provides a number of callbacks and a method for calling remote procedure calls on the corresponding\n// Channel instance on the server side.\n//\n// An example demonstrates the basic functionality:\n//\n// App.appearance = App.cable.subscriptions.create(\"AppearanceChannel\", {\n// connected() {\n// // Called once the subscription has been successfully completed\n// },\n//\n// disconnected({ willAttemptReconnect: boolean }) {\n// // Called when the client has disconnected with the server.\n// // The object will have an `willAttemptReconnect` property which\n// // says whether the client has the intention of attempting\n// // to reconnect.\n// },\n//\n// appear() {\n// this.perform('appear', {appearing_on: this.appearingOn()})\n// },\n//\n// away() {\n// this.perform('away')\n// },\n//\n// appearingOn() {\n// $('main').data('appearing-on')\n// }\n// })\n//\n// The methods #appear and #away forward their intent to the remote AppearanceChannel instance on the server\n// by calling the `perform` method with the first parameter being the action (which maps to AppearanceChannel#appear/away).\n// The second parameter is a hash that'll get JSON encoded and made available on the server in the data parameter.\n//\n// This is how the server component would look:\n//\n// class AppearanceChannel < ApplicationActionCable::Channel\n// def subscribed\n// current_user.appear\n// end\n//\n// def unsubscribed\n// current_user.disappear\n// end\n//\n// def appear(data)\n// current_user.appear on: data['appearing_on']\n// end\n//\n// def away\n// current_user.away\n// end\n// end\n//\n// The \"AppearanceChannel\" name is automatically mapped between the client-side subscription creation and the server-side Ruby class name.\n// The AppearanceChannel#appear/away public methods are exposed automatically to client-side invocation through the perform method.\n\nconst extend = function(object, properties) {\n if (properties != null) {\n for (let key in properties) {\n const value = properties[key]\n object[key] = value\n }\n }\n return object\n}\n\nexport default class Subscription {\n constructor(consumer, params = {}, mixin) {\n this.consumer = consumer\n this.identifier = JSON.stringify(params)\n extend(this, mixin)\n }\n\n // Perform a channel action with the optional data passed as an attribute\n perform(action, data = {}) {\n data.action = action\n return this.send(data)\n }\n\n send(data) {\n return this.consumer.send({command: \"message\", identifier: this.identifier, data: JSON.stringify(data)})\n }\n\n unsubscribe() {\n return this.consumer.subscriptions.remove(this)\n }\n}\n","import logger from \"./logger\"\n\n// Responsible for ensuring channel subscribe command is confirmed, retrying until confirmation is received.\n// Internal class, not intended for direct user manipulation.\n\nclass SubscriptionGuarantor {\n constructor(subscriptions) {\n this.subscriptions = subscriptions\n this.pendingSubscriptions = []\n }\n\n guarantee(subscription) {\n if(this.pendingSubscriptions.indexOf(subscription) == -1){ \n logger.log(`SubscriptionGuarantor guaranteeing ${subscription.identifier}`)\n this.pendingSubscriptions.push(subscription) \n }\n else {\n logger.log(`SubscriptionGuarantor already guaranteeing ${subscription.identifier}`)\n }\n this.startGuaranteeing()\n }\n\n forget(subscription) {\n logger.log(`SubscriptionGuarantor forgetting ${subscription.identifier}`)\n this.pendingSubscriptions = (this.pendingSubscriptions.filter((s) => s !== subscription))\n }\n\n startGuaranteeing() {\n this.stopGuaranteeing()\n this.retrySubscribing()\n }\n \n stopGuaranteeing() {\n clearTimeout(this.retryTimeout)\n }\n\n retrySubscribing() {\n this.retryTimeout = setTimeout(() => {\n if (this.subscriptions && typeof(this.subscriptions.subscribe) === \"function\") {\n this.pendingSubscriptions.map((subscription) => {\n logger.log(`SubscriptionGuarantor resubscribing ${subscription.identifier}`)\n this.subscriptions.subscribe(subscription)\n })\n }\n }\n , 500)\n }\n}\n\nexport default SubscriptionGuarantor","import Subscription from \"./subscription\"\nimport SubscriptionGuarantor from \"./subscription_guarantor\"\nimport logger from \"./logger\"\n\n// Collection class for creating (and internally managing) channel subscriptions.\n// The only method intended to be triggered by the user is ActionCable.Subscriptions#create,\n// and it should be called through the consumer like so:\n//\n// App = {}\n// App.cable = ActionCable.createConsumer(\"ws://example.com/accounts/1\")\n// App.appearance = App.cable.subscriptions.create(\"AppearanceChannel\")\n//\n// For more details on how you'd configure an actual channel subscription, see ActionCable.Subscription.\n\nexport default class Subscriptions {\n constructor(consumer) {\n this.consumer = consumer\n this.guarantor = new SubscriptionGuarantor(this)\n this.subscriptions = []\n }\n\n create(channelName, mixin) {\n const channel = channelName\n const params = typeof channel === \"object\" ? channel : {channel}\n const subscription = new Subscription(this.consumer, params, mixin)\n return this.add(subscription)\n }\n\n // Private\n\n add(subscription) {\n this.subscriptions.push(subscription)\n this.consumer.ensureActiveConnection()\n this.notify(subscription, \"initialized\")\n this.subscribe(subscription)\n return subscription\n }\n\n remove(subscription) {\n this.forget(subscription)\n if (!this.findAll(subscription.identifier).length) {\n this.sendCommand(subscription, \"unsubscribe\")\n }\n return subscription\n }\n\n reject(identifier) {\n return this.findAll(identifier).map((subscription) => {\n this.forget(subscription)\n this.notify(subscription, \"rejected\")\n return subscription\n })\n }\n\n forget(subscription) {\n this.guarantor.forget(subscription)\n this.subscriptions = (this.subscriptions.filter((s) => s !== subscription))\n return subscription\n }\n\n findAll(identifier) {\n return this.subscriptions.filter((s) => s.identifier === identifier)\n }\n\n reload() {\n return this.subscriptions.map((subscription) =>\n this.subscribe(subscription))\n }\n\n notifyAll(callbackName, ...args) {\n return this.subscriptions.map((subscription) =>\n this.notify(subscription, callbackName, ...args))\n }\n\n notify(subscription, callbackName, ...args) {\n let subscriptions\n if (typeof subscription === \"string\") {\n subscriptions = this.findAll(subscription)\n } else {\n subscriptions = [subscription]\n }\n\n return subscriptions.map((subscription) =>\n (typeof subscription[callbackName] === \"function\" ? subscription[callbackName](...args) : undefined))\n }\n\n subscribe(subscription) {\n if (this.sendCommand(subscription, \"subscribe\")) {\n this.guarantor.guarantee(subscription)\n }\n }\n\n confirmSubscription(identifier) {\n logger.log(`Subscription confirmed ${identifier}`)\n this.findAll(identifier).map((subscription) =>\n this.guarantor.forget(subscription))\n }\n\n sendCommand(subscription, command) {\n const {identifier} = subscription\n return this.consumer.send({command, identifier})\n }\n}\n","import Connection from \"./connection\"\nimport Subscriptions from \"./subscriptions\"\n\n// The ActionCable.Consumer establishes the connection to a server-side Ruby Connection object. Once established,\n// the ActionCable.ConnectionMonitor will ensure that its properly maintained through heartbeats and checking for stale updates.\n// The Consumer instance is also the gateway to establishing subscriptions to desired channels through the #createSubscription\n// method.\n//\n// The following example shows how this can be set up:\n//\n// App = {}\n// App.cable = ActionCable.createConsumer(\"ws://example.com/accounts/1\")\n// App.appearance = App.cable.subscriptions.create(\"AppearanceChannel\")\n//\n// For more details on how you'd configure an actual channel subscription, see ActionCable.Subscription.\n//\n// When a consumer is created, it automatically connects with the server.\n//\n// To disconnect from the server, call\n//\n// App.cable.disconnect()\n//\n// and to restart the connection:\n//\n// App.cable.connect()\n//\n// Any channel subscriptions which existed prior to disconnecting will\n// automatically resubscribe.\n\nexport default class Consumer {\n constructor(url) {\n this._url = url\n this.subscriptions = new Subscriptions(this)\n this.connection = new Connection(this)\n }\n\n get url() {\n return createWebSocketURL(this._url)\n }\n\n send(data) {\n return this.connection.send(data)\n }\n\n connect() {\n return this.connection.open()\n }\n\n disconnect() {\n return this.connection.close({allowReconnect: false})\n }\n\n ensureActiveConnection() {\n if (!this.connection.isActive()) {\n return this.connection.open()\n }\n }\n}\n\nexport function createWebSocketURL(url) {\n if (typeof url === \"function\") {\n url = url()\n }\n\n if (url && !/^wss?:/i.test(url)) {\n const a = document.createElement(\"a\")\n a.href = url\n // Fix populating Location properties in IE. Otherwise, protocol will be blank.\n a.href = a.href\n a.protocol = a.protocol.replace(\"http\", \"ws\")\n return a.href\n } else {\n return url\n }\n}\n","import Connection from \"./connection\"\nimport ConnectionMonitor from \"./connection_monitor\"\nimport Consumer, { createWebSocketURL } from \"./consumer\"\nimport INTERNAL from \"./internal\"\nimport Subscription from \"./subscription\"\nimport Subscriptions from \"./subscriptions\"\nimport SubscriptionGuarantor from \"./subscription_guarantor\"\nimport adapters from \"./adapters\"\nimport logger from \"./logger\"\n\nexport {\n Connection,\n ConnectionMonitor,\n Consumer,\n INTERNAL,\n Subscription,\n Subscriptions,\n SubscriptionGuarantor,\n adapters,\n createWebSocketURL,\n logger,\n}\n\nexport function createConsumer(url = getConfig(\"url\") || INTERNAL.default_mount_path) {\n return new Consumer(url)\n}\n\nexport function getConfig(name) {\n const element = document.head.querySelector(`meta[name='action-cable-${name}']`)\n if (element) {\n return element.getAttribute(\"content\")\n }\n}\n"],"sourceRoot":""}