Skip to content
Open
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
23 changes: 19 additions & 4 deletions .github/workflows/docker-publish.yml
Original file line number Diff line number Diff line change
Expand Up @@ -4,15 +4,18 @@
# timeplus/tpk all-in-one image (timeplusd + tpk) -> all-in-one mode
#
# Tags produced: `latest` (main only), the git short SHA, and — on a vX.Y.Z tag —
# the semver `X.Y.Z` and `X.Y`.
# the semver `X.Y.Z` and `X.Y`. Every pushed tag is a multi-arch manifest list
# (linux/amd64 + linux/arm64, issue #72) so the images run natively on Apple
# Silicon and on ARM (Graviton) Kubernetes nodes. The arm64 leg is built under
# QEMU; pull requests build linux/amd64 only as a smoke test.
#
# Required repository secrets:
# DOCKERHUB_USERNAME / DOCKERHUB_TOKEN Docker Hub creds with push access to
# the `timeplus` org (a Hub access token).
# Optional (only if the timeplusd base image needs auth to pull):
# TIMEPLUSD_REGISTRY_USERNAME / TIMEPLUSD_REGISTRY_PASSWORD for docker.timeplus.com
#
# Pull requests build the app image as a smoke test but never push.
# Pull requests build the app image (amd64 only) as a smoke test but never push.

name: Docker

Expand All @@ -30,13 +33,21 @@ concurrency:
permissions:
contents: read

env:
# Multi-arch for anything we publish; PRs stay single-arch to keep CI fast.
PLATFORMS: ${{ github.event_name == 'pull_request' && 'linux/amd64' || 'linux/amd64,linux/arm64' }}

jobs:
app:
name: app image (timeplus/tpk-app)
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4

- uses: docker/setup-qemu-action@v3
with:
platforms: arm64

- uses: docker/setup-buildx-action@v3

- name: Log in to Docker Hub
Expand All @@ -63,7 +74,7 @@ jobs:
context: .
file: deploy/docker/Dockerfile
target: app
platforms: linux/amd64
platforms: ${{ env.PLATFORMS }}
push: ${{ github.event_name != 'pull_request' }}
tags: ${{ steps.meta.outputs.tags }}
labels: ${{ steps.meta.outputs.labels }}
Expand All @@ -82,6 +93,10 @@ jobs:
steps:
- uses: actions/checkout@v4

- uses: docker/setup-qemu-action@v3
with:
platforms: arm64

- uses: docker/setup-buildx-action@v3

- name: Log in to Docker Hub
Expand Down Expand Up @@ -115,7 +130,7 @@ jobs:
context: .
file: deploy/docker/Dockerfile
target: allinone
platforms: linux/amd64
platforms: ${{ env.PLATFORMS }}
push: true
tags: ${{ steps.meta.outputs.tags }}
labels: ${{ steps.meta.outputs.labels }}
Expand Down
19 changes: 14 additions & 5 deletions Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -97,11 +97,20 @@ down-allinone: ## Stop the all-in-one stack (named data volumes are kept)

APP_IMAGE ?= timeplus/tpk-app:dev

docker-build-allinone: ## Build the all-in-one image (timeplusd + tpk)
docker build -f deploy/docker/Dockerfile --target allinone -t $(IMAGE) .

docker-build-app: ## Build the tpk app-only image (pure-Python; no timeplusd)
docker build -f deploy/docker/Dockerfile --target app -t $(APP_IMAGE) .
# Local builds target the host arch. Set PLATFORMS for a cross/multi-arch build
# via buildx, e.g.
# make docker-build-app PLATFORMS=linux/arm64
# make docker-build PLATFORMS=linux/amd64,linux/arm64 DOCKER_BUILD_FLAGS=--push
# (a multi-platform build can't be loaded into the local daemon; add --push).
PLATFORMS ?=
DOCKER_BUILD_FLAGS ?=
DOCKER_BUILD = docker $(if $(PLATFORMS),buildx build --platform $(PLATFORMS),build) $(DOCKER_BUILD_FLAGS)

docker-build-allinone: ## Build the all-in-one image (proton + tpk); PLATFORMS=... for multi-arch
$(DOCKER_BUILD) -f deploy/docker/Dockerfile --target allinone -t $(IMAGE) .

docker-build-app: ## Build the tpk app-only image (pure-Python; no timeplusd); PLATFORMS=... for multi-arch
$(DOCKER_BUILD) -f deploy/docker/Dockerfile --target app -t $(APP_IMAGE) .

docker-build: docker-build-allinone docker-build-app ## Build both deployable images

Expand Down
5 changes: 3 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -16,8 +16,9 @@ single container (fully open-source, no separate database, no build):
docker exec tpk tpk ingest # build the knowledge graph
open http://localhost:8000 # chat + web UI — log in as admin / changeme

Use `-e ANTHROPIC_API_KEY=...` instead for Claude; the same key powers both chat
and semantic ingest. `tpk ingest` fetches the repos from the image's baked
The image is multi-arch (`linux/amd64` + `linux/arm64`), so it runs natively on
Apple Silicon. Use `-e ANTHROPIC_API_KEY=...` instead for Claude; the same key
powers both chat and semantic ingest. `tpk ingest` fetches the repos from the image's baked
config (`deploy/docker/repos.container.toml`) — private repos need
`-e GITHUB_TOKEN=...`. You'll be prompted to change the seed `admin` password on
first login.
Expand Down
2 changes: 2 additions & 0 deletions deploy/k8s/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,8 @@ so they're alternatives, not layers.
The images are the ones published by [`.github/workflows/docker-publish.yml`](../../.github/workflows/docker-publish.yml):
`timeplus/tpk-app` (app-only) and `timeplus/tpk` (all-in-one). Pin `:latest` to a
released tag (e.g. `timeplus/tpk-app:1.2.3`) for reproducible rollouts.
Both are multi-arch (`linux/amd64` + `linux/arm64`), so they schedule onto
x86 and ARM (e.g. Graviton) nodes alike without a `nodeSelector`.

## Prerequisites

Expand Down
Loading