Deploy a Go service
A stateless Go HTTP service in a 5 MB scratch image — the smallest possible Rune spec.
This recipe deploys a plain Go net/http service: no framework, no dependencies, a static binary in a scratch image. It's the minimal case — if you're deploying any stateless HTTP service on Rune, this is the spec shape you start from.
Full source: runestack/rune-examples/go-http.
The app
One JSON endpoint plus a health endpoint. The response includes the instance hostname — that's how you'll see load-balancing work in a minute:
mux.HandleFunc("GET /api/hello", func(w http.ResponseWriter, r *http.Request) {
w.Header().Set("Content-Type", "application/json")
json.NewEncoder(w).Encode(helloResponse{
Message: "hello from go on rune",
Instance: hostname,
})
})
mux.HandleFunc("GET /healthz", func(w http.ResponseWriter, r *http.Request) {
w.WriteHeader(http.StatusOK)
w.Write([]byte("ok"))
})
The Dockerfile compiles a static binary and ships it in scratch — the final image is about 5 MB:
FROM golang:1.23-alpine AS build
WORKDIR /build
COPY go.mod main.go ./
RUN CGO_ENABLED=0 go build -ldflags="-s -w" -o hello .
FROM scratch
COPY --from=build /build/hello /hello
USER 1000
EXPOSE 8080
ENTRYPOINT ["/hello"]
The spec
This is the whole deployment — a service with a port, a probe, and an expose block:
---
service:
name: go-hello
namespace: demo
image: go-hello:dev
scale: 2
ports:
- name: http
port: 8080
health:
liveness:
type: http
path: /healthz
port: 8080
initialDelaySeconds: 2
intervalSeconds: 10
expose:
port: http
host: go-hello.local
Cast it
git clone https://github.com/runestack/rune-examples
cd rune-examples/go-http
docker build -t go-hello:dev ./app
rune lint deploy/app.yaml
rune cast deploy/app.yaml
Watch the VIP balance traffic
scale: 2 gives the service two instances behind one VIP. The instance hostname in the response shows which one answered:
echo "127.0.0.1 go-hello.local" | sudo tee -a /etc/hosts
curl -s http://go-hello.local/api/hello
# {"message":"hello from go on rune","instance":"1a16044cc04d"}
curl -s http://go-hello.local/api/hello
# {"message":"hello from go on rune","instance":"9f2b77c01e88"}
In dev mode the ingress binds :8080, so use http://go-hello.local:8080.
rune scale go-hello 4 -n demo # more replicas, same VIP
rune delete -f deploy/app.yaml # tear down
Adapting
Change the image, the port, and the probe path — that's it. The same spec deploys Rust, Zig, or anything else that compiles to a binary and listens on a port. For a service with runtime configuration, see Deploy a Node.js service; for a multi-service stack with a database, see Deploy Spring Boot + React.