Skip to content

Commit 3eb57f3

Browse files
committed
fix: revert refresh
1 parent 50164fe commit 3eb57f3

2 files changed

Lines changed: 116 additions & 118 deletions

File tree

docker/runner-default/Dockerfile

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9,8 +9,6 @@ USER beet-bot
99
# Do not copy uv.lock to let environment rebuilds upgrade to new versions
1010
COPY pyproject.toml ./
1111
COPY src ./src
12-
13-
ARG REFRESH=0
1412
RUN uv sync
1513

1614
RUN echo '{"pipeline": ["runner_default.bootstrap_environment"]}' \

packages/runner/src/docker.ts

Lines changed: 116 additions & 116 deletions
Original file line numberDiff line numberDiff line change
@@ -1,116 +1,116 @@
1-
import { execa } from 'execa'
2-
3-
type DockerImage = {
4-
tag: string
5-
status: 'toBuild' | 'buildingImage' | 'ready' | 'broken' | 'deletingImage'
6-
promise: Promise<void>
7-
}
8-
9-
const imageRegistry: Map<string, DockerImage> = new Map()
10-
const getDockerImage = (path: string) => {
11-
let image = imageRegistry.get(path)
12-
if (!image) {
13-
image = {
14-
tag: `beet-bot-env${imageRegistry.size}`,
15-
status: 'toBuild',
16-
promise: Promise.resolve()
17-
}
18-
imageRegistry.set(path, image)
19-
}
20-
return image
21-
}
22-
23-
const runDockerBuild = async (image: DockerImage, path: string) => {
24-
try {
25-
console.log(`INFO: Start building image "${image.tag}"`)
26-
await execa('docker', ['build', path, '--build-arg', `REFRESH=${Date.now()}`, '--tag', image.tag], { stdio: 'inherit' })
27-
console.log(`INFO: Done building image "${image.tag}"`)
28-
image.status = 'ready'
29-
} catch {
30-
console.log(`WARN: Error building image "${image.tag}"`)
31-
image.status = 'broken'
32-
}
33-
}
34-
35-
const runDockerRmi = async (image: DockerImage) => {
36-
try {
37-
console.log(`INFO: Deleting image "${image.tag}"`)
38-
await execa('docker', ['rmi', '--force', image.tag], { stdio: 'inherit' })
39-
console.log(`INFO: Deleted image "${image.tag}"`)
40-
image.status = 'toBuild'
41-
} catch {
42-
console.log(`WARN: Error deleting image "${image.tag}"`)
43-
image.status = 'ready'
44-
}
45-
}
46-
47-
const buildDockerImage = async (path: string): Promise<DockerImage> => {
48-
const image = getDockerImage(path)
49-
50-
switch (image.status) {
51-
case 'deletingImage':
52-
await image.promise
53-
return await buildDockerImage(path)
54-
case 'toBuild':
55-
case 'broken':
56-
image.status = 'buildingImage'
57-
image.promise = runDockerBuild(image, path)
58-
break
59-
}
60-
61-
await image.promise
62-
return image
63-
}
64-
65-
const deleteDockerImage = async (path: string): Promise<DockerImage> => {
66-
const image = getDockerImage(path)
67-
68-
switch (image.status) {
69-
case 'buildingImage':
70-
await image.promise
71-
return await deleteDockerImage(path)
72-
case 'ready':
73-
image.status = 'deletingImage'
74-
image.promise = runDockerRmi(image)
75-
break
76-
}
77-
78-
await image.promise
79-
return image
80-
}
81-
82-
export const setupDockerBuilder = async (
83-
name: string,
84-
path: string,
85-
isolated: boolean,
86-
overrides: string[] = []
87-
) => {
88-
const image = await buildDockerImage(path)
89-
90-
if (image.status === 'broken') {
91-
return () => Promise.reject(new Error(`Environment "${name}" is broken`))
92-
}
93-
94-
return (id: number) => {
95-
const container = `${image.tag}-${name}-${id}`
96-
97-
const handle = execa('docker', [
98-
'run', '--name', container, ...(isolated ? ['--network', 'none'] : []), '--rm', '-i', image.tag,
99-
'beet', '-p', '@beet/preset_stdin.yml', ...overrides.flatMap(override => ['-s', override]), 'build', '--json'
100-
])
101-
102-
const stop = async () => {
103-
try {
104-
await execa('docker', ['rm', '-f', container], { stdio: 'inherit' })
105-
} catch {
106-
console.log(`WARN: Stopping build #${handle.pid} failed`)
107-
}
108-
}
109-
110-
return Promise.resolve({ handle, stop })
111-
}
112-
}
113-
114-
export const deleteDockerBuilder = async (path: string) => {
115-
await deleteDockerImage(path)
116-
}
1+
import { execa } from 'execa'
2+
3+
type DockerImage = {
4+
tag: string
5+
status: 'toBuild' | 'buildingImage' | 'ready' | 'broken' | 'deletingImage'
6+
promise: Promise<void>
7+
}
8+
9+
const imageRegistry: Map<string, DockerImage> = new Map()
10+
const getDockerImage = (path: string) => {
11+
let image = imageRegistry.get(path)
12+
if (!image) {
13+
image = {
14+
tag: `beet-bot-env${imageRegistry.size}`,
15+
status: 'toBuild',
16+
promise: Promise.resolve()
17+
}
18+
imageRegistry.set(path, image)
19+
}
20+
return image
21+
}
22+
23+
const runDockerBuild = async (image: DockerImage, path: string) => {
24+
try {
25+
console.log(`INFO: Start building image "${image.tag}"`)
26+
await execa('docker', ['build', path, '--tag', image.tag], { stdio: 'inherit' })
27+
console.log(`INFO: Done building image "${image.tag}"`)
28+
image.status = 'ready'
29+
} catch {
30+
console.log(`WARN: Error building image "${image.tag}"`)
31+
image.status = 'broken'
32+
}
33+
}
34+
35+
const runDockerRmi = async (image: DockerImage) => {
36+
try {
37+
console.log(`INFO: Deleting image "${image.tag}"`)
38+
await execa('docker', ['rmi', '--force', image.tag], { stdio: 'inherit' })
39+
console.log(`INFO: Deleted image "${image.tag}"`)
40+
image.status = 'toBuild'
41+
} catch {
42+
console.log(`WARN: Error deleting image "${image.tag}"`)
43+
image.status = 'ready'
44+
}
45+
}
46+
47+
const buildDockerImage = async (path: string): Promise<DockerImage> => {
48+
const image = getDockerImage(path)
49+
50+
switch (image.status) {
51+
case 'deletingImage':
52+
await image.promise
53+
return await buildDockerImage(path)
54+
case 'toBuild':
55+
case 'broken':
56+
image.status = 'buildingImage'
57+
image.promise = runDockerBuild(image, path)
58+
break
59+
}
60+
61+
await image.promise
62+
return image
63+
}
64+
65+
const deleteDockerImage = async (path: string): Promise<DockerImage> => {
66+
const image = getDockerImage(path)
67+
68+
switch (image.status) {
69+
case 'buildingImage':
70+
await image.promise
71+
return await deleteDockerImage(path)
72+
case 'ready':
73+
image.status = 'deletingImage'
74+
image.promise = runDockerRmi(image)
75+
break
76+
}
77+
78+
await image.promise
79+
return image
80+
}
81+
82+
export const setupDockerBuilder = async (
83+
name: string,
84+
path: string,
85+
isolated: boolean,
86+
overrides: string[] = []
87+
) => {
88+
const image = await buildDockerImage(path)
89+
90+
if (image.status === 'broken') {
91+
return () => Promise.reject(new Error(`Environment "${name}" is broken`))
92+
}
93+
94+
return (id: number) => {
95+
const container = `${image.tag}-${name}-${id}`
96+
97+
const handle = execa('docker', [
98+
'run', '--name', container, ...(isolated ? ['--network', 'none'] : []), '--rm', '-i', image.tag,
99+
'beet', '-p', '@beet/preset_stdin.yml', ...overrides.flatMap(override => ['-s', override]), 'build', '--json'
100+
])
101+
102+
const stop = async () => {
103+
try {
104+
await execa('docker', ['rm', '-f', container], { stdio: 'inherit' })
105+
} catch {
106+
console.log(`WARN: Stopping build #${handle.pid} failed`)
107+
}
108+
}
109+
110+
return Promise.resolve({ handle, stop })
111+
}
112+
}
113+
114+
export const deleteDockerBuilder = async (path: string) => {
115+
await deleteDockerImage(path)
116+
}

0 commit comments

Comments
 (0)