Compare commits
3 Commits
04ab968e0f
...
06b73f90eb
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
06b73f90eb | ||
|
|
6bc692c558 | ||
|
|
38e081f2cf |
|
|
@ -5,7 +5,7 @@ import { join } from "path"
|
||||||
import { readdirSync, type Dirent } from "fs"
|
import { readdirSync, type Dirent } from "fs"
|
||||||
import { sessionGet } from "./session"
|
import { sessionGet } from "./session"
|
||||||
import { DEFAULT_PROJECT, NOSE_DIR } from "./config"
|
import { DEFAULT_PROJECT, NOSE_DIR } from "./config"
|
||||||
import { isDir } from "./utils"
|
import { isDir, isFile } from "./utils"
|
||||||
|
|
||||||
export function projectName(): string {
|
export function projectName(): string {
|
||||||
const state = sessionGet()
|
const state = sessionGet()
|
||||||
|
|
@ -16,7 +16,7 @@ export function projectName(): string {
|
||||||
|
|
||||||
export function projects(): string[] {
|
export function projects(): string[] {
|
||||||
return readdirSync(NOSE_DIR, { withFileTypes: true })
|
return readdirSync(NOSE_DIR, { withFileTypes: true })
|
||||||
.filter(file => file.isDirectory())
|
.filter(dir => dir.isDirectory() && isProject(join(NOSE_DIR, dir.name)))
|
||||||
.map(dir => dir.name)
|
.map(dir => dir.name)
|
||||||
.sort()
|
.sort()
|
||||||
}
|
}
|
||||||
|
|
@ -34,4 +34,8 @@ export function projectBin(name = projectName()): string {
|
||||||
|
|
||||||
export function projectFiles(name = projectName()): Dirent[] {
|
export function projectFiles(name = projectName()): Dirent[] {
|
||||||
return readdirSync(projectDir(name), { recursive: true, withFileTypes: true })
|
return readdirSync(projectDir(name), { recursive: true, withFileTypes: true })
|
||||||
|
}
|
||||||
|
|
||||||
|
function isProject(path: string): boolean {
|
||||||
|
return join(NOSE_DIR, "root") === path || isFile(join(path, "index.ts")) || isFile(join(path, "index.tsx")) || isDir(join(path, "pub"))
|
||||||
}
|
}
|
||||||
|
|
@ -14,7 +14,13 @@ import { apps, isApp, appDir, isStaticApp, webappLog } from "./utils"
|
||||||
export type Handler = (r: Context) => string | Child | Response | Promise<Response>
|
export type Handler = (r: Context) => string | Child | Response | Promise<Response>
|
||||||
export type App = Hono | Handler
|
export type App = Hono | Handler
|
||||||
|
|
||||||
const processes = new Map<string, { port: string, proc: ReturnType<typeof Bun.spawn> }>()
|
type ProcInfo = {
|
||||||
|
port: string,
|
||||||
|
proc: ReturnType<typeof Bun.spawn>,
|
||||||
|
killed?: boolean
|
||||||
|
}
|
||||||
|
|
||||||
|
const processes = new Map<string, ProcInfo>()
|
||||||
const restarting = new Set<string>()
|
const restarting = new Set<string>()
|
||||||
const STARTING_PORT = 10000
|
const STARTING_PORT = 10000
|
||||||
let nextPort = STARTING_PORT
|
let nextPort = STARTING_PORT
|
||||||
|
|
@ -67,8 +73,9 @@ async function startApp(name: string): Promise<string | undefined> {
|
||||||
stderr: "inherit",
|
stderr: "inherit",
|
||||||
})
|
})
|
||||||
|
|
||||||
processes.set(name, { port, proc })
|
const info: ProcInfo = { port, proc }
|
||||||
proc.exited.then(() => restartApp(name))
|
processes.set(name, info)
|
||||||
|
proc.exited.then(code => !info.killed && code !== 0 ? restartApp(name) : {})
|
||||||
|
|
||||||
await Bun.sleep(100) // give it time before first request
|
await Bun.sleep(100) // give it time before first request
|
||||||
|
|
||||||
|
|
@ -89,13 +96,15 @@ export async function shutdownWebapps() {
|
||||||
wwwWatcher?.close()
|
wwwWatcher?.close()
|
||||||
nextPort = STARTING_PORT
|
nextPort = STARTING_PORT
|
||||||
|
|
||||||
for (const [name, { port, proc }] of processes) {
|
for (const [name, proc] of processes) {
|
||||||
webappLog(name, "Shutting down")
|
webappLog(name, "Shutting down")
|
||||||
try { proc.kill() } catch { }
|
try {
|
||||||
|
proc.killed = true
|
||||||
|
proc.proc.kill()
|
||||||
|
} catch { }
|
||||||
}
|
}
|
||||||
|
|
||||||
processes.clear()
|
processes.clear()
|
||||||
process.exit(0)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
async function restartApp(name: string) {
|
async function restartApp(name: string) {
|
||||||
|
|
@ -107,7 +116,10 @@ async function restartApp(name: string) {
|
||||||
webappLog(name, "restarting")
|
webappLog(name, "restarting")
|
||||||
const existing = processes.get(name)
|
const existing = processes.get(name)
|
||||||
if (existing) {
|
if (existing) {
|
||||||
try { existing.proc.kill() } catch { }
|
try {
|
||||||
|
existing.killed = true
|
||||||
|
existing.proc.kill()
|
||||||
|
} catch { }
|
||||||
processes.delete(name)
|
processes.delete(name)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -121,7 +133,6 @@ async function startSubprocs() {
|
||||||
await Promise.all(list.map(app => startApp(app)))
|
await Promise.all(list.map(app => startApp(app)))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
let wwwWatcher: any
|
let wwwWatcher: any
|
||||||
function startWatcher() {
|
function startWatcher() {
|
||||||
if (!expectDir(NOSE_DIR)) return
|
if (!expectDir(NOSE_DIR)) return
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue
Block a user