diff --git a/.gitignore b/.gitignore index 92da579..2d6a65b 100644 --- a/.gitignore +++ b/.gitignore @@ -32,6 +32,7 @@ go.work.sum *.key build/ bins/ +**/tmp/ # Claude Code settings .claude/ diff --git a/Makefile b/Makefile index 4e5a870..e320b73 100644 --- a/Makefile +++ b/Makefile @@ -144,3 +144,33 @@ helm-test: helm-example: cd charts; helm template example ./s2s-proxy -f ./s2s-proxy/values.example.yaml > s2s-proxy/example.yaml @echo "Example written to charts/s2s-proxy/example.yaml" + +# Local development environment +DEVELOP_ENV_FILE = develop/docker-compose/develop.env +DOCKER_COMPOSE_FILE ?= ./develop/docker-compose/develop.docker-compose.yaml +DOCKER_COMPOSE = docker compose --file $(DOCKER_COMPOSE_FILE) --env-file $(DEVELOP_ENV_FILE) + +PROXY_LEFT_CONFIG_TMPL = develop/docker-compose/develop.proxy-left.tmpl.yaml +PROXY_RIGHT_CONFIG_TMPL = develop/docker-compose/develop.proxy-right.tmpl.yaml +PROXY_LEFT_CONFIG = develop/docker-compose/tmp/develop.proxy-left.yaml +PROXY_RIGHT_CONFIG = develop/docker-compose/tmp/develop.proxy-right.yaml + +.PHONY: generate-configs +generate-configs: + mkdir -p develop/docker-compose/tmp + set -a && . $(DEVELOP_ENV_FILE) && set +a && \ + envsubst < $(PROXY_LEFT_CONFIG_TMPL) > $(PROXY_LEFT_CONFIG) && \ + envsubst < $(PROXY_RIGHT_CONFIG_TMPL) > $(PROXY_RIGHT_CONFIG) + +.PHONY: start-dependencies +start-dependencies: generate-configs + $(DOCKER_COMPOSE) up --detach --build --wait --wait-timeout 120 + @echo >&2 'Dependencies ready!' + +.PHONY: stop-dependencies +stop-dependencies: + $(DOCKER_COMPOSE) down --timeout 60 + +.PHONY: nuke-dependencies +nuke-dependencies: + $(DOCKER_COMPOSE) down --timeout 60 --volumes --remove-orphans diff --git a/develop/README.md b/develop/README.md index 28548af..194f2dc 100644 --- a/develop/README.md +++ b/develop/README.md @@ -10,7 +10,20 @@ # How-Tos -## Setup a local proxy pair with two Temporal clusters +## Setup a local proxy pair with two Temporal clusters (docker compose) + +### Steps + +1. To start the development environment: `make start-dependencies` +2. Done! Run tests against these services. The default ports are specified in an [environment file](docker-compose/develop.env) +3. To stop the development environment: `make stop-dependencies` + +### Logs + +- To view container logs, run `docker logs `. For example `docker logs docker-compose-smoke-test-1`. +- To find container name, run `docker ps -a`, or grep for specific compose service name, e.g. `docker ps -a | grep smoke-test` + +## Setup a local proxy pair with two Temporal clusters (manual) ### Ports | Service | port | Connected to | diff --git a/develop/docker-compose/develop.docker-compose.yaml b/develop/docker-compose/develop.docker-compose.yaml new file mode 100644 index 0000000..38bf814 --- /dev/null +++ b/develop/docker-compose/develop.docker-compose.yaml @@ -0,0 +1,138 @@ +x-volumes: &x-volumes + - ./..:/etc/develop:ro + +services: + temporal-left: + image: temporalio/temporal:1.5.0 + command: + - server + - start-dev + - --port + - "${TEMPORAL_INTERNAL_PORT}" + - --ip + - "0.0.0.0" + - --headless + - --namespace + - default + - --log-level + - warn + ports: + - "${TEMPORAL_LEFT_EXTERNAL_PORT}:${TEMPORAL_INTERNAL_PORT}" + networks: + - develop + healthcheck: + test: + - CMD + - temporal + - operator + - cluster + - health + - --address + - "localhost:${TEMPORAL_INTERNAL_PORT}" + interval: 5s + timeout: 5s + retries: 30 + start_period: 5s + + temporal-right: + image: temporalio/temporal:1.5.0 + command: + - server + - start-dev + - --port + - "${TEMPORAL_INTERNAL_PORT}" + - --ip + - "0.0.0.0" + - --headless + - --namespace + - default + - --log-level + - warn + ports: + - "${TEMPORAL_RIGHT_EXTERNAL_PORT}:${TEMPORAL_INTERNAL_PORT}" + networks: + - develop + healthcheck: + test: + - CMD + - temporal + - operator + - cluster + - health + - --address + - "localhost:${TEMPORAL_INTERNAL_PORT}" + interval: 5s + timeout: 5s + retries: 30 + start_period: 5s + + proxy-right: + build: + context: ../.. + dockerfile: Dockerfile + environment: + CONFIG_YML: /etc/develop/docker-compose/tmp/develop.proxy-right.yaml + volumes: *x-volumes + ports: + - "${PROXY_RIGHT_EXTERNAL_PORT}:${PROXY_RIGHT_INTERNAL_PORT}" + networks: + - develop + depends_on: + temporal-right: + condition: service_healthy + healthcheck: # TODO: Replace with healthcheck endpoint. + test: + - CMD-SHELL + - "wget -q -O /dev/null -T 3 http://localhost:6060/debug/pprof/ || exit 1" + interval: 5s + timeout: 5s + retries: 30 + start_period: 10s + + proxy-left: + build: + context: ../.. + dockerfile: Dockerfile + environment: + CONFIG_YML: /etc/develop/docker-compose/tmp/develop.proxy-left.yaml + volumes: *x-volumes + ports: + - "${PROXY_LEFT_EXTERNAL_PORT}:${PROXY_LEFT_INTERNAL_PORT}" + networks: + - develop + depends_on: + temporal-left: + condition: service_healthy + proxy-right: + condition: service_healthy + healthcheck: # TODO: Replace with healthcheck endpoint. + test: + - CMD-SHELL + - "wget -q -O /dev/null -T 3 http://localhost:6060/debug/pprof/ || exit 1" + interval: 5s + timeout: 5s + retries: 30 + start_period: 10s + + smoke-test: + image: temporalio/temporal:1.5.0 + entrypoint: /bin/sh + networks: + - develop + depends_on: + proxy-left: + condition: service_healthy + proxy-right: + condition: service_healthy + volumes: *x-volumes + environment: + TEMPORAL_LEFT_INBOUND: "temporal-left:${TEMPORAL_INTERNAL_PORT}" + TEMPORAL_RIGHT_INBOUND: "temporal-right:${TEMPORAL_INTERNAL_PORT}" + PROXY_LEFT_OUTBOUND: "proxy-left:${PROXY_LEFT_INTERNAL_PORT}" + PROXY_RIGHT_OUTBOUND: "proxy-right:${PROXY_RIGHT_INTERNAL_PORT}" + command: + - /etc/develop/docker-compose/smoke-test.sh + +networks: + develop: + driver: bridge diff --git a/develop/docker-compose/develop.env b/develop/docker-compose/develop.env new file mode 100644 index 0000000..4d2655a --- /dev/null +++ b/develop/docker-compose/develop.env @@ -0,0 +1,11 @@ +# External Ports (exposed via localhost) +TEMPORAL_LEFT_EXTERNAL_PORT=4000 +TEMPORAL_RIGHT_EXTERNAL_PORT=5000 +PROXY_LEFT_EXTERNAL_PORT=4001 +PROXY_RIGHT_EXTERNAL_PORT=5001 + +# Internal Ports (exposed on containers in docker network) +TEMPORAL_INTERNAL_PORT=7233 +PROXY_LEFT_INTERNAL_PORT=6233 +PROXY_RIGHT_INTERNAL_PORT=6333 +PROXY_MUX_INTERNAL_PORT=6334 diff --git a/develop/docker-compose/develop.proxy-left.tmpl.yaml b/develop/docker-compose/develop.proxy-left.tmpl.yaml new file mode 100644 index 0000000..c235578 --- /dev/null +++ b/develop/docker-compose/develop.proxy-left.tmpl.yaml @@ -0,0 +1,15 @@ +clusterConnections: + - name: "cluster-left" + local: + connectionType: "tcp" + tcpClient: + address: "temporal-left:${TEMPORAL_INTERNAL_PORT}" + tcpServer: + address: "0.0.0.0:${PROXY_LEFT_INTERNAL_PORT}" + remote: + connectionType: "mux-client" + muxCount: 1 + muxAddressInfo: + address: "proxy-right:${PROXY_MUX_INTERNAL_PORT}" +profiling: + pprofAddress: "0.0.0.0:6060" diff --git a/develop/docker-compose/develop.proxy-right.tmpl.yaml b/develop/docker-compose/develop.proxy-right.tmpl.yaml new file mode 100644 index 0000000..d723078 --- /dev/null +++ b/develop/docker-compose/develop.proxy-right.tmpl.yaml @@ -0,0 +1,15 @@ +clusterConnections: + - name: "cluster-right" + local: + connectionType: "tcp" + tcpClient: + address: "temporal-right:${TEMPORAL_INTERNAL_PORT}" + tcpServer: + address: "0.0.0.0:${PROXY_RIGHT_INTERNAL_PORT}" + remote: + connectionType: "mux-server" + muxCount: 1 + muxAddressInfo: + address: "0.0.0.0:${PROXY_MUX_INTERNAL_PORT}" +profiling: + pprofAddress: "0.0.0.0:6060" diff --git a/develop/docker-compose/smoke-test.sh b/develop/docker-compose/smoke-test.sh new file mode 100755 index 0000000..f94ef21 --- /dev/null +++ b/develop/docker-compose/smoke-test.sh @@ -0,0 +1,25 @@ +#!/bin/sh +set -e + +sleep 20 # TODO: remove after addition of reliable s2s-proxy healthcheck endpoint. + +# connectivity (also covered by docker-compose healthcheck) +temporal operator cluster health --address "$TEMPORAL_LEFT_INBOUND" +temporal operator cluster health --address "$TEMPORAL_RIGHT_INBOUND" + +# cross-server proxy-left routes to temporal-right +NS_L="smoketest-left-$$" +temporal operator namespace create "$NS_L" --retention 24h --address "$TEMPORAL_RIGHT_INBOUND" +temporal operator namespace describe "$NS_L" --address "$PROXY_LEFT_OUTBOUND" + +# cross-server proxy-right routes to temporal-left +NS_R="smoketest-right-$$" +temporal operator namespace create "$NS_R" --retention 24h --address "$TEMPORAL_LEFT_INBOUND" +temporal operator namespace describe "$NS_R" --address "$PROXY_RIGHT_OUTBOUND" + +# outbound route is routed through each proxy +# TODO: for strong validation - after migrating off of temporal cli dev server, we can override and check the cluster name (currently both are named 'active') +temporal operator cluster describe --address "$PROXY_LEFT_OUTBOUND" +temporal operator cluster describe --address "$PROXY_RIGHT_OUTBOUND" + +echo "smoke tests succeeded. 🚬"