debug output [infra] #746
15
Makefile
15
Makefile
@@ -34,6 +34,9 @@
|
|||||||
update \
|
update \
|
||||||
update-backend \
|
update-backend \
|
||||||
update-frontend \
|
update-frontend \
|
||||||
|
bump-version \
|
||||||
|
prepare-release \
|
||||||
|
tag-release \
|
||||||
test \
|
test \
|
||||||
test-backend \
|
test-backend \
|
||||||
test-frontend \
|
test-frontend \
|
||||||
@@ -125,6 +128,9 @@ help:
|
|||||||
@echo " make update Update all dependencies (Go + Flutter)"
|
@echo " make update Update all dependencies (Go + Flutter)"
|
||||||
@echo " make update-backend Update Go dependencies only"
|
@echo " make update-backend Update Go dependencies only"
|
||||||
@echo " make update-frontend Update Flutter dependencies only"
|
@echo " make update-frontend Update Flutter dependencies only"
|
||||||
|
@echo " make bump-version Bump ./version and frontend/pweb/pubspec.yaml"
|
||||||
|
@echo " make prepare-release Bump versions and create the release-prep commit for a PR"
|
||||||
|
@echo " make tag-release Create the local release tag from main after the PR is merged"
|
||||||
@echo " make test Run all tests (backend + frontend)"
|
@echo " make test Run all tests (backend + frontend)"
|
||||||
@echo " make test-backend Run Go backend tests only"
|
@echo " make test-backend Run Go backend tests only"
|
||||||
@echo " make test-frontend Run Flutter tests only"
|
@echo " make test-frontend Run Flutter tests only"
|
||||||
@@ -135,6 +141,15 @@ help:
|
|||||||
@echo " make logs SERVICE=dev-ledger"
|
@echo " make logs SERVICE=dev-ledger"
|
||||||
@echo " make rebuild SERVICE=dev-ledger"
|
@echo " make rebuild SERVICE=dev-ledger"
|
||||||
|
|
||||||
|
bump-version:
|
||||||
|
@./ci/scripts/common/bump_version.sh
|
||||||
|
|
||||||
|
prepare-release:
|
||||||
|
@./ci/scripts/common/release.sh
|
||||||
|
|
||||||
|
tag-release:
|
||||||
|
@./ci/scripts/common/tag_release.sh
|
||||||
|
|
||||||
# First-time initialization
|
# First-time initialization
|
||||||
init:
|
init:
|
||||||
@echo "$(GREEN)Initializing development environment...$(NC)"
|
@echo "$(GREEN)Initializing development environment...$(NC)"
|
||||||
|
|||||||
14
README.md
14
README.md
@@ -116,7 +116,19 @@ make test-frontend # Run Flutter tests only
|
|||||||
- Tags matching `v*` trigger a full production rebuild and deployment from that exact tagged revision.
|
- Tags matching `v*` trigger a full production rebuild and deployment from that exact tagged revision.
|
||||||
- Infrastructure workflows for `db` and `nats` remain separately controlled.
|
- Infrastructure workflows for `db` and `nats` remain separately controlled.
|
||||||
|
|
||||||
Example production release:
|
Recommended release preparation:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
./ci/scripts/common/release.sh
|
||||||
|
# push your branch and open a PR
|
||||||
|
# merge the PR to main
|
||||||
|
git checkout main && git pull
|
||||||
|
# verify the dev deployment from main
|
||||||
|
./ci/scripts/common/tag_release.sh
|
||||||
|
git push origin v$(cat version)
|
||||||
|
```
|
||||||
|
|
||||||
|
Manual production release from an already-prepared commit:
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
git tag -a v1.4.0 <commit-sha>
|
git tag -a v1.4.0 <commit-sha>
|
||||||
|
|||||||
@@ -14,15 +14,28 @@ SSH_OPTS=(
|
|||||||
-o StrictHostKeyChecking=no
|
-o StrictHostKeyChecking=no
|
||||||
-o UserKnownHostsFile=/dev/null
|
-o UserKnownHostsFile=/dev/null
|
||||||
-o LogLevel=ERROR
|
-o LogLevel=ERROR
|
||||||
-q
|
|
||||||
)
|
)
|
||||||
if [[ "${DEBUG_DEPLOY:-0}" = "1" ]]; then
|
if [[ "${DEBUG_DEPLOY:-0}" = "1" ]]; then
|
||||||
SSH_OPTS=("${SSH_OPTS[@]/-q/}" -vv)
|
SSH_OPTS+=(-vv)
|
||||||
fi
|
fi
|
||||||
|
|
||||||
|
printf '[bootstrap-shared-network] target=%s network=%s\n' "$REMOTE_TARGET" "$DOCKER_SHARED_NETWORK" >&2
|
||||||
|
|
||||||
|
set +e
|
||||||
|
ssh_output="$(
|
||||||
ssh "${SSH_OPTS[@]}" "$REMOTE_TARGET" \
|
ssh "${SSH_OPTS[@]}" "$REMOTE_TARGET" \
|
||||||
DOCKER_SHARED_NETWORK="$DOCKER_SHARED_NETWORK" bash -s <<'EOSSH'
|
DOCKER_SHARED_NETWORK="$DOCKER_SHARED_NETWORK" bash -s 2>&1 <<'EOSSH'
|
||||||
set -euo pipefail
|
set -euo pipefail
|
||||||
docker network inspect "$DOCKER_SHARED_NETWORK" >/dev/null 2>&1 || \
|
docker network inspect "$DOCKER_SHARED_NETWORK" >/dev/null 2>&1 || \
|
||||||
docker network create "$DOCKER_SHARED_NETWORK"
|
docker network create "$DOCKER_SHARED_NETWORK"
|
||||||
EOSSH
|
EOSSH
|
||||||
|
)"
|
||||||
|
ssh_status=$?
|
||||||
|
set -e
|
||||||
|
|
||||||
|
if [[ $ssh_status -ne 0 ]]; then
|
||||||
|
[[ -n "$ssh_output" ]] && printf '%s\n' "$ssh_output" >&2
|
||||||
|
exit "$ssh_status"
|
||||||
|
fi
|
||||||
|
|
||||||
|
[[ -n "$ssh_output" ]] && printf '%s\n' "$ssh_output"
|
||||||
|
|||||||
@@ -1,34 +1,89 @@
|
|||||||
# /bin/bash
|
#!/usr/bin/env bash
|
||||||
|
|
||||||
echo "===================================="
|
|
||||||
echo "Incrementing build version..."
|
|
||||||
echo "===================================="
|
|
||||||
VERSION_FILE=./version
|
|
||||||
|
|
||||||
NEW_VERSION=$(cat $VERSION_FILE | awk -F. -v OFS=. 'NF==1{print ++$NF}; NF>1{$NF=sprintf("%0*d", length($NF), ($NF+1)); print}')
|
|
||||||
echo $NEW_VERSION > $VERSION_FILE
|
|
||||||
|
|
||||||
echo "New version is "$NEW_VERSION
|
|
||||||
|
|
||||||
echo "===================================="
|
|
||||||
echo "Bumping client version..."
|
|
||||||
echo "===================================="
|
|
||||||
FILE="./frontend/mweb/pubspec.yaml"
|
|
||||||
if sed --version >/dev/null 2>&1; then
|
|
||||||
# GNU sed
|
|
||||||
sed -i "s/^version: .*/version: ${NEW_VERSION}+1/" "$FILE"
|
|
||||||
else
|
|
||||||
# BSD/macOS sed
|
|
||||||
sed -i '' -e "s/^version: .*/version: ${NEW_VERSION}+1/" "$FILE"
|
|
||||||
fi
|
|
||||||
|
|
||||||
set -euo pipefail
|
set -euo pipefail
|
||||||
|
|
||||||
# update version file(s) here
|
REPO_ROOT="$(cd "$(dirname "$0")/../../.." && pwd)"
|
||||||
# e.g.: ./ci/scripts/common/update_version_file.sh
|
cd "${REPO_ROOT}"
|
||||||
|
|
||||||
if ! git diff --quiet; then
|
VERSION_FILE="./version"
|
||||||
git add .
|
PUBSPEC_FILE="./frontend/pweb/pubspec.yaml"
|
||||||
git commit -m "chore: bump build version [skip ci]"
|
if [[ ! -f "${PUBSPEC_FILE}" && -f "./frontend/pweb/pubspec.yml" ]]; then
|
||||||
git push origin HEAD:main
|
PUBSPEC_FILE="./frontend/pweb/pubspec.yml"
|
||||||
fi
|
fi
|
||||||
|
|
||||||
|
if [[ ! -f "${VERSION_FILE}" ]]; then
|
||||||
|
echo "[bump-version] missing ${VERSION_FILE}" >&2
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
if [[ ! -f "${PUBSPEC_FILE}" ]]; then
|
||||||
|
echo "[bump-version] missing frontend pubspec file" >&2
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
current_version="$(tr -d '[:space:]' < "${VERSION_FILE}")"
|
||||||
|
if [[ -z "${current_version}" ]]; then
|
||||||
|
echo "[bump-version] ${VERSION_FILE} is empty" >&2
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
new_version="$(printf '%s\n' "${current_version}" | awk -F. -v OFS=. '
|
||||||
|
NF == 1 { print ++$NF; next }
|
||||||
|
{ $NF = sprintf("%0*d", length($NF), ($NF + 1)); print }
|
||||||
|
')"
|
||||||
|
|
||||||
|
current_pubspec_version="$(
|
||||||
|
awk '/^version:[[:space:]]*/ {
|
||||||
|
sub(/^version:[[:space:]]*/, "", $0)
|
||||||
|
print
|
||||||
|
exit
|
||||||
|
}' "${PUBSPEC_FILE}"
|
||||||
|
)"
|
||||||
|
|
||||||
|
if [[ -z "${current_pubspec_version}" ]]; then
|
||||||
|
echo "[bump-version] could not find version line in ${PUBSPEC_FILE}" >&2
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
build_number=0
|
||||||
|
if [[ "${current_pubspec_version}" == *+* ]]; then
|
||||||
|
build_number="${current_pubspec_version##*+}"
|
||||||
|
fi
|
||||||
|
|
||||||
|
if [[ ! "${build_number}" =~ ^[0-9]+$ ]]; then
|
||||||
|
echo "[bump-version] invalid build number in ${PUBSPEC_FILE}: ${current_pubspec_version}" >&2
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
next_build_number=$((build_number + 1))
|
||||||
|
|
||||||
|
version_tmp="${VERSION_FILE}.tmp.$$"
|
||||||
|
pubspec_tmp="${PUBSPEC_FILE}.tmp.$$"
|
||||||
|
cleanup() {
|
||||||
|
rm -f "${version_tmp}" "${pubspec_tmp}"
|
||||||
|
}
|
||||||
|
trap cleanup EXIT INT TERM
|
||||||
|
|
||||||
|
printf '%s\n' "${new_version}" > "${version_tmp}"
|
||||||
|
awk -v version="${new_version}" -v build="${next_build_number}" '
|
||||||
|
BEGIN { updated = 0 }
|
||||||
|
/^version:[[:space:]]*/ && !updated {
|
||||||
|
print "version: " version "+" build
|
||||||
|
updated = 1
|
||||||
|
next
|
||||||
|
}
|
||||||
|
{ print }
|
||||||
|
END {
|
||||||
|
if (!updated) {
|
||||||
|
exit 1
|
||||||
|
}
|
||||||
|
}
|
||||||
|
' "${PUBSPEC_FILE}" > "${pubspec_tmp}"
|
||||||
|
|
||||||
|
mv "${version_tmp}" "${VERSION_FILE}"
|
||||||
|
mv "${pubspec_tmp}" "${PUBSPEC_FILE}"
|
||||||
|
|
||||||
|
echo "===================================="
|
||||||
|
echo "Release version bumped"
|
||||||
|
echo "===================================="
|
||||||
|
echo "version: ${current_version} -> ${new_version}"
|
||||||
|
echo "${PUBSPEC_FILE}: ${current_pubspec_version} -> ${new_version}+${next_build_number}"
|
||||||
|
|||||||
36
ci/scripts/common/release.sh
Executable file
36
ci/scripts/common/release.sh
Executable file
@@ -0,0 +1,36 @@
|
|||||||
|
#!/usr/bin/env bash
|
||||||
|
set -euo pipefail
|
||||||
|
|
||||||
|
REPO_ROOT="$(cd "$(dirname "$0")/../../.." && pwd)"
|
||||||
|
cd "${REPO_ROOT}"
|
||||||
|
|
||||||
|
VERSION_FILE="./version"
|
||||||
|
PUBSPEC_FILE="./frontend/pweb/pubspec.yaml"
|
||||||
|
if [[ ! -f "${PUBSPEC_FILE}" && -f "./frontend/pweb/pubspec.yml" ]]; then
|
||||||
|
PUBSPEC_FILE="./frontend/pweb/pubspec.yml"
|
||||||
|
fi
|
||||||
|
|
||||||
|
require_clean_worktree() {
|
||||||
|
if ! git diff --quiet --ignore-submodules -- || ! git diff --cached --quiet --ignore-submodules --; then
|
||||||
|
echo "[release] working tree is not clean; commit or stash changes before preparing a release" >&2
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
require_clean_worktree
|
||||||
|
|
||||||
|
"${REPO_ROOT}/ci/scripts/common/bump_version.sh"
|
||||||
|
|
||||||
|
new_version="$(tr -d '[:space:]' < "${VERSION_FILE}")"
|
||||||
|
release_tag="v${new_version}"
|
||||||
|
|
||||||
|
git add "${VERSION_FILE}" "${PUBSPEC_FILE}"
|
||||||
|
git commit -m "chore: prepare release ${release_tag}"
|
||||||
|
|
||||||
|
echo
|
||||||
|
echo "Prepared release commit for ${release_tag}"
|
||||||
|
echo "Next steps:"
|
||||||
|
echo " 1. push this branch and open a PR"
|
||||||
|
echo " 2. merge the PR to main"
|
||||||
|
echo " 3. verify the dev deployment from main"
|
||||||
|
echo " 4. checkout main and run ./ci/scripts/common/tag_release.sh"
|
||||||
45
ci/scripts/common/tag_release.sh
Executable file
45
ci/scripts/common/tag_release.sh
Executable file
@@ -0,0 +1,45 @@
|
|||||||
|
#!/usr/bin/env bash
|
||||||
|
set -euo pipefail
|
||||||
|
|
||||||
|
REPO_ROOT="$(cd "$(dirname "$0")/../../.." && pwd)"
|
||||||
|
cd "${REPO_ROOT}"
|
||||||
|
|
||||||
|
VERSION_FILE="./version"
|
||||||
|
|
||||||
|
require_clean_worktree() {
|
||||||
|
if ! git diff --quiet --ignore-submodules -- || ! git diff --cached --quiet --ignore-submodules --; then
|
||||||
|
echo "[tag-release] working tree is not clean; commit or stash changes before tagging a release" >&2
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
require_clean_worktree
|
||||||
|
|
||||||
|
current_branch="$(git symbolic-ref --short -q HEAD || true)"
|
||||||
|
if [[ -n "${current_branch}" && "${current_branch}" != "main" ]]; then
|
||||||
|
echo "[tag-release] checkout main before creating the release tag" >&2
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
if [[ ! -f "${VERSION_FILE}" ]]; then
|
||||||
|
echo "[tag-release] missing ${VERSION_FILE}" >&2
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
release_version="$(tr -d '[:space:]' < "${VERSION_FILE}")"
|
||||||
|
if [[ -z "${release_version}" ]]; then
|
||||||
|
echo "[tag-release] ${VERSION_FILE} is empty" >&2
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
release_tag="v${release_version}"
|
||||||
|
if git rev-parse -q --verify "refs/tags/${release_tag}" >/dev/null; then
|
||||||
|
echo "[tag-release] tag ${release_tag} already exists locally" >&2
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
git tag -a "${release_tag}" -m "Release ${release_tag}"
|
||||||
|
|
||||||
|
echo "Created release tag ${release_tag} at $(git rev-parse --short HEAD)"
|
||||||
|
echo "Next step:"
|
||||||
|
echo " git push origin ${release_tag}"
|
||||||
Reference in New Issue
Block a user