2015-07-21 02:32:42 +03:00
|
|
|
#!/usr/bin/env bash
|
2014-09-09 10:06:03 +04:00
|
|
|
#
|
|
|
|
# Run all etcd tests
|
|
|
|
# ./test
|
|
|
|
# ./test -v
|
|
|
|
#
|
2018-03-13 03:03:43 +03:00
|
|
|
#
|
|
|
|
# Run specified test pass
|
|
|
|
#
|
|
|
|
# $ PASSES=unit ./test
|
|
|
|
# $ PASSES=integration ./test
|
|
|
|
#
|
|
|
|
#
|
2014-09-09 10:06:03 +04:00
|
|
|
# Run tests for one package
|
2018-03-13 03:03:43 +03:00
|
|
|
# Each pass has different default timeout, if you just run tests in one package or 1 test case then you can set TIMEOUT
|
|
|
|
# flag for different expectation
|
|
|
|
#
|
|
|
|
# $ PASSES=unit PKG=./wal TIMEOUT=1m ./test
|
|
|
|
# $ PASSES=integration PKG=client/integration TIMEOUT=1m ./test
|
|
|
|
#
|
|
|
|
#
|
|
|
|
# Run specified unit tests in one package
|
|
|
|
# To run all the tests with prefix of "TestNew", set "TESTCASE=TestNew ";
|
|
|
|
# to run only "TestNew", set "TESTCASE="\bTestNew\b""
|
|
|
|
#
|
|
|
|
# $ PASSES=unit PKG=./wal TESTCASE=TestNew TIMEOUT=1m ./test
|
|
|
|
# $ PASSES=unit PKG=./wal TESTCASE="\bTestNew\b" TIMEOUT=1m ./test
|
|
|
|
# $ PASSES=integration PKG=client/integration TESTCASE="\bTestV2NoRetryEOF\b" TIMEOUT=1m ./test
|
2014-09-09 10:06:03 +04:00
|
|
|
#
|
2016-12-28 02:15:57 +03:00
|
|
|
#
|
2017-02-24 01:39:34 +03:00
|
|
|
# Run code coverage
|
2017-01-31 03:05:21 +03:00
|
|
|
# COVERDIR must either be a absolute path or a relative path to the etcd root
|
2018-03-13 03:03:43 +03:00
|
|
|
# $ COVERDIR=coverage PASSES="build_cov cov" ./test
|
2015-07-21 02:32:42 +03:00
|
|
|
set -e
|
2014-09-09 10:06:03 +04:00
|
|
|
|
2016-06-21 22:12:50 +03:00
|
|
|
source ./build
|
|
|
|
|
2017-06-20 01:51:21 +03:00
|
|
|
# build before setting up test GOPATH
|
|
|
|
if [[ "${PASSES}" == *"functional"* ]]; then
|
2018-04-09 17:09:48 +03:00
|
|
|
./functional/build
|
2017-06-20 01:51:21 +03:00
|
|
|
fi
|
|
|
|
|
2016-07-15 04:13:07 +03:00
|
|
|
if [ -z "$PASSES" ]; then
|
2018-04-11 02:43:01 +03:00
|
|
|
PASSES="fmt bom dep build unit"
|
2016-07-15 04:13:07 +03:00
|
|
|
fi
|
|
|
|
|
2017-06-03 21:02:08 +03:00
|
|
|
USERPKG=${PKG:-}
|
|
|
|
|
2018-04-09 20:46:39 +03:00
|
|
|
# Invoke ./tests/cover.test.bash for HTML output
|
2014-09-09 10:06:03 +04:00
|
|
|
COVER=${COVER:-"-cover"}
|
|
|
|
|
2014-09-23 04:11:20 +04:00
|
|
|
# Hack: gofmt ./ will recursively check the .git directory. So use *.go for gofmt.
|
2018-01-15 06:44:18 +03:00
|
|
|
IGNORE_PKGS="(vendor/|etcdserverpb|rafttest|gopath.proto|v3lockpb|v3electionpb)"
|
2018-04-09 20:39:41 +03:00
|
|
|
INTEGRATION_PKGS="(integration|tests/e2e|contrib|functional)"
|
2017-03-14 09:58:29 +03:00
|
|
|
|
2018-09-03 19:27:23 +03:00
|
|
|
# all github.com/etcd-io/etcd/whatever pkgs that are not auto-generated / tools
|
2018-03-22 20:39:23 +03:00
|
|
|
# shellcheck disable=SC1117
|
2018-04-09 20:39:41 +03:00
|
|
|
PKGS=$(find . -name \*.go | while read -r a; do dirname "$a"; done | sort | uniq | grep -vE "$IGNORE_PKGS" | grep -vE "(tools/|contrib/|tests/e2e|pb)" | sed "s|\.|${REPO_PATH}|g" | xargs echo)
|
2017-03-14 09:58:29 +03:00
|
|
|
# pkg1,pkg2,pkg3
|
2017-06-03 21:02:08 +03:00
|
|
|
PKGS_COMMA=${PKGS// /,}
|
2017-03-14 09:58:29 +03:00
|
|
|
|
2018-03-22 20:39:23 +03:00
|
|
|
# shellcheck disable=SC1117
|
2017-09-08 04:37:33 +03:00
|
|
|
TEST_PKGS=$(find . -name \*_test.go | while read -r a; do dirname "$a"; done | sort | uniq | grep -vE "$IGNORE_PKGS" | sed "s|\./||g")
|
2018-03-22 20:39:23 +03:00
|
|
|
|
|
|
|
# shellcheck disable=SC1117
|
2017-09-08 04:37:33 +03:00
|
|
|
FORMATTABLE=$(find . -name \*.go | while read -r a; do echo "$(dirname "$a")/*.go"; done | sort | uniq | grep -vE "$IGNORE_PKGS" | sed "s|\./||g")
|
2018-03-22 20:39:23 +03:00
|
|
|
|
2017-09-08 04:37:33 +03:00
|
|
|
TESTABLE_AND_FORMATTABLE=$(echo "$TEST_PKGS" | grep -vE "$INTEGRATION_PKGS")
|
2014-09-09 10:06:03 +04:00
|
|
|
|
2017-06-03 21:02:08 +03:00
|
|
|
# check if user provided PKG override
|
|
|
|
if [ -z "${USERPKG}" ]; then
|
2014-10-30 02:14:31 +03:00
|
|
|
TEST=$TESTABLE_AND_FORMATTABLE
|
2014-09-09 10:06:03 +04:00
|
|
|
FMT=$FORMATTABLE
|
|
|
|
else
|
|
|
|
# strip out leading dotslashes and trailing slashes from PKG=./foo/
|
2017-06-03 21:02:08 +03:00
|
|
|
TEST=${USERPKG/#./}
|
2014-09-09 10:06:03 +04:00
|
|
|
TEST=${TEST/#\//}
|
|
|
|
TEST=${TEST/%\//}
|
|
|
|
# only run gofmt on packages provided by user
|
|
|
|
FMT="$TEST"
|
|
|
|
fi
|
2018-03-22 20:39:23 +03:00
|
|
|
|
|
|
|
# shellcheck disable=SC2206
|
2017-09-06 20:38:08 +03:00
|
|
|
FMT=($FMT)
|
2018-05-01 20:07:25 +03:00
|
|
|
if [ "${VERBOSE}" == "1" ]; then
|
|
|
|
# shellcheck disable=SC2128
|
|
|
|
echo "Running with FMT:" "${FMT[@]}"
|
|
|
|
fi
|
2014-09-09 10:06:03 +04:00
|
|
|
|
2017-06-07 01:20:39 +03:00
|
|
|
# prepend REPO_PATH to each local package
|
|
|
|
split=$TEST
|
|
|
|
TEST=""
|
|
|
|
for a in $split; do TEST="$TEST ${REPO_PATH}/${a}"; done
|
2018-03-22 20:39:23 +03:00
|
|
|
|
|
|
|
# shellcheck disable=SC2206
|
2017-09-06 20:38:08 +03:00
|
|
|
TEST=($TEST)
|
2018-05-01 20:07:25 +03:00
|
|
|
if [ "${VERBOSE}" == "1" ]; then
|
|
|
|
# shellcheck disable=SC2128
|
|
|
|
echo "Running with TEST:" "${TEST[@]}"
|
|
|
|
fi
|
2017-06-03 21:02:08 +03:00
|
|
|
|
|
|
|
# TODO: 'rafttest' is failing with unused
|
2019-02-01 22:17:58 +03:00
|
|
|
STATIC_ANALYSIS_PATHS=$(find . -name \*.go ! -path './vendor/*' ! -path './gopath.proto/*' ! -path '*pb/*' | while read -r a; do dirname "$a"; done | sort | uniq | grep -vE "$IGNORE_PKGS")
|
2018-03-22 20:39:23 +03:00
|
|
|
# shellcheck disable=SC2206
|
2017-09-06 20:38:08 +03:00
|
|
|
STATIC_ANALYSIS_PATHS=($STATIC_ANALYSIS_PATHS)
|
2018-05-01 20:07:25 +03:00
|
|
|
if [ "${VERBOSE}" == "1" ]; then
|
|
|
|
# shellcheck disable=SC2128
|
|
|
|
echo "Running with STATIC_ANALYSIS_PATHS:" "${STATIC_ANALYSIS_PATHS[@]}"
|
|
|
|
fi
|
2017-06-03 21:02:08 +03:00
|
|
|
|
|
|
|
if [ -z "$GOARCH" ]; then
|
|
|
|
GOARCH=$(go env GOARCH);
|
|
|
|
fi
|
|
|
|
|
2018-04-20 23:19:06 +03:00
|
|
|
# determine the number of CPUs to use for Go tests
|
|
|
|
TEST_CPUS="1,2,4"
|
2019-01-08 20:02:40 +03:00
|
|
|
if [ -n "${CPU}" ]; then
|
2018-04-20 23:19:06 +03:00
|
|
|
TEST_CPUS="${CPU}"
|
|
|
|
fi
|
2018-05-01 00:25:24 +03:00
|
|
|
echo "Running with TEST_CPUS:" "${TEST_CPUS}"
|
2018-04-20 23:19:06 +03:00
|
|
|
|
2016-07-15 04:13:07 +03:00
|
|
|
# determine whether target supports race detection
|
2016-10-04 23:42:53 +03:00
|
|
|
if [ "$GOARCH" == "amd64" ]; then
|
2016-03-27 12:07:32 +03:00
|
|
|
RACE="--race"
|
|
|
|
fi
|
2014-09-09 10:06:03 +04:00
|
|
|
|
2018-03-13 03:03:43 +03:00
|
|
|
RUN_ARG=""
|
2019-01-08 20:02:40 +03:00
|
|
|
if [ -n "${TESTCASE}" ]; then
|
2018-03-13 03:03:43 +03:00
|
|
|
RUN_ARG="-run=${TESTCASE}"
|
|
|
|
fi
|
|
|
|
|
2016-07-15 04:13:07 +03:00
|
|
|
function unit_pass {
|
|
|
|
echo "Running unit tests..."
|
2017-10-23 23:12:43 +03:00
|
|
|
GO_TEST_FLAG=""
|
|
|
|
if [ "${VERBOSE}" == "1" ]; then
|
|
|
|
GO_TEST_FLAG="-v"
|
|
|
|
fi
|
|
|
|
if [ "${VERBOSE}" == "2" ]; then
|
|
|
|
GO_TEST_FLAG="-v"
|
|
|
|
export CLIENT_DEBUG=1
|
|
|
|
fi
|
2018-03-13 03:03:43 +03:00
|
|
|
|
|
|
|
if [ "${RUN_ARG}" == "" ]; then
|
|
|
|
RUN_ARG="-run=Test"
|
|
|
|
fi
|
|
|
|
|
|
|
|
# check if user provided time out, especially useful when just run one test case
|
|
|
|
# expectation could be different
|
|
|
|
USERTIMEOUT=""
|
|
|
|
if [ -z "${TIMEOUT}" ]; then
|
|
|
|
USERTIMEOUT="3m"
|
|
|
|
else
|
|
|
|
USERTIMEOUT="${TIMEOUT}"
|
|
|
|
fi
|
2020-05-10 22:39:11 +03:00
|
|
|
go test -mod=mod ${GO_TEST_FLAG} -timeout "${USERTIMEOUT}" "${COVER}" ${RACE} -cpu "${TEST_CPUS}" ${RUN_ARG} "$@" "${TEST[@]}"
|
2016-01-18 11:07:09 +03:00
|
|
|
}
|
2014-09-09 10:06:03 +04:00
|
|
|
|
2016-07-15 04:13:07 +03:00
|
|
|
function integration_pass {
|
|
|
|
echo "Running integration tests..."
|
2018-03-13 03:03:43 +03:00
|
|
|
|
|
|
|
# check if user provided time out, especially useful when just run one test case
|
|
|
|
# expectation could be different
|
|
|
|
USERTIMEOUT=""
|
|
|
|
if [ -z "${TIMEOUT}" ]; then
|
2019-06-20 23:54:56 +03:00
|
|
|
USERTIMEOUT="30m"
|
2018-03-13 03:03:43 +03:00
|
|
|
else
|
|
|
|
USERTIMEOUT="${TIMEOUT}"
|
|
|
|
fi
|
|
|
|
|
|
|
|
# if TESTCASE and PKG set, run specified test case in specified PKG
|
|
|
|
# if TESTCASE set, PKG not set, run specified test case in all integration and integration_extra packages
|
|
|
|
# if TESTCASE not set, PKG set, run all test cases in specified package
|
|
|
|
# if TESTCASE not set, PKG not set, run all tests in all integration and integration_extra packages
|
|
|
|
if [ -z "${TESTCASE}" ] && [ -z "${USERPKG}" ]; then
|
2020-05-10 22:39:11 +03:00
|
|
|
go test -mod=mod -timeout "${USERTIMEOUT}" -v -cpu "${TEST_CPUS}" "$@" "${REPO_PATH}/integration"
|
2018-03-13 03:03:43 +03:00
|
|
|
integration_extra "$@"
|
|
|
|
else
|
|
|
|
if [ -z "${USERPKG}" ]; then
|
|
|
|
INTEGTESTPKG=("${REPO_PATH}/integration"
|
|
|
|
"${REPO_PATH}/client/integration"
|
|
|
|
"${REPO_PATH}/clientv3/integration"
|
2020-08-02 18:13:47 +03:00
|
|
|
"${REPO_PATH}/contrib/raftexample")
|
2018-03-13 03:03:43 +03:00
|
|
|
else
|
|
|
|
INTEGTESTPKG=("${TEST[@]}")
|
|
|
|
fi
|
2020-05-10 22:39:11 +03:00
|
|
|
go test -mod=mod -timeout "${USERTIMEOUT}" -v -cpu "${TEST_CPUS}" "${RUN_ARG}" "$@" "${INTEGTESTPKG[@]}"
|
2018-03-13 03:03:43 +03:00
|
|
|
fi
|
2017-08-25 08:55:41 +03:00
|
|
|
}
|
|
|
|
|
|
|
|
function integration_extra {
|
2020-05-10 22:39:11 +03:00
|
|
|
go test -mod=mod -timeout 1m -v ${RACE} -cpu "${TEST_CPUS}" "$@" "${REPO_PATH}/client/integration"
|
|
|
|
go test -mod=mod -timeout 25m -v ${RACE} -cpu "${TEST_CPUS}" "$@" "${REPO_PATH}/clientv3/integration"
|
|
|
|
go test -mod=mod -timeout 1m -v -cpu "${TEST_CPUS}" "$@" "${REPO_PATH}/contrib/raftexample"
|
|
|
|
go test -mod=mod -timeout 5m -v ${RACE} -tags v2v3 "$@" "${REPO_PATH}/etcdserver/api/v2store"
|
|
|
|
go test -mod=mod -timeout 1m -v ${RACE} -cpu "${TEST_CPUS}" -run=Example "$@" "${TEST[@]}"
|
2016-10-06 01:35:14 +03:00
|
|
|
}
|
|
|
|
|
2017-06-20 01:51:21 +03:00
|
|
|
function functional_pass {
|
2017-11-14 23:17:15 +03:00
|
|
|
# Clean up any data and logs from previous runs
|
2018-04-11 22:51:26 +03:00
|
|
|
rm -rf /tmp/etcd-functional-* /tmp/etcd-functional-*.backup
|
2017-11-14 23:17:15 +03:00
|
|
|
|
2017-06-20 01:51:21 +03:00
|
|
|
for a in 1 2 3; do
|
2018-03-30 06:42:17 +03:00
|
|
|
./bin/etcd-agent --network tcp --address 127.0.0.1:${a}9027 &
|
2017-06-20 01:51:21 +03:00
|
|
|
pid="$!"
|
|
|
|
agent_pids="${agent_pids} $pid"
|
|
|
|
done
|
|
|
|
|
2017-07-13 00:46:43 +03:00
|
|
|
for a in 1 2 3; do
|
|
|
|
echo "Waiting for 'etcd-agent' on ${a}9027..."
|
|
|
|
while ! nc -z localhost ${a}9027; do
|
|
|
|
sleep 1
|
|
|
|
done
|
|
|
|
done
|
|
|
|
|
2018-04-11 04:11:14 +03:00
|
|
|
echo "functional test START!"
|
2018-04-09 17:09:48 +03:00
|
|
|
./bin/etcd-tester --config ./functional.yaml && echo "'etcd-tester' succeeded"
|
2017-06-20 01:51:21 +03:00
|
|
|
ETCD_TESTER_EXIT_CODE=$?
|
|
|
|
echo "ETCD_TESTER_EXIT_CODE:" ${ETCD_TESTER_EXIT_CODE}
|
|
|
|
|
2018-03-22 20:39:23 +03:00
|
|
|
# shellcheck disable=SC2206
|
2017-09-06 20:38:08 +03:00
|
|
|
agent_pids=($agent_pids)
|
2018-04-11 04:11:14 +03:00
|
|
|
kill -s TERM "${agent_pids[@]}" || true
|
2017-06-20 01:51:21 +03:00
|
|
|
|
|
|
|
if [[ "${ETCD_TESTER_EXIT_CODE}" -ne "0" ]]; then
|
2019-08-07 20:16:15 +03:00
|
|
|
printf "\n"
|
|
|
|
echo "FAILED! 'tail -1000 /tmp/etcd-functional-1/etcd.log'"
|
|
|
|
tail -1000 /tmp/etcd-functional-1/etcd.log
|
|
|
|
|
|
|
|
printf "\n"
|
|
|
|
echo "FAILED! 'tail -1000 /tmp/etcd-functional-2/etcd.log'"
|
|
|
|
tail -1000 /tmp/etcd-functional-2/etcd.log
|
|
|
|
|
|
|
|
printf "\n"
|
|
|
|
echo "FAILED! 'tail -1000 /tmp/etcd-functional-3/etcd.log'"
|
|
|
|
tail -1000 /tmp/etcd-functional-3/etcd.log
|
|
|
|
|
2017-11-03 08:39:34 +03:00
|
|
|
echo "--- FAIL: exit code" ${ETCD_TESTER_EXIT_CODE}
|
2017-06-20 01:51:21 +03:00
|
|
|
exit ${ETCD_TESTER_EXIT_CODE}
|
|
|
|
fi
|
2018-04-11 04:11:14 +03:00
|
|
|
echo "functional test PASS!"
|
2017-06-20 01:51:21 +03:00
|
|
|
}
|
|
|
|
|
2016-12-28 02:15:57 +03:00
|
|
|
function cov_pass {
|
|
|
|
echo "Running code coverage..."
|
|
|
|
# install gocovmerge before running code coverage from github.com/wadey/gocovmerge
|
2017-02-24 01:39:34 +03:00
|
|
|
# gocovmerge merges coverage files
|
2018-10-26 00:53:05 +03:00
|
|
|
if ! command -v gocovmerge >/dev/null; then
|
2016-12-28 02:15:57 +03:00
|
|
|
echo "gocovmerge not installed"
|
|
|
|
exit 255
|
|
|
|
fi
|
|
|
|
|
|
|
|
if [ -z "$COVERDIR" ]; then
|
|
|
|
echo "COVERDIR undeclared"
|
|
|
|
exit 255
|
|
|
|
fi
|
|
|
|
|
2017-01-31 03:05:21 +03:00
|
|
|
if [ ! -f "bin/etcd_test" ]; then
|
|
|
|
echo "etcd_test binary not found"
|
|
|
|
exit 255
|
|
|
|
fi
|
|
|
|
|
2016-12-28 02:15:57 +03:00
|
|
|
mkdir -p "$COVERDIR"
|
|
|
|
|
2017-01-31 03:05:21 +03:00
|
|
|
# run code coverage for unit and integration tests
|
2019-06-20 23:54:56 +03:00
|
|
|
GOCOVFLAGS="-covermode=set -coverpkg ${PKGS_COMMA} -v -timeout 30m"
|
2018-03-22 20:39:23 +03:00
|
|
|
# shellcheck disable=SC2206
|
2017-09-17 10:33:56 +03:00
|
|
|
GOCOVFLAGS=($GOCOVFLAGS)
|
2017-04-04 20:44:29 +03:00
|
|
|
failed=""
|
2018-04-09 20:39:41 +03:00
|
|
|
for t in $(echo "${TEST_PKGS}" | grep -vE "(tests/e2e|functional)"); do
|
2017-09-06 20:38:08 +03:00
|
|
|
tf=$(echo "$t" | tr / _)
|
2017-03-09 09:24:16 +03:00
|
|
|
# cache package compilation data for faster repeated builds
|
2020-05-10 22:39:11 +03:00
|
|
|
go test -mod=mod "${GOCOVFLAGS[@]}" -i "${REPO_PATH}/$t" || true
|
2017-01-31 03:05:21 +03:00
|
|
|
# uses -run=Test to skip examples because clientv3/ example tests will leak goroutines
|
2020-05-10 22:39:11 +03:00
|
|
|
go test -mod=mod "${GOCOVFLAGS[@]}" -run=Test -coverprofile "$COVERDIR/${tf}.coverprofile" "${REPO_PATH}/$t" || failed="$failed $t"
|
2016-12-28 02:15:57 +03:00
|
|
|
done
|
|
|
|
|
2017-08-25 08:55:41 +03:00
|
|
|
# v2v3 tests
|
2020-05-10 22:39:11 +03:00
|
|
|
go test -mod=mod -tags v2v3 "${GOCOVFLAGS[@]}" -coverprofile "$COVERDIR/store-v2v3.coverprofile" "${REPO_PATH}/clientv3/integration" || failed="$failed store-v2v3"
|
2017-08-25 08:55:41 +03:00
|
|
|
|
2017-03-24 04:27:09 +03:00
|
|
|
# proxy tests
|
2020-05-10 22:39:11 +03:00
|
|
|
go test -mod=mod -tags cluster_proxy "${GOCOVFLAGS[@]}" -coverprofile "$COVERDIR/proxy_integration.coverprofile" "${REPO_PATH}/integration" || failed="$failed proxy-integration"
|
|
|
|
go test -mod=mod -tags cluster_proxy "${GOCOVFLAGS[@]}" -coverprofile "$COVERDIR/proxy_clientv3.coverprofile" "${REPO_PATH}/clientv3/integration" || failed="$failed proxy-clientv3/integration"
|
2017-03-24 04:27:09 +03:00
|
|
|
|
2017-01-31 03:05:21 +03:00
|
|
|
# run code coverage for e2e tests
|
2017-02-24 01:39:34 +03:00
|
|
|
# use 30m timeout because e2e coverage takes longer
|
2017-01-31 03:05:21 +03:00
|
|
|
# due to many tests cause etcd process to wait
|
|
|
|
# on leadership transfer timeout during gracefully shutdown
|
2018-04-09 20:39:41 +03:00
|
|
|
echo Testing tests/e2e without proxy...
|
2020-05-10 22:39:11 +03:00
|
|
|
go test -mod=mod -tags cov -timeout 30m -v "${REPO_PATH}/tests/e2e" || failed="$failed tests/e2e"
|
2018-04-09 20:39:41 +03:00
|
|
|
echo Testing tests/e2e with proxy...
|
2020-05-10 22:39:11 +03:00
|
|
|
go test -mod=mod -tags "cov cluster_proxy" -timeout 30m -v "${REPO_PATH}/tests/e2e" || failed="$failed tests/e2e-proxy"
|
2017-01-31 03:05:21 +03:00
|
|
|
|
2017-05-31 23:50:09 +03:00
|
|
|
# incrementally merge to get coverage data even if some coverage files are corrupted
|
|
|
|
# optimistically assume etcdserver package's coverage file is OK since gocovmerge
|
|
|
|
# expects to start with a non-empty file
|
|
|
|
cp "$COVERDIR"/etcdserver.coverprofile "$COVERDIR"/cover.out
|
|
|
|
for f in "$COVERDIR"/*.coverprofile; do
|
2017-12-05 05:56:20 +03:00
|
|
|
echo "merging test coverage file ${f}"
|
2017-09-06 20:38:08 +03:00
|
|
|
gocovmerge "$f" "$COVERDIR"/cover.out >"$COVERDIR"/cover.tmp || failed="$failed $f"
|
2017-05-31 23:50:09 +03:00
|
|
|
if [ -s "$COVERDIR"/cover.tmp ]; then
|
|
|
|
mv "$COVERDIR"/cover.tmp "$COVERDIR"/cover.out
|
|
|
|
fi
|
|
|
|
done
|
2017-04-10 22:32:13 +03:00
|
|
|
# strip out generated files (using GNU-style sed)
|
|
|
|
sed --in-place '/generated.go/d' "$COVERDIR"/cover.out || true
|
2017-04-04 20:44:29 +03:00
|
|
|
|
2020-09-07 15:05:08 +03:00
|
|
|
echo -e "\nTo generate coverage report use:"
|
|
|
|
echo -e " go tool cover --html=$COVERDIR/cover.out\n"
|
|
|
|
|
2017-04-04 20:44:29 +03:00
|
|
|
# held failures to generate the full coverage file, now fail
|
|
|
|
if [ -n "$failed" ]; then
|
|
|
|
for f in $failed; do
|
2017-11-03 08:39:34 +03:00
|
|
|
echo "--- FAIL:" "$f"
|
2017-04-04 20:44:29 +03:00
|
|
|
done
|
|
|
|
exit 255
|
|
|
|
fi
|
2016-12-28 02:15:57 +03:00
|
|
|
}
|
|
|
|
|
2016-10-06 01:35:14 +03:00
|
|
|
function e2e_pass {
|
|
|
|
echo "Running e2e tests..."
|
2018-03-13 03:03:43 +03:00
|
|
|
|
|
|
|
# check if user provided time out, especially useful when just run one test case
|
|
|
|
# expectation could be different
|
|
|
|
USERTIMEOUT=""
|
|
|
|
if [ -z "${TIMEOUT}" ]; then
|
2019-06-20 23:54:56 +03:00
|
|
|
USERTIMEOUT="30m"
|
2018-03-13 03:03:43 +03:00
|
|
|
else
|
|
|
|
USERTIMEOUT="${TIMEOUT}"
|
|
|
|
fi
|
|
|
|
|
2020-05-10 22:39:11 +03:00
|
|
|
go test -mod=mod -timeout "${USERTIMEOUT}" -v -cpu "${TEST_CPUS}" "${RUN_ARG}" "$@" "${REPO_PATH}/tests/e2e"
|
2016-10-06 01:35:14 +03:00
|
|
|
}
|
|
|
|
|
|
|
|
function integration_e2e_pass {
|
|
|
|
echo "Running integration and e2e tests..."
|
2016-07-11 20:43:42 +03:00
|
|
|
|
2020-05-10 22:39:11 +03:00
|
|
|
go test -mod=mod -timeout 30m -v -cpu "${TEST_CPUS}" "$@" "${REPO_PATH}/tests/e2e" &
|
2016-04-28 20:02:36 +03:00
|
|
|
e2epid="$!"
|
2020-05-10 22:39:11 +03:00
|
|
|
go test -mod=mod -timeout 30m -v -cpu "${TEST_CPUS}" "$@" "${REPO_PATH}/integration" &
|
2016-05-16 16:32:38 +03:00
|
|
|
intpid="$!"
|
2016-04-28 20:02:36 +03:00
|
|
|
wait $e2epid
|
|
|
|
wait $intpid
|
2017-09-06 20:38:08 +03:00
|
|
|
integration_extra "$@"
|
2016-01-18 11:07:09 +03:00
|
|
|
}
|
2014-09-09 10:06:03 +04:00
|
|
|
|
2016-07-06 19:27:02 +03:00
|
|
|
function grpcproxy_pass {
|
2020-05-10 22:39:11 +03:00
|
|
|
go test -mod=mod -timeout 30m -v ${RACE} -tags cluster_proxy -cpu "${TEST_CPUS}" "$@" "${REPO_PATH}/integration"
|
|
|
|
go test -mod=mod -timeout 30m -v ${RACE} -tags cluster_proxy -cpu "${TEST_CPUS}" "$@" "${REPO_PATH}/clientv3/integration"
|
|
|
|
go test -mod=mod -timeout 30m -v -tags cluster_proxy "$@" "${REPO_PATH}/tests/e2e"
|
2016-07-06 19:27:02 +03:00
|
|
|
}
|
|
|
|
|
2016-07-15 04:13:07 +03:00
|
|
|
function release_pass {
|
2016-10-04 23:42:53 +03:00
|
|
|
rm -f ./bin/etcd-last-release
|
2016-08-31 06:54:07 +03:00
|
|
|
# to grab latest patch release; bump this up for every minor release
|
2017-12-21 01:16:59 +03:00
|
|
|
UPGRADE_VER=$(git tag -l --sort=-version:refname "v3.3.*" | head -1)
|
2016-07-15 04:13:07 +03:00
|
|
|
if [ -n "$MANUAL_VER" ]; then
|
|
|
|
# in case, we need to test against different version
|
|
|
|
UPGRADE_VER=$MANUAL_VER
|
|
|
|
fi
|
2017-06-19 18:30:42 +03:00
|
|
|
if [[ -z ${UPGRADE_VER} ]]; then
|
2017-12-21 01:16:59 +03:00
|
|
|
UPGRADE_VER="v3.3.0"
|
2017-06-19 18:30:42 +03:00
|
|
|
echo "fallback to" ${UPGRADE_VER}
|
|
|
|
fi
|
2016-10-04 23:42:53 +03:00
|
|
|
|
|
|
|
local file="etcd-$UPGRADE_VER-linux-$GOARCH.tar.gz"
|
|
|
|
echo "Downloading $file"
|
|
|
|
|
|
|
|
set +e
|
2018-09-03 19:27:23 +03:00
|
|
|
curl --fail -L "https://github.com/etcd-io/etcd/releases/download/$UPGRADE_VER/$file" -o "/tmp/$file"
|
2016-10-04 23:42:53 +03:00
|
|
|
local result=$?
|
|
|
|
set -e
|
|
|
|
case $result in
|
|
|
|
0) ;;
|
2017-11-03 08:39:34 +03:00
|
|
|
*) echo "--- FAIL:" ${result}
|
2017-06-19 18:30:42 +03:00
|
|
|
exit $result
|
2016-10-04 23:42:53 +03:00
|
|
|
;;
|
|
|
|
esac
|
|
|
|
|
2017-09-06 20:38:08 +03:00
|
|
|
tar xzvf "/tmp/$file" -C /tmp/ --strip-components=1
|
2016-10-04 23:42:53 +03:00
|
|
|
mkdir -p ./bin
|
2016-07-15 04:13:07 +03:00
|
|
|
mv /tmp/etcd ./bin/etcd-last-release
|
|
|
|
}
|
|
|
|
|
2017-11-11 08:31:08 +03:00
|
|
|
function shellcheck_pass {
|
2018-10-26 00:53:05 +03:00
|
|
|
if command -v shellcheck >/dev/null; then
|
2018-04-02 21:45:04 +03:00
|
|
|
shellcheckResult=$(shellcheck -fgcc build test scripts/*.sh 2>&1 || true)
|
2017-06-03 20:47:28 +03:00
|
|
|
if [ -n "${shellcheckResult}" ]; then
|
2018-03-22 20:39:23 +03:00
|
|
|
echo -e "shellcheck checking failed:\\n${shellcheckResult}"
|
2017-09-06 20:38:08 +03:00
|
|
|
exit 255
|
2017-06-03 20:47:28 +03:00
|
|
|
fi
|
|
|
|
fi
|
2017-11-11 08:31:08 +03:00
|
|
|
}
|
2017-06-03 20:47:28 +03:00
|
|
|
|
2017-11-11 08:31:08 +03:00
|
|
|
function markdown_you_pass {
|
2017-03-03 22:22:51 +03:00
|
|
|
# eschew you
|
2019-12-02 22:03:32 +03:00
|
|
|
yous=$(find . -name \*.md ! -path './vendor/*' ! -path './Documentation/*' ! -path './gopath.proto/*' -exec grep -E --color "[Yy]ou[r]?[ '.,;]" {} + || true)
|
2019-01-08 20:02:40 +03:00
|
|
|
if [ -n "$yous" ]; then
|
2018-03-22 20:39:23 +03:00
|
|
|
echo -e "found 'you' in documentation:\\n${yous}"
|
2017-03-03 22:22:51 +03:00
|
|
|
exit 255
|
|
|
|
fi
|
2017-11-11 08:31:08 +03:00
|
|
|
}
|
2017-03-03 22:22:51 +03:00
|
|
|
|
2017-11-11 08:31:08 +03:00
|
|
|
function markdown_marker_pass {
|
2017-05-03 19:16:57 +03:00
|
|
|
# TODO: check other markdown files when marker handles headers with '[]'
|
2018-10-26 00:53:05 +03:00
|
|
|
if command -v marker >/dev/null; then
|
2017-09-06 20:38:08 +03:00
|
|
|
markerResult=$(marker --skip-http --root ./Documentation 2>&1 || true)
|
2017-05-03 19:16:57 +03:00
|
|
|
if [ -n "${markerResult}" ]; then
|
2018-03-22 20:39:23 +03:00
|
|
|
echo -e "marker checking failed:\\n${markerResult}"
|
2017-05-03 19:16:57 +03:00
|
|
|
exit 255
|
|
|
|
fi
|
|
|
|
else
|
|
|
|
echo "Skipping marker..."
|
|
|
|
fi
|
2017-11-11 08:31:08 +03:00
|
|
|
}
|
2017-05-03 19:16:57 +03:00
|
|
|
|
2017-11-11 08:31:08 +03:00
|
|
|
function goword_pass {
|
2018-10-26 00:53:05 +03:00
|
|
|
if command -v goword >/dev/null; then
|
2016-04-08 08:09:04 +03:00
|
|
|
# get all go files to process
|
2017-09-06 20:38:08 +03:00
|
|
|
gofiles=$(find "${FMT[@]}" -iname '*.go' 2>/dev/null)
|
2018-03-22 20:39:23 +03:00
|
|
|
# shellcheck disable=SC2206
|
2017-09-06 20:38:08 +03:00
|
|
|
gofiles_all=($gofiles)
|
2016-04-08 08:09:04 +03:00
|
|
|
# ignore tests and protobuf files
|
2018-03-22 20:39:23 +03:00
|
|
|
# shellcheck disable=SC1117
|
2017-09-08 04:37:33 +03:00
|
|
|
gofiles=$(echo "${gofiles_all[@]}" | sort | uniq | sed "s/ /\n/g" | grep -vE "(\\_test.go|\\.pb\\.go)")
|
2018-03-22 20:39:23 +03:00
|
|
|
# shellcheck disable=SC2206
|
2017-09-06 20:38:08 +03:00
|
|
|
gofiles=($gofiles)
|
2016-04-08 08:09:04 +03:00
|
|
|
# only check for broken exported godocs
|
2017-09-06 20:38:08 +03:00
|
|
|
gowordRes=$(goword -use-spell=false "${gofiles[@]}" | grep godoc-export | sort)
|
2019-01-08 20:02:40 +03:00
|
|
|
if [ -n "$gowordRes" ]; then
|
2018-03-22 20:39:23 +03:00
|
|
|
echo -e "goword checking failed:\\n${gowordRes}"
|
2016-04-08 08:09:04 +03:00
|
|
|
exit 255
|
|
|
|
fi
|
2017-09-04 13:09:32 +03:00
|
|
|
# check some spelling
|
|
|
|
gowordRes=$(goword -ignore-file=.words clientv3/{*,*/*}.go 2>&1 | grep spell | sort)
|
2019-01-08 20:02:40 +03:00
|
|
|
if [ -n "$gowordRes" ]; then
|
2018-03-22 20:39:23 +03:00
|
|
|
echo -e "goword checking failed:\\n${gowordRes}"
|
2017-09-04 13:09:32 +03:00
|
|
|
exit 255
|
|
|
|
fi
|
2016-04-08 08:09:04 +03:00
|
|
|
else
|
2016-05-11 09:05:58 +03:00
|
|
|
echo "Skipping goword..."
|
2016-04-08 08:09:04 +03:00
|
|
|
fi
|
2017-11-11 08:31:08 +03:00
|
|
|
}
|
2016-04-08 08:09:04 +03:00
|
|
|
|
2018-02-27 21:39:34 +03:00
|
|
|
function gofmt_pass {
|
|
|
|
fmtRes=$(gofmt -l -s -d "${FMT[@]}")
|
|
|
|
if [ -n "${fmtRes}" ]; then
|
2018-03-22 20:39:23 +03:00
|
|
|
echo -e "gofmt checking failed:\\n${fmtRes}"
|
2018-02-27 21:39:34 +03:00
|
|
|
exit 255
|
|
|
|
fi
|
|
|
|
}
|
|
|
|
|
|
|
|
function govet_pass {
|
2020-05-10 22:35:15 +03:00
|
|
|
vetRes=$(go vet -mod=mod "${TEST[@]}")
|
2018-02-27 21:39:34 +03:00
|
|
|
if [ -n "${vetRes}" ]; then
|
2018-03-22 20:39:23 +03:00
|
|
|
echo -e "govet checking failed:\\n${vetRes}"
|
2018-02-27 21:39:34 +03:00
|
|
|
exit 255
|
|
|
|
fi
|
|
|
|
}
|
|
|
|
|
|
|
|
function govet_shadow_pass {
|
|
|
|
fmtpkgs=$(for a in "${FMT[@]}"; do dirname "$a"; done | sort | uniq | grep -v "\\.")
|
2018-03-22 20:39:23 +03:00
|
|
|
# shellcheck disable=SC2206
|
2018-02-27 21:39:34 +03:00
|
|
|
fmtpkgs=($fmtpkgs)
|
2019-02-06 21:12:20 +03:00
|
|
|
# Golang 1.12 onwards the experimental -shadow option is no longer available with go vet
|
vendor: Get rid of ./vendor cleanup
Updated scripts and documentation to not recommend vendoring.
Implemented best practices for tools installation.
Performed multiple tests to confirm its not breaking any workflows and
has no negative performance impact. Rather see 3x speedup.
1. PASSES="fmt unit integration e2e functional" ./test
2. ./scripts/updatebom.sh
3. ./scripts/updatedep.sh
4. ./scripts/genproto.sh - works - ca be simplified - in follow up PR
5. Installation without explicit GOPATH:
```
% unset GOPATH
% [sudo] rm -rf ~/go
% git clone https://github.com/etcd-io/etcd.git
% time ./build
go: downloading google.golang.org/grpc v1.26.0
go: downloading github.com/jonboulle/clockwork v0.1.0
go: downloading github.com/prometheus/client_golang v1.0.0
go: downloading github.com/soheilhy/cmux v0.1.4
go: downloading github.com/gogo/protobuf v1.2.1
go: downloading sigs.k8s.io/yaml v1.1.0
go: downloading golang.org/x/time v0.0.0-20180412165947-fbb02b2291d2
go: downloading github.com/golang/groupcache v0.0.0-20160516000752-02826c3e7903
go: downloading go.etcd.io/bbolt v1.3.5
go: downloading go.uber.org/zap v1.15.0
go: downloading golang.org/x/crypto v0.0.0-20191002192127-34f69633bfdc
go: downloading github.com/golang/protobuf v1.3.2
go: downloading github.com/tmc/grpc-websocket-proxy v0.0.0-20170815181823-89b8d40f7ca8
go: downloading github.com/beorn7/perks v1.0.0
go: downloading github.com/dustin/go-humanize v0.0.0-20171111073723-bb3d318650d4
go: downloading github.com/coreos/go-systemd/v22 v22.0.0
go: downloading gopkg.in/yaml.v2 v2.2.2
go: downloading github.com/coreos/go-semver v0.2.0
go: downloading github.com/sirupsen/logrus v1.4.2
go: downloading golang.org/x/net v0.0.0-20190813141303-74dc4d7220e7
go: downloading github.com/grpc-ecosystem/go-grpc-prometheus v1.2.0
go: downloading github.com/google/uuid v1.0.0
go: downloading github.com/modern-go/reflect2 v1.0.1
go: downloading github.com/prometheus/common v0.4.1
go: downloading github.com/spf13/cobra v0.0.3
go: downloading github.com/xiang90/probing v0.0.0-20190116061207-43a291ad63a2
go: downloading github.com/gorilla/websocket v0.0.0-20170926233335-4201258b820c
go: downloading github.com/spf13/pflag v1.0.1
go: downloading github.com/json-iterator/go v1.1.7
go: downloading github.com/dgrijalva/jwt-go v3.2.0+incompatible
go: downloading github.com/google/btree v1.0.0
go: downloading go.uber.org/atomic v1.6.0
go: downloading github.com/prometheus/procfs v0.0.2
go: downloading go.uber.org/multierr v1.5.0
go: downloading github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd
go: downloading golang.org/x/sys v0.0.0-20200202164722-d101bd2416d5
go: downloading github.com/grpc-ecosystem/grpc-gateway v1.9.5
go: downloading github.com/grpc-ecosystem/go-grpc-middleware v1.0.1-0.20190118093823-f849b5445de4
go: downloading github.com/prometheus/client_model v0.0.0-20190812154241-14fe0d1b01d4
go: downloading google.golang.org/genproto v0.0.0-20190819201941-24fa4b261c55
go: downloading github.com/matttproud/golang_protobuf_extensions v1.0.1
go: downloading golang.org/x/text v0.3.3
go: downloading github.com/olekukonko/tablewriter v0.0.0-20170122224234-a0225b3f23b5
go: downloading github.com/bgentry/speakeasy v0.1.0
go: downloading gopkg.in/cheggaaa/pb.v1 v1.0.25
go: downloading github.com/urfave/cli v1.20.0
go: downloading github.com/mattn/go-runewidth v0.0.2
./build 8.22s user 2.31s system 117% cpu 8.961 total
```
Before:
```
% git clone https://github.com/etcd-io/etcd.git && cd etcd && time ./build
Cloning into 'etcd'...
remote: Enumerating objects: 97872, done.
remote: Total 97872 (delta 0), reused 0 (delta 0), pack-reused 97872
Receiving objects: 100% (97872/97872), 58.97 MiB | 19.85 MiB/s, done.
Resolving deltas: 100% (63091/63091), done.
./build 34.97s user 4.15s system 236% cpu 16.555 total
```
6. Rebuild without changes:
```
% time ./build
./build 1.43s user 0.83s system 168% cpu 1.336 total
```
7. Instantation of vendor directory (assuming ./build loaded them to
$GOPATH/pkg):
```
time go mod vendor
go: downloading github.com/inconshreveable/mousetrap v1.0.0
go: downloading github.com/cockroachdb/datadriven v0.0.0-20190809214429-80d97fb3cbaa
go: downloading github.com/creack/pty v1.1.11
go: downloading github.com/etcd-io/gofail v0.0.0-20190801230047-ad7f989257ca
go: downloading github.com/konsorten/go-windows-terminal-sequences v1.0.1
go mod vendor 0.51s user 0.44s system 110% cpu 0.861 total
```
8. Fresh instantation of vendor:
```
% rm -rf vendor
% [sudo] rm -rf ~/go
% time go mod vendor
go: downloading github.com/coreos/go-systemd/v22 v22.0.0
go: downloading github.com/spf13/cobra v0.0.3
go: downloading github.com/prometheus/client_golang v1.0.0
go: downloading golang.org/x/net v0.0.0-20190813141303-74dc4d7220e7
go: downloading github.com/dustin/go-humanize v0.0.0-20171111073723-bb3d318650d4
go: downloading github.com/gogo/protobuf v1.2.1
go: downloading sigs.k8s.io/yaml v1.1.0
go: downloading google.golang.org/grpc v1.26.0
go: downloading github.com/urfave/cli v1.20.0
go: downloading go.uber.org/zap v1.15.0
go: downloading github.com/spf13/pflag v1.0.1
go: downloading github.com/soheilhy/cmux v0.1.4
go: downloading github.com/json-iterator/go v1.1.7
go: downloading github.com/coreos/go-semver v0.2.0
go: downloading github.com/prometheus/common v0.4.1
go: downloading github.com/prometheus/procfs v0.0.2
go: downloading go.uber.org/atomic v1.6.0
go: downloading github.com/olekukonko/tablewriter v0.0.0-20170122224234-a0225b3f23b5
go: downloading github.com/golang/protobuf v1.3.2
go: downloading github.com/cockroachdb/datadriven v0.0.0-20190809214429-80d97fb3cbaa
go: downloading github.com/grpc-ecosystem/go-grpc-middleware v1.0.1-0.20190118093823-f849b5445de4
go: downloading github.com/modern-go/reflect2 v1.0.1
go: downloading github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd
go: downloading go.uber.org/multierr v1.5.0
go: downloading github.com/creack/pty v1.1.11
go: downloading github.com/mattn/go-runewidth v0.0.2
go: downloading github.com/grpc-ecosystem/go-grpc-prometheus v1.2.0
go: downloading golang.org/x/crypto v0.0.0-20191002192127-34f69633bfdc
go: downloading golang.org/x/sys v0.0.0-20200202164722-d101bd2416d5
go: downloading github.com/jonboulle/clockwork v0.1.0
go: downloading gopkg.in/yaml.v2 v2.2.2
go: downloading github.com/etcd-io/gofail v0.0.0-20190801230047-ad7f989257ca
go: downloading github.com/grpc-ecosystem/grpc-gateway v1.9.5
go: downloading github.com/google/btree v1.0.0
go: downloading google.golang.org/genproto v0.0.0-20190819201941-24fa4b261c55
go: downloading github.com/beorn7/perks v1.0.0
go: downloading github.com/dgrijalva/jwt-go v3.2.0+incompatible
go: downloading github.com/google/uuid v1.0.0
go: downloading golang.org/x/time v0.0.0-20180412165947-fbb02b2291d2
go: downloading github.com/tmc/grpc-websocket-proxy v0.0.0-20170815181823-89b8d40f7ca8
go: downloading go.etcd.io/bbolt v1.3.5
go: downloading golang.org/x/text v0.3.3
go: downloading gopkg.in/cheggaaa/pb.v1 v1.0.25
go: downloading github.com/xiang90/probing v0.0.0-20190116061207-43a291ad63a2
go: downloading github.com/prometheus/client_model v0.0.0-20190812154241-14fe0d1b01d4
go: downloading github.com/inconshreveable/mousetrap v1.0.0
go: downloading github.com/gorilla/websocket v0.0.0-20170926233335-4201258b820c
go: downloading github.com/matttproud/golang_protobuf_extensions v1.0.1
go: downloading github.com/bgentry/speakeasy v0.1.0
go: downloading github.com/golang/groupcache v0.0.0-20160516000752-02826c3e7903
go: downloading github.com/sirupsen/logrus v1.4.2
go: downloading github.com/konsorten/go-windows-terminal-sequences v1.0.1
go mod vendor 3.62s user 1.30s system 127% cpu 3.854 total
```
9. Size of the repository - before: 39M, after: 18M
Before:
```
% time git clone https://github.com/etcd-io/etcd.git
Cloning into 'etcd'...
remote: Enumerating objects: 97872, done.
remote: Total 97872 (delta 0), reused 0 (delta 0), pack-reused 97872
Receiving objects: 100% (97872/97872), 58.97 MiB | 20.53 MiB/s, done.
Resolving deltas: 100% (63091/63091), done.
git clone https://github.com/etcd-io/etcd.git 4.66s user 1.02s system 93% cpu 6.068 total
% du -h --exclude .git -d 1
944K ./clientv3
108K ./etcdmain
5.4M ./Documentation
384K ./security
384K ./mvcc
28K ./.github
8.0K ./version
144K ./contrib
240K ./proxy
2.5M ./etcdserver
112K ./embed
536K ./integration
332K ./tools
116K ./lease
108K ./logos
896K ./tests
960K ./raft
216K ./client
52K ./scripts
100K ./hack
464K ./etcdctl
3.0M ./pkg
620K ./functional
136K ./wal
152K ./auth
21M ./vendor
39M
```
After:
```
% time git clone https://github.com/ptabor/etcd.git -b 20200908-no-vendor
Cloning into 'etcd'...
remote: Enumerating objects: 38, done.
remote: Counting objects: 100% (38/38), done.
remote: Compressing objects: 100% (37/37), done.
remote: Total 98489 (delta 10), reused 8 (delta 1), pack-reused 98451
Receiving objects: 100% (98489/98489), 59.23 MiB | 21.26 MiB/s, done.
Resolving deltas: 100% (63572/63572), done.
git clone https://github.com/ptabor/etcd.git -b 20200908-no-vendor 5.56s user 1.05s system 105% cpu 6.260 total
% du -h --exclude .git -d 1
944K ./clientv3
108K ./etcdmain
5.4M ./Documentation
384K ./security
384K ./mvcc
28K ./.github
8.0K ./version
144K ./contrib
240K ./proxy
2.5M ./etcdserver
112K ./embed
536K ./integration
332K ./tools
116K ./lease
108K ./logos
896K ./tests
960K ./raft
216K ./client
56K ./scripts
100K ./hack
464K ./etcdctl
3.0M ./pkg
620K ./functional
136K ./wal
152K ./auth
19M .
```
2020-09-09 17:12:31 +03:00
|
|
|
./scripts/install_tool.sh golang.org/x/tools/go/analysis/passes/shadow/cmd/shadow
|
2019-02-06 21:12:20 +03:00
|
|
|
export PATH=${GOPATH}/bin:${PATH}
|
|
|
|
shadow_tool=$(which shadow)
|
|
|
|
vetRes=$(go vet -all -vettool="${shadow_tool}" "${TEST[@]}")
|
2018-02-27 21:39:34 +03:00
|
|
|
if [ -n "${vetRes}" ]; then
|
2019-09-06 22:31:55 +03:00
|
|
|
echo -e "govet -shadow checking failed:\\n${vetRes}"
|
2018-02-27 21:39:34 +03:00
|
|
|
exit 255
|
|
|
|
fi
|
|
|
|
}
|
|
|
|
|
2018-05-09 21:25:15 +03:00
|
|
|
function unparam_pass {
|
2018-10-26 00:53:05 +03:00
|
|
|
if command -v unparam >/dev/null; then
|
2018-05-09 21:25:15 +03:00
|
|
|
unparamResult=$(unparam "${STATIC_ANALYSIS_PATHS[@]}" 2>&1 || true)
|
|
|
|
if [ -n "${unparamResult}" ]; then
|
|
|
|
echo -e "unparam checking failed:\\n${unparamResult}"
|
|
|
|
exit 255
|
|
|
|
fi
|
|
|
|
else
|
|
|
|
echo "Skipping unparam..."
|
|
|
|
fi
|
|
|
|
}
|
|
|
|
|
2017-11-11 08:31:08 +03:00
|
|
|
function staticcheck_pass {
|
2018-10-26 00:53:05 +03:00
|
|
|
if command -v staticcheck >/dev/null; then
|
2017-09-06 20:38:08 +03:00
|
|
|
staticcheckResult=$(staticcheck "${STATIC_ANALYSIS_PATHS[@]}" 2>&1 || true)
|
2017-04-07 07:24:39 +03:00
|
|
|
if [ -n "${staticcheckResult}" ]; then
|
|
|
|
# TODO: resolve these after go1.8 migration
|
|
|
|
# See https://github.com/dominikh/go-tools/tree/master/cmd/staticcheck
|
2019-02-01 22:17:58 +03:00
|
|
|
STATIC_CHECK_MASK="S(A|T)(1002|1005|1006|1008|1012|1019|1032|2002|4003|4006)"
|
2017-09-08 04:37:33 +03:00
|
|
|
if echo "${staticcheckResult}" | grep -vE "$STATIC_CHECK_MASK"; then
|
2018-03-22 20:39:23 +03:00
|
|
|
echo -e "staticcheck checking failed:\\n${staticcheckResult}"
|
2017-04-07 07:24:39 +03:00
|
|
|
exit 255
|
|
|
|
else
|
2017-09-06 20:38:08 +03:00
|
|
|
suppressed=$(echo "${staticcheckResult}" | sed 's/ /\n/g' | grep "(SA" | sort | uniq -c)
|
2018-03-22 20:39:23 +03:00
|
|
|
echo -e "staticcheck suppressed warnings:\\n${suppressed}"
|
2017-04-07 07:24:39 +03:00
|
|
|
fi
|
2017-03-07 00:38:02 +03:00
|
|
|
fi
|
|
|
|
else
|
|
|
|
echo "Skipping staticcheck..."
|
|
|
|
fi
|
2017-11-11 08:31:08 +03:00
|
|
|
}
|
2017-03-07 00:38:02 +03:00
|
|
|
|
2018-07-22 01:32:28 +03:00
|
|
|
function revive_pass {
|
2018-10-26 00:53:05 +03:00
|
|
|
if command -v revive >/dev/null; then
|
2018-07-22 01:32:28 +03:00
|
|
|
reviveResult=$(revive -config ./tests/revive.toml -exclude "vendor/..." ./... 2>&1 || true)
|
|
|
|
if [ -n "${reviveResult}" ]; then
|
|
|
|
echo -e "revive checking failed:\\n${reviveResult}"
|
|
|
|
exit 255
|
|
|
|
fi
|
|
|
|
else
|
|
|
|
echo "Skipping revive..."
|
|
|
|
fi
|
|
|
|
}
|
|
|
|
|
2018-05-01 00:25:24 +03:00
|
|
|
function unconvert_pass {
|
2018-10-26 00:53:05 +03:00
|
|
|
if command -v unconvert >/dev/null; then
|
2018-05-01 00:25:24 +03:00
|
|
|
unconvertResult=$(unconvert -v "${STATIC_ANALYSIS_PATHS[@]}" 2>&1 || true)
|
|
|
|
if [ -n "${unconvertResult}" ]; then
|
|
|
|
echo -e "unconvert checking failed:\\n${unconvertResult}"
|
|
|
|
exit 255
|
|
|
|
fi
|
|
|
|
else
|
|
|
|
echo "Skipping unconvert..."
|
|
|
|
fi
|
|
|
|
}
|
|
|
|
|
2017-11-11 08:31:08 +03:00
|
|
|
function ineffassign_pass {
|
2018-10-26 00:53:05 +03:00
|
|
|
if command -v ineffassign >/dev/null; then
|
2017-10-03 12:14:02 +03:00
|
|
|
ineffassignResult=$(ineffassign "${STATIC_ANALYSIS_PATHS[@]}" 2>&1 || true)
|
|
|
|
if [ -n "${ineffassignResult}" ]; then
|
2018-03-22 20:39:23 +03:00
|
|
|
echo -e "ineffassign checking failed:\\n${ineffassignResult}"
|
2017-10-03 12:14:02 +03:00
|
|
|
exit 255
|
|
|
|
fi
|
|
|
|
else
|
|
|
|
echo "Skipping ineffassign..."
|
|
|
|
fi
|
2017-11-11 08:31:08 +03:00
|
|
|
}
|
2017-10-03 12:14:02 +03:00
|
|
|
|
2017-11-11 08:31:08 +03:00
|
|
|
function nakedret_pass {
|
2018-10-26 00:53:05 +03:00
|
|
|
if command -v nakedret >/dev/null; then
|
2017-11-11 04:55:55 +03:00
|
|
|
nakedretResult=$(nakedret "${STATIC_ANALYSIS_PATHS[@]}" 2>&1 || true)
|
|
|
|
if [ -n "${nakedretResult}" ]; then
|
2018-03-22 20:39:23 +03:00
|
|
|
echo -e "nakedret checking failed:\\n${nakedretResult}"
|
2017-11-11 04:55:55 +03:00
|
|
|
exit 255
|
|
|
|
fi
|
|
|
|
else
|
|
|
|
echo "Skipping nakedret..."
|
|
|
|
fi
|
2017-11-11 08:31:08 +03:00
|
|
|
}
|
2017-11-11 04:55:55 +03:00
|
|
|
|
2017-11-11 08:31:08 +03:00
|
|
|
function license_header_pass {
|
2017-06-03 21:02:08 +03:00
|
|
|
licRes=""
|
2018-01-15 06:44:18 +03:00
|
|
|
files=$(find . -type f -iname '*.go' ! -path './vendor/*' ! -path './gopath.proto/*')
|
2017-06-03 21:02:08 +03:00
|
|
|
for file in $files; do
|
|
|
|
if ! head -n3 "${file}" | grep -Eq "(Copyright|generated|GENERATED)" ; then
|
|
|
|
licRes="${licRes}"$(echo -e " ${file}")
|
|
|
|
fi
|
|
|
|
done
|
2016-01-18 11:07:09 +03:00
|
|
|
if [ -n "${licRes}" ]; then
|
2018-03-22 20:39:23 +03:00
|
|
|
echo -e "license header checking failed:\\n${licRes}"
|
2016-01-18 11:07:09 +03:00
|
|
|
exit 255
|
|
|
|
fi
|
2017-11-11 08:31:08 +03:00
|
|
|
}
|
2016-06-22 23:08:30 +03:00
|
|
|
|
2017-11-11 08:31:08 +03:00
|
|
|
function receiver_name_pass {
|
2018-03-22 20:39:23 +03:00
|
|
|
# shellcheck disable=SC1117
|
2017-09-12 13:41:10 +03:00
|
|
|
recvs=$(grep 'func ([^*]' {*,*/*,*/*/*}.go | grep -Ev "(generated|pb/)" | tr ':' ' ' | \
|
|
|
|
awk ' { print $2" "$3" "$4" "$1 }' | sed "s/[a-zA-Z\.]*go//g" | sort | uniq | \
|
|
|
|
grep -Ev "(Descriptor|Proto|_)" | awk ' { print $3" "$4 } ' | sort | uniq -c | grep -v ' 1 ' | awk ' { print $2 } ')
|
|
|
|
if [ -n "${recvs}" ]; then
|
2018-03-22 20:39:23 +03:00
|
|
|
# shellcheck disable=SC2206
|
2017-09-12 13:41:10 +03:00
|
|
|
recvs=($recvs)
|
|
|
|
for recv in "${recvs[@]}"; do
|
|
|
|
echo "Mismatched receiver for $recv..."
|
|
|
|
grep "$recv" "${FMT[@]}" | grep 'func ('
|
|
|
|
done
|
|
|
|
exit 255
|
|
|
|
fi
|
2017-11-11 08:31:08 +03:00
|
|
|
}
|
2017-09-12 13:41:10 +03:00
|
|
|
|
2017-11-11 08:31:08 +03:00
|
|
|
function commit_title_pass {
|
2017-09-06 20:38:08 +03:00
|
|
|
git log --oneline "$(git merge-base HEAD master)"...HEAD | while read -r l; do
|
|
|
|
commitMsg=$(echo "$l" | cut -f2- -d' ')
|
2016-06-26 15:54:02 +03:00
|
|
|
if [[ "$commitMsg" == Merge* ]]; then
|
2016-06-22 23:08:30 +03:00
|
|
|
# ignore "Merge pull" commits
|
|
|
|
continue
|
|
|
|
fi
|
2016-06-26 15:54:02 +03:00
|
|
|
if [[ "$commitMsg" == Revert* ]]; then
|
2016-06-22 23:08:30 +03:00
|
|
|
# ignore revert commits
|
|
|
|
continue
|
|
|
|
fi
|
2016-06-26 15:54:02 +03:00
|
|
|
|
2017-09-06 20:38:08 +03:00
|
|
|
pkgPrefix=$(echo "$commitMsg" | cut -f1 -d':')
|
|
|
|
spaceCommas=$(echo "$commitMsg" | sed 's/ /\n/g' | grep -c ',$' || echo 0)
|
|
|
|
commaSpaces=$(echo "$commitMsg" | sed 's/,/\n/g' | grep -c '^ ' || echo 0)
|
|
|
|
if [[ $(echo "$commitMsg" | grep -c ":..*") == 0 || "$commitMsg" == "$pkgPrefix" || "$spaceCommas" != "$commaSpaces" ]]; then
|
2018-04-11 04:11:14 +03:00
|
|
|
echo "$l"...
|
2016-06-26 15:54:02 +03:00
|
|
|
echo "Expected commit title format '<package>{\", \"<package>}: <description>'"
|
2016-06-22 23:08:30 +03:00
|
|
|
echo "Got: $l"
|
|
|
|
exit 255
|
|
|
|
fi
|
|
|
|
done
|
2016-01-18 11:07:09 +03:00
|
|
|
}
|
2015-09-15 23:54:20 +03:00
|
|
|
|
2019-04-27 00:17:16 +03:00
|
|
|
# tools gosimple,unused,staticheck,unconvert,ineffasign,nakedret
|
|
|
|
# are not module-aware. See https://github.com/golang/go/issues/24661
|
|
|
|
# The module-aware versions need to be used when they become available
|
2017-11-11 08:31:08 +03:00
|
|
|
function fmt_pass {
|
|
|
|
toggle_failpoints disable
|
|
|
|
|
2018-12-17 22:30:28 +03:00
|
|
|
# TODO: add "unparam"
|
2018-02-27 21:39:34 +03:00
|
|
|
for p in shellcheck \
|
2017-11-11 08:31:08 +03:00
|
|
|
markdown_you \
|
|
|
|
goword \
|
2018-02-27 21:39:34 +03:00
|
|
|
gofmt \
|
|
|
|
govet \
|
2018-07-22 01:32:28 +03:00
|
|
|
revive \
|
2017-11-11 08:31:08 +03:00
|
|
|
license_header \
|
|
|
|
receiver_name \
|
|
|
|
commit_title \
|
|
|
|
; do
|
2018-02-27 21:39:34 +03:00
|
|
|
echo "'$p' started at $(date)"
|
2017-11-11 08:31:08 +03:00
|
|
|
"${p}"_pass "$@"
|
2018-02-27 21:39:34 +03:00
|
|
|
echo "'$p' completed at $(date)"
|
2017-11-11 08:31:08 +03:00
|
|
|
done
|
|
|
|
}
|
|
|
|
|
2017-04-25 02:10:32 +03:00
|
|
|
function bom_pass {
|
2018-10-26 00:53:05 +03:00
|
|
|
if ! command -v license-bill-of-materials >/dev/null; then
|
2017-04-25 02:10:32 +03:00
|
|
|
return
|
|
|
|
fi
|
2019-04-27 00:17:16 +03:00
|
|
|
if [ "${GO111MODULE}" == "on" ]; then
|
|
|
|
# license-bill-off-materials calls "go list std cmd" which cannot handle modules
|
|
|
|
# Please see https://github.com/golang/go/issues/26924
|
|
|
|
echo "Skipping license-bill-of-materials with go modules..."
|
|
|
|
return
|
|
|
|
fi
|
2017-04-25 02:10:32 +03:00
|
|
|
echo "Checking bill of materials..."
|
2020-05-10 23:37:18 +03:00
|
|
|
# https://github.com/golang/go/commit/7c388cc89c76bc7167287fb488afcaf5a4aa12bf
|
|
|
|
GOFLAGS="-mod=mod" license-bill-of-materials \
|
2017-04-25 02:10:32 +03:00
|
|
|
--override-file bill-of-materials.override.json \
|
2020-04-27 18:41:00 +03:00
|
|
|
go.etcd.io/etcd/v3 go.etcd.io/etcd/v3/etcdctl >bom-now.json || true
|
2017-04-25 02:10:32 +03:00
|
|
|
if ! diff bill-of-materials.json bom-now.json; then
|
2017-06-03 21:02:08 +03:00
|
|
|
echo "vendored licenses do not match given bill of materials"
|
2017-04-25 02:10:32 +03:00
|
|
|
exit 255
|
|
|
|
fi
|
|
|
|
rm bom-now.json
|
|
|
|
}
|
|
|
|
|
2016-07-15 04:13:07 +03:00
|
|
|
function dep_pass {
|
2016-03-17 20:18:35 +03:00
|
|
|
echo "Checking package dependencies..."
|
|
|
|
# don't pull in etcdserver package
|
|
|
|
pushd clientv3 >/dev/null
|
2017-04-19 22:54:10 +03:00
|
|
|
badpkg="(etcdserver$|mvcc$|backend$|grpc-gateway)"
|
2017-09-08 05:59:51 +03:00
|
|
|
deps=$(go list -f '{{ .Deps }}' | sed 's/ /\n/g' | grep -E "${badpkg}" || echo "")
|
2016-03-17 20:18:35 +03:00
|
|
|
popd >/dev/null
|
2019-01-08 20:02:40 +03:00
|
|
|
if [ -n "$deps" ]; then
|
2018-03-22 20:39:23 +03:00
|
|
|
echo -e "clientv3 has masked dependencies:\\n${deps}"
|
2016-03-17 20:18:35 +03:00
|
|
|
exit 255
|
|
|
|
fi
|
|
|
|
}
|
|
|
|
|
2017-01-31 03:05:21 +03:00
|
|
|
function build_cov_pass {
|
|
|
|
out="bin"
|
|
|
|
if [ -n "${BINDIR}" ]; then out="${BINDIR}"; fi
|
2020-05-10 22:39:11 +03:00
|
|
|
go test -mod=mod -tags cov -c -covermode=set -coverpkg="$PKGS_COMMA" -o "${out}/etcd_test"
|
2020-09-07 15:05:08 +03:00
|
|
|
|
2020-05-10 22:39:11 +03:00
|
|
|
go test -mod=mod -tags cov -c -covermode=set -coverpkg="$PKGS_COMMA" -o "${out}/etcdctl_test" "${REPO_PATH}/etcdctl"
|
2017-01-31 03:05:21 +03:00
|
|
|
}
|
|
|
|
|
2016-07-15 04:13:07 +03:00
|
|
|
# fail fast on static tests
|
|
|
|
function build_pass {
|
2018-04-11 02:43:01 +03:00
|
|
|
echo "Checking build..."
|
2020-05-11 00:18:43 +03:00
|
|
|
GO_BUILD_FLAGS="-v -mod=mod" etcd_build
|
|
|
|
GO_BUILD_FLAGS="-v -mod=mod" tools_build
|
2016-07-15 04:13:07 +03:00
|
|
|
}
|
|
|
|
|
|
|
|
for pass in $PASSES; do
|
2017-07-06 22:51:24 +03:00
|
|
|
echo "Starting '$pass' pass at $(date)"
|
2017-09-06 20:38:08 +03:00
|
|
|
"${pass}"_pass "$@"
|
2017-07-06 22:51:24 +03:00
|
|
|
echo "Finished '$pass' pass at $(date)"
|
2016-07-15 04:13:07 +03:00
|
|
|
done
|
2016-06-21 22:44:11 +03:00
|
|
|
|
2014-09-09 10:06:03 +04:00
|
|
|
echo "Success"
|
2019-04-27 00:17:16 +03:00
|
|
|
|