This repository has been archived by the owner on Aug 13, 2020. It is now read-only.
-
Notifications
You must be signed in to change notification settings - Fork 15
/
set_default.sh
executable file
·99 lines (79 loc) · 3.78 KB
/
set_default.sh
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
#!/bin/sh -e
# Set the deploy corresponding to the latest commit as default
: ${PROJECT:=khan-academy}
: ${DOCKER:=}
die() {
echo "FATAL ERROR: $@"
exit 1
}
if [ -n "$DOCKER" ]; then
APP_YAML=app-flex.yaml
else
APP_YAML=app-standard.yaml
fi
# Calculate the version name for the latest commit
# Format is: YYMMDD-HHMM-RRRRRRRRRRRR
#
# Keep this in sync with VERSION in deploy.sh
VERSION=`git log -n1 --format="format:%H %ct" | perl -ne '$ENV{TZ} = "US/Pacific"; ($rev, $t) = split; @lt = localtime($t); printf "%02d%02d%02d-%02d%02d-%.12s\n", $lt[5] % 100, $lt[4] + 1, $lt[3], $lt[2], $lt[1], $rev'`
MODULE=`sed -ne 's/\(module\|service\): //p' "$APP_YAML"`
echo "Setting ${VERSION} as default on module ${MODULE}..."
NON_DEFAULT_HOSTNAME="https://${VERSION}-dot-${MODULE}-dot-${PROJECT}.appspot.com"
HEALTHCHECK_URL="${NON_DEFAULT_HOSTNAME}/_ah/health"
curl -s -I "${HEALTHCHECK_URL}" | head -n1 | grep -q -w '200' \
|| die "Server at ${NON_DEFAULT_HOSTNAME} not healthy"
# TODO(jlfwong): Prime the new version of the servers before we set default. We
# want them to load their caches with the most frequently used JS packages from
# khanacademy.org.
# Do a simplistic priming by calling the priming URL 100 times in
# parallel. We wait for the requests to finish in hopes that that
# autoscaler has done its work by then.
PRIME_URL="${NON_DEFAULT_HOSTNAME}/prime"
for i in `seq 100`; do
curl -s ${PRIME_URL} &
done
wait
gcloud -q --verbosity info app services set-traffic \
--project "$PROJECT" --splits "$VERSION"=1 "$MODULE"
# Ensure that the version flipped
DEFAULT_HOSTNAME="https://${MODULE}-dot-${PROJECT}.appspot.com/_api/version"
# Wait for the new version to become accessible, waiting up a minute(ish).
for i in `seq 10`; do
LIVE_VERSION=`curl -s ${DEFAULT_HOSTNAME}`
[ "${LIVE_VERSION}" = "${VERSION}" ] && break
[ $i -eq 10 ] && die "Expected live version to be ${VERSION}, but saw ${LIVE_VERSION}."
sleep "$i"
done
# TODO(csilvers): git tag the release.
echo "Default set, now deleting old versions."
# TODO(csilvers): make this more sophisticated, a la audit_gae_versions.py:
# 1) support 'good' and 'bad' versions via git tag.
# 2) prefer to keep versions that have a long uptime.
# 3) always keep the most recent deploys.
# This lists the module-name, version, and traffic-split. First we
# grep to remove versions that are getting traffic (so the candidates
# to delete will include only versions getting no traffic). Then we
# grep again to extract out the version-names.
VERSIONS=`gcloud app versions list --project "$PROJECT" --service react-render | fgrep -w 0.00 | grep -o '[0-9][0-9][0-9][0-9][0-9][0-9]-[0-9][0-9][0-9][0-9]-[0-9a-fA-F]*'`
# This keeps the most recent 5 versions (that are not getting any traffic).
VERSIONS_TO_DELETE=`echo "$VERSIONS" | sort -r | tail -n+6`
if [ -n "$VERSIONS_TO_DELETE" ]; then
echo "Deleting old versions: $VERSIONS_TO_DELETE"
gcloud -q --verbosity info app versions delete \
--project "$PROJECT" --service react-render $VERSIONS_TO_DELETE
fi
# And we'll stop the recent versions that are not getting any traffic,
# so we're not charged for them, except the most recent, which we leave
# running in order to allow rollback in case there's a problem with the
# newly deployed version.
# NOTE: this will fail if the version was deployed using appengine
# standard instead of appengine flex.
# TODO(csilvers): Notice what kind the version is, and don't bother
# trying to stop standard-versions, insteaad of trying and failing.
VERSIONS_TO_STOP=`echo "$VERSIONS" | sort -r | tail -n+2 | head -n4`
if [ -n "$VERSIONS_TO_STOP" ]; then
echo "Stopping old versions: $VERSIONS_TO_STOP"
gcloud -q --verbosity info app versions stop \
--project "$PROJECT" --service react-render $VERSIONS_TO_STOP || true
fi
echo "DONE"