Skip to content

Jenkins pipeline for sending PRs to agents when changing the BDD specs #231

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 27 commits into from
Mar 30, 2020
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
27 commits
Select commit Hold shift + click to select a range
de5c757
ci: first iteration to send a PR to apm agents
mdelapenya Mar 25, 2020
14cc5c7
ci: use a build agent in the stage
mdelapenya Mar 25, 2020
9008ffb
ci: remove when clause
mdelapenya Mar 25, 2020
d9cca8c
ci: perform checkout in the proper dir
mdelapenya Mar 25, 2020
8f2155d
ci: support sending PRs to the subscribed agents in parallel
mdelapenya Mar 25, 2020
ca7e0fb
ci: install HUB in the build agent
mdelapenya Mar 25, 2020
96bf7f6
ci: remove leftovers from template pipeline
mdelapenya Mar 25, 2020
2b9b494
ci: improve build agents usage
mdelapenya Mar 26, 2020
da7ce62
ci: refine environment variables definition
mdelapenya Mar 26, 2020
c62df02
ci: fix hub path
mdelapenya Mar 26, 2020
27b14f6
ci: use gitCheckout build step
mdelapenya Mar 26, 2020
a154543
ci: subscribe more agents
mdelapenya Mar 26, 2020
bb85e67
ci: fixed BASE_DIR for parallel execution
mdelapenya Mar 26, 2020
ba0cba6
ci: simplify stage name
mdelapenya Mar 26, 2020
b65be94
ci: support a parameter to send the pr, false by default
mdelapenya Mar 26, 2020
8da3a39
ci: improve send-pr script using HUB
mdelapenya Mar 26, 2020
34c1ce0
ci: refine pipeline after review
mdelapenya Mar 26, 2020
522bb6c
ci: simplify git dir calculation
mdelapenya Mar 26, 2020
7698953
ci: fix typo in env var
mdelapenya Mar 26, 2020
b9512f0
ci: quote values and remove non-needed mkdir
mdelapenya Mar 26, 2020
0f57f6a
ci: use conventional commits
mdelapenya Mar 26, 2020
c1cb41e
ci: use default branch as target of the PR
mdelapenya Mar 26, 2020
44f84ea
ci: refine messages
mdelapenya Mar 26, 2020
08f9d9a
ci: set default git user in the build agent
mdelapenya Mar 26, 2020
d50d4ae
ci: send the PRs if and only if there are changes in the gherkin specs
mdelapenya Mar 26, 2020
d2d7ed4
ci: indent block properly
mdelapenya Mar 26, 2020
9ed5ddd
ci: fix github reviewer
mdelapenya Mar 27, 2020
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
12 changes: 12 additions & 0 deletions .ci/.jenkins-agents.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
---
agents:
- NAME: "dotnet"
FEATURES_PATH: "test/Elastic.Apm.Feature.Tests/Features"
- NAME: "go"
FEATURES_PATH: "features"
- NAME: "java"
FEATURES_PATH: "apm-agent-core/src/test/resources/specs"
- NAME: "python"
FEATURES_PATH: "tests/bdd/features"
- NAME: "ruby"
FEATURES_PATH: "features"
121 changes: 121 additions & 0 deletions .ci/Jenkinsfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,121 @@
// Licensed to Elasticsearch B.V. under one or more contributor
// license agreements. See the NOTICE file distributed with
// this work for additional information regarding copyright
// ownership. Elasticsearch B.V. licenses this file to you under
// the Apache License, Version 2.0 (the "License"); you may
// not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing,
// software distributed under the License is distributed on an
// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
// KIND, either express or implied. See the License for the
// specific language governing permissions and limitations
// under the License.

@Library('apm@current') _

pipeline {
agent { label 'linux && immutable' }
environment {
REPO = 'apm'
BASE_DIR = "src/github.com/elastic/${env.REPO}"
HOME = "${env.WORKSPACE}"
NOTIFY_TO = credentials('notify-to')
JOB_GCS_BUCKET = credentials('gcs-bucket')
JOB_GIT_CREDENTIALS = "f6c7695a-671e-4f4f-a331-acdce44ff9ba"
PATH = "${env.PATH}:${env.WORKSPACE}/bin"
PIPELINE_LOG_LEVEL='INFO'
}
options {
timeout(time: 3, unit: 'HOURS')
buildDiscarder(logRotator(numToKeepStr: '5', artifactNumToKeepStr: '5'))
timestamps()
ansiColor('xterm')
disableResume()
durabilityHint('PERFORMANCE_OPTIMIZED')
}
parameters {
booleanParam(name: 'Do_Send_PR', defaultValue: false, description: 'Allows to execute this pipeline in dry run mode, without sending a PR.')
}
stages {
stage('Initializing'){
options { skipDefaultCheckout() }
stages {
stage('Checkout'){
steps {
deleteDir()
gitCheckout(basedir: "${BASE_DIR}",
branch: "master",
repo: "git@github.com:elastic/${REPO}.git",
credentialsId: "${JOB_GIT_CREDENTIALS}"
)
stash allowEmpty: true, name: 'source', useDefaultExcludes: false
script {
dir("${BASE_DIR}"){
def regexps =[
"^tests/agents/gherkin-specs/"
]
env.GHERKIN_SPECS_UPDATED = isGitRegionMatch(patterns: regexps)
}
}
Comment on lines +56 to +63
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is the block that controls if there are changes in the gherkin files. If so, the environment variable will be set to true, causing https://github.com/elastic/apm/pull/231/files#diff-8db37e8fcea0f1a8f2f39667e94ebcc4R76 to evaluate to true too

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Because of this, the script sending the PR has to add no logic for checking if changes exist, so it just follow orders from the pipeline.

}
}
stage('Send Pull Request'){
options {
skipDefaultCheckout()
warnError('Pull Requests to APM agents failed')
}
environment {
DO_SEND_PR = "${params.Do_Send_PR}"
}
when {
beforeAgent true
expression { return env.GHERKIN_SPECS_UPDATED != "false" }
}
steps {
unstash 'source'
dir("${BASE_DIR}"){
script {
def agents = readYaml(file: '.ci/.jenkins-agents.yml')
def parallelTasks = [:]
agents['agents'].each { agent ->
parallelTasks["apm-agent-${agent.NAME}"] = generateStepForAgent(agent: "${agent.NAME}", featuresPath: "${agent.FEATURES_PATH}")
}

parallel(parallelTasks)
}
}
}
}
}
}
}
post {
cleanup {
notifyBuildResult()
}
}
}

def generateStepForAgent(Map params = [:]){
def agent = params.get('agent')
def featuresPath = params.get('featuresPath')
log(level: 'INFO', text: "agent=${agent} featuresPath=${featuresPath}")
return {
node('linux && immutable') {
catchError(buildResult: 'SUCCESS', stageResult: 'UNSTABLE') {
deleteDir()
gitCmd(cmd: "config", credentialsId: '', args: '--global user.name elasticmachine')
gitCmd(cmd: "config", credentialsId: '', args: '--global user.email infra-root-elasticmachine@elastic.co')
unstash 'source'
dir("${BASE_DIR}"){
sh script: '.ci/scripts/install-dependencies.sh', label: "Install dependencies"
sh script: """.ci/scripts/send-pr.sh "${agent}" "${featuresPath}" """, label: "Send Pull Request for apm-agent-${agent}"
}
}
}
}
}
11 changes: 11 additions & 0 deletions .ci/scripts/install-dependencies.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
#!/usr/bin/env bash

set -uexo pipefail

readonly HUB_VERSION="2.14.2"
readonly HUB_CMD="${HOME}/bin"

# install GitHub's hub
curl -fsSL https://github.com/github/hub/raw/master/script/get | bash -s ${HUB_VERSION}
mkdir -p ${HUB_CMD}
mv bin/hub "${HUB_CMD}/hub"
30 changes: 30 additions & 0 deletions .ci/scripts/send-pr.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
#!/usr/bin/env bash

set -uexo pipefail

readonly APM_AGENT=${1}
readonly APM_AGENT_SPECS_DIR=${2}
readonly APM_AGENT_REPO_NAME="apm-agent-${APM_AGENT}"
readonly GIT_DIR=".ci/git"
readonly APM_AGENT_REPO_DIR="${GIT_DIR}/${APM_AGENT_REPO_NAME}"

git clone "https://github.com/elastic/${APM_AGENT_REPO_NAME}" "${APM_AGENT_REPO_DIR}"

mkdir -p "${APM_AGENT_REPO_DIR}/${APM_AGENT_SPECS_DIR}"
echo "Copying feature files to the ${APM_AGENT_REPO_NAME} repo"
cp tests/agents/gherkin-specs/*.feature "${APM_AGENT_REPO_DIR}/${APM_AGENT_SPECS_DIR}"

cd ${APM_AGENT_REPO_DIR}
git checkout -b update-feature-files-$(date "+%Y%m%d%H%M%S")
git add ${APM_AGENT_SPECS_DIR}
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ideally, the git user.name and user.email should be in place (see PR 17214 in the infra repo), if that's not the case, then you might get some warnings, or maybe some errors, although I don't recall now.

I'd say to use some validation in case they are not defined to set them. what do you think?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Instead of a validation, I have added two gitCmd calls to ensure they are present in the build agent (see 08f9d9a). wdyt?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I started with the check, but I realised that it is worth it to be prescriptive in this case, where we do not want other configuration. Just in case, that was my initial validation, at script level:

readonly GIT_USERNAME="elasticmachine"
readonly GIT_EMAIL="infra-root-${GIT_USERNAME}@elastic.co"

function checkGitConfig {
    local config="${1}"
    local defaultValue="${2}"

    git config "${config}"
    local exitCode=$?
    if [ ${exitCode} -ne 0 ]; then
        git config "${config}" "${defaultValue}"
    fi
}

function checkGit {
    checkGitConfig "user.name" "${GIT_USERNAME}"
    checkGitConfig "user.email" "${GIT_EMAIL}"
}

git commit -m "test: synchronizing bdd specs"

if [[ "${DO_SEND_PR}" == "true" ]]; then
hub pull-request \
-p \ # push the branch to the remote
--labels automation \ # comma-separated list of tags
--reviewer @elastic/apm-agent-devs \ # set agents as reviewer of the PR
-m "test: synchronizing bdd specs" # PR message
else
echo "PR sent to ${APM_AGENT_REPO_NAME}"
fi