Sync modal state with page state
This commit is contained in:
parent
24a506ea85
commit
ac7108c2c4
2 changed files with 44 additions and 0 deletions
|
|
@ -1,4 +1,5 @@
|
|||
import {execFile} from "node:child_process"
|
||||
import {createConnection} from "node:net"
|
||||
import {chmod, cp, readdir, rm} from "node:fs/promises"
|
||||
import {tmpdir} from "node:os"
|
||||
import {join} from "node:path"
|
||||
|
|
@ -39,6 +40,32 @@ const execFileAsync = promisify(execFile)
|
|||
// typed. Name the executable to drive with E2E_DOCKER in that case.
|
||||
const dockerCommand = process.env.E2E_DOCKER ?? "docker"
|
||||
|
||||
// The loopback port the container publishes and transport.ts dials. It is fixed rather than
|
||||
// configurable on purpose: the harness talks to whatever answers here, so a copy of the suite left
|
||||
// running by anyone else on the machine — under another user, even — would be seeded, queried and
|
||||
// reset out from under this run. Both places have to agree, so this must match the published port
|
||||
// in docker/compose.yaml and `port` in transport.ts.
|
||||
const relayHostPort = 3334
|
||||
|
||||
// Whether something already answers on the relay's loopback port. Used as a pre-flight: the port is
|
||||
// the harness's alone for the length of a run, so anything holding it before this run brings its own
|
||||
// container up is a foreign occupant we must refuse rather than quietly share.
|
||||
const isRelayPortTaken = () =>
|
||||
new Promise<boolean>(resolve => {
|
||||
const socket = createConnection({port: relayHostPort, host: "127.0.0.1"})
|
||||
|
||||
socket.setTimeout(1000)
|
||||
socket.once("connect", () => {
|
||||
socket.destroy()
|
||||
resolve(true)
|
||||
})
|
||||
socket.once("timeout", () => {
|
||||
socket.destroy()
|
||||
resolve(false)
|
||||
})
|
||||
socket.once("error", () => resolve(false))
|
||||
})
|
||||
|
||||
// Every invocation carries ZOOID_CONFIG, `down` included: the compose file names it without a
|
||||
// default, so a call that left it out would fail to interpolate rather than quietly mounting
|
||||
// something else.
|
||||
|
|
@ -177,6 +204,20 @@ export class Zooid {
|
|||
)
|
||||
}
|
||||
|
||||
// Nothing should answer on the relay port yet: this run has not brought its container up. If
|
||||
// something does, it is a leftover container from an aborted run or another copy of the suite —
|
||||
// and because the harness dials this fixed port, sharing it silently corrupts both runs. Refuse
|
||||
// loudly instead. `compose down` clears a leftover of this project's own.
|
||||
if (await isRelayPortTaken()) {
|
||||
throw new Error(
|
||||
`127.0.0.1:${relayHostPort} is already in use, but the zooid relay container publishes ` +
|
||||
"exactly that port and the harness talks to whatever answers there. This is a leftover " +
|
||||
"container from an interrupted run, or another copy of this suite running on the machine " +
|
||||
`(under any user). Free it before running — \`${dockerCommand} compose -f ` +
|
||||
"e2e/harness/zooid/docker/compose.yaml down\` clears one this project started.",
|
||||
)
|
||||
}
|
||||
|
||||
this.started = true
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -38,6 +38,9 @@ const modalHash = writable(typeof location === "undefined" ? "" : location.hash)
|
|||
|
||||
if (typeof window !== "undefined") {
|
||||
window.addEventListener("popstate", () => modalHash.set(location.hash))
|
||||
|
||||
// Close modals on navigate
|
||||
page.subscribe($page => modalHash.set($page.url?.hash ?? ""))
|
||||
}
|
||||
|
||||
const setModalHash = (hash: string, replace: boolean) => {
|
||||
|
|
|
|||
Loading…
Reference in a new issue