const context = (() => {
  if (typeof globalThis !== 'undefined') {
    return globalThis
  } else if (typeof self !== 'undefined') {
    return self
  } else if (typeof window !== 'undefined') {
    return window
  } else {
    return Function('return this')()
  }
})()
const defines = __DEFINES__
Object.keys(defines).forEach((key) => {
  const segments = key.split('.')
  let target = context
  for (let i = 0; i < segments.length; i++) {
    const segment = segments[i]
    if (i === segments.length - 1) {
      target[segment] = defines[key]
    } else {
      target = target[segment] || (target[segment] = {})
    }
  }
})

const bgTriggerReload = ['/src/background']

class HMRContext {
  constructor(hmrClient, ownerPath) {
    this.hmrClient = hmrClient
    this.ownerPath = ownerPath
    if (!hmrClient.dataMap.has(ownerPath)) {
      hmrClient.dataMap.set(ownerPath, {})
    }
    const mod = hmrClient.hotModulesMap.get(ownerPath)
    if (mod) {
      mod.callbacks = []
    }
    const staleListeners = hmrClient.ctxToListenersMap.get(ownerPath)
    if (staleListeners) {
      for (const [event, staleFns] of staleListeners) {
        const listeners = hmrClient.customListenersMap.get(event)
        if (listeners) {
          hmrClient.customListenersMap.set(
            event,
            listeners.filter((l) => !staleFns.includes(l)),
          )
        }
      }
    }
    this.newListeners = /* @__PURE__ */ new Map()
    hmrClient.ctxToListenersMap.set(ownerPath, this.newListeners)
  }
  get data() {
    return this.hmrClient.dataMap.get(this.ownerPath)
  }
  accept(deps, callback) {
    if (typeof deps === 'function' || !deps) {
      this.acceptDeps([this.ownerPath], ([mod]) => deps?.(mod))
    } else if (typeof deps === 'string') {
      this.acceptDeps([deps], ([mod]) => callback?.(mod))
    } else if (Array.isArray(deps)) {
      this.acceptDeps(deps, callback)
    } else {
      throw new Error(`invalid hot.accept() usage.`)
    }
  }
  // export names (first arg) are irrelevant on the client side, they're
  // extracted in the server for propagation
  acceptExports(_, callback) {
    this.acceptDeps([this.ownerPath], ([mod]) => callback?.(mod))
  }
  dispose(cb) {
    this.hmrClient.disposeMap.set(this.ownerPath, cb)
  }
  prune(cb) {
    this.hmrClient.pruneMap.set(this.ownerPath, cb)
  }
  // Kept for backward compatibility (#11036)

  decline() {}
  invalidate(message) {
    this.hmrClient.notifyListeners('vite:invalidate', {
      path: this.ownerPath,
      message,
    })
    this.send('vite:invalidate', {
      path: this.ownerPath,
      message,
    })
    this.hmrClient.logger.debug(
      `invalidate ${this.ownerPath}${message ? `: ${message}` : ''}`,
    )
  }
  on(event, cb) {
    const addToMap = (map) => {
      const existing = map.get(event) || []
      existing.push(cb)
      map.set(event, existing)
    }
    addToMap(this.hmrClient.customListenersMap)
    addToMap(this.newListeners)
  }
  off(event, cb) {
    const removeFromMap = (map) => {
      const existing = map.get(event)
      if (existing === void 0) {
        return
      }
      const pruned = existing.filter((l) => l !== cb)
      if (pruned.length === 0) {
        map.delete(event)
        return
      }
      map.set(event, pruned)
    }
    removeFromMap(this.hmrClient.customListenersMap)
    removeFromMap(this.newListeners)
  }
  send(event, data) {
    this.hmrClient.send({
      type: 'custom',
      event,
      data,
    })
  }
  acceptDeps(deps, callback = () => {}) {
    const mod = this.hmrClient.hotModulesMap.get(this.ownerPath) || {
      id: this.ownerPath,
      callbacks: [],
    }
    mod.callbacks.push({
      deps,
      fn: callback,
    })
    this.hmrClient.hotModulesMap.set(this.ownerPath, mod)
  }
}
class HMRClient {
  constructor(logger, transport, importUpdatedModule) {
    this.logger = logger
    this.transport = transport
    this.importUpdatedModule = importUpdatedModule
    this.hotModulesMap = /* @__PURE__ */ new Map()
    this.disposeMap = /* @__PURE__ */ new Map()
    this.pruneMap = /* @__PURE__ */ new Map()
    this.dataMap = /* @__PURE__ */ new Map()
    this.customListenersMap = /* @__PURE__ */ new Map()
    this.ctxToListenersMap = /* @__PURE__ */ new Map()
    this.updateQueue = []
    this.pendingUpdateQueue = false
  }
  async notifyListeners(event, data) {
    const cbs = this.customListenersMap.get(event)
    if (cbs) {
      await Promise.allSettled(cbs.map((cb) => cb(data)))
    }
  }
  send(payload) {
    this.transport.send(payload).catch((err) => {
      this.logger.error(err)
    })
  }
  clear() {
    this.hotModulesMap.clear()
    this.disposeMap.clear()
    this.pruneMap.clear()
    this.dataMap.clear()
    this.customListenersMap.clear()
    this.ctxToListenersMap.clear()
  }
  // After an HMR update, some modules are no longer imported on the page
  // but they may have left behind side effects that need to be cleaned up
  // (e.g. style injections)
  async prunePaths(paths) {
    await Promise.all(
      paths.map((path) => {
        const disposer = this.disposeMap.get(path)
        if (disposer) return disposer(this.dataMap.get(path))
      }),
    )
    paths.forEach((path) => {
      const fn = this.pruneMap.get(path)
      if (fn) {
        fn(this.dataMap.get(path))
      }
    })
  }
  warnFailedUpdate(err, path) {
    if (!err.message.includes('fetch')) {
      this.logger.error(err)
    }
    this.logger.error(
      `Failed to reload ${path}. This could be due to syntax errors or importing non-existent modules. (see errors above)`,
    )
  }
  /**
   * buffer multiple hot updates triggered by the same src change
   * so that they are invoked in the same order they were sent.
   * (otherwise the order may be inconsistent because of the http request round trip)
   */
  async queueUpdate(payload) {
    this.updateQueue.push(this.fetchUpdate(payload))
    if (!this.pendingUpdateQueue) {
      this.pendingUpdateQueue = true
      await Promise.resolve()
      this.pendingUpdateQueue = false
      const loading = [...this.updateQueue]
      this.updateQueue = []
      ;(await Promise.all(loading)).forEach((fn) => fn && fn())
    }
  }
  async fetchUpdate(update) {
    const { path, acceptedPath } = update
    const mod = this.hotModulesMap.get(path)
    if (!mod) {
      return
    }
    let fetchedModule
    const isSelfUpdate = path === acceptedPath
    const qualifiedCallbacks = mod.callbacks.filter(({ deps }) =>
      deps.includes(acceptedPath),
    )
    if (isSelfUpdate || qualifiedCallbacks.length > 0) {
      const disposer = this.disposeMap.get(acceptedPath)
      if (disposer) await disposer(this.dataMap.get(acceptedPath))
      try {
        fetchedModule = await this.importUpdatedModule(update)
      } catch (e) {
        this.warnFailedUpdate(e, acceptedPath)
      }
    }
    return () => {
      for (const { deps, fn } of qualifiedCallbacks) {
        fn(deps.map((dep) => (dep === acceptedPath ? fetchedModule : void 0)))
      }
      const loggedPath = isSelfUpdate ? path : `${acceptedPath} via ${path}`
      this.logger.debug(`hot updated: ${loggedPath}`)
    }
  }
}

/* @ts-self-types="./index.d.ts" */
let urlAlphabet =
  'useandom-26T198340PX75pxJACKVERYMINDBUSHWOLF_GQZbfghjklqvwyzrict'
let nanoid = (size = 21) => {
  let id = ''
  let i = size | 0
  while (i--) {
    id += urlAlphabet[(Math.random() * 64) | 0]
  }
  return id
}
typeof process !== 'undefined' && process.platform === 'win32'
function promiseWithResolvers() {
  let resolve
  let reject
  const promise = new Promise((_resolve, _reject) => {
    resolve = _resolve
    reject = _reject
  })
  return {
    promise,
    resolve,
    reject,
  }
}

function reviveInvokeError(e) {
  const error = new Error(e.message || 'Unknown invoke error')
  Object.assign(error, e, {
    // pass the whole error instead of just the stacktrace
    // so that it gets formatted nicely with console.log
    runnerError: new Error('RunnerError'),
  })
  return error
}
const createInvokeableTransport = (transport) => {
  if (transport.invoke) {
    return {
      ...transport,
      async invoke(name, data) {
        const result = await transport.invoke({
          type: 'custom',
          event: 'vite:invoke',
          data: {
            id: 'send',
            name,
            data,
          },
        })
        if ('error' in result) {
          throw reviveInvokeError(result.error)
        }
        return result.result
      },
    }
  }
  if (!transport.send || !transport.connect) {
    throw new Error(
      'transport must implement send and connect when invoke is not implemented',
    )
  }
  const rpcPromises = /* @__PURE__ */ new Map()
  return {
    ...transport,
    connect({ onMessage, onDisconnection }) {
      return transport.connect({
        onMessage(payload) {
          if (payload.type === 'custom' && payload.event === 'vite:invoke') {
            const data = payload.data
            if (data.id.startsWith('response:')) {
              const invokeId = data.id.slice('response:'.length)
              const promise = rpcPromises.get(invokeId)
              if (!promise) return
              if (promise.timeoutId) clearTimeout(promise.timeoutId)
              rpcPromises.delete(invokeId)
              const { error, result } = data.data
              if (error) {
                promise.reject(error)
              } else {
                promise.resolve(result)
              }
              return
            }
          }
          onMessage(payload)
        },
        onDisconnection,
      })
    },
    disconnect() {
      rpcPromises.forEach((promise) => {
        promise.reject(
          new Error(
            `transport was disconnected, cannot call ${JSON.stringify(promise.name)}`,
          ),
        )
      })
      rpcPromises.clear()
      return transport.disconnect?.()
    },
    send(data) {
      return transport.send(data)
    },
    async invoke(name, data) {
      const promiseId = nanoid()
      const wrappedData = {
        type: 'custom',
        event: 'vite:invoke',
        data: {
          name,
          id: `send:${promiseId}`,
          data,
        },
      }
      const sendPromise = transport.send(wrappedData)
      const { promise, resolve, reject } = promiseWithResolvers()
      const timeout = transport.timeout ?? 6e4
      let timeoutId
      if (timeout > 0) {
        timeoutId = setTimeout(() => {
          rpcPromises.delete(promiseId)
          reject(
            new Error(
              `transport invoke timed out after ${timeout}ms (data: ${JSON.stringify(wrappedData)})`,
            ),
          )
        }, timeout)
        timeoutId?.unref?.()
      }
      rpcPromises.set(promiseId, {
        resolve,
        reject,
        name,
        timeoutId,
      })
      if (sendPromise) {
        sendPromise.catch((err) => {
          clearTimeout(timeoutId)
          rpcPromises.delete(promiseId)
          reject(err)
        })
      }
      try {
        return await promise
      } catch (err) {
        throw reviveInvokeError(err)
      }
    },
  }
}
const normalizeModuleRunnerTransport = (transport) => {
  const invokeableTransport = createInvokeableTransport(transport)
  let isConnected = !invokeableTransport.connect
  let connectingPromise
  return {
    ...transport,
    ...(invokeableTransport.connect
      ? {
          async connect(onMessage) {
            if (isConnected) return
            if (connectingPromise) {
              await connectingPromise
              return
            }
            const maybePromise = invokeableTransport.connect({
              onMessage: onMessage ?? (() => {}),
              onDisconnection() {
                isConnected = false
              },
            })
            if (maybePromise) {
              connectingPromise = maybePromise
              await connectingPromise
              connectingPromise = void 0
            }
            isConnected = true
          },
        }
      : {}),
    ...(invokeableTransport.disconnect
      ? {
          async disconnect() {
            if (!isConnected) return
            if (connectingPromise) {
              await connectingPromise
            }
            isConnected = false
            await invokeableTransport.disconnect()
          },
        }
      : {}),
    async send(data) {
      if (!invokeableTransport.send) return
      if (!isConnected) {
        if (connectingPromise) {
          await connectingPromise
        } else {
          throw new Error('send was called before connect')
        }
      }
      await invokeableTransport.send(data)
    },
    async invoke(name, data) {
      if (!isConnected) {
        if (connectingPromise) {
          await connectingPromise
        } else {
          throw new Error('invoke was called before connect')
        }
      }
      return invokeableTransport.invoke(name, data)
    },
  }
}
const createWebSocketModuleRunnerTransport = (options) => {
  const pingInterval = options.pingInterval ?? 3e4
  let ws
  let pingIntervalId
  return {
    async connect({ onMessage, onDisconnection }) {
      const socket = options.createConnection()
      socket.addEventListener('message', async ({ data }) => {
        onMessage(JSON.parse(data))
      })
      let isOpened = socket.readyState === socket.OPEN
      if (!isOpened) {
        await new Promise((resolve, reject) => {
          socket.addEventListener(
            'open',
            () => {
              isOpened = true
              resolve()
            },
            {
              once: true,
            },
          )
          socket.addEventListener('close', async () => {
            if (!isOpened) {
              reject(new Error('WebSocket closed without opened.'))
              return
            }
            onMessage({
              type: 'custom',
              event: 'vite:ws:disconnect',
              data: {
                webSocket: socket,
              },
            })
            onDisconnection()
          })
        })
      }
      onMessage({
        type: 'custom',
        event: 'vite:ws:connect',
        data: {
          webSocket: socket,
        },
      })
      ws = socket
      pingIntervalId = setInterval(() => {
        if (socket.readyState === socket.OPEN) {
          socket.send(
            JSON.stringify({
              type: 'ping',
            }),
          )
        }
      }, pingInterval)
    },
    disconnect() {
      clearInterval(pingIntervalId)
      ws?.close()
    },
    send(data) {
      ws.send(JSON.stringify(data))
    },
  }
}
const hmrConfigName = 'vite.dev.ts'
const base$1 = '/' || '/'
function h(e, attrs = {}, ...children) {
  const elem = document.createElement(e)
  for (const [k, v] of Object.entries(attrs)) {
    elem.setAttribute(k, v)
  }
  elem.append(...children)
  return elem
}
const templateStyle =
  /*css*/
  `
:host {
  position: fixed;
  top: 0;
  left: 0;
  width: 100%;
  height: 100%;
  z-index: 99999;
  --monospace: 'SFMono-Regular', Consolas,
  'Liberation Mono', Menlo, Courier, monospace;
  --red: #ff5555;
  --yellow: #e2aa53;
  --purple: #cfa4ff;
  --cyan: #2dd9da;
  --dim: #c9c9c9;

  --window-background: #181818;
  --window-color: #d8d8d8;
}

.backdrop {
  position: fixed;
  z-index: 99999;
  top: 0;
  left: 0;
  width: 100%;
  height: 100%;
  overflow-y: scroll;
  margin: 0;
  background: rgba(0, 0, 0, 0.66);
}

.window {
  font-family: var(--monospace);
  line-height: 1.5;
  max-width: 80vw;
  color: var(--window-color);
  box-sizing: border-box;
  margin: 30px auto;
  padding: 2.5vh 4vw;
  position: relative;
  background: var(--window-background);
  border-radius: 6px 6px 8px 8px;
  box-shadow: 0 19px 38px rgba(0,0,0,0.30), 0 15px 12px rgba(0,0,0,0.22);
  overflow: hidden;
  border-top: 8px solid var(--red);
  direction: ltr;
  text-align: left;
}

pre {
  font-family: var(--monospace);
  font-size: 16px;
  margin-top: 0;
  margin-bottom: 1em;
  overflow-x: scroll;
  scrollbar-width: none;
}

pre::-webkit-scrollbar {
  display: none;
}

pre.frame::-webkit-scrollbar {
  display: block;
  height: 5px;
}

pre.frame::-webkit-scrollbar-thumb {
  background: #999;
  border-radius: 5px;
}

pre.frame {
  scrollbar-width: thin;
}

.message {
  line-height: 1.3;
  font-weight: 600;
  white-space: pre-wrap;
}

.message-body {
  color: var(--red);
}

.plugin {
  color: var(--purple);
}

.file {
  color: var(--cyan);
  margin-bottom: 0;
  white-space: pre-wrap;
  word-break: break-all;
}

.frame {
  color: var(--yellow);
}

.stack {
  font-size: 13px;
  color: var(--dim);
}

.tip {
  font-size: 13px;
  color: #999;
  border-top: 1px dotted #999;
  padding-top: 13px;
  line-height: 1.8;
}

code {
  font-size: 13px;
  font-family: var(--monospace);
  color: var(--yellow);
}

.file-link {
  text-decoration: underline;
  cursor: pointer;
}

kbd {
  line-height: 1.5;
  font-family: ui-monospace, Menlo, Monaco, Consolas, "Liberation Mono", "Courier New", monospace;
  font-size: 0.75rem;
  font-weight: 700;
  background-color: rgb(38, 40, 44);
  color: rgb(166, 167, 171);
  padding: 0.15rem 0.3rem;
  border-radius: 0.25rem;
  border-width: 0.0625rem 0.0625rem 0.1875rem;
  border-style: solid;
  border-color: rgb(54, 57, 64);
  border-image: initial;
}
`
const createTemplate = () =>
  h(
    'div',
    {
      class: 'backdrop',
      part: 'backdrop',
    },
    h(
      'div',
      {
        class: 'window',
        part: 'window',
      },
      h(
        'pre',
        {
          class: 'message',
          part: 'message',
        },
        h('span', {
          class: 'plugin',
          part: 'plugin',
        }),
        h('span', {
          class: 'message-body',
          part: 'message-body',
        }),
      ),
      h('pre', {
        class: 'file',
        part: 'file',
      }),
      h('pre', {
        class: 'frame',
        part: 'frame',
      }),
      h('pre', {
        class: 'stack',
        part: 'stack',
      }),
      h(
        'div',
        {
          class: 'tip',
          part: 'tip',
        },
        'Click outside, press ',
        h('kbd', {}, 'Esc'),
        ' key, or fix the code to dismiss.',
        h('br'),
        'You can also disable this overlay by setting ',
        h(
          'code',
          {
            part: 'config-option-name',
          },
          'server.hmr.overlay',
        ),
        ' to ',
        h(
          'code',
          {
            part: 'config-option-value',
          },
          'false',
        ),
        ' in ',
        h(
          'code',
          {
            part: 'config-file-name',
          },
          hmrConfigName,
        ),
        '.',
      ),
    ),
    h('style', {}, templateStyle),
  )
const fileRE = /(?:[a-zA-Z]:\\|\/).*?:\d+:\d+/g
const codeframeRE = /^(?:>?\s*\d+\s+\|.*|\s+\|\s*\^.*)\r?\n/gm
const { HTMLElement = class {} } = globalThis
class ErrorOverlay extends HTMLElement {
  constructor(err, links = true) {
    super()
    this.root = this.attachShadow({
      mode: 'open',
    })
    this.root.appendChild(createTemplate())
    codeframeRE.lastIndex = 0
    const hasFrame = err.frame && codeframeRE.test(err.frame)
    const message = hasFrame
      ? err.message.replace(codeframeRE, '')
      : err.message
    if (err.plugin) {
      this.text('.plugin', `[plugin:${err.plugin}] `)
    }
    this.text('.message-body', message.trim())
    const [file] = (err.loc?.file || err.id || 'unknown file').split(`?`)
    if (err.loc) {
      this.text('.file', `${file}:${err.loc.line}:${err.loc.column}`, links)
    } else if (err.id) {
      this.text('.file', file)
    }
    if (hasFrame) {
      this.text('.frame', err.frame.trim())
    }
    this.text('.stack', err.stack, links)
    this.root.querySelector('.window').addEventListener('click', (e) => {
      e.stopPropagation()
    })
    this.addEventListener('click', () => {
      this.close()
    })
    this.closeOnEsc = (e) => {
      if (e.key === 'Escape' || e.code === 'Escape') {
        this.close()
      }
    }
    document.addEventListener('keydown', this.closeOnEsc)
  }
  text(selector, text, linkFiles = false) {
    const el = this.root.querySelector(selector)
    if (!linkFiles) {
      el.textContent = text
    } else {
      let curIndex = 0
      let match
      fileRE.lastIndex = 0
      while ((match = fileRE.exec(text))) {
        const { 0: file, index } = match
        const frag = text.slice(curIndex, index)
        el.appendChild(document.createTextNode(frag))
        const link = document.createElement('a')
        link.textContent = file
        link.className = 'file-link'
        link.onclick = () => {
          fetch(
            new URL(
              `${base$1}__open-in-editor?file=${encodeURIComponent(file)}`,
              import.meta.url,
            ),
          )
        }
        el.appendChild(link)
        curIndex += frag.length + file.length
      }
    }
  }
  close() {
    this.parentNode?.removeChild(this)
    document.removeEventListener('keydown', this.closeOnEsc)
  }
}
const overlayId = 'vite-error-overlay'
const { customElements } = globalThis
if (customElements && !customElements.get(overlayId)) {
  customElements.define(overlayId, ErrorOverlay)
}

console.debug('[vite] connecting...')
const importMetaUrl = new URL(import.meta.url)
const serverHost = 'localhost:4196/'
const socketProtocol = 'ws'
const hmrPort = null
const socketHost = serverHost
const directSocketHost = 'localhost:4196/'
const base = '/' || '/'
const hmrTimeout = 30000
const wsToken = 'BgXVFGEFg78I'
const transport = normalizeModuleRunnerTransport(
  (() => {
    let wsTransport = createWebSocketModuleRunnerTransport({
      createConnection: () =>
        new WebSocket(
          `${socketProtocol}://${socketHost}?token=${wsToken}`,
          'vite-hmr',
        ),
      pingInterval: hmrTimeout,
    })
    return {
      async connect(handlers) {
        try {
          await wsTransport.connect(handlers)
        } catch (e) {
          if (!hmrPort) {
            wsTransport = createWebSocketModuleRunnerTransport({
              createConnection: () =>
                new WebSocket(
                  `${socketProtocol}://${directSocketHost}?token=${wsToken}`,
                  'vite-hmr',
                ),
              pingInterval: hmrTimeout,
            })
            try {
              await wsTransport.connect(handlers)
              console.info(
                '[vite] Direct websocket connection fallback. Check out https://vite.dev/config/server-options.html#server-hmr to remove the previous connection error.',
              )
            } catch (e2) {
              if (
                e2 instanceof Error &&
                e2.message.includes('WebSocket closed without opened.')
              ) {
                const currentScriptHostURL = new URL(import.meta.url)
                const currentScriptHost =
                  currentScriptHostURL.host +
                  currentScriptHostURL.pathname.replace(/@vite\/client$/, '')
                console.error(`[vite] failed to connect to websocket.
your current setup:
  (browser) ${currentScriptHost} <--[HTTP]--> ${serverHost} (server)
  (browser) ${socketHost} <--[WebSocket (failing)]--> ${directSocketHost} (server)
Check out your Vite / network configuration and https://vite.dev/config/server-options.html#server-hmr .`)
              }
            }
            return
          }
          console.error(`[vite] failed to connect to websocket (${e}). `)
          throw e
        }
      },
      async disconnect() {
        await wsTransport.disconnect()
      },
      send(data) {
        wsTransport.send(data)
      },
    }
  })(),
)
let willUnload = false
if (typeof window !== 'undefined') {
  window.addEventListener('beforeunload', () => {
    willUnload = true
  })
}
function cleanUrl(pathname) {
  const url = new URL(pathname, 'http://vite.dev')
  url.searchParams.delete('direct')
  return url.pathname + url.search
}
let isFirstUpdate = true
const outdatedLinkTags = /* @__PURE__ */ new WeakSet()
const debounceReload = (time) => {
  let timer
  return () => {
    if (timer) {
      clearTimeout(timer)
      timer = null
    }
    timer = setTimeout(() => {
      location.reload()
    }, time)
  }
}
const pageReload = debounceReload(50)
const hmrClient = new HMRClient(
  {
    error: (err) => console.error('[vite]', err),
    debug: (...msg) => console.debug('[vite]', ...msg),
  },
  transport,
  async function importUpdatedModule({
    acceptedPath,
    timestamp,
    explicitImportRequired,
    isWithinCircularImport,
  }) {
    const [acceptedPathWithoutQuery, query] = acceptedPath.split(`?`)
    const importPromise = import(
      /* @vite-ignore */
      base +
        acceptedPathWithoutQuery.slice(1) +
        `?${explicitImportRequired ? 'import&' : ''}t=${timestamp}${query ? `&${query}` : ''}`
    )
    if (isWithinCircularImport) {
      importPromise.catch(() => {
        console.info(
          `[hmr] ${acceptedPath} failed to apply HMR as it's within a circular import. Reloading page to reset the execution order. To debug and break the circular import, you can run \`vite --debug hmr\` to log the circular dependency path if a file change triggered it.`,
        )
        pageReload()
      })
    }
    return await importPromise
  },
)
transport.connect(handleMessage)
async function handleMessage(payload) {
  console.log(`[handleMessage] ${payload.type}`, payload)
  switch (payload.type) {
    case 'connected':
      console.debug(`[vite] connected.`)
      break
    case 'update':
      notifyListeners('vite:beforeUpdate', payload)
      if (hasDocument) {
        if (isFirstUpdate && hasErrorOverlay()) {
          location.reload()
          return
        } else {
          if (enableOverlay) {
            clearErrorOverlay()
          }
          isFirstUpdate = false
        }
      }
      await Promise.all(
        payload.updates.map(async (update) => {
          if (update.type === 'js-update') {
            return hmrClient.queueUpdate(update)
          }
          const { path, timestamp } = update
          const searchUrl = cleanUrl(path)
          const el = Array.from(document.querySelectorAll('link')).find(
            (e) =>
              !outdatedLinkTags.has(e) && cleanUrl(e.href).includes(searchUrl),
          )
          if (!el) {
            return
          }
          const newPath = `${base}${searchUrl.slice(1)}${searchUrl.includes('?') ? '&' : '?'}t=${timestamp}`
          return new Promise((resolve) => {
            const newLinkTag = el.cloneNode()
            newLinkTag.href = new URL(newPath, el.href).href
            const removeOldEl = () => {
              el.remove()
              console.debug(`[vite] css hot updated: ${searchUrl}`)
              resolve()
            }
            newLinkTag.addEventListener('load', removeOldEl)
            newLinkTag.addEventListener('error', removeOldEl)
            outdatedLinkTags.add(el)
            el.after(newLinkTag)
          })
        }),
      )
      notifyListeners('vite:afterUpdate', payload)
      break
    case 'custom': {
      notifyListeners(payload.event, payload.data)
      if (payload.event === 'vite:ws:disconnect') {
        if (hasDocument && !willUnload) {
          console.log(`[vite] server connection lost. Polling for restart...`)
          const socket = payload.data.webSocket
          const url = new URL(socket.url)
          url.search = ''
          await waitForSuccessfulPing(url.href)
          //   location.reload()
        }
      }
      break
    }
    case 'full-reload':
      notifyListeners('vite:beforeFullReload', payload)
      console.log('full reload')
      const nPath = normalizePath(payload.triggeredBy)
      const reloadExt = bgTriggerReload.find((t) => nPath.includes(t))

      if (reloadExt) {
        console.log('reloadExt')
        window.dispatchEvent(new Event('dm-ext:reload'))
        return
      }

      if (hasDocument) {
        if (payload.path && payload.path.endsWith('.html')) {
          const pagePath = decodeURI(location.pathname)
          const payloadPath = base + payload.path.slice(1)
          if (
            pagePath === payloadPath ||
            payload.path === '/index.html' ||
            (pagePath.endsWith('/') && pagePath + 'index.html' === payloadPath)
          ) {
            pageReload()
          }
          return
        } else {
          pageReload()
        }
      }
      break
    case 'prune':
      notifyListeners('vite:beforePrune', payload)
      await hmrClient.prunePaths(payload.paths)
      break
    case 'error': {
      notifyListeners('vite:error', payload)
      if (hasDocument) {
        const err = payload.err
        if (enableOverlay) {
          createErrorOverlay(err)
        } else {
          console.error(`[vite] Internal Server Error
${err.message}
${err.stack}`)
        }
      }
      break
    }
    case 'ping':
      break
    default: {
      const check = payload
      return check
    }
  }
}
function notifyListeners(event, data) {
  hmrClient.notifyListeners(event, data)
}
const enableOverlay = true
const hasDocument = 'document' in globalThis
function createErrorOverlay(err) {
  clearErrorOverlay()
  const { customElements } = globalThis
  if (customElements) {
    const ErrorOverlayConstructor = customElements.get(overlayId)
    document.body.appendChild(new ErrorOverlayConstructor(err))
  }
}
function clearErrorOverlay() {
  document.querySelectorAll(overlayId).forEach((n) => n.close())
}
function hasErrorOverlay() {
  return document.querySelectorAll(overlayId).length
}
async function waitForSuccessfulPing(socketUrl, ms = 1e3) {
  async function ping() {
    const socket = new WebSocket(socketUrl, 'vite-ping')
    return new Promise((resolve) => {
      function onOpen() {
        resolve(true)
        close()
      }
      function onError() {
        resolve(false)
        close()
      }
      function close() {
        socket.removeEventListener('open', onOpen)
        socket.removeEventListener('error', onError)
        socket.close()
      }
      socket.addEventListener('open', onOpen)
      socket.addEventListener('error', onError)
    })
  }
  if (await ping()) {
    return
  }
  await wait(ms)
  while (true) {
    if (document.visibilityState === 'visible') {
      if (await ping()) {
        break
      }
      await wait(ms)
    } else {
      await waitForWindowShow()
    }
  }
}
function wait(ms) {
  return new Promise((resolve) => setTimeout(resolve, ms))
}
function waitForWindowShow() {
  return new Promise((resolve) => {
    const onChange = async () => {
      if (document.visibilityState === 'visible') {
        resolve()
        document.removeEventListener('visibilitychange', onChange)
      }
    }
    document.addEventListener('visibilitychange', onChange)
  })
}
const sheetsMap = /* @__PURE__ */ new Map()
if ('document' in globalThis) {
  document.querySelectorAll('style[data-vite-dev-id]').forEach((el) => {
    sheetsMap.set(el.getAttribute('data-vite-dev-id'), el)
  })
}
const cspNonce =
  'document' in globalThis
    ? document.querySelector('meta[property=csp-nonce]')?.nonce
    : void 0
let lastInsertedStyle
function updateStyle(id, content) {
  let style = sheetsMap.get(id)
  if (!style) {
    style = document.createElement('style')
    style.setAttribute('type', 'text/css')
    style.setAttribute('data-vite-dev-id', id)
    style.textContent = content
    if (cspNonce) {
      style.setAttribute('nonce', cspNonce)
    }
    if (!lastInsertedStyle) {
      document.head.appendChild(style)
      setTimeout(() => {
        lastInsertedStyle = void 0
      }, 0)
    } else {
      lastInsertedStyle.insertAdjacentElement('afterend', style)
    }
    lastInsertedStyle = style
  } else {
    style.textContent = content
  }
  sheetsMap.set(id, style)
}
function removeStyle(id) {
  const style = sheetsMap.get(id)
  if (style) {
    document.head.removeChild(style)
    sheetsMap.delete(id)
  }
}
function createHotContext(ownerPath) {
  return new HMRContext(hmrClient, ownerPath)
}
function injectQuery(url, queryToInject) {
  if (url[0] !== '.' && url[0] !== '/') {
    return url
  }
  const pathname = url.replace(/[?#].*$/, '')
  const { search, hash } = new URL(url, 'http://vite.dev')
  return `${pathname}?${queryToInject}${search ? `&` + search.slice(1) : ''}${hash || ''}`
}

function normalizePath(path) {
  return path.replace(/\\/g, '/')
}

export { ErrorOverlay, createHotContext, injectQuery, removeStyle, updateStyle }
