| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125 |
- import { buttonResults } from '../resources/vue/stores/buttonResults.js'
- import { rateLimits } from '../resources/vue/stores/rateLimits.js'
- import { connectionState } from '../resources/vue/stores/connectionState.js'
- const RECONNECT_DELAY_MS = 10000
- export function initWebsocket () {
- window.addEventListener('EventOutputChunk', onOutputChunk)
- window.addEventListener('EventExecutionStarted', onExecutionChanged)
- window.addEventListener('EventExecutionFinished', onExecutionChanged)
- reconnectWebsocket()
- }
- window.websocketAvailable = false
- async function reconnectWebsocket () {
- if (window.websocketAvailable) {
- return
- }
- connectionState.reconnecting = true
- connectionState.connected = false
- if (connectionState.disconnectedAt == null) {
- connectionState.disconnectedAt = Date.now()
- }
- connectionState.nextReconnectAt = null
- try {
- window.websocketAvailable = true
- const stream = window.client.eventStream()
- connectionState.connected = true
- connectionState.reconnecting = false
- connectionState.nextReconnectAt = null
- for await (const e of stream) {
- connectionState.disconnectedAt = null
- handleEvent(e)
- }
- } catch (err) {
- console.error('Websocket connection failed: ', err)
- }
- window.websocketAvailable = false
- connectionState.connected = false
- connectionState.disconnectedAt = connectionState.disconnectedAt ?? Date.now()
- connectionState.nextReconnectAt = Date.now() + RECONNECT_DELAY_MS
- console.log('Reconnecting websocket in ' + RECONNECT_DELAY_MS + 'ms...')
- setTimeout(() => {
- reconnectWebsocket()
- }, RECONNECT_DELAY_MS)
- }
- async function refreshInitAfterConfigChange () {
- if (!window.client) {
- return
- }
- try {
- window.initResponse = await window.client.init({})
- if (typeof window.updateHeaderFromInit === 'function') {
- window.updateHeaderFromInit()
- }
- } catch (err) {
- console.error('Failed to refresh config from server after EventConfigChanged:', err)
- }
- }
- async function handleConfigChangedEvent (j) {
- await refreshInitAfterConfigChange()
- window.dispatchEvent(j)
- }
- function handleEvent (msg) {
- const typeName = msg.event.value.$typeName.replace('olivetin.api.v1.', '')
- const j = new Event(typeName)
- j.payload = msg.event.value
- switch (typeName) {
- case 'EventConfigChanged':
- handleConfigChangedEvent(j).catch((err) => {
- console.error('EventConfigChanged handler failed:', err)
- })
- break
- case 'EventOutputChunk':
- case 'EventEntityChanged':
- window.dispatchEvent(j)
- break
- case 'EventExecutionFinished':
- case 'EventExecutionStarted':
- window.dispatchEvent(j)
- break
- default:
- console.warn('Unhandled websocket message type from server: ', typeName)
- window.showBigError('ws-unhandled-message', 'handling websocket message', 'Unhandled websocket message type from server: ' + typeName, true)
- }
- }
- function onOutputChunk (evt) {
- const chunk = evt.payload
- if (window.terminal) {
- if (chunk.executionTrackingId === window.terminal.executionTrackingId) {
- window.terminal.write(chunk.output)
- }
- }
- }
- function onExecutionChanged (evt) {
- buttonResults[evt.payload.logEntry.executionTrackingId] = evt.payload.logEntry
- const logEntry = evt.payload.logEntry
- // Update rate limit store from logEntry if rate limit expiry datetime is provided
- if (logEntry && logEntry.datetimeRateLimitExpires && logEntry.bindingId) {
- // Parse datetime string "2006-01-02 15:04:05" and convert to Unix timestamp
- const date = new Date(logEntry.datetimeRateLimitExpires.replace(' ', 'T') + 'Z')
- rateLimits[logEntry.bindingId] = date.getTime() / 1000
- } else if (logEntry && logEntry.bindingId) {
- // Clear rate limit if not set
- rateLimits[logEntry.bindingId] = 0
- }
- }
|