Releases: mtsfoni/construct
Releases · mtsfoni/construct
v0.9.0
Added
- Auto-port fallback for serve mode — when
--serve-portis not specified and the default port (4096) is already in use on the host,constructnow automatically picks the next free higher port instead of failing. A yellow diagnostic is printed to stderr:construct: port 4096 is already in use; using port 4097 instead. If--serve-portis specified explicitly, no fallback occurs.
v0.8.0
Fixed
- Session history now scoped per project — previously, opencode's session database (
opencode.db) was stored inside a global Docker volume (construct-auth-opencode) that was shared across all repos. This meant the session list showed sessions from every project regardless of which repoconstructwas launched for. The fix replaces the directory volume mount with a file bind-mount of onlyauth.json(from~/.construct/opencode/auth.jsonon the host). The session database now lives in the per-repo home volume and is isolated to the current project. OAuth tokens inauth.jsonremain global (shared across repos, survive--reset) so users still only need to authenticate once. Note:opencode.dbis now wiped by--resetalong with the rest of the home volume. - opencode health check timeout after auth.json bind-mount — when Docker bind-mounts a file into a container, it auto-creates any missing parent directories as root. After switching to the
auth.jsonfile bind-mount,/home/agent/.local/,.local/share/, and.local/share/opencode/were created root-owned, so opencode could not write itsbin/directory or.local/state/siblings and crashed immediately. The fix pre-creates the parent directory (/home/agent/.local/share/opencode/) in the tool image Dockerfile as theagentuser — Docker's bind-mount then finds the directory already present and does not recreate it. Requires a one-time--rebuildto pick up the updated image. - Health-check timeout now shows container logs and recovery hints — previously, when the opencode server failed to start in serve mode, the only output was
server did not become ready: timed out after 15s waiting for …, with no indication of why it failed or what to do. On timeout,constructnow retrieves and prints the container's stderr/stdout (which almost always names the root cause directly, e.g. anEACCESerror or a missing API key), followed by actionable recovery hints: try--rebuildif opencode just updated,--resetif the home volume is corrupt or stale, or--debugto inspect the container interactively.
v0.7.2
Fix Windows build: split dockerSocketGID into platform-specific files syscall.Stat_t is not defined on Windows. Move dockerSocketGID into socket_gid_unix.go (!windows build tag) and provide a no-op stub in socket_gid_windows.go. syscall is still imported in runner.go for SIGTERM. Generated by construct
v0.6.3
Added
- Richer agent context in AGENTS.md — the generated
~/.config/opencode/AGENTS.mdnow includes a Workspace section (explaining that/workspaceis the user's repo, bind-mounted and immediately visible) and an Isolation section (explaining that the rest of the container is isolated, and that/home/agentpersists across sessions via a named volume).
v0.6.0
Added
rubystack —construct-base+ Ruby (system package), Bundler, and Jekyll. Use--stack rubyfor Jekyll sites and Ruby projects.ruby-uistack —construct-ruby+@playwright/mcp+ Chromium. Use--stack ruby-ui --mcpfor Jekyll/Ruby projects that also need browser automation.- Global opencode slash commands — when
~/.config/opencode/commands/exists on the host, it is automatically bind-mounted read-only into the opencode agent container. Custom slash commands defined globally on the host are now available inside the container without any extra flags. --versionflag — prints the construct version (e.g.construct v0.6.0) and exits. Reportsconstruct devwhen built without ldflags.- ARM64 support for the
gostack — thegostack Dockerfile now usesTARGETARCHto select the correct Go tarball, soconstruct-gobuilds correctly on bothlinux/amd64andlinux/arm64hosts. - Automatic image rebuild on version mismatch — stack and tool images are now stamped with an
io.construct.versionlabel at build time. On startup, construct compares the label against the running binary version and automatically rebuilds any stale image (one built by a different version, or one that predates this feature and carries no label). Dev builds (no ldflags version) skip the check entirely so local iteration is unaffected.
Fixed
--stackdefault corrected tobase— the default was incorrectly left asnode(a stack removed in v0.3.0), which would cause an error for users who omitted--stack. It now correctly defaults tobase.
v0.5.0
Added
- Changelog-driven release notes — the release pipeline now extracts the
## [Unreleased]block fromCHANGELOG.mdand uses it as the GitHub
release body. After tagging, the changelog is automatically updated:
[Unreleased]is renamed to the tag version with today's date, and a fresh
empty[Unreleased]block is inserted above it. The commit is pushed back
tomainbygithub-actions[bot].
Changed
- Agent commits now carry the host user's real git identity instead of the
syntheticconstruct agentidentity. Author and committer are resolved
independently using git's own precedence:GIT_AUTHOR_*/GIT_COMMITTER_*
host env vars take priority, thengit config user.name/user.email, then
the committer falls back to the author (matching git's default behaviour). The
synthetic fallback (construct user <user@construct.local>) is only used when
no author identity at all is available on the host, and triggers a warning. - A
commit-msghook is injected into the container at startup via
core.hooksPath. It appends aGenerated by constructgit trailer to every
commit message (idempotent — safe with amend and rebase).
v0.4.0
[v0.4.0] — 2026-03-03
Added
--dockerflag — selects Docker access mode for the agent container.--docker none(default) starts no sidecar and sets noDOCKER_HOST, following the principle of least privilege.--docker doodbind-mounts the host socket (/var/run/docker.sock) for Docker-outside-of-Docker access.--docker dindstarts an isolated privilegeddocker:dindsidecar (previous default behaviour). The mode is saved in~/.construct/last-used.jsonand replayed byqs. The injectedAGENTS.mdnetworking section is tailored to the active mode.dotnet-bigstack — newconstruct-dotnet-bigimage extendingconstruct-basewith the .NET 8, 9, and 10 SDKs installed side-by-side. Use when a project targets multiple .NET generations or must verify cross-version compatibility.dotnet-big-uistack — newconstruct-dotnet-big-uiimage extendingconstruct-dotnet-bigwith@playwright/mcpand Chromium. Use with--mcpfor projects that need multi-version .NET support and browser automation in the same session.
Full Changelog: v0.3.2...v0.4.0
v0.3.2
[v0.3.2] — 2026-03-01
Added
Static dind network alias — the dind sidecar now registers the alias dind on its session-scoped bridge network. DOCKER_HOST is always tcp://dind:2375, matching the hostname already documented in the injected AGENTS.md. This makes the alias real rather than implied and keeps it stable across sessions.
Fixed
dotnet/dotnet-ui stack — libicu70 is now installed in the image, resolving a runtime crash when .NET applications use globalization (ICU mode). Previously .NET would abort on startup with Couldn't find a valid ICU package.
Full Changelog: v0.3.0...v0.3.2
v0.3.0
[v0.3.0] — 2026-02-23
Added
--portflag — publish container ports to the host. Repeatable; accepts any formatdocker run -psupports (3000,9000:3000,127.0.0.1:3000:3000). A bare port number is automatically expanded tohost:container.--mcpflag — activate MCP servers at container startup. When passed, the entrypoint writes~/.config/opencode/opencode.jsonregistering@playwright/mcp; without it the file is removed. Requires--stack uior--stack dotnet-uifor full browser automation support.dotnet-uistack — newconstruct-dotnet-uiimage combining the .NET 10 SDK with@playwright/mcpand Chromium. Extendsconstruct-dotnet; use with--mcpfor Blazor/ASP.NET projects that need browser automation.- Automatic AGENTS.md injection — the entrypoint always writes
~/.config/opencode/AGENTS.mdso opencode knows it is running inside a construct container. When--portis used the file also contains server binding rules (bind to0.0.0.0, use the ports listed in$CONSTRUCT_PORTS), preventing the common mistake of agents starting dev servers on127.0.0.1which is unreachable from the host. - Networking context in AGENTS.md — the injected file now always explains that Docker runs on a separate sidecar host (
dind), notlocalhost. Containers started via Docker are reachable atdind:<port>, not127.0.0.1. Also clarifies that the user can access ports on the agent machine directly but not ports inside Docker containers, so agents should run services on the machine itself. OPENCODE_EXPERIMENTAL_DISABLE_COPY_ON_SELECT=true— injected into the opencode container to prevent unwanted clipboard interference from terminal text selection.CONSTRUCT=1env var — always injected into the agent container so tools can detect they are running inside construct.CONSTRUCT_PORTSenv var — injected when--portis used; contains the comma-separated list of container-side port numbers.qsnow replays--mcpand--port— the quickstart command restores the full previous invocation, not just--tooland--stack.~/.construct/last-used.jsonnow storesmcpandportsalongsidetoolandstack.install.sh— convenience script that builds the binary from source and installs it to~/.local/bin/construct.
Changed
- Stack consolidation —
nodeandpythonstacks are removed. Python 3, pip, and venv are now included in thebaseimage alongside Node.js 20. Theuistack now extendsbasedirectly. Any invocation using--stack nodeor--stack pythonshould switch to--stack base(or a more specific stack). - Default stack changed from
nodetobase— reflects the consolidation above. - MCP activation decoupled from stack —
@playwright/mcpis installed in theuianddotnet-uistack images at build time but is only activated at runtime when--mcpis passed. Previously the MCP config was seeded unconditionally into the home volume.
Full Changelog: v0.2.0...v0.3.0
v0.2.0
Full Changelog: v0.1.0...v0.2.0
Full Changelog: v0.1.0...v0.2.0