blob: fff9f6e62da14e37747b1e15bb38590578326c8f [file]
#!/bin/bash
#
# Copyright 2016 The Chromium Authors. All rights reserved.
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.
#
# This script is to ease running Predator locally, running its unit tests, and
# deploying Predator to App Engine.
set -e
PROD_APP_ID="predator-for-me"
THIS_SCRIPT_DIR="$( cd "$( dirname "${BASH_SOURCE:-$0}" )" && pwd )"
PREDATOR_DIR="${THIS_SCRIPT_DIR}/.."
PREDATOR_APP_DIR="${THIS_SCRIPT_DIR}/../app"
INFRA_DIR="${PREDATOR_DIR}/../.."
GOOGLE_APP_ENGINE_DIR="${INFRA_DIR}/../google_appengine"
has_realpath="$(which realpath 1>/dev/null 2>/dev/null && echo 0)"
if [[ ${has_realpath} == "0" ]]; then
PREDATOR_DIR="$(realpath ${PREDATOR_DIR})"
PREDATOR_APP_DIR="$(realpath ${PREDATOR_APP_DIR})"
INFRA_DIR="$(realpath ${INFRA_DIR})"
GOOGLE_APP_ENGINE_DIR="$(realpath ${GOOGLE_APP_ENGINE_DIR})"
fi
APP_CFG="${GOOGLE_APP_ENGINE_DIR}/appcfg.py"
DEFAULT_MODULE="${PREDATOR_APP_DIR}/app.yaml"
BACKEND_MODULES="${PREDATOR_APP_DIR}/backend-clusterfuzz.yaml ${PREDATOR_APP_DIR}/backend-fracas.yaml ${PREDATOR_APP_DIR}/backend-cracas.yaml ${PREDATOR_APP_DIR}/backend-uma-sampling-profiler.yaml ${PREDATOR_APP_DIR}/backend-process.yaml"
if [[ -z "${USER}" ]]; then
echo "Cannot identify who is deploying Predator. Please set USER."
exit 1
fi
if [[ -z "${APPENGINE_TMP}" ]]; then
TMP_DIR="${PREDATOR_DIR}/.tmp"
else
TMP_DIR=${APPENGINE_TMP}
fi
print_usage() {
echo
echo "Usage:"
echo "$0 <command>"
echo
echo "Supported commands:"
echo " test Run unittests"
echo " run Run Predator locally"
echo " deploy-prod Deploy predator to $PROD_APP_ID for release"
echo " deploy-test-prod Deploy predator to predator-for-me-test for test"
echo " deploy-staging Deploy predator to predator-for-me-staging for test"
exit 1
}
print_command_for_queue_cron_dispatch() {
app_id=$1
echo
echo "If there is any change to cron.yaml, dispatch.yaml, index.yaml, or"
echo " queue.yaml since last deployment, please run appropriate commands"
echo " below to update them:"
echo " ${APP_CFG} update_cron -A ${app_id} ${PREDATOR_APP_DIR}"
echo " ${APP_CFG} update_dispatch -A ${app_id} ${PREDATOR_APP_DIR}"
echo " ${APP_CFG} update_indexes -A ${app_id} ${PREDATOR_APP_DIR}"
echo " ${APP_CFG} update_queues -A ${app_id} ${PREDATOR_APP_DIR}"
}
run_unittests() {
local predator="appengine/predator"
local coverage_report_parent_dir="${TMP_DIR}/coverage"
mkdir -p ${coverage_report_parent_dir}
python ${INFRA_DIR}/test.py test ${predator} --html-report ${coverage_report_parent_dir}
echo "Code coverage report file://${coverage_report_parent_dir}/${predator}/index.html"
}
run_locally() {
local storage_path="${TMP_DIR}/predator"
local options="--storage_path ${storage_path}"
mkdir -p "${storage_path}"
python ${GOOGLE_APP_ENGINE_DIR}/dev_appserver.py ${options} ${DEFAULT_MODULE} ${BACKEND_MODULES}
}
get_default_host() {
# Gets default host for app_id.
local app_id=$1
# Check if the app_id looks like 'google.com:app-id'.
if [[ ${app_id} == "google.com:"* ]]; then
# Strip 'google.com' in the front of app_id.
local stripped_app_id=${app_id:11}
echo "${stripped_app_id}.googleplex.com"
else
echo "${app_id}.appspot.com"
fi
}
deploy_for_test() {
# Deploy a version for testing, the version name is the same as the user name.
local app_id_to_use=${APP_ID}
local app_env=$1
if [[ -z ${app_id_to_use} ]]; then
if [[ "${app_env}" == "prod" ]]; then
local app_id_to_use="$PROD_APP_ID"
else
local app_id_to_use="predator-for-me-staging"
fi
fi
echo "app id is ${app_id_to_use}"
local new_version="${USER}"
echo "-----------------------------------"
python ${APP_CFG} update -A ${app_id_to_use} --version ${new_version} ${DEFAULT_MODULE} ${BACKEND_MODULES}
echo "-----------------------------------"
print_command_for_queue_cron_dispatch ${app_id_to_use}
echo "-----------------------------------"
echo "Predator was deployed to https://${new_version}-dot-$(get_default_host ${app_id_to_use})/"
}
deploy_for_prod() {
local app_id="$PROD_APP_ID"
# Sync to latest code.
local update_log="${TMP_DIR}/update.log"
echo "Syncing code to tip of tree, logging in ${update_log} ..."
local update="0" #"$(cd ${INFRA_DIR} && git pull >>${update_log} 2>>${update_log} && gclient sync >>${update_log} >>${update_log} 2>>${update_log} && echo $?)"
if [[ "${update}" != "0" ]]; then
echo "Failed to run 'git pull && gclient sync'!"
echo "Please check log at ${update_log}"
return
fi
echo "Code was synced successfully."
# Check uncommitted local changes.
local changed_file_number="$(git status --porcelain | wc -l)"
if [[ "${changed_file_number}" != "0" ]]; then
echo "You have uncommitted local changes!"
echo "Please run 'git status' to check local changes."
return
fi
local new_version="$(git rev-parse --short HEAD)"
# Check committed local changes.
local tot_version="$(git rev-parse --short origin/master)"
if [[ "${new_version}" != "${tot_version}" ]]; then
echo "You have local commits!"
echo "Please run 'git reset ${tot_version}' to reset the local changes."
return
fi
# Check current deployed version.
local current_version=`curl -s https://$(get_default_host ${app_id})/version`
if ! [[ ${current_version} =~ ^[0-9a-fA-F]+$ ]]; then
echo "Failed to retrieve current version of predator from the live app."
echo "Please input the current version, followed by [ENTER]:"
read current_version
fi
echo "Current deployed version is ${current_version}"
echo "Deploying new version '${new_version}'..."
echo
echo "-----------------------------------"
python ${APP_CFG} update -A ${app_id} --version ${new_version} ${DEFAULT_MODULE} ${BACKEND_MODULES}
echo "-----------------------------------"
print_command_for_queue_cron_dispatch ${app_id}
echo "-----------------------------------"
echo
echo "New version '${new_version}' of Predator was deployed to ${app_id}."
app_console_url="https://pantheon.corp.google.com/appengine/versions?project=${app_id}"
local frontend_url="https://${new_version}-dot-$(get_default_host ${app_id})/"
echo "Please checkout the frontend ${frontend_url}, and verify that the new version works as expected."
echo
echo "Then press [ENTER] to confirm that the new version works as expected:"
read unused_var
echo "Now please set the new version ${new_version} as default for the modules default, and backend-* on ${app_console_url}."
echo "Then press [ENTER] to confirm that the new version was set default:"
read unused_var
local change_logs_url="https://chromium.googlesource.com/infra/infra/+log/${current_version}..${new_version}/appengine/predator"
echo "Please email chrome-predator@ with the following:"
echo
echo "Subject: Release: ${app_id} updated to ${new_version}."
echo "Hi all,"
echo
echo "The app ${app_id} was updated from ${current_version} to ${new_version}."
echo "Changelogs: ${change_logs_url}"
echo
echo "If your bug fixes/features are included in the release, please verify on ${app_id} and mark them as verified on http://crbug.com"
echo
echo "Thanks,"
echo "Released by ${USER}@"
}
case "$1" in
test)
run_unittests
;;
run)
run_locally
;;
deploy-prod)
deploy_for_prod
;;
deploy-test-prod)
deploy_for_test "prod"
;;
deploy-staging)
deploy_for_test "dev"
;;
*)
print_usage
;;
esac