Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
52 changes: 50 additions & 2 deletions .github/workflows/docker-publish.yml
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
name: Build and Publish Docker Image
name: Build and Publish Docker Images

on:
push:
Expand All @@ -12,7 +12,7 @@ on:
workflow_dispatch:

jobs:
build-and-push:
build-and-push-server:
runs-on: ubuntu-latest
permissions:
contents: read
Expand Down Expand Up @@ -59,3 +59,51 @@ jobs:
labels: ${{ steps.meta.outputs.labels }}
cache-from: type=gha
cache-to: type=gha,mode=max

build-and-push-ui:
runs-on: ubuntu-latest
permissions:
contents: read
packages: write
steps:
- name: Checkout
uses: actions/checkout@v4

- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v3

- name: Login to Docker Hub
if: github.event_name != 'pull_request'
uses: docker/login-action@v3
with:
username: ${{ secrets.DOCKERHUB_USERNAME }}
password: ${{ secrets.DOCKERHUB_TOKEN }}

- name: Extract metadata for Docker
id: meta
uses: docker/metadata-action@v5
with:
images: galileoai/agent-control-ui
tags: |
# For version tags: v1.2.3 -> 1.2.3, 1.2, 1, latest
type=semver,pattern={{version}}
type=semver,pattern={{major}}.{{minor}}
type=semver,pattern={{major}}
# For main branch: latest
type=raw,value=latest,enable={{is_default_branch}}
# For branches: branch name (sanitized)
type=ref,event=branch,enable=${{ github.ref != 'refs/heads/main' }}
# For PRs: pr-123
type=ref,event=pr

- name: Build and push
uses: docker/build-push-action@v5
with:
context: ui
file: ui/Dockerfile
platforms: linux/amd64 # Build only for Intel to keep UI image CI fast
push: ${{ github.event_name != 'pull_request' }}
tags: ${{ steps.meta.outputs.tags }}
labels: ${{ steps.meta.outputs.labels }}
cache-from: type=gha,scope=ui-image
cache-to: type=gha,mode=max,scope=ui-image
4 changes: 2 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -84,10 +84,10 @@ cd agent-control
**What the script does:**
- ✓ Check Python 3.12+ is installed
- ✓ Create a virtual environment
- ✓ Pull and start PostgreSQL + Agent Control Server via Docker
- ✓ Pull and start PostgreSQL + Agent Control Server + UI via Docker
- ✓ Install the Agent Control SDK

**Server will be running at `http://localhost:8000` — ready to use!**
**Server will be running at `http://localhost:8000` and UI at `http://localhost:4000` — ready to use!**


---
Expand Down
14 changes: 13 additions & 1 deletion docker-compose.yml
Original file line number Diff line number Diff line change
Expand Up @@ -6,9 +6,11 @@
# Services:
# - PostgreSQL database (port 5432)
# - Agent Control Server API (port 8000)
# - Agent Control UI Dashboard (port 4000)
#
# The server image is published to Docker Hub at:
# The images are published to Docker Hub at:
# galileoai/agent-control-server:latest
# galileoai/agent-control-ui:latest
#
# For local development (run server with uvicorn), use:
# docker compose -f docker-compose.dev.yml up -d
Expand Down Expand Up @@ -49,5 +51,15 @@ services:
condition: service_healthy
restart: unless-stopped

ui:
image: galileoai/agent-control-ui:latest
platform: linux/amd64
container_name: agent_control_ui
ports:
- "4000:4000"
depends_on:
- server
restart: unless-stopped

volumes:
pgdata:
10 changes: 10 additions & 0 deletions ui/.dockerignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
node_modules
.next
out
playwright-report
test-results
pnpm-debug.log*
npm-debug.log*
yarn-debug.log*
yarn-error.log*
.DS_Store
50 changes: 50 additions & 0 deletions ui/Dockerfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
# Dockerfile for Agent Control UI
#
# Build from repository root:
# docker build -t agent-control-ui -f ui/Dockerfile ui
#
# Run:
# docker run -p 4000:4000 agent-control-ui

FROM node:20-alpine AS base

WORKDIR /app

ENV PNPM_HOME=/pnpm
ENV PATH=$PNPM_HOME:$PATH

RUN corepack enable && corepack prepare pnpm@9 --activate

FROM base AS deps

COPY package.json pnpm-lock.yaml ./
RUN pnpm install --frozen-lockfile

FROM base AS builder

# Next.js NEXT_PUBLIC_* values are bundled at build time.
ARG NEXT_PUBLIC_API_URL=http://localhost:8000
ENV NEXT_PUBLIC_API_URL=$NEXT_PUBLIC_API_URL
ENV NEXT_TELEMETRY_DISABLED=1

COPY --from=deps /app/node_modules ./node_modules
COPY . .

RUN pnpm build && pnpm prune --prod

FROM base AS runner

WORKDIR /app

ENV NODE_ENV=production
ENV NEXT_TELEMETRY_DISABLED=1
ENV PORT=4000

COPY --from=builder /app/package.json ./package.json
COPY --from=builder /app/public ./public
COPY --from=builder /app/.next ./.next
COPY --from=builder /app/node_modules ./node_modules

EXPOSE 4000

CMD ["pnpm", "start", "-p", "4000"]
Loading