2 # Copyright (C) The Arvados Authors. All rights reserved.
4 # SPDX-License-Identifier: AGPL-3.0
6 read -rd "\000" helpmessage <<EOF
7 $(basename $0): Orchestrate run-build-packages.sh for one target
10 WORKSPACE=/path/to/arvados $(basename $0) [options]
13 Distribution to build packages for (default: debian10)
15 Build command to execute (default: use built-in Docker image command)
17 Run package install test script "test-packages-[target].sh"
19 Output debug information (default: false)
20 --only-build <package>
21 Build only a specific package
23 Test only a specific package
25 Build a specific architecture (amd64 or arm64, defaults to native architecture)
27 Build even if the package exists upstream or if it has already been
30 Test even if there is no new untested package
31 --build-version <string>
32 Version to build (default:
33 \$ARVADOS_BUILDING_VERSION-\$ARVADOS_BUILDING_ITERATION or
34 0.1.timestamp.commithash)
36 Don't try to build Docker images
38 WORKSPACE=path Path to the Arvados source tree to build packages from
44 if ! [[ -n "$WORKSPACE" ]]; then
45 echo >&2 "$helpmessage"
47 echo >&2 "Error: WORKSPACE environment variable not set"
52 if ! [[ -d "$WORKSPACE" ]]; then
53 echo >&2 "$helpmessage"
55 echo >&2 "Error: $WORKSPACE is not a directory"
60 PARSEDOPTS=$(getopt --name "$0" --longoptions \
61 help,debug,test-packages,target:,command:,only-test:,force-test,only-build:,force-build,arch:,build-version:,skip-docker-build \
72 eval set -- "$PARSEDOPTS"
73 while [ $# -gt 0 ]; do
76 echo >&2 "$helpmessage"
95 ONLY_BUILD="$2"; shift
111 if [[ -z "$2" ]]; then
113 elif ! [[ "$2" =~ (.*)-(.*) ]]; then
114 echo >&2 "FATAL: --build-version '$2' does not include an iteration. Try '${2}-1'?"
116 elif ! [[ "$2" =~ ^[0-9]+\.[0-9]+\.[0-9]+(\.[0-9]+|)(~rc[0-9]+|~dev[0-9]+|)-[0-9]+$ ]]; then
117 echo >&2 "FATAL: --build-version '$2' is invalid, must match pattern ^[0-9]+\.[0-9]+\.[0-9]+(\.[0-9]+|)(~rc[0-9]+|~dev[0-9]+|)-[0-9]+$"
120 [[ "$2" =~ (.*)-(.*) ]]
121 ARVADOS_BUILDING_VERSION="${BASH_REMATCH[1]}"
122 ARVADOS_BUILDING_ITERATION="${BASH_REMATCH[2]}"
130 if [ $# -gt 1 ]; then
131 echo >&2 "$0: unrecognized argument '$2'. Try: $0 --help"
141 if [[ -n "$ARVADOS_BUILDING_VERSION" ]]; then
142 echo "build version='$ARVADOS_BUILDING_VERSION', package iteration='$ARVADOS_BUILDING_ITERATION'"
145 if [[ -n "$test_packages" ]]; then
146 if [[ -n "$(find $WORKSPACE/packages/$TARGET -name '*.rpm')" ]] ; then
147 CREATEREPO="$(command -v createrepo createrepo_c | tail -n1)"
148 if [[ -z "$CREATEREPO" ]]; then
150 echo >&2 "Error: please install createrepo. E.g. sudo apt install createrepo-c"
154 "$CREATEREPO" $WORKSPACE/packages/$TARGET
157 if [[ -n "$(find $WORKSPACE/packages/$TARGET -name '*.deb')" ]] ; then
159 /usr/bin/which dpkg-scanpackages >/dev/null
160 if [[ "$?" != "0" ]]; then
162 echo >&2 "Error: please install dpkg-dev. E.g. sudo apt-get install dpkg-dev"
166 /usr/bin/which apt-ftparchive >/dev/null
167 if [[ "$?" != "0" ]]; then
169 echo >&2 "Error: please install apt-utils. E.g. sudo apt-get install apt-utils"
174 (cd $WORKSPACE/packages/$TARGET
175 dpkg-scanpackages --multiversion . 2> >(grep -v 'warning' 1>&2) | tee Packages | gzip -c > Packages.gz
176 apt-ftparchive -o APT::FTPArchive::Release::Origin=Arvados release . > Release
180 COMMAND="/jenkins/package-testing/test-packages-$TARGET.sh"
181 IMAGE="arvados/package-test:$TARGET"
183 IMAGE="arvados/build:$TARGET"
184 if [[ "$COMMAND" != "" ]]; then
185 COMMAND="/usr/local/rvm/bin/rvm-exec default bash /jenkins/$COMMAND --target $TARGET$DEBUG"
189 JENKINS_DIR=$(dirname "$(readlink -e "$0")")
191 if [[ "$SKIP_DOCKER_BUILD" != 1 ]] ; then
192 if [[ -n "$test_packages" ]]; then
193 pushd "$JENKINS_DIR/package-test-dockerfiles"
194 make "$TARGET/generated"
196 pushd "$JENKINS_DIR/package-build-dockerfiles"
197 make "$TARGET/generated"
200 GOVERSION=$(grep 'const goversion =' $WORKSPACE/lib/install/deps.go |awk -F'"' '{print $2}')
204 time docker build --tag "$IMAGE" \
205 --build-arg HOSTTYPE=$HOSTTYPE \
206 --build-arg BRANCH=$(git rev-parse --abbrev-ref HEAD) \
207 --build-arg GOVERSION=$GOVERSION --no-cache .
211 if test -z "$packages" ; then
212 packages="arvados-api-server
215 arvados-dispatch-cloud
217 arvados-docker-cleaner
226 crunch-dispatch-local
227 crunch-dispatch-slurm
241 python3-arvados-python-client
242 python3-arvados-cwl-runner
243 python3-crunchstat-summary
244 python3-arvados-user-activity"
251 mkdir -p "$WORKSPACE/services/api/vendor/cache-$TARGET"
254 -v "$JENKINS_DIR:/jenkins"
255 -v "$WORKSPACE:/arvados"
256 -v /arvados/services/api/vendor/bundle
257 -v "$WORKSPACE/services/api/vendor/cache-$TARGET:/arvados/services/api/vendor/cache"
260 if [[ -n "$test_packages" ]]; then
261 for p in $packages ; do
262 if [[ -n "$ONLY_BUILD" ]] && [[ "$p" != "$ONLY_BUILD" ]]; then
265 if [[ -e "${WORKSPACE}/packages/.last_test_${TARGET}" ]] && [[ -z "$FORCE_TEST" ]]; then
266 MATCH=`find ${WORKSPACE}/packages/ -newer ${WORKSPACE}/packages/.last_test_${TARGET} -regex .*${TARGET}/$p.*`
267 if [[ "$MATCH" == "" ]]; then
268 # No new package has been built that needs testing
269 echo "Skipping $p test because no new package was built since the last test."
273 # If we're testing all packages, we should not error out on packages that don't exist.
274 # If we are testing one specific package only (i.e. --only-test was given), we should
275 # error out if that package does not exist.
276 if [[ -z "$testing_one_package" ]]; then
277 MATCH=`find ${WORKSPACE}/packages/ -regextype posix-extended -regex .*${TARGET}/$p.*\\(deb\\|rpm\\)`
278 if [[ "$MATCH" == "" ]]; then
279 # No new package has been built that needs testing
280 echo "Skipping $p test because no package file is available to test."
285 echo "START: $p test on $IMAGE" >&2
288 "${docker_volume_args[@]}" \
289 --env ARVADOS_DEBUG=$ARVADOS_DEBUG \
290 --env "TARGET=$TARGET" \
291 --env "WORKSPACE=/arvados" \
294 echo "OK: $p test on $IMAGE succeeded" >&2
297 package_fails="$package_fails $p"
298 echo "ERROR: $p test on $IMAGE failed with exit status $FINAL_EXITCODE" >&2
302 if [[ "$FINAL_EXITCODE" == "0" ]]; then
303 touch ${WORKSPACE}/packages/.last_test_${TARGET}
307 echo "START: build packages on $IMAGE" >&2
308 # Move existing packages and other files into the processed/ subdirectory
309 if [[ ! -e "${WORKSPACE}/packages/${TARGET}/processed" ]]; then
310 mkdir -p "${WORKSPACE}/packages/${TARGET}/processed"
313 mv -f ${WORKSPACE}/packages/${TARGET}/* ${WORKSPACE}/packages/${TARGET}/processed/ 2>/dev/null
315 # give bundle (almost) all the cores. See also the MAKE env var that is passed into the
316 # docker run command below.
317 # Cf. https://build.betterup.com/one-weird-trick-that-will-speed-up-your-bundle-install/
318 tmpfile=$(mktemp /tmp/run-build-packages-one-target.XXXXXX)
319 cores=$(let a=$(grep -c processor /proc/cpuinfo )-1; echo $a)
320 printf -- "---\nBUNDLE_JOBS: \"$cores\"" > $tmpfile
324 "${docker_volume_args[@]}" \
325 -v $tmpfile:/root/.bundle/config \
326 --env ARVADOS_BUILDING_VERSION="$ARVADOS_BUILDING_VERSION" \
327 --env ARVADOS_BUILDING_ITERATION="$ARVADOS_BUILDING_ITERATION" \
328 --env ARVADOS_DEBUG=$ARVADOS_DEBUG \
329 --env "ONLY_BUILD=$ONLY_BUILD" \
330 --env "FORCE_BUILD=$FORCE_BUILD" \
332 --env "MAKE=make --jobs $cores" \
336 echo "OK: build packages on $IMAGE succeeded" >&2
339 echo "ERROR: build packages on $IMAGE failed with exit status $FINAL_EXITCODE" >&2
341 # Clean up the bundle config file
345 if test -n "$package_fails" ; then
346 echo "Failed package tests:$package_fails" >&2