blob: f4fe9d0eca1bfa2ef319e1e21f39c029bf987cef [file] [log] [blame]
Denis Egorenko8c606552016-12-07 14:22:50 +04001package com.mirantis.mcp
2
Artem Panchenkobc13d262017-01-20 12:40:58 +02003
Denis Egorenko8c606552016-12-07 14:22:50 +04004/**
Artem Panchenkobc13d262017-01-20 12:40:58 +02005 * Checkout Calico repository stage
Denis Egorenko8c606552016-12-07 14:22:50 +04006 *
Artem Panchenkobc13d262017-01-20 12:40:58 +02007 * @param config LinkedHashMap
8 * config includes next parameters:
9 * - project_name String, Calico project to clone
Artem Panchenkobc13d262017-01-20 12:40:58 +020010 * - host String, gerrit host
Artem Panchenko6fd07222017-02-13 17:13:23 +020011 * - projectNamespace String, gerrit namespace (optional)
12 * - commit String, Git commit to checkout (optional)
13 * - credentialsId String, gerrit credentials ID (optional)
14 * - refspec String, remote refs to be retrieved (optional)
Artem Panchenkobc13d262017-01-20 12:40:58 +020015 *
16 * Usage example:
17 *
18 * def calico = new com.mirantis.mcp.Calico()
19 * calico.checkoutCalico([
20 * project_name : 'cni-plugin',
21 * commit : 'mcp',
22 * host : 'gerrit.mcp.mirantis.net',
23 * ])
24 *
25 */
26def checkoutCalico(LinkedHashMap config) {
27
28 def git = new com.mirantis.mcp.Git()
29
30 def project_name = config.get('project_name')
31 def projectNamespace = config.get('projectNamespace', 'projectcalico')
Artem Panchenko6fd07222017-02-13 17:13:23 +020032 def commit = config.get('commit', '*')
Artem Panchenkobc13d262017-01-20 12:40:58 +020033 def host = config.get('host')
Artem Panchenkod10610b2017-01-27 18:09:52 +020034 def credentialsId = config.get('credentialsId', 'mcp-ci-gerrit')
Artem Panchenko6fd07222017-02-13 17:13:23 +020035 def refspec = config.get('refspec')
Artem Panchenkobc13d262017-01-20 12:40:58 +020036
37 if (!project_name) {
38 throw new RuntimeException("Parameter 'project_name' must be set for checkoutCalico() !")
39 }
Artem Panchenko6fd07222017-02-13 17:13:23 +020040 if (!host) {
41 throw new RuntimeException("Parameter 'host' must be set for checkoutCalico() !")
Artem Panchenkobc13d262017-01-20 12:40:58 +020042 }
43
44 stage ("Checkout ${project_name}"){
45 git.gitSSHCheckout([
46 credentialsId : credentialsId,
47 branch : commit,
48 host : host,
49 project : "${projectNamespace}/${project_name}",
50 withWipeOut : true,
Artem Panchenko6fd07222017-02-13 17:13:23 +020051 refspec : refspec,
Artem Panchenkobc13d262017-01-20 12:40:58 +020052 ])
53 }
54}
55
56
57/**
58 * Build bird binaries stage
59 *
60 * Usage example:
61 *
62 * def calico = new com.mirantis.mcp.Calico()
63 * calico.buildCalicoBird()
64 *
65 */
66def buildCalicoBird() {
67 stage ('Build bird binaries'){
68 sh "/bin/sh -x build.sh"
69 }
70}
71
72
73/**
74 * Publish bird binaries stage
75 *
76 * @param config LinkedHashMap
77 * config includes next parameters:
78 * - artifactoryServerName String, artifactory server name
79 * - binaryRepo String, repository (artifactory) for binary files
80 * - projectNamespace String, artifactory server namespace (optional)
81 * - publishInfo Boolean, whether publish a build-info object to Artifactory (optional)
82 *
83 * Usage example:
84 *
85 * def calico = new com.mirantis.mcp.Calico()
86 * calico.publishCalicoBird([
87 * artifactoryServerName : 'mcp-ci',
88 * binaryRepo : 'sandbox-binary-dev-local',
89 * ])
90 *
91 */
92def publishCalicoBird(LinkedHashMap config) {
93
94 def common = new com.mirantis.mcp.Common()
95 def git = new com.mirantis.mcp.Git()
96 def artifactory = new com.mirantis.mcp.MCPArtifactory()
97
98 def artifactoryServerName = config.get('artifactoryServerName')
99 def binaryRepo = config.get('binaryRepo')
100 def projectNamespace = config.get('projectNamespace', 'mirantis/projectcalico')
101 def publishInfo = config.get('publishInfo', true)
102
103 if (!artifactoryServerName) {
104 throw new RuntimeException("Parameter 'artifactoryServerName' must be set for publishCalicoBird() !")
105 }
106 if (!binaryRepo) {
107 throw new RuntimeException("Parameter 'binaryRepo' must be set for publishCalicoBird() !")
108 }
109
110 def artifactoryServer = Artifactory.server(artifactoryServerName)
111 def buildInfo = Artifactory.newBuildInfo()
112
113 stage('Publishing bird artifacts') {
114 dir("artifacts"){
115 // define tag for bird
116 binaryTag = git.getGitDescribe(true) + "-" + common.getDatetime()
117 sh """
118 cp ../dist/bird bird-${binaryTag}
119 cp ../dist/bird6 bird6-${binaryTag}
120 cp ../dist/birdcl birdcl-${binaryTag}
121 """
122 writeFile file: "latest", text: "${binaryTag}"
123 // define mandatory properties for binary artifacts
124 // and some additional
125 def properties = artifactory.getBinaryBuildProperties([
126 "tag=${binaryTag}",
127 "project=bird"
128 ])
129
130 def uploadSpec = """{
131 "files": [
132 {
133 "pattern": "**",
134 "target": "${binaryRepo}/${projectNamespace}/bird/",
135 "props": "${properties}"
136 }
137 ]
138 }"""
139
140 // Upload to Artifactory.
141 artifactory.uploadBinariesToArtifactory(artifactoryServer, buildInfo, uploadSpec, publishInfo)
142 }// dir
143 }
144 return binaryTag
145}
146
147
148/**
149 * Test confd stage
150 *
151 *
152 * Usage example:
153 *
154 * def calico = new com.mirantis.mcp.Calico()
155 * calico.testCalicoConfd()
156 *
157 */
158def testCalicoConfd() {
159 stage ('Run unittest for confd'){
160 sh """
161 docker run --rm \
162 -v \$(pwd):/usr/src/confd \
163 -w /usr/src/confd \
164 golang:1.7 \
165 bash -c \
166 \"go get github.com/constabulary/gb/...; gb test -v\"
167 """
168 }
169}
170
171
172/**
173 * Build confd binaries stage
174 *
175 *
176 * Usage example:
177 *
178 * def calico = new com.mirantis.mcp.Calico()
179 * calico.buildCalicoConfd()
180 *
181 */
182def buildCalicoConfd() {
183 def container_src_dir = "/usr/src/confd"
184 def src_suffix = "src/github.com/kelseyhightower/confd"
185 def container_workdir = "${container_src_dir}/${src_suffix}"
186 def container_gopath = "${container_src_dir}/vendor:${container_src_dir}"
187
188 stage ('Build confd binary'){
189 sh """
190 docker run --rm \
191 -v \$(pwd):${container_src_dir} \
192 -w ${container_workdir} \
193 -e GOPATH=${container_gopath} \
194 golang:1.7 \
195 bash -c \
196 \"go build -a -installsuffix cgo -ldflags '-extld ld -extldflags -static' -a -x .\"
197 """
198 }
199}
200
201
202/**
203 * Publish confd binaries stage
204 *
205 * @param config LinkedHashMap
206 * config includes next parameters:
207 * - artifactoryServerName String, artifactory server name
208 * - binaryRepo String, repository (artifactory) for binary files
209 * - projectNamespace String, artifactory server namespace (optional)
210 * - publishInfo Boolean, whether publish a build-info object to Artifactory (optional)
211 *
212 * Usage example:
213 *
214 * def calico = new com.mirantis.mcp.Calico()
215 * calico.publishCalicoConfd([
216 * artifactoryServerName : 'mcp-ci',
217 * binaryRepo : 'sandbox-binary-dev-local',
218 * ])
219 *
220 */
221def publishCalicoConfd(LinkedHashMap config) {
222
223 def common = new com.mirantis.mcp.Common()
224 def git = new com.mirantis.mcp.Git()
225 def artifactory = new com.mirantis.mcp.MCPArtifactory()
226
227 def artifactoryServerName = config.get('artifactoryServerName')
228 def binaryRepo = config.get('binaryRepo')
229 def projectNamespace = config.get('projectNamespace', 'mirantis/projectcalico')
230 def publishInfo = config.get('publishInfo', true)
231 def src_suffix = "src/github.com/kelseyhightower/confd"
232
233 if (!artifactoryServerName) {
234 throw new RuntimeException("Parameter 'artifactoryServerName' must be set for publishCalicoConfd() !")
235 }
236 if (!binaryRepo) {
237 throw new RuntimeException("Parameter 'binaryRepo' must be set for publishCalicoConfd() !")
238 }
239
240 def artifactoryServer = Artifactory.server(artifactoryServerName)
241 def buildInfo = Artifactory.newBuildInfo()
242
243 stage('Publishing confd artifacts') {
244
245 dir("artifacts"){
246 // define tag for confd
247 binaryTag = git.getGitDescribe(true) + "-" + common.getDatetime()
248 // create two files confd and confd+tag
249 sh "cp ../${src_suffix}/confd confd-${binaryTag}"
250 writeFile file: "latest", text: "${binaryTag}"
251
252 // define mandatory properties for binary artifacts
253 // and some additional
254 def properties = artifactory.getBinaryBuildProperties([
255 "tag=${binaryTag}",
256 "project=confd"
257 ])
258
259 def uploadSpec = """{
260 "files": [
261 {
262 "pattern": "**",
263 "target": "${binaryRepo}/${projectNamespace}/confd/",
264 "props": "${properties}"
265 }
266 ]
267 }"""
268
269 // Upload to Artifactory.
270 artifactory.uploadBinariesToArtifactory(artifactoryServer, buildInfo, uploadSpec, publishInfo)
271 }// dir
272 }
273 return binaryTag
274}
275
276
277/**
278 * Test libcalico stage
279 *
280 * Usage example:
281 *
282 * def calico = new com.mirantis.mcp.Calico()
283 * calico.testLibcalico()
284 *
285 */
286def testLibcalico() {
287 stage ('Run libcalico unittests'){
288 sh "make test"
289 }
290}
291
292
293/**
294 * Build calico/build image stage
295 *
296 * @param config LinkedHashMap
297 * config includes next parameters:
298 * - dockerRegistry String, Docker registry host to push image to (optional)
299 * - projectNamespace String, artifactory server namespace (optional)
300 * - buildImageTag String, calico/build image name (optional)
301 * - imageTag String, tag of docker image (optional)
302 *
303 * Usage example:
304 *
305 * def calicoFunc = new com.mirantis.mcp.Calico()
306 * calicoFunc.buildLibcalico([
307 * dockerRegistry : 'sandbox-docker-dev-virtual.docker.mirantis.net',
308 * ])
309 *
310 */
311def buildLibcalico(LinkedHashMap config) {
312
313 def common = new com.mirantis.mcp.Common()
314 def docker = new com.mirantis.mcp.Docker()
315 def git = new com.mirantis.mcp.Git()
316
317 def dockerRegistry = config.get('dockerRegistry')
318 def projectNamespace = config.get('projectNamespace', 'mirantis/projectcalico')
319
320 def buildImage = config.get('buildImage', "calico/build")
321 def buildImageTag = config.get('buildImageTag', git.getGitDescribe(true) + "-" + common.getDatetime())
322
323 def buildContainerName = dockerRegistry ? "${dockerRegistry}/${projectNamespace}/${buildImage}:${buildImageTag}" : "${buildImage}:${buildImageTag}"
324
325 stage ('Build calico/build image') {
326 docker.setDockerfileLabels("./Dockerfile", ["docker.imgTag=${buildImageTag}"])
327 sh """
328 make calico/build BUILD_CONTAINER_NAME=${buildContainerName}
329 """
330 }
331 return [buildImage : buildImage,
332 buildImageTag : buildImageTag]
333}
334
335
336/**
337 * Switch Calico to use dowstream libcalico-go repository stage
338 *
339 * @param libCalicoGoCommit String, libcalico-go repository commit to checkout to
340 * @param host String, gerrit host
341 * @param glideLockFilePath String, relative path to glide.lock file
342 *
343 * Usage example:
344 *
345 * def calico = new com.mirantis.mcp.Calico()
346 * // Checkout calico code using calico.checkoutCalico() and then call this method from the same dir
347 * calico.switchCalicoToDownstreamLibcalicoGo('mcp', 'gerrit.mcp.mirantis.net', './glide.lock')
348 *
349 */
350def switchCalicoToDownstreamLibcalicoGo(String libCalicoGoCommit, String host, String glideLockFilePath) {
Sergey Reshetnyak70b1fe62017-01-31 22:27:06 +0300351 def common = new com.mirantis.mcp.Common()
Artem Panchenkobc13d262017-01-20 12:40:58 +0200352 def git = new com.mirantis.mcp.Git()
353
354 stage ('Switch to downstream libcalico-go') {
355 def libcalicogo_path = "${env.WORKSPACE}/tmp_libcalico-go"
356
357 git.gitSSHCheckout([
Artem Panchenkod10610b2017-01-27 18:09:52 +0200358 credentialsId : "mcp-ci-gerrit",
Artem Panchenkobc13d262017-01-20 12:40:58 +0200359 branch : libCalicoGoCommit,
360 host : host,
361 project : "projectcalico/libcalico-go",
362 targetDir : libcalicogo_path,
363 withWipeOut : true,
364 ])
365
Sergey Kulanovdef4df02017-02-01 14:17:46 +0200366 //FIXME(skulanov) we need to clean local cache for libcalico-go
367 sh "rm -rf ~/.glide/cache/src/file-*"
368
Artem Panchenkobc13d262017-01-20 12:40:58 +0200369 sh "cp ${glideLockFilePath} ${glideLockFilePath}.bak"
370 def glideLockFileContent = readFile file: glideLockFilePath
Sergey Reshetnyak70b1fe62017-01-31 22:27:06 +0300371 def glideMap = common.loadYAML(glideLockFileContent)
Artem Panchenkobc13d262017-01-20 12:40:58 +0200372
373 for (goImport in glideMap['imports']) {
374 if (goImport['name'].contains('libcalico-go')) {
375 goImport['repo'] = 'file:///go/src/github.com/projectcalico/libcalico-go'
376 goImport['vcs'] = 'git'
377 }
378 }
379
Sergey Reshetnyak70b1fe62017-01-31 22:27:06 +0300380 writeFile file: glideLockFilePath, text: common.dumpYAML(glideMap)
Artem Panchenkobc13d262017-01-20 12:40:58 +0200381
382 sh "LIBCALICOGO_PATH=${libcalicogo_path} make vendor"
Artem Panchenkod79430f2017-02-01 00:34:21 +0200383 // need this to reset glide.lock changes (vendor dir is already compiled)
384 // otherwise binaries will be versioned with '-dirty' suffix
385 sh "git checkout ."
Artem Panchenkobc13d262017-01-20 12:40:58 +0200386 }
387}
388
389
390/**
391 * Test Felix stage
392 *
393 * Usage example:
394 *
395 * def calico = new com.mirantis.mcp.Calico()
396 * calico.testFelix()
397 *
398 */
399def testFelix() {
400 stage ('Run felix unittests'){
401 // inject COMPARE_BRANCH variable for felix tests coverage (python code) check
402 def COMPARE_BRANCH = env.GERRIT_BRANCH ? "gerrit/${env.GERRIT_BRANCH}" : "origin/mcp"
403 sh "make ut UT_COMPARE_BRANCH=${COMPARE_BRANCH}"
404 }
405}
406
407
408/**
409 * Build calico/felix image stage
410 *
411 * @param config LinkedHashMap
412 * config includes next parameters:
413 * - dockerRegistry String, Docker registry host to push image to (optional)
414 * - projectNamespace String, artifactory server namespace (optional)
415 * - felixImage String, calico/felix image name (optional)
416 * - felixImageTag String, tag of docker image (optional)
Artem Panchenkocde3c232017-04-19 18:06:37 +0300417 * - dockerFilePath String, path to the Dockerfile for image (optional)
Artem Panchenkobc13d262017-01-20 12:40:58 +0200418 *
419 * Usage example:
420 *
421 * def calicoFunc = new com.mirantis.mcp.Calico()
422 * calicoFunc.buildFelix([
423 * dockerRegistry : 'sandbox-docker-dev-virtual.docker.mirantis.net',
424 * ])
425 *
426 */
427def buildFelix(LinkedHashMap config) {
428
429 def common = new com.mirantis.mcp.Common()
430 def docker = new com.mirantis.mcp.Docker()
431 def git = new com.mirantis.mcp.Git()
432
433 def dockerRegistry = config.get('dockerRegistry')
434 def projectNamespace = config.get('projectNamespace', 'mirantis/projectcalico')
435
436 def felixImage = config.get('felixImage', "calico/felix")
437 def felixImageTag = config.get('felixImageTag', git.getGitDescribe(true) + "-" + common.getDatetime())
Artem Panchenkocde3c232017-04-19 18:06:37 +0300438 def dockerFilePath = config.get('dockerFilePath', "./docker-image/Dockerfile")
Artem Panchenkobc13d262017-01-20 12:40:58 +0200439
440 def felixContainerName = dockerRegistry ? "${dockerRegistry}/${projectNamespace}/${felixImage}:${felixImageTag}" : "${felixImage}:${felixImageTag}"
441
442 stage ('Build calico/felix image') {
Artem Panchenkocde3c232017-04-19 18:06:37 +0300443 docker.setDockerfileLabels(dockerFilePath, ["docker.imgTag=${felixImageTag}"])
Artem Panchenkobc13d262017-01-20 12:40:58 +0200444 sh """
445 make calico/felix
446 docker tag calico/felix ${felixContainerName}
447 """
448 }
449 return [felixImage : felixImage,
450 felixImageTag : felixImageTag]
451}
452
453/**
454 * Test Calicoctl stage
455 *
456 * Usage example:
457 *
458 * def calico = new com.mirantis.mcp.Calico()
459 * calico.testCalicoctl()
460 *
461 */
462def testCalicoctl() {
463 stage ('Run calicoctl unittests'){
464 sh "make test-containerized"
465 }
466}
467
468
469/**
Artem Panchenko6fd07222017-02-13 17:13:23 +0200470 * Run Calico system tests stage
471 *
472 * @param nodeImage String, docker image for calico/node container
473 * @param ctlImage String, docker image with calicoctl binary
474 * @param failOnErrors Boolean, raise exception if some tests fail (default true)
475 *
476 * Usage example:
477 *
478 * def calico = new com.mirantis.mcp.Calico()
479 * calico.systestCalico('calico/node:latest', 'calico/ctl:latest')
480 *
481 */
482def systestCalico(nodeImage, ctlImage, failOnErrors = true) {
483 stage ('Run Calico system tests'){
484 try {
485 // create fake targets to avoid execution of unneeded operations
486 sh """
Pavel Petrov479f04f2017-08-04 23:38:38 +0300487 mkdir -p calicoctl_home/vendor
488 mkdir -p calico_home/vendor
Artem Panchenko6fd07222017-02-13 17:13:23 +0200489 """
490 // pull calico/ctl image and extract calicoctl binary from it
491 sh """
Pavel Petrov479f04f2017-08-04 23:38:38 +0300492 cd calicoctl_home
Artem Panchenko6fd07222017-02-13 17:13:23 +0200493 mkdir -p dist
494 docker run --rm -u \$(id -u):\$(id -g) --entrypoint /bin/cp -v \$(pwd)/dist:/dist ${ctlImage} /calicoctl /dist/calicoctl
495 touch dist/calicoctl dist/calicoctl-linux-amd64
496 """
497 // pull calico/node image and extract required binaries
498 sh """
Pavel Petrov479f04f2017-08-04 23:38:38 +0300499 cd calico_home
500 mkdir -p dist
Artem Panchenko6fd07222017-02-13 17:13:23 +0200501 mkdir -p calico_node/filesystem/bin
502 for calico_binary in startup allocate-ipip-addr calico-felix bird calico-bgp-daemon confd libnetwork-plugin; do
503 docker run --rm -u \$(id -u):\$(id -g) --entrypoint /bin/cp -v \$(pwd)/calico_node/filesystem/bin:/calicobin ${nodeImage} /bin/\${calico_binary} /calicobin/
504 done
505 cp calico_node/filesystem/bin/startup dist/
506 cp calico_node/filesystem/bin/allocate-ipip-addr dist/
507 touch calico_node/filesystem/bin/*
508 touch calico_node/.calico_node.created
509 """
Pavel Petrov479f04f2017-08-04 23:38:38 +0300510 // execute systests against calico/node
511 sh """
Pavel Petrov367bfb12017-09-04 19:53:35 +0300512 cd calico_home/calico_node
Pavel Petrov479f04f2017-08-04 23:38:38 +0300513 NODE_CONTAINER_NAME=${nodeImage} make st
514 """
Artem Panchenko6fd07222017-02-13 17:13:23 +0200515 } catch (Exception e) {
Artem Panchenko6fd07222017-02-13 17:13:23 +0200516 sh """
Pavel Petrovb0accec2017-09-12 14:53:44 +0300517 cd calico_home/calico_node
518 make stop-etcd
519 make clean
520 """
Artem Panchenko6fd07222017-02-13 17:13:23 +0200521 if (failOnErrors) {
522 throw e
523 }
524 }
525 }
526}
527
528
529/**
Artem Panchenkobc13d262017-01-20 12:40:58 +0200530 * Build Calico containers stages
531 *
532 * @param config LinkedHashMap
533 * config includes next parameters:
534 * - dockerRegistry String, repo with docker images
535 * - projectNamespace String, artifactory server namespace
536 * - artifactoryURL String, URL to repo with calico-binaries
Denis Egorenko8c606552016-12-07 14:22:50 +0400537 * - imageTag String, tag of images
538 * - nodeImage String, Calico Node image name
539 * - ctlImage String, Calico CTL image name
Denis Egorenko8c606552016-12-07 14:22:50 +0400540 * - felixImage String, Calico Felix image name
541 * - confdBuildId String, Version of Calico Confd
542 * - confdUrl String, URL to Calico Confd
543 * - birdUrl, URL to Calico Bird
544 * - birdBuildId, Version of Calico Bird
545 * - bird6Url, URL to Calico Bird6
546 * - birdclUrl, URL to Calico BirdCL
547 *
548 * Usage example:
549 *
550 * def calicoFunc = new com.mirantis.mcp.Calico()
Artem Panchenkobc13d262017-01-20 12:40:58 +0200551 * calicoFunc.buildCalicoContainers([
552 * dockerRegistry : 'sandbox-docker-dev-virtual.docker.mirantis.net',
553 * artifactoryURL : 'https://artifactory.mcp.mirantis.net/artifactory/sandbox',
554 * ])
Denis Egorenko8c606552016-12-07 14:22:50 +0400555 *
556 */
Artem Panchenkobc13d262017-01-20 12:40:58 +0200557def buildCalicoContainers(LinkedHashMap config) {
Denis Egorenko8c606552016-12-07 14:22:50 +0400558
Artem Panchenkobc13d262017-01-20 12:40:58 +0200559 def common = new com.mirantis.mcp.Common()
560 def docker = new com.mirantis.mcp.Docker()
561 def git = new com.mirantis.mcp.Git()
Denis Egorenko8c606552016-12-07 14:22:50 +0400562
Artem Panchenkobc13d262017-01-20 12:40:58 +0200563 def dockerRegistry = config.get('dockerRegistry')
564 def projectNamespace = config.get('projectNamespace', 'mirantis/projectcalico')
565 def artifactoryURL = config.get('artifactoryURL')
Denis Egorenko8c606552016-12-07 14:22:50 +0400566
Artem Panchenkobc13d262017-01-20 12:40:58 +0200567 if (! dockerRegistry ) {
568 error('dockerRegistry parameter has to be set.')
Denis Egorenko8c606552016-12-07 14:22:50 +0400569 }
570
Artem Panchenkobc13d262017-01-20 12:40:58 +0200571 if (! artifactoryURL ) {
572 error('artifactoryURL parameter has to be set.')
Denis Egorenko8c606552016-12-07 14:22:50 +0400573 }
574
Pavel Petrov48bc43e2017-08-08 23:32:52 +0300575 def ctlImgTag = null
576 def nodeImgTag = null
Denis Egorenko8c606552016-12-07 14:22:50 +0400577
Artem Panchenkobc13d262017-01-20 12:40:58 +0200578 def nodeImage = config.get('nodeImage', "calico/node")
579 def nodeRepo = "${dockerRegistry}/${projectNamespace}/${nodeImage}"
Pavel Petrov48bc43e2017-08-08 23:32:52 +0300580 def nodeName = null
Denis Egorenko8c606552016-12-07 14:22:50 +0400581
Artem Panchenkobc13d262017-01-20 12:40:58 +0200582 def ctlImage = config.get('ctlImage', "calico/ctl")
583 def ctlRepo = "${dockerRegistry}/${projectNamespace}/${ctlImage}"
Pavel Petrov48bc43e2017-08-08 23:32:52 +0300584 def ctlName = null
Denis Egorenko8c606552016-12-07 14:22:50 +0400585
Denis Egorenko8c606552016-12-07 14:22:50 +0400586 // calico/felix goes from felix
Artem Panchenkobc13d262017-01-20 12:40:58 +0200587 def felixImage = config.get('felixImage', "${dockerRegistry}/${projectNamespace}/calico/felix:latest")
Denis Egorenko8c606552016-12-07 14:22:50 +0400588
Artem Panchenkobc13d262017-01-20 12:40:58 +0200589 def confdBuildId = config.get('confdBuildId', "${artifactoryURL}/${projectNamespace}/confd/latest".toURL().text.trim())
590 def confdUrl = config.get('confdUrl', "${artifactoryURL}/${projectNamespace}/confd/confd-${confdBuildId}")
Denis Egorenko8c606552016-12-07 14:22:50 +0400591
Artem Panchenkobc13d262017-01-20 12:40:58 +0200592 def birdBuildId = config.get('birdBuildId', "${artifactoryURL}/${projectNamespace}/bird/latest".toURL().text.trim())
593 def birdUrl = config.get('birdUrl', "${artifactoryURL}/${projectNamespace}/bird/bird-${birdBuildId}")
594 def bird6Url = config.get('bird6Url', "${artifactoryURL}/${projectNamespace}/bird/bird6-${birdBuildId}")
595 def birdclUrl = config.get('birdclUrl', "${artifactoryURL}/${projectNamespace}/bird/birdcl-${birdBuildId}")
Denis Egorenko8c606552016-12-07 14:22:50 +0400596
Pavel Petrov563f2f72017-09-28 15:14:02 +0300597
Pavel Petrov48bc43e2017-08-08 23:32:52 +0300598 // Configure and build calico/ctl image
599 dir("./calicoctl_home"){
600 ctlImgTag = config.get('imageTag', git.getGitDescribe(true) + "-" + common.getDatetime())
601 ctlName = "${ctlRepo}:${ctlImgTag}"
Denis Egorenko8c606552016-12-07 14:22:50 +0400602
Pavel Petrov48bc43e2017-08-08 23:32:52 +0300603 // Add LABELs to dockerfile
604 docker.setDockerfileLabels("./calicoctl/Dockerfile.calicoctl",
Pavel Petrovfda77592017-08-09 12:18:10 +0300605 ["docker.imgTag=${ctlImgTag}",
Pavel Petrov48bc43e2017-08-08 23:32:52 +0300606 "calico.birdclUrl=${birdclUrl}"])
Denis Egorenko8c606552016-12-07 14:22:50 +0400607
Pavel Petrov48bc43e2017-08-08 23:32:52 +0300608 // Start build process
609 stage ('Build calico/ctl image'){
Pavel Petrovfe753ff2017-08-09 18:17:56 +0300610
611 withEnv(["CTL_CONTAINER_NAME=${ctlName}",
Pavel Petrovfe753ff2017-08-09 18:17:56 +0300612 "BIRDCL_URL=${birdclUrl}"]){
613 sh "make calico/ctl"
614 }
Pavel Petrov48bc43e2017-08-08 23:32:52 +0300615 }
616
Denis Egorenko8c606552016-12-07 14:22:50 +0400617 }
618
Pavel Petrov48bc43e2017-08-08 23:32:52 +0300619 // Configure and build calico/node image
620 dir("./calico_home"){
621 nodeImgTag = config.get('imageTag', git.getGitDescribe(true) + "-" + common.getDatetime())
622 nodeName = "${nodeRepo}:${nodeImgTag}"
Denis Egorenko8c606552016-12-07 14:22:50 +0400623
Pavel Petrov48bc43e2017-08-08 23:32:52 +0300624 // Add LABELs to dockerfile
625 docker.setDockerfileLabels("./calico_node/Dockerfile",
Pavel Petrovfda77592017-08-09 12:18:10 +0300626 ["docker.imgTag=${nodeImgTag}",
Pavel Petrov48bc43e2017-08-08 23:32:52 +0300627 "calico.felixImage=${felixImage}",
628 "calico.confdUrl=${confdUrl}",
629 "calico.birdUrl=${birdUrl}",
630 "calico.bird6Url=${bird6Url}",
631 "calico.birdclUrl=${birdclUrl}"])
632
633 // Start build process
634 stage('Build calico/node'){
Pavel Petrovfe753ff2017-08-09 18:17:56 +0300635
636 withEnv(["NODE_CONTAINER_NAME=${nodeName}",
Pavel Petrovfe753ff2017-08-09 18:17:56 +0300637 "FELIX_CONTAINER_NAME=${felixImage}",
638 "CONFD_URL=${confdUrl}",
639 "BIRD_URL=${birdUrl}",
640 "BIRD6_URL=${bird6Url}",
641 "BIRDCL_URL=${birdclUrl}"]){
642 sh "make -C calico_node calico/node"
643 }
Pavel Petrov48bc43e2017-08-08 23:32:52 +0300644 }
645
Denis Egorenko8c606552016-12-07 14:22:50 +0400646 }
647
648
649 return [
Artem Panchenkobc13d262017-01-20 12:40:58 +0200650 CTL_CONTAINER_NAME:"${ctlImage}",
651 NODE_CONTAINER_NAME:"${nodeImage}",
652 CALICO_NODE_IMAGE_REPO:"${nodeRepo}",
653 CALICOCTL_IMAGE_REPO:"${ctlRepo}",
Pavel Petrov48bc43e2017-08-08 23:32:52 +0300654 CALICO_NODE_VERSION: "${nodeImgTag}",
655 CALICOCTL_VERSION: "${ctlImgTag}"
Denis Egorenko8c606552016-12-07 14:22:50 +0400656 ]
657
658}
Artem Panchenkobc13d262017-01-20 12:40:58 +0200659
660
661/**
662 * Test Calico CNI plugin stage
663 *
664 * Usage example:
665 *
666 * def calico = new com.mirantis.mcp.Calico()
667 * calico.testCniPlugin()
668 *
669 */
670def testCniPlugin() {
671 stage ('Run cni-plugin unittests'){
672 // 'static-checks-containerized' target is removed from master
673 // and kept here only for backward compatibility
674 sh "make static-checks || make static-checks-containerized"
675 sh "make stop-etcd stop-kubernetes-master"
676 // 'stop-k8s-apiserver' target doesn't exist in Calico v2.0.0,
677 // so do not fail the stage if it's not found
678 sh "make stop-k8s-apiserver || true"
679 sh "make test-containerized"
680 }
681}
682
683
684/**
685 * Build calico/cni image stage
686 *
687 * @param config LinkedHashMap
688 * config includes next parameters:
689 * - dockerRegistry String, Docker registry host to push image to (optional)
690 * - projectNamespace String, artifactory server namespace (optional)
691 * - cniImage String, calico/cni image name (optional)
692 * - cniImageTag String, tag of docker image (optional)
693 *
694 * Usage example:
695 *
696 * def calicoFunc = new com.mirantis.mcp.Calico()
697 * calicoFunc.buildFelix([
698 * dockerRegistry : 'sandbox-docker-dev-virtual.docker.mirantis.net',
699 * ])
700 *
701 */
702def buildCniPlugin(LinkedHashMap config) {
703
704 def common = new com.mirantis.mcp.Common()
705 def docker = new com.mirantis.mcp.Docker()
706 def git = new com.mirantis.mcp.Git()
707
708 def dockerRegistry = config.get('dockerRegistry')
709 def projectNamespace = config.get('projectNamespace', 'mirantis/projectcalico')
710
711 def cniImage = config.get('cniImage', "calico/cni")
712 def cniImageTag = config.get('cniImageTag', git.getGitDescribe(true) + "-" + common.getDatetime())
713
714 def cniContainerName = dockerRegistry ? "${dockerRegistry}/${projectNamespace}/${cniImage}:${cniImageTag}" : "${cniImage}:${cniImageTag}"
715
716 stage ('Build calico/cni image') {
717 docker.setDockerfileLabels("./Dockerfile", ["docker.imgTag=${cniImageTag}"])
718 sh """
719 make docker-image
720 docker tag calico/cni ${cniContainerName}
721 """
722 }
723 return [cniImage : cniImage,
724 cniImageTag : cniImageTag]
725}
726
727
728/**
729 * Publish calico docker image stage
730 *
731 * @param config LinkedHashMap
732 * config includes next parameters:
733 * - artifactoryServerName String, artifactory server name
734 * - dockerRegistry String, Docker registry host to push image to
Sergey Kulanova9e65042017-01-31 14:20:24 +0200735 * - dockerRepo String, repository (artifactory) for docker images, must not be Virtual
Artem Panchenkobc13d262017-01-20 12:40:58 +0200736 * - imageName String, Docker image name
737 * - imageTag String, Docker image tag
738 * - projectNamespace String, artifactory server namespace (optional)
739 * - publishInfo Boolean, whether publish a build-info object to Artifactory (optional)
740 *
741 * Usage example:
742 *
743 * def calico = new com.mirantis.mcp.Calico()
744 * calico.publishCalicoImage([
745 * artifactoryServerName : 'mcp-ci',
746 * dockerRegistry : 'sandbox-docker-dev-local.docker.mirantis.net'
747 * dockerRepo : 'sandbox-docker-dev-local',
748 * imageName : 'calico/node',
749 * imageTag : 'v.1.0.0',
750 * ])
751 *
752 */
Sergey Kulanova9e65042017-01-31 14:20:24 +0200753def publishCalicoImage(LinkedHashMap config) {
Artem Panchenkobc13d262017-01-20 12:40:58 +0200754 def artifactory = new com.mirantis.mcp.MCPArtifactory()
755
756 def artifactoryServerName = config.get('artifactoryServerName')
757 def dockerRegistry = config.get('dockerRegistry')
758 def dockerRepo = config.get('dockerRepo')
759 def imageName = config.get('imageName')
760 def imageTag = config.get('imageTag')
761 def projectNamespace = config.get('projectNamespace', 'mirantis/projectcalico')
762 def publishInfo = config.get('publishInfo', true)
763
764 if (!artifactoryServerName) {
765 throw new RuntimeException("Parameter 'artifactoryServerName' must be set for publishCalicoImage() !")
766 }
767 if (!dockerRegistry) {
768 throw new RuntimeException("Parameter 'dockerRegistry' must be set for publishCalicoImage() !")
769 }
770 if (!dockerRepo) {
Sergey Kulanova9e65042017-01-31 14:20:24 +0200771 throw new RuntimeException("Parameter 'dockerRepo' must be set for publishCalicoImage() !")
Artem Panchenkobc13d262017-01-20 12:40:58 +0200772 }
773 if (!imageName) {
774 throw new RuntimeException("Parameter 'imageName' must be set for publishCalicoImage() !")
775 }
776 if (!imageTag) {
777 throw new RuntimeException("Parameter 'imageTag' must be set for publishCalicoImage() !")
778 }
779
780 def artifactoryServer = Artifactory.server(artifactoryServerName)
781 def buildInfo = publishInfo ? Artifactory.newBuildInfo() : null
782
783 stage("Publishing ${imageName}") {
784 artifactory.uploadImageToArtifactory(artifactoryServer,
785 dockerRegistry,
786 "${projectNamespace}/${imageName}",
787 imageTag,
788 dockerRepo,
789 buildInfo)
790 }
791 return "${dockerRegistry}/${projectNamespace}/${imageName}:${imageTag}"
792}
793
794
795/**
796 * Promote calico docker image stage
797 *
798 * @param config LinkedHashMap
799 * config includes next parameters:
800 * - imageProperties Map, docker image search properties in artifactory
801 * - artifactoryServerName String, artifactory server name
802 * - dockerLookupRepo String, docker repository (artifactory) to take image from
803 * - dockerPromoteRepo String, docker repository (artifactory) to promote image to
804 * - imageName String, Docker image name to promote with
805 * - imageTag String, Docker image tag to promote with
806 * - projectNamespace String, artifactory server namespace (optional)
807 * - defineLatest Boolean, promote with latest tag if true, default false (optional)
808 *
809 * Usage example:
810 *
811 * def calico = new com.mirantis.mcp.Calico()
812 * calico.promoteCalicoImage([
813 * imageProperties: [
814 * 'com.mirantis.targetImg': 'mirantis/projectcalico/calico/node',
815 * 'com.mirantis.targetTag': 'v1.0.0-2017010100000',
816 * ]
817 * artifactoryServerName : 'mcp-ci',
818 * dockerLookupRepo : 'sandbox-docker-dev-local',
819 * dockerPromoteRepo: 'sandbox-docker-prod-local',
820 * imageName: 'calico/node',
821 * imageTag: 'v1.0.0',
822 * defineLatest: true
823 * ])
824 *
825 */
826def promoteCalicoImage (LinkedHashMap config) {
827 def common = new com.mirantis.mcp.Common()
828 def git = new com.mirantis.mcp.Git()
829 def artifactory = new com.mirantis.mcp.MCPArtifactory()
830
831 def imageProperties = config.get('imageProperties')
832 def artifactoryServerName = config.get('artifactoryServerName')
833 def dockerLookupRepo = config.get('dockerLookupRepo')
834 def dockerPromoteRepo = config.get('dockerPromoteRepo')
835 def imageName = config.get('imageName')
836 def imageTag = config.get('imageTag')
837 def projectNamespace = config.get('projectNamespace', 'mirantis/projectcalico')
838 def defineLatest = config.get('defineLatest', false)
839
840if (!imageProperties) {
841 throw new RuntimeException("Parameter 'imageProperties' must be set for promoteCalicoImage() !")
842 }
843 if (!artifactoryServerName) {
844 throw new RuntimeException("Parameter 'artifactoryServerName' must be set for promoteCalicoImage() !")
845 }
846 if (!dockerLookupRepo) {
847 throw new RuntimeException("Parameter 'dockerLookupRepo' must be set for promoteCalicoImage() !")
848 }
849 if (!dockerPromoteRepo) {
850 throw new RuntimeException("Parameter 'dockerPromoteRepo' must be set for promoteCalicoImage() !")
851 }
852 if (!imageName) {
853 throw new RuntimeException("Parameter 'imageName' must be set for promoteCalicoImage() !")
854 }
855 if (!imageTag) {
856 throw new RuntimeException("Parameter 'imageTag' must be set for promoteCalicoImage() !")
857 }
858
859 def artifactoryServer = Artifactory.server(artifactoryServerName)
860 def artifactURI = artifactory.uriByProperties(artifactoryServer.getUrl(), imageProperties)
861
862 stage("Promote ${imageName}") {
863 if ( artifactURI ) {
864 def buildProperties = artifactory.getPropertiesForArtifact(artifactURI)
865 if (defineLatest) {
866 artifactory.promoteDockerArtifact(
867 artifactoryServer.getUrl(),
868 dockerLookupRepo,
869 dockerPromoteRepo,
870 "${projectNamespace}/${imageName}",
871 buildProperties.get('com.mirantis.targetTag').join(','),
872 'latest',
873 true
874 )
875 }
876 artifactory.promoteDockerArtifact(
877 artifactoryServer.getUrl(),
878 dockerLookupRepo,
879 dockerPromoteRepo,
880 "${projectNamespace}/${imageName}",
881 buildProperties.get('com.mirantis.targetTag').join(','),
882 "${imageTag}",
883 false
884 )
885 }
886 else {
887 throw new RuntimeException("Artifacts were not found, nothing to promote! "
888 +"Given image properties: ${imageProperties}")
889 }
890 }
891}
892
893
894def calicoFixOwnership() {
895 // files created inside container could be owned by root, fixing that
896 sh "sudo chown -R \$(id -u):\$(id -g) ${env.WORKSPACE} ${env.HOME}/.glide || true"
Pavel Petrov48bc43e2017-08-08 23:32:52 +0300897}