Something went wrong. Try again.
Backend environment for match hosting for lance.blue
Something went wrong. Try again.
Shell
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125#!/usr/bin/env bash# Push the match image and point infra at it.## ./scripts/deploy.sh## Runs the build and push, then writes the tag it was named after into infra's# releases.auto.tfvars.json. The result is one uncommitted infra diff; applying# it is the deploy, and this script does not apply anything.## The headquarters repo has the same script for its two artifacts. This one# differs in two ways, both because arena ships a single image: the release id# is the full image tag rather than the build ref, and there is no separate# fail-fast build - scripts/push.sh builds before it touches the registry, and# with one artifact there is no half-finished state for a second build to# protect against.## INFRA_DIR overrides where the infra checkout is; the default is the sibling# directory, which is how the repos are laid out.set -euo pipefail
ROOT="$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)"cd "$ROOT"
# Everything below fails before anything is built. A wasted image build is# fifteen minutes, and every one of these is knowable up front.
: "${AWS_PROFILE:?set AWS_PROFILE; default credentials are almost never the right account}"
# The variable being set says nothing about the session behind it. Ask STS# now, so an expired login fails here instead of after the image build, when# the push is the first thing to touch AWS.if ! aws sts get-caller-identity --query Account --output text >/dev/null; then echo "deploy: no working AWS session for profile $AWS_PROFILE; log in again" >&2 exit 1fi
command -v jq >/dev/null || { echo "deploy: jq is not installed; it writes releases.auto.tfvars.json" >&2 exit 1}
if ! infra="$(cd "${INFRA_DIR:-../infra}" 2>/dev/null && pwd)"; then echo "deploy: no infra checkout at ${INFRA_DIR:-../infra}; set INFRA_DIR" >&2 exit 1fitfvars="$infra/envs/lance.blue/releases.auto.tfvars.json"
[ -f "$tfvars" ] || { echo "deploy: $infra has no envs/lance.blue/releases.auto.tfvars.json" >&2 exit 1}
# A dirty tree gets a -dirty ref, which names a build nobody else can rebuild.# push.sh refuses to push one; catching it here saves the build as well.if [ -n "$(git status --porcelain)" ]; then echo "deploy: arena has uncommitted changes; commit or stash them" >&2 exit 1fi
# Deploying off a branch is fine: the branch name is part of the image tag, so# what is serving is legible from the tag alone. main is the one branch with a# rule, because a main build is meant to be exactly what the remote has. Ask# the remote rather than trusting whatever the last fetch left behind.branch=$(git rev-parse --abbrev-ref HEAD)if [ "$branch" = main ]; then git fetch --quiet origin main if [ "$(git rev-parse HEAD)" != "$(git rev-parse origin/main)" ]; then echo "deploy: on main, but HEAD is not origin/main; pull or push first" >&2 exit 1 fifi
# Nothing here cares whether infra is dirty. arena and headquarters each write# their own keys in the same file, so the second one to deploy would always# find the first one's bump sitting there uncommitted. infra's own deploy.sh is# where a clean tree is required.
# versions.env is what build.sh and push.sh name the image from, so sourcing it# here is how this script knows what tag to expect back. It computes BUILD_REF# from git, which the guards above have already pinned down.# shellcheck source=../versions.env. "$ROOT/versions.env"
echo "deploy: $IMAGE_TAG -> $AWS_PROFILE"echo
# What the tfvars file gets is read back out of the push rather than assumed,# so a change to how the image is named fails here instead of pointing# production at a tag that does not exist.log="$(mktemp)"trap 'rm -f "$log" "$tfvars.new"' EXIT
IMAGE_TAG="$IMAGE_TAG" BUILD_REF="$BUILD_REF" scripts/push.sh 2>&1 | tee "$log"
# "pushed <registry>/arena:<tag>", and push.sh now emits exactly one such line.# The `latest` rejection below is kept anyway: it is the check that would catch# a moving tag being pushed again, which is the mistake worth failing on.line="$(grep -E '^pushed ' "$log" | tail -n 1 || true)"pushed="${line##*:}"
if [ -z "$pushed" ] || [ "$pushed" = latest ]; then echo >&2 echo "deploy: could not read an immutable tag out of the push" >&2 echo "deploy: $tfvars not touched" >&2 exit 1fi
if [ "$pushed" != "$IMAGE_TAG" ]; then echo >&2 echo "deploy: pushed $pushed, expected $IMAGE_TAG" >&2 echo "deploy: $tfvars not touched" >&2 exit 1fi
# Written beside the file it replaces so the move is atomic; a jq that fails# halfway leaves the current release id in place.jq --arg tag "$IMAGE_TAG" '.releases.arena = $tag' "$tfvars" >"$tfvars.new"mv "$tfvars.new" "$tfvars"
echoecho "Wrote releases.arena = $IMAGE_TAG"echo "To serve it:"echo " tofu -chdir=$infra/envs/lance.blue plan -out=lance.blue.tfplan"echo " tofu -chdir=$infra/envs/lance.blue apply lance.blue.tfplan"