@opencode-cloud/core 0.1.2 → 1.0.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/Cargo.toml +13 -0
- package/README.md +172 -0
- package/core.darwin-arm64.node +0 -0
- package/package.json +1 -1
- package/src/config/schema.rs +62 -8
- package/src/docker/Dockerfile +444 -0
- package/src/docker/client.rs +84 -0
- package/src/docker/container.rs +317 -0
- package/src/docker/dockerfile.rs +41 -0
- package/src/docker/error.rs +79 -0
- package/src/docker/image.rs +502 -0
- package/src/docker/mod.rs +112 -0
- package/src/docker/progress.rs +401 -0
- package/src/docker/volume.rs +144 -0
- package/src/lib.rs +14 -0
- package/src/platform/launchd.rs +363 -0
- package/src/platform/mod.rs +191 -0
- package/src/platform/systemd.rs +346 -0
|
@@ -0,0 +1,444 @@
|
|
|
1
|
+
# =============================================================================
|
|
2
|
+
# opencode-cloud Container Image
|
|
3
|
+
# =============================================================================
|
|
4
|
+
# A comprehensive development environment for AI-assisted coding with opencode.
|
|
5
|
+
#
|
|
6
|
+
# Features:
|
|
7
|
+
# - Ubuntu 24.04 LTS (noble) base
|
|
8
|
+
# - Non-root user with passwordless sudo
|
|
9
|
+
# - Multiple languages via mise (Node.js, Python, Rust, Go)
|
|
10
|
+
# - Modern CLI tools (ripgrep, eza, fzf, lazygit, etc.)
|
|
11
|
+
# - GSD opencode plugin for task management
|
|
12
|
+
#
|
|
13
|
+
# Usage:
|
|
14
|
+
# docker build -t opencode-cloud .
|
|
15
|
+
# docker run -it opencode-cloud
|
|
16
|
+
#
|
|
17
|
+
# =============================================================================
|
|
18
|
+
|
|
19
|
+
# -----------------------------------------------------------------------------
|
|
20
|
+
# Stage 1: Builder
|
|
21
|
+
# -----------------------------------------------------------------------------
|
|
22
|
+
# Install build dependencies and tools that require compilation
|
|
23
|
+
FROM ubuntu:24.04 AS builder
|
|
24
|
+
|
|
25
|
+
# Avoid interactive prompts during package installation
|
|
26
|
+
ENV DEBIAN_FRONTEND=noninteractive
|
|
27
|
+
ENV TZ=UTC
|
|
28
|
+
|
|
29
|
+
# Install build essentials
|
|
30
|
+
RUN apt-get update && apt-get install -y --no-install-recommends \
|
|
31
|
+
build-essential \
|
|
32
|
+
ca-certificates \
|
|
33
|
+
curl \
|
|
34
|
+
git \
|
|
35
|
+
&& rm -rf /var/lib/apt/lists/*
|
|
36
|
+
|
|
37
|
+
# -----------------------------------------------------------------------------
|
|
38
|
+
# Stage 2: Runtime
|
|
39
|
+
# -----------------------------------------------------------------------------
|
|
40
|
+
FROM ubuntu:24.04 AS runtime
|
|
41
|
+
|
|
42
|
+
# OCI Labels for image metadata
|
|
43
|
+
LABEL org.opencontainers.image.title="opencode-cloud"
|
|
44
|
+
LABEL org.opencontainers.image.description="AI-assisted development environment with opencode"
|
|
45
|
+
LABEL org.opencontainers.image.url="https://github.com/pRizz/opencode-cloud"
|
|
46
|
+
LABEL org.opencontainers.image.source="https://github.com/pRizz/opencode-cloud"
|
|
47
|
+
LABEL org.opencontainers.image.vendor="pRizz"
|
|
48
|
+
LABEL org.opencontainers.image.licenses="MIT"
|
|
49
|
+
LABEL org.opencontainers.image.base.name="ubuntu:24.04"
|
|
50
|
+
|
|
51
|
+
# Environment configuration
|
|
52
|
+
ENV DEBIAN_FRONTEND=noninteractive
|
|
53
|
+
ENV TZ=UTC
|
|
54
|
+
ENV LANG=C.UTF-8
|
|
55
|
+
ENV LC_ALL=C.UTF-8
|
|
56
|
+
|
|
57
|
+
# -----------------------------------------------------------------------------
|
|
58
|
+
# System Dependencies
|
|
59
|
+
# -----------------------------------------------------------------------------
|
|
60
|
+
# Install core system packages in logical groups for better caching
|
|
61
|
+
|
|
62
|
+
# Group 1: Core utilities and build tools
|
|
63
|
+
RUN apt-get update && apt-get install -y --no-install-recommends \
|
|
64
|
+
# Signal handling
|
|
65
|
+
tini \
|
|
66
|
+
dumb-init \
|
|
67
|
+
# Shell and terminal
|
|
68
|
+
zsh \
|
|
69
|
+
tmux \
|
|
70
|
+
# Editors
|
|
71
|
+
vim \
|
|
72
|
+
neovim \
|
|
73
|
+
nano \
|
|
74
|
+
# Build essentials
|
|
75
|
+
build-essential \
|
|
76
|
+
pkg-config \
|
|
77
|
+
cmake \
|
|
78
|
+
# Version control
|
|
79
|
+
git \
|
|
80
|
+
git-lfs \
|
|
81
|
+
# Core utilities
|
|
82
|
+
curl \
|
|
83
|
+
wget \
|
|
84
|
+
ca-certificates \
|
|
85
|
+
gnupg \
|
|
86
|
+
lsb-release \
|
|
87
|
+
software-properties-common \
|
|
88
|
+
sudo \
|
|
89
|
+
openssh-client \
|
|
90
|
+
# Process/system tools
|
|
91
|
+
htop \
|
|
92
|
+
procps \
|
|
93
|
+
less \
|
|
94
|
+
file \
|
|
95
|
+
tree \
|
|
96
|
+
# JSON/YAML processing
|
|
97
|
+
jq \
|
|
98
|
+
# Network tools
|
|
99
|
+
netcat-openbsd \
|
|
100
|
+
iputils-ping \
|
|
101
|
+
dnsutils \
|
|
102
|
+
# Compression
|
|
103
|
+
zip \
|
|
104
|
+
unzip \
|
|
105
|
+
xz-utils \
|
|
106
|
+
p7zip-full \
|
|
107
|
+
&& rm -rf /var/lib/apt/lists/*
|
|
108
|
+
|
|
109
|
+
# Group 2: Database clients
|
|
110
|
+
RUN apt-get update && apt-get install -y --no-install-recommends \
|
|
111
|
+
sqlite3 \
|
|
112
|
+
postgresql-client \
|
|
113
|
+
default-mysql-client \
|
|
114
|
+
&& rm -rf /var/lib/apt/lists/*
|
|
115
|
+
|
|
116
|
+
# Group 3: Development libraries (for compiling tools)
|
|
117
|
+
RUN apt-get update && apt-get install -y --no-install-recommends \
|
|
118
|
+
libssl-dev \
|
|
119
|
+
libffi-dev \
|
|
120
|
+
zlib1g-dev \
|
|
121
|
+
libbz2-dev \
|
|
122
|
+
libreadline-dev \
|
|
123
|
+
libsqlite3-dev \
|
|
124
|
+
libncurses-dev \
|
|
125
|
+
liblzma-dev \
|
|
126
|
+
&& rm -rf /var/lib/apt/lists/*
|
|
127
|
+
|
|
128
|
+
# -----------------------------------------------------------------------------
|
|
129
|
+
# Create Non-Root User
|
|
130
|
+
# -----------------------------------------------------------------------------
|
|
131
|
+
# Create 'opencode' user with passwordless sudo
|
|
132
|
+
RUN useradd -m -s /bin/zsh -G sudo opencode \
|
|
133
|
+
&& echo "opencode ALL=(ALL) NOPASSWD:ALL" > /etc/sudoers.d/opencode \
|
|
134
|
+
&& chmod 0440 /etc/sudoers.d/opencode
|
|
135
|
+
|
|
136
|
+
# Switch to opencode user for remaining setup
|
|
137
|
+
USER opencode
|
|
138
|
+
WORKDIR /home/opencode
|
|
139
|
+
|
|
140
|
+
# Set up directories
|
|
141
|
+
RUN mkdir -p \
|
|
142
|
+
/home/opencode/.config \
|
|
143
|
+
/home/opencode/.local/bin \
|
|
144
|
+
/home/opencode/.local/share \
|
|
145
|
+
/home/opencode/.cache \
|
|
146
|
+
/home/opencode/workspace
|
|
147
|
+
|
|
148
|
+
# Add local bin to PATH
|
|
149
|
+
ENV PATH="/home/opencode/.local/bin:${PATH}"
|
|
150
|
+
|
|
151
|
+
# -----------------------------------------------------------------------------
|
|
152
|
+
# Shell Setup: Zsh + Oh My Zsh + Starship
|
|
153
|
+
# -----------------------------------------------------------------------------
|
|
154
|
+
# Install Oh My Zsh
|
|
155
|
+
RUN sh -c "$(curl -fsSL https://raw.githubusercontent.com/ohmyzsh/ohmyzsh/master/tools/install.sh)" "" --unattended
|
|
156
|
+
|
|
157
|
+
# Install Starship prompt
|
|
158
|
+
RUN curl -sS https://starship.rs/install.sh | sh -s -- --yes --bin-dir /home/opencode/.local/bin
|
|
159
|
+
|
|
160
|
+
# Configure zsh with starship
|
|
161
|
+
RUN echo 'eval "$(starship init zsh)"' >> /home/opencode/.zshrc \
|
|
162
|
+
&& echo 'export PATH="/home/opencode/.local/bin:$PATH"' >> /home/opencode/.zshrc
|
|
163
|
+
|
|
164
|
+
# -----------------------------------------------------------------------------
|
|
165
|
+
# mise: Universal Version Manager
|
|
166
|
+
# -----------------------------------------------------------------------------
|
|
167
|
+
# Install mise for managing Node.js, Python, Rust, Go
|
|
168
|
+
RUN curl https://mise.run | sh \
|
|
169
|
+
&& echo 'eval "$(/home/opencode/.local/bin/mise activate zsh)"' >> /home/opencode/.zshrc
|
|
170
|
+
|
|
171
|
+
# Install language runtimes via mise
|
|
172
|
+
# Using specific LTS/stable versions for reproducibility
|
|
173
|
+
RUN /home/opencode/.local/bin/mise install node@lts \
|
|
174
|
+
&& /home/opencode/.local/bin/mise install python@3.12 \
|
|
175
|
+
&& /home/opencode/.local/bin/mise install go@latest \
|
|
176
|
+
&& /home/opencode/.local/bin/mise use --global node@lts \
|
|
177
|
+
&& /home/opencode/.local/bin/mise use --global python@3.12 \
|
|
178
|
+
&& /home/opencode/.local/bin/mise use --global go@latest
|
|
179
|
+
|
|
180
|
+
# Set up mise shims in PATH for non-interactive shells
|
|
181
|
+
ENV PATH="/home/opencode/.local/share/mise/shims:${PATH}"
|
|
182
|
+
|
|
183
|
+
# -----------------------------------------------------------------------------
|
|
184
|
+
# Rust Installation
|
|
185
|
+
# -----------------------------------------------------------------------------
|
|
186
|
+
# Install Rust via rustup (mise rust support is experimental)
|
|
187
|
+
RUN curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh -s -- -y --default-toolchain stable \
|
|
188
|
+
&& . /home/opencode/.cargo/env \
|
|
189
|
+
&& rustup component add rust-analyzer rustfmt clippy
|
|
190
|
+
|
|
191
|
+
ENV PATH="/home/opencode/.cargo/bin:${PATH}"
|
|
192
|
+
|
|
193
|
+
# -----------------------------------------------------------------------------
|
|
194
|
+
# Package Managers
|
|
195
|
+
# -----------------------------------------------------------------------------
|
|
196
|
+
# Switch to bash for mise activation (mise outputs bash-specific syntax)
|
|
197
|
+
SHELL ["/bin/bash", "-c"]
|
|
198
|
+
|
|
199
|
+
# Install pnpm (corepack is included with Node.js)
|
|
200
|
+
RUN eval "$(/home/opencode/.local/bin/mise activate bash)" \
|
|
201
|
+
&& corepack enable \
|
|
202
|
+
&& corepack prepare pnpm@latest --activate
|
|
203
|
+
|
|
204
|
+
# Set up pnpm global bin directory
|
|
205
|
+
ENV PNPM_HOME="/home/opencode/.local/share/pnpm"
|
|
206
|
+
ENV PATH="${PNPM_HOME}:${PATH}"
|
|
207
|
+
RUN mkdir -p "${PNPM_HOME}"
|
|
208
|
+
|
|
209
|
+
# Install uv (fast Python package manager)
|
|
210
|
+
RUN curl -LsSf https://astral.sh/uv/install.sh | sh
|
|
211
|
+
|
|
212
|
+
# Install pipx for isolated Python application installs
|
|
213
|
+
RUN eval "$(/home/opencode/.local/bin/mise activate bash)" \
|
|
214
|
+
&& pip install --user pipx \
|
|
215
|
+
&& pipx ensurepath
|
|
216
|
+
|
|
217
|
+
# Install global TypeScript compiler
|
|
218
|
+
RUN eval "$(/home/opencode/.local/bin/mise activate bash)" \
|
|
219
|
+
&& pnpm add -g typescript
|
|
220
|
+
|
|
221
|
+
# -----------------------------------------------------------------------------
|
|
222
|
+
# Modern CLI Tools (Rust-based)
|
|
223
|
+
# -----------------------------------------------------------------------------
|
|
224
|
+
# Install via cargo for latest versions
|
|
225
|
+
RUN . /home/opencode/.cargo/env \
|
|
226
|
+
&& cargo install --locked \
|
|
227
|
+
ripgrep \
|
|
228
|
+
eza
|
|
229
|
+
|
|
230
|
+
# Install lazygit (Go-based)
|
|
231
|
+
RUN eval "$(/home/opencode/.local/bin/mise activate bash)" \
|
|
232
|
+
&& go install github.com/jesseduffield/lazygit@latest
|
|
233
|
+
|
|
234
|
+
# -----------------------------------------------------------------------------
|
|
235
|
+
# Additional Development Tools
|
|
236
|
+
# -----------------------------------------------------------------------------
|
|
237
|
+
# Install fzf
|
|
238
|
+
RUN git clone --depth 1 https://github.com/junegunn/fzf.git /home/opencode/.fzf \
|
|
239
|
+
&& /home/opencode/.fzf/install --all --no-bash --no-fish
|
|
240
|
+
|
|
241
|
+
# Install yq (YAML processor)
|
|
242
|
+
RUN curl -sL https://github.com/mikefarah/yq/releases/latest/download/yq_linux_$(dpkg --print-architecture) -o /home/opencode/.local/bin/yq \
|
|
243
|
+
&& chmod +x /home/opencode/.local/bin/yq
|
|
244
|
+
|
|
245
|
+
# Install direnv
|
|
246
|
+
USER root
|
|
247
|
+
RUN apt-get update && apt-get install -y --no-install-recommends direnv \
|
|
248
|
+
&& rm -rf /var/lib/apt/lists/*
|
|
249
|
+
USER opencode
|
|
250
|
+
RUN echo 'eval "$(direnv hook zsh)"' >> /home/opencode/.zshrc
|
|
251
|
+
|
|
252
|
+
# Install HTTPie
|
|
253
|
+
RUN eval "$(/home/opencode/.local/bin/mise activate bash)" \
|
|
254
|
+
&& pipx install httpie
|
|
255
|
+
|
|
256
|
+
# Install shellcheck and shfmt
|
|
257
|
+
USER root
|
|
258
|
+
RUN apt-get update && apt-get install -y --no-install-recommends shellcheck \
|
|
259
|
+
&& rm -rf /var/lib/apt/lists/*
|
|
260
|
+
USER opencode
|
|
261
|
+
RUN eval "$(/home/opencode/.local/bin/mise activate bash)" \
|
|
262
|
+
&& go install mvdan.cc/sh/v3/cmd/shfmt@latest
|
|
263
|
+
|
|
264
|
+
# Install btop (system monitor)
|
|
265
|
+
USER root
|
|
266
|
+
RUN apt-get update && apt-get install -y --no-install-recommends btop \
|
|
267
|
+
&& rm -rf /var/lib/apt/lists/*
|
|
268
|
+
USER opencode
|
|
269
|
+
|
|
270
|
+
# -----------------------------------------------------------------------------
|
|
271
|
+
# GitHub CLI
|
|
272
|
+
# -----------------------------------------------------------------------------
|
|
273
|
+
USER root
|
|
274
|
+
RUN curl -fsSL https://cli.github.com/packages/githubcli-archive-keyring.gpg | dd of=/usr/share/keyrings/githubcli-archive-keyring.gpg \
|
|
275
|
+
&& chmod go+r /usr/share/keyrings/githubcli-archive-keyring.gpg \
|
|
276
|
+
&& echo "deb [arch=$(dpkg --print-architecture) signed-by=/usr/share/keyrings/githubcli-archive-keyring.gpg] https://cli.github.com/packages stable main" > /etc/apt/sources.list.d/github-cli.list \
|
|
277
|
+
&& apt-get update && apt-get install -y --no-install-recommends gh \
|
|
278
|
+
&& rm -rf /var/lib/apt/lists/*
|
|
279
|
+
USER opencode
|
|
280
|
+
|
|
281
|
+
# -----------------------------------------------------------------------------
|
|
282
|
+
# CI/CD Tools
|
|
283
|
+
# -----------------------------------------------------------------------------
|
|
284
|
+
# Install act (run GitHub Actions locally)
|
|
285
|
+
RUN curl -sL https://raw.githubusercontent.com/nektos/act/master/install.sh | sudo bash -s -- -b /home/opencode/.local/bin
|
|
286
|
+
|
|
287
|
+
# -----------------------------------------------------------------------------
|
|
288
|
+
# Rust Tooling
|
|
289
|
+
# -----------------------------------------------------------------------------
|
|
290
|
+
RUN . /home/opencode/.cargo/env \
|
|
291
|
+
&& cargo install --locked \
|
|
292
|
+
cargo-nextest \
|
|
293
|
+
cargo-audit \
|
|
294
|
+
cargo-deny
|
|
295
|
+
|
|
296
|
+
# Install mold (fast linker) via apt for easier setup
|
|
297
|
+
USER root
|
|
298
|
+
RUN apt-get update && apt-get install -y --no-install-recommends mold \
|
|
299
|
+
&& rm -rf /var/lib/apt/lists/*
|
|
300
|
+
USER opencode
|
|
301
|
+
|
|
302
|
+
# -----------------------------------------------------------------------------
|
|
303
|
+
# Code Quality Tools
|
|
304
|
+
# -----------------------------------------------------------------------------
|
|
305
|
+
# JavaScript/TypeScript tools
|
|
306
|
+
RUN eval "$(/home/opencode/.local/bin/mise activate bash)" \
|
|
307
|
+
&& pnpm add -g \
|
|
308
|
+
prettier \
|
|
309
|
+
eslint \
|
|
310
|
+
@biomejs/biome
|
|
311
|
+
|
|
312
|
+
# Python tools
|
|
313
|
+
RUN eval "$(/home/opencode/.local/bin/mise activate bash)" \
|
|
314
|
+
&& pipx install black \
|
|
315
|
+
&& pipx install ruff
|
|
316
|
+
|
|
317
|
+
# Test runners (commonly needed)
|
|
318
|
+
RUN eval "$(/home/opencode/.local/bin/mise activate bash)" \
|
|
319
|
+
&& pnpm add -g jest vitest
|
|
320
|
+
|
|
321
|
+
# Python pytest via pipx
|
|
322
|
+
RUN eval "$(/home/opencode/.local/bin/mise activate bash)" \
|
|
323
|
+
&& pipx install pytest
|
|
324
|
+
|
|
325
|
+
# -----------------------------------------------------------------------------
|
|
326
|
+
# Protocol Buffers / gRPC
|
|
327
|
+
# -----------------------------------------------------------------------------
|
|
328
|
+
USER root
|
|
329
|
+
RUN apt-get update && apt-get install -y --no-install-recommends protobuf-compiler \
|
|
330
|
+
&& rm -rf /var/lib/apt/lists/*
|
|
331
|
+
USER opencode
|
|
332
|
+
|
|
333
|
+
# Install grpcurl
|
|
334
|
+
RUN eval "$(/home/opencode/.local/bin/mise activate bash)" \
|
|
335
|
+
&& go install github.com/fullstorydev/grpcurl/cmd/grpcurl@latest
|
|
336
|
+
|
|
337
|
+
# -----------------------------------------------------------------------------
|
|
338
|
+
# opencode Installation
|
|
339
|
+
# -----------------------------------------------------------------------------
|
|
340
|
+
# Install opencode using official install script
|
|
341
|
+
# The script installs to ~/.opencode/bin/
|
|
342
|
+
RUN curl -fsSL https://opencode.ai/install | bash \
|
|
343
|
+
&& ls -la /home/opencode/.opencode/bin/opencode \
|
|
344
|
+
&& /home/opencode/.opencode/bin/opencode --version
|
|
345
|
+
|
|
346
|
+
# Add opencode to PATH
|
|
347
|
+
ENV PATH="/home/opencode/.opencode/bin:${PATH}"
|
|
348
|
+
|
|
349
|
+
# -----------------------------------------------------------------------------
|
|
350
|
+
# GSD Plugin Installation
|
|
351
|
+
# -----------------------------------------------------------------------------
|
|
352
|
+
# Install the GSD (Get Shit Done) plugin for opencode
|
|
353
|
+
RUN git clone https://github.com/rokicool/gsd-opencode.git /home/opencode/.config/opencode/plugins/gsd-opencode
|
|
354
|
+
|
|
355
|
+
# -----------------------------------------------------------------------------
|
|
356
|
+
# Sensible Defaults Configuration
|
|
357
|
+
# -----------------------------------------------------------------------------
|
|
358
|
+
# Git configuration
|
|
359
|
+
RUN git config --global init.defaultBranch main \
|
|
360
|
+
&& git config --global core.editor "nvim" \
|
|
361
|
+
&& git config --global pull.rebase false \
|
|
362
|
+
&& git config --global merge.conflictstyle diff3 \
|
|
363
|
+
&& git config --global diff.colorMoved default
|
|
364
|
+
|
|
365
|
+
# Starship configuration (minimal, fast prompt)
|
|
366
|
+
RUN mkdir -p /home/opencode/.config \
|
|
367
|
+
&& cat > /home/opencode/.config/starship.toml << 'STARSHIP'
|
|
368
|
+
# Minimal starship config for fast prompt
|
|
369
|
+
format = """
|
|
370
|
+
$directory\
|
|
371
|
+
$git_branch\
|
|
372
|
+
$git_status\
|
|
373
|
+
$character"""
|
|
374
|
+
|
|
375
|
+
[directory]
|
|
376
|
+
truncation_length = 3
|
|
377
|
+
truncate_to_repo = true
|
|
378
|
+
|
|
379
|
+
[git_branch]
|
|
380
|
+
format = "[$branch]($style) "
|
|
381
|
+
style = "bold purple"
|
|
382
|
+
|
|
383
|
+
[git_status]
|
|
384
|
+
format = '([$all_status$ahead_behind]($style) )'
|
|
385
|
+
|
|
386
|
+
[character]
|
|
387
|
+
success_symbol = "[>](bold green)"
|
|
388
|
+
error_symbol = "[>](bold red)"
|
|
389
|
+
STARSHIP
|
|
390
|
+
|
|
391
|
+
# Shell aliases
|
|
392
|
+
RUN cat >> /home/opencode/.zshrc << 'ALIASES'
|
|
393
|
+
|
|
394
|
+
# Modern CLI aliases
|
|
395
|
+
alias ls="eza --icons"
|
|
396
|
+
alias ll="eza -l --icons"
|
|
397
|
+
alias la="eza -la --icons"
|
|
398
|
+
alias lt="eza --tree --icons"
|
|
399
|
+
alias grep="rg"
|
|
400
|
+
alias top="btop"
|
|
401
|
+
|
|
402
|
+
# Git aliases
|
|
403
|
+
alias g="git"
|
|
404
|
+
alias gs="git status"
|
|
405
|
+
alias gd="git diff"
|
|
406
|
+
alias gc="git commit"
|
|
407
|
+
alias gp="git push"
|
|
408
|
+
alias gl="git pull"
|
|
409
|
+
alias gco="git checkout"
|
|
410
|
+
alias gb="git branch"
|
|
411
|
+
alias lg="lazygit"
|
|
412
|
+
|
|
413
|
+
# Docker aliases (for Docker-in-Docker)
|
|
414
|
+
alias d="docker"
|
|
415
|
+
alias dc="docker compose"
|
|
416
|
+
|
|
417
|
+
ALIASES
|
|
418
|
+
|
|
419
|
+
# Set up pipx path
|
|
420
|
+
RUN echo 'export PATH="/home/opencode/.local/bin:$PATH"' >> /home/opencode/.zshrc
|
|
421
|
+
|
|
422
|
+
# -----------------------------------------------------------------------------
|
|
423
|
+
# Health Check
|
|
424
|
+
# -----------------------------------------------------------------------------
|
|
425
|
+
# Port 3000 must match OPENCODE_WEB_PORT in container.rs
|
|
426
|
+
HEALTHCHECK --interval=30s --timeout=10s --start-period=5s --retries=3 \
|
|
427
|
+
CMD curl -f http://localhost:3000/health || exit 1
|
|
428
|
+
|
|
429
|
+
# -----------------------------------------------------------------------------
|
|
430
|
+
# Final Configuration
|
|
431
|
+
# -----------------------------------------------------------------------------
|
|
432
|
+
WORKDIR /home/opencode/workspace
|
|
433
|
+
|
|
434
|
+
# Expose opencode web port (matches OPENCODE_WEB_PORT in container.rs)
|
|
435
|
+
EXPOSE 3000
|
|
436
|
+
|
|
437
|
+
# Use tini as init system for proper signal handling
|
|
438
|
+
ENTRYPOINT ["/usr/bin/tini", "--"]
|
|
439
|
+
|
|
440
|
+
# Default command: start opencode web interface
|
|
441
|
+
# - Port 3000 must match OPENCODE_WEB_PORT in container.rs
|
|
442
|
+
# - Using full path to ensure binary is found (opencode installs to ~/.opencode/bin/)
|
|
443
|
+
# - --hostname 0.0.0.0 is required for Docker port mapping (default 127.0.0.1 only listens on loopback)
|
|
444
|
+
CMD ["/home/opencode/.opencode/bin/opencode", "web", "--port", "3000", "--hostname", "0.0.0.0"]
|
|
@@ -0,0 +1,84 @@
|
|
|
1
|
+
//! Docker client wrapper with connection handling
|
|
2
|
+
//!
|
|
3
|
+
//! This module provides a wrapped Docker client that handles connection
|
|
4
|
+
//! errors gracefully and provides clear error messages.
|
|
5
|
+
|
|
6
|
+
use bollard::Docker;
|
|
7
|
+
|
|
8
|
+
use super::error::DockerError;
|
|
9
|
+
|
|
10
|
+
/// Docker client wrapper with connection handling
|
|
11
|
+
pub struct DockerClient {
|
|
12
|
+
inner: Docker,
|
|
13
|
+
}
|
|
14
|
+
|
|
15
|
+
impl DockerClient {
|
|
16
|
+
/// Create new client connecting to local Docker daemon
|
|
17
|
+
///
|
|
18
|
+
/// Uses platform-appropriate socket (Unix socket on Linux/macOS).
|
|
19
|
+
/// Returns a clear error if Docker is not running or accessible.
|
|
20
|
+
pub fn new() -> Result<Self, DockerError> {
|
|
21
|
+
let docker = Docker::connect_with_local_defaults()
|
|
22
|
+
.map_err(|e| DockerError::Connection(e.to_string()))?;
|
|
23
|
+
|
|
24
|
+
Ok(Self { inner: docker })
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
/// Create client with custom timeout (in seconds)
|
|
28
|
+
///
|
|
29
|
+
/// Use for long-running operations like image builds.
|
|
30
|
+
/// Default timeout is 120 seconds; build timeout should be 600+ seconds.
|
|
31
|
+
pub fn with_timeout(timeout_secs: u64) -> Result<Self, DockerError> {
|
|
32
|
+
let docker = Docker::connect_with_local_defaults()
|
|
33
|
+
.map_err(|e| DockerError::Connection(e.to_string()))?
|
|
34
|
+
.with_timeout(std::time::Duration::from_secs(timeout_secs));
|
|
35
|
+
|
|
36
|
+
Ok(Self { inner: docker })
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
/// Verify connection to Docker daemon
|
|
40
|
+
///
|
|
41
|
+
/// Returns Ok(()) if connected, descriptive error otherwise.
|
|
42
|
+
pub async fn verify_connection(&self) -> Result<(), DockerError> {
|
|
43
|
+
self.inner.ping().await.map_err(DockerError::from)?;
|
|
44
|
+
Ok(())
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
/// Get Docker version info (useful for debugging)
|
|
48
|
+
pub async fn version(&self) -> Result<String, DockerError> {
|
|
49
|
+
let version = self.inner.version().await.map_err(DockerError::from)?;
|
|
50
|
+
|
|
51
|
+
let version_str = format!(
|
|
52
|
+
"Docker {} (API {})",
|
|
53
|
+
version.version.unwrap_or_else(|| "unknown".to_string()),
|
|
54
|
+
version.api_version.unwrap_or_else(|| "unknown".to_string())
|
|
55
|
+
);
|
|
56
|
+
|
|
57
|
+
Ok(version_str)
|
|
58
|
+
}
|
|
59
|
+
|
|
60
|
+
/// Access inner Bollard client for advanced operations
|
|
61
|
+
pub fn inner(&self) -> &Docker {
|
|
62
|
+
&self.inner
|
|
63
|
+
}
|
|
64
|
+
}
|
|
65
|
+
|
|
66
|
+
#[cfg(test)]
|
|
67
|
+
mod tests {
|
|
68
|
+
use super::*;
|
|
69
|
+
|
|
70
|
+
#[test]
|
|
71
|
+
fn docker_client_creation_does_not_panic() {
|
|
72
|
+
// This test just verifies the code compiles and doesn't panic
|
|
73
|
+
// Actual connection test requires Docker to be running
|
|
74
|
+
let result = DockerClient::new();
|
|
75
|
+
// We don't assert success because Docker may not be running in CI
|
|
76
|
+
drop(result);
|
|
77
|
+
}
|
|
78
|
+
|
|
79
|
+
#[test]
|
|
80
|
+
fn docker_client_with_timeout_does_not_panic() {
|
|
81
|
+
let result = DockerClient::with_timeout(600);
|
|
82
|
+
drop(result);
|
|
83
|
+
}
|
|
84
|
+
}
|