Configuration for multi-step parallel stages - drone.io

I have a mono-repo that contains multiple services. Ideally, I want to test each service in parallel. Each branch has 2 stages:
test
benchmark
To give something similar to this:
clone
/ \
/ \
/ \
/ \
svc1-test svc2-test
| |
svc1-bench svc2-bench
\ /
\ /
\ /
\ /
notify
The build would pass only if the all branches have succeeded. Furthermore, we could fail a branch early and not execute the benchmarking if the tests fail for any given branch.
From reading the documentation I see how I can run parallel stages using group, but not how to put many stages in a single branch.
I guess my fallback solution would be to put combine test+benchmark in a single stage, but I think it would be nice to isolate them, especially since the dependencies may vary for each.

I was looking for something similar and found it answered here by the user cdieck.
This is how it looks in Blue Ocean.
Copying the same for quick reference:
pipeline {
agent none
stages {
stage("Example") {
failFast true
parallel {
stage("win7-vs2012") {
agent {
label "win7-vs2012"
}
stages {
stage("checkout (win7-vs2012)") {
steps {
echo "win7-vs2012 checkout"
}
}
stage("build (win7-vs2012)") {
steps {
echo "win7-vs2012 build"
}
}
stage("test (win7-vs2012)") {
steps {
build 'test-win7-vs2012'
}
}
}
}
stage("win10-vs2015") {
agent {
label "win10-vs2015"
}
stages {
stage("checkout (win10-vs2015)") {
steps {
echo "win10-vs2015 checkout"
}
}
stage("build (win10-vs2015)") {
steps {
echo "win10-vs2015 build"
}
}
stage("test (win10-vs2015)") {
steps {
build 'test-win10-vs2015'
}
}
}
}
stage("linux-gcc5") {
agent {
label "linux-gcc5"
}
stages {
stage("checkout (linux-gcc5)") {
steps {
echo "linux-gcc5 checkout"
}
}
stage("build (linux-gcc5)") {
steps {
echo "linux-gcc5 build"
}
}
stage("test (linux-gcc5)") {
steps {
build 'test-linux-gcc5'
}
}
}
}
}
}
}
}

Related

How to set a pre-defined dynamic name for a variable in a jenkins declarative pipeline

Is it possible to set a pre-defined dynamic name for a variable in a jenkins declarative pipeline ?
env {
TEST_2_SERIAL = 456789
}
stage('Test') {
steps {
echo ${TEST_${HARDWARE}_SERIAL}
}
}
when ${HARDWARE} value is 2 and ${TEST_2_SERIAL} value is predefined as 456789, then ${TEST_${HARDWARE}_SERIAL} should be 456789
I don't know if it achieves what you expect but it is possible to access the environment variable dynamically in this way.
pipeline {
agent any
environment {
TEST_2_SERIAL = 456789
HARDWARE = '2'
}
stages{
stage('Test') {
steps {
echo env["TEST_${HARDWARE}_SERIAL"]
}
}
}
}
The echo will print out the value of TEST_2_SERIAL.

How to fetch all repositories with specific topic, using GitHub GraphQL API?

I am trying to fetch all my repositories that contain topic "portfolio" using Github GraphQL API.
For now, I found only how to fetch all repos on github with a specific topic, like so :
{
search(type: REPOSITORY, query: "topic: portfolio", last: 50) {
repos: edges {
repo: node {
... on Repository {
url
}
}
}
}
}
And I know how to fetch all repos for a specific user, like so:
{
user(login: "VitFL") {
repositories(last: 50) {
repos: nodes {
url
}
}
}
}
But I have no idea how to combine those queries, so I could receive all repos with topic "portfolio" for a specific user.
Does anyone know how to achieve this result?
Using search(), a user argument can be added to the query value.
Also, the whitespace after the colon should be removed, i.e. topic: portfolio -> topic:portfolio. You will notice far more results with this change.
{
search(type: REPOSITORY, query: "user:VitFL topic:portfolio", last: 50) {
repos: edges {
repo: node {
... on Repository {
url
}
}
}
}
}

Issue using Mobbeel Fataar plugin with uploadArchives task

I'm in the process of trying to create a fat AAR to distribute my Android library. I'm using the Mobbeel Fataar plugin to package all of my dependencies into an AAR for ease of distribution. This works perfectly, and when I run ./gradlew build, I get an AAR file in mylibrary/build/outputs/aar/ called mylibrary-release.aar and it includes all of my dependencies in its libs directory. The issue arises when I attempt to distribute the AAR.
In order to distribute, I found this tutorial to take me through it, which I'm using virtually unchanged. Here's that code (in my build.gradle):
apply plugin: 'maven'
apply plugin: 'signing'
def isReleaseBuild() {
return VERSION_NAME.contains("SNAPSHOT") == false
}
def getReleaseRepositoryUrl() {
return hasProperty('RELEASE_REPOSITORY_URL') ? RELEASE_REPOSITORY_URL
: "https://oss.sonatype.org/service/local/staging/deploy/maven2/"
}
def getSnapshotRepositoryUrl() {
return hasProperty('SNAPSHOT_REPOSITORY_URL') ? SNAPSHOT_REPOSITORY_URL
: "https://oss.sonatype.org/content/repositories/snapshots/"
}
def getRepositoryUsername() {
return hasProperty('NEXUS_USERNAME') ? NEXUS_USERNAME : ""
}
def getRepositoryPassword() {
return hasProperty('NEXUS_PASSWORD') ? NEXUS_PASSWORD : ""
}
afterEvaluate { project ->
uploadArchives {
repositories {
mavenDeployer {
beforeDeployment { MavenDeployment deployment -> signing.signPom(deployment) }
pom.groupId = GROUP
pom.artifactId = POM_ARTIFACT_ID
pom.version = VERSION_NAME
repository(url: getReleaseRepositoryUrl()) {
authentication(userName: getRepositoryUsername(), password: getRepositoryPassword())
}
snapshotRepository(url: getSnapshotRepositoryUrl()) {
authentication(userName: getRepositoryUsername(), password: getRepositoryPassword())
}
pom.project {
name POM_NAME
packaging POM_PACKAGING
description POM_DESCRIPTION
url POM_URL
scm {
url POM_SCM_URL
connection POM_SCM_CONNECTION
developerConnection POM_SCM_DEV_CONNECTION
}
licenses {
license {
name POM_LICENCE_NAME
url POM_LICENCE_URL
distribution POM_LICENCE_DIST
}
}
developers {
developer {
id POM_DEVELOPER_ID
name POM_DEVELOPER_NAME
}
}
}
}
}
}
signing {
required { isReleaseBuild() && gradle.taskGraph.hasTask("uploadArchives") }
sign configurations.archives
}
task androidSourcesJar(type: Jar) {
classifier = 'sources'
from android.sourceSets.main.java.sourceFiles
}
artifacts {
archives androidSourcesJar
}
}
The issue is that, when I run ./gradlew :mylibrary:uploadArchives, it creates a mylibrary-1.0.aar file in mylibrary/build/outputs/aar/ and uploads that file. The problem is that it doesn't have my dependencies bundled in.
I'd like to somehow create mylibrary-1.0.aar with all of my dependencies bundled, and then have that be uploaded. Unfortunately I don't have a completely clear understanding of how the upload code I'm using works. Does anyone know how I can do what I want?

Custom Gradle task to build all projects without testing?

I know I can execute 'gradle build -x test', but is there a way to create a custom Gradle task, say, buildNoTests, which will build all of my projects but will completely ignore tests (don't compile/run them)?
I read that the 'assemble' task is not enough as it may miss other tasks which are not tests but are included in the 'build' task.
Put this in the root build.gradle
allprojects {
afterEvaluate {
def buildTask = tasks.findByPath('build')
if (buildTask) {
task buildNoTests {
dependsOn buildTask
}
gradle.taskGraph.whenReady { TaskExecutionGraph graph ->
if (graph.hasTask(buildNoTests)) {
def skipNames = ['test', 'compileTestJava', 'processTestResources', 'testClasses'] as Set
Collection<Task> testTasks = graph.allTasks.findAll { skipNames.contains(it.name) }
testTasks.each { it.enabled = false }
}
}
}
}
}

Configuring multiple upload repositories in Gradle build

I want to upload my artifacts to a remote Nexus repo. Therefore I have configured a snaphot and a release repo in Nexus. Deployment to both works.
Now I want to configure my build so I can decide in which repo I want to deploy:
gradle uploadArchives should deploy to my snapshots repo
gradle release uploadArchives should deploy to my release repo
This was my try:
apply plugin: 'war'
apply plugin: 'maven'
group = 'testgroup'
version = '2.0.0'
def release = false
repositories {
mavenCentral()
mavenLocal()
}
dependencies{ providedCompile 'javax:javaee-api:6.0' }
task release <<{
release = true;
println 'releasing!'
}
uploadArchives {
repositories {
mavenDeployer {
repository(url: "http://.../nexus/content/repositories/releases"){
authentication(userName: "admin", password: "admin123")
}
addFilter('lala'){ x, y -> release }
}
mavenDeployer {
repository(url: "http://.../nexus/content/repositories/snapshots"){
authentication(userName: "admin", password: "admin123")
}
addFilter('lala'){ x, y ->!release}
pom.version = version + '-SNAPSHOT'
}
}
}
The build works if I comment out one of the two mavenDeployer configs, but not as a whole.
Any ideas how to configure two target archives in one build file?
One solution is to add an if-else statement that adds exactly one of the two deployers depending on the circumstances. For example:
// should defer decision until end of configuration phase
gradle.projectsEvaluated {
uploadArchives {
repositories {
mavenDeployer {
if (version.endsWith("-SNAPSHOT")) { ... } else { ... }
}
}
}
}
If you do need to vary the configuration based on whether some task is "present", you can either make an eager decision based on gradle.startParameter.taskNames (but then you'll only catch tasks that are specified as part of the Gradle invocation), or use the gradle.taskGraph.whenReady callback (instead of gradle.projectsEvaluated) and check whether the task is scheduled for execution.
Correct me if I'm wrong, but shouldn't you use the separate snapshotRepository in this case (as opposed to an if statement)? For example,
mavenDeployer {
repository(url: "https://oss.sonatype.org/service/local/staging/deploy/maven2/") {
authentication(userName: sonatypeUsername, password: sonatypePassword)
}
snapshotRepository(url: "https://oss.sonatype.org/content/repositories/snapshots/") {
authentication(userName: sonatypeUsername, password: sonatypePassword)
}
}