aboutsummaryrefslogtreecommitdiffstats
path: root/jenkins-common.sh
blob: 1cfbbfcf7b6428b0437dc53a7c37be7e10da085d (plain)
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
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
docker_image_exists() {
	test -n "$(docker images -q "$REPO_USER/$1")"
}

docker_depends() {
	case "$1" in
	osmo-*-centos8) echo "centos8-build" ;;
	osmo-*) echo "debian-stretch-build" ;;
	ttcn3-*) echo "debian-stretch-titan" ;;
	esac
}

docker_distro_from_image_name() {
	case "$1" in
	osmo-*-centos8) echo "centos8" ;;
	centos8-*) echo "centos8" ;;
	*) echo "debian-stretch" ;;
	esac
}

docker_upstream_distro_from_image_name() {
	case "$1" in
	osmo-*-centos8) echo "centos:centos8"; ;;
	centos8-*) echo "centos:centos8" ;;
	debian10-*) echo "debian:buster" ;;
	*) echo "debian:stretch" ;;
	esac
}

docker_dir_from_image_name() {
	case "$1" in
	osmo-*-centos8) echo "$1" | sed 's/\-centos8$//' ;;
	*) echo "$1" ;;
	esac
}

# Make sure required images are available and build them if necessary.
# $*: image names (e.g. "debian-stretch-build", "osmo-mgw-master", "osmo-mgw-master-centos8")
#	The images are automatically built from the Dockerfile of the subdir of
#	the same name. If there is a distribution name at the end of the image
#	name (e.g. osmo-mgw-master-centos8), it gets removed from the subdir
#	where the Dockerfile is taken from (e.g. osmo-mgw-master/Dockerfile)
#	and UPSTREAM_DISTRO and DISTRO are passed accordingly (e.g.
#	UPSTREAM_DISTRO=centos:centos8 DISTRO=centos8). This allows one
#	Dockerfile for multiple distributions, without duplicating configs for
#	each distribution. Dependencies listed in docker_depends() are built
#	automatically too.
IMAGE_DIR_PREFIX=".."
docker_images_require() {
	local i
	local from_line
	local pull_arg
	local upstream_distro_arg
	local distro_arg
	local depends
	local dir

	for i in $@; do
		# Build dependencies first
		depends="$(docker_depends "$i")"
		if [ -n "$depends" ]; then
			docker_images_require $depends
		fi

		# Trigger image build (cache will be used when up-to-date)
		if [ -z "$NO_DOCKER_IMAGE_BUILD" ]; then
			upstream_distro_arg="$(docker_upstream_distro_from_image_name "$i")"
			distro_arg="$(docker_distro_from_image_name "$i")"
			dir="$(docker_dir_from_image_name "$i")"

			# Pull upstream base images
			pull_arg="--pull"
			from_line="$(grep '^FROM' ${IMAGE_DIR_PREFIX}/${dir}/Dockerfile)"
			if echo "$from_line" | grep -q '$USER'; then
				pull_arg=""
			fi

			echo "Building image: $i (export NO_DOCKER_IMAGE_BUILD=1 to prevent this)"
			make -C "${IMAGE_DIR_PREFIX}/${dir}" \
				PULL="$pull_arg" \
				UPSTREAM_DISTRO="$upstream_distro_arg" \
				DISTRO="$distro_arg" \
				IMAGE="$REPO_USER/$i" \
				|| exit 1
		fi

		# Detect missing images (build skipped)
		if ! docker_image_exists "$i"; then
			echo "ERROR: missing image: $i"
			exit 1
		fi
	done
}

#kills all containers attached to network
network_clean() {
	docker network inspect $NET_NAME | grep Name | cut -d : -f2 | awk -F\" 'NR>1{print $2}' | xargs -rn1 docker kill
}

network_create() {
	NET=$1
	if docker network ls | grep -q $NET_NAME; then
		echo removing stale network and containers...
		network_clean
		network_remove
	fi
	SUB4="172.18.$NET.0/24"
	SUB6="fd02:db8:$NET::/64"
	echo Creating network $NET_NAME
	docker network create --internal --subnet $SUB4 --ipv6 --subnet $SUB6 $NET_NAME
}

network_bridge_create() {
	NET=$1
	if docker network ls | grep -q $NET_NAME; then
		echo removing stale network and containers...
		network_clean
		network_remove
	fi
	SUB4="172.18.$NET.0/24"
	SUB6="fd02:db8:$NET::/64"
	echo Creating network $NET_NAME
	docker network create \
		--driver=bridge \
		--subnet $SUB4 \
		--ipv6 --subnet $SUB6 \
		-o "com.docker.network.bridge.host_binding_ipv4"="172.18.$NET.1" \
		$NET_NAME
}

network_remove() {
	echo Removing network $NET_NAME
	docker network remove $NET_NAME
}

# Generates list of params to pass to "docker run" to configure IP addresses
# $1: SUBNET to use, same as passed to network_create()
# $2: Address suffix from SUBNET to apply to the container
docker_network_params() {
	NET=$1
	ADDR_SUFIX=$2
	echo --network $NET_NAME --ip "172.18.$NET.$ADDR_SUFIX" --ip6 "fd02:db8:$NET::$ADDR_SUFIX"
}

fix_perms() {
	if ! docker_image_exists "debian-stretch-build"; then
		docker_images_require "debian-stretch-build"
	fi

	echo Fixing permissions
	docker run 	--rm \
			-v $VOL_BASE_DIR:/data \
			--name ${BUILD_TAG}-cleaner \
			$REPO_USER/debian-stretch-build \
			chmod -R a+rX /data/
}

collect_logs() {
	fix_perms
	cat "$VOL_BASE_DIR"/*/junit-*.log || true
}

set -x

# non-jenkins execution: assume local user name
if [ "x$REPO_USER" = "x" ]; then
	REPO_USER=$USER
fi

if [ "x$WORKSPACE" = "x" ]; then
	# non-jenkins execution: put logs in /tmp
	VOL_BASE_DIR="$(mktemp -d)"

	# point /tmp/logs to the last ttcn3 run
	rm /tmp/logs || true
	ln -s "$VOL_BASE_DIR" /tmp/logs || true
else
	# jenkins execution: put logs in workspace
	VOL_BASE_DIR="$WORKSPACE/logs"
	rm -rf "$VOL_BASE_DIR"
	mkdir -p "$VOL_BASE_DIR"
fi

if [ ! -d "$VOL_BASE_DIR" ]; then
	echo "ERROR: \$VOL_BASE_DIR does not exist: '$VOL_BASE_DIR'"
	exit 1
fi

# non-jenkins execution: put logs in /tmp
if [ "x$BUILD_TAG" = "x" ]; then
	BUILD_TAG=nonjenkins
fi

SUITE_NAME=`basename $PWD`

NET_NAME=$SUITE_NAME