I am writing a Jenkinsplugin. I have set up a pipeline script, when I execute the script its calling some shell scripts and setting up a pipeline. Thats working fine.
Example of my code:
node('master') {
try {
def appWorkspace = './app/'
def testWorkspace = './tests/'
stage('Clean up') {
// cleanWs()
}
stage('Build') {
parallel (
app: {
dir(appWorkspace) {
git changelog: false, credentialsId: 'jenkins.git', poll: false, url: 'https://src.url/to/our/repo'
dir('./App') {
sh "#!/bin/bash -lx \n ./gradlew assembleRelease"
}
}
},
tests: {
dir(testWorkspace) {
git changelog: false, credentialsId: 'jenkins.git', poll: false, url: 'https://src.url/to/our/repo'
sh "#!/bin/bash -lx \n nuget restore ./Tests/MyProject/MyProject.sln"
sh "#!/bin/bash -lx \n msbuild ./Tests/MyProject/MyProject.Core/ /p:Configuration=Debug"
}
}
)
}
stage('Prepare') {
parallel (
'install-apk': {
sh '''#!/bin/bash -lx
result="$(adbExtendedVersion shell pm list packages packagename.app)"
if [ ! -z "$result" ]
then
adbExtendedVersion uninstall packagename.app
fi
adbExtendedVersion install ''' + appWorkspace + '''/path/to/app-release.apk'''
},
'start-appium': {
sh "#!/bin/bash -lx \n GetAllAttachedDevices.sh"
sh "sleep 20s"
}
)
}
stage('Test') {
// Reading content of the file
def portsFileContent = readFile 'file.txt'
// Split the file by next line
def ports = portsFileContent.split('\n')
// Getting device IDs to get properties of device
def deviceIDFileContent = readFile 'IDs.txt'
def deviceIDs = deviceIDFileContent.split('\n')
// Define port and id as an pair
def pairs = (0..<Math.min(ports.size(), deviceIDs.size())).collect { i -> [id: deviceIDs[i], port: ports[i]] }
def steps = pairs.collectEntries { pair ->
["UI Test on ${pair.id}", {
sh "#!/bin/bash -lx \n mono $testWorkspace/Tests/packages/NUnit.ConsoleRunner.3.7.0/tools/nunit3-console.exe $testWorkspace/Tests/bin/Debug/MyProject.Core.dll --params=port=${pair.port}"
}]
}
parallel steps
}
}
catch (Exception e) {
println(e);
}
finally {
stage('Clean') {
archiveArtifacts 'TestResult.xml'
sh "#!/bin/bash -lx \n KillInstance.sh"
}
}
}
This is a groovy script defining my pipeline. What I am trying to achieve with my plugin is, that the user who uses this plugin just inserts some pathvariables eg. path to his solution, or path to his github source. My Plugin then executes the above listed script automatically with the given parameters.
My problem is, that I cant find any documentation how to write such a pipeline construct in Java. If someone could point me in the right direction I would appreciate that.
Related
i'm trying to build tasks to help my team. i have 2 mains branch for front & back and if the developper working on back and need to update front i want to cherry pick all commits from front and vice versa for front to back.
I'm using gradle 7.4.2
Here is my pseudocode to what i want to do :
if (${git branch --show-current} == 'front') {
def st = git cherry-pick $(git merge-base --fork-point back)..back
} else if (${git branch --show-current} == 'back') {
def st = git cherry-pick $(git merge-base --fork-point front)..front
}
But yeah, gradle don't look at that friendly ahahah
Well.. i'm badly new with gradle tasks so don't hesitate to tips me
Actually i have an error to the step to construct the request to get the commit to my final request
plugins {
id 'java'
id 'io.quarkus'
id 'base'
}
ext {
charset = 'UTF-8'
}
def current
task getGitCurrent(type: Exec) {
commandLine 'git', 'branch', '--show-current'
standardOutput = new ByteArrayOutputStream()
ext.current = {
standardOutput.toString(charset)
}
def currentRes = file("${buildDir}/current.txt")
outputs.file currentRes
doLast {
if (!buildDir.exists()) {
buildDir.mkdirs()
}
current = tasks.getGitCurrent.current()
println "current branch : ${current}"
}
}
def commitStart
task getGitCommitStart(dependsOn: 'getGitCurrent') {
doLast {
println "Branche A : ${current}"
def String notCurrent
if (current == "front") {
notCurrent = "back"
} else if (current == "back") {
notCurrent = "front"
} else notCurrent = "master"
println "Branche B : ${notCurrent}"
exec {
commandLine 'git', 'merge-base', '--fork-point', "$notCurrent"
standardOutput = new ByteArrayOutputStream()
ext.commitStartRes = {
standardOutput.toString(charset)
}
def commitStartRes = file("${buildDir}/commitStart.txt")
outputs.file commitStartRes
if (!buildDir.exists()) {
buildDir.mkdirs()
}
commitStart = tasks.getGitCommitStart.commitStart()
}
}
}
And i have this exception who correspond to the line :
outputs.file commitStartRes
* What went wrong:
Execution failed for task ':getGitCommitStart'.
> Cannot call TaskOutputs.file(Object) on task ':getGitCommitStart' after task has started execution.
I just don't understand why my task getGitCommitStart() don't working like getGitCurrent() because it gives me good results. The problem looks about doLast scope, something looks wrong but I'm a little confused, what i'm missing there ?
Well i decomposed step-by-step and i'm so close to get a result, here i am :
task first(type: Exec) {
commandLine 'git', 'branch', '--show-current'
standardOutput = new ByteArrayOutputStream()
ext.current = {
standardOutput.toString(charset)
}
}
task second(dependsOn: 'first') {
def currentRes = file("${buildDir}/current.txt")
outputs.file currentRes
doLast {
if (!buildDir.exists()) {
buildDir.mkdirs()
}
current = tasks.first.current()
currentRes.write(current, charset)
if (current == "front") {
notCurrent = "back"
} else if (current == "back") {
notCurrent = "front"
} else notCurrent = "main"
}
}
task third(type: Exec) {
commandLine 'cmd', 'git', 'merge-base', '--fork-point', "$notCurrent"
standardOutput = new ByteArrayOutputStream()
ext.commitStart = {
standardOutput.toString(charset)
}
}
task last(dependsOn :[second,third]) {
commitStartRes = file("${buildDir}/commitStart.txt")
outputs.file commitStartRes
doLast {
if (!buildDir.exists()) {
buildDir.mkdirs()
}
commitStart = tasks.third.commitStart()
commitStartRes.write(commitStart, charset)
println "current branch : ${current}"
println "not current branch : ${notCurrent}"
println "commit start from : ${commitStart}"
}
}
And this... is working up to the task third where my output is unfortunatly not a commit id but a
Microsoft Windows [version 10.0.22000.795]
(c) Microsoft Corporation. Tous droits r�serv�s.
C:\Users\xxxxx\Documents\Projects\xxx\back>
Well i'm on progress i guess...
When i try to build my main in jenkins it gives me the error in the title, even though i checked and this seems like a valid configuration.
This is th code :
pipeline {
agent any
environment {
DOCKER_PASSWORD = credentials("docker_password")
GITHUB_TOKEN = credentials(".....")
}
stages {
stage('Build & Test') {
steps {
sh './gradlew clean build'
}
stage('Tag image') {
steps {
script {
GIT_TAG = sh([script: 'git fetch --tag && git tag', returnStdout: true]).trim()
MAJOR_VERSION = sh([script: 'git tag | cut -d . -f 1', returnStdout: true]).trim()
MINOR_VERSION = sh([script: 'git tag | cut -d . -f 2', returnStdout: true]).trim()
PATCH_VERSION = sh([script: 'git tag | cut -d . -f 3', returnStdout: true]).trim()
}
sh '''
docker build -t tibicode/hello-img:${MAJOR_VERSION}.\$((${MINOR_VERSION} + 1)).${PATCH_VERSION} ."
docker login docker.io -u tibicode -p ........"
docker push <tibicode>/hello-img:$IMAGE_VERSION"
'''
}
}
}
}
I'm trying to setup logstash in docker.
I'm using the logstash:8.0.0 image.
This is my logstash.yml
http.host: "0.0.0.0"
xpack.monitoring.enabled: false
This is my pipeline.conf
input {
beats {
port => 5044
}
}
output {
elasticsearch {
hosts => ["http://10.135.95.164:9200"]
index => "instameister"
username => "elastic"
password => ""
}
stdout { codec => rubydebug }
}
And this is the error im getting:
Failed to execute action {:action=>LogStash::PipelineAction::Create/pipeline_id:main, :exception=>"Java::JavaLang::IllegalStateException", :message=>"Unable to configure plugins: (ConfigurationError) Something is wrong with your configuration.", :backtrace=>["org.logstash.config.ir.CompiledPipeline.<init>(CompiledPipeline.java:120)", "org.logstash.execution.JavaBasePipelineExt.initialize(JavaBasePipelineExt.java:85)", "org.logstash.execution.JavaBasePipelineExt$INVOKER$i$1$0$initialize.call(JavaBasePipelineExt$INVOKER$i$1$0$initialize.gen)", "org.jruby.internal.runtime.methods.JavaMethod$JavaMethodN.call(JavaMethod.java:837)", "org.jruby.ir.runtime.IRRuntimeHelpers.instanceSuper(IRRuntimeHelpers.java:1169)", "org.jruby.ir.runtime.IRRuntimeHelpers.instanceSuperSplatArgs(IRRuntimeHelpers.java:1156)", "org.jruby.ir.targets.InstanceSuperInvokeSite.invoke(InstanceSuperInvokeSite.java:39)", "usr.share.logstash.logstash_minus_core.lib.logstash.java_pipeline.RUBY$method$initialize$0(/usr/share/logstash/logstash-core/lib/logstash/java_pipeline.rb:47)", "org.jruby.internal.runtime.methods.CompiledIRMethod.call(CompiledIRMethod.java:80)", "org.jruby.internal.runtime.methods.MixedModeIRMethod.call(MixedModeIRMethod.java:70)", "org.jruby.runtime.callsite.CachingCallSite.cacheAndCall(CachingCallSite.java:333)", "org.jruby.runtime.callsite.CachingCallSite.call(CachingCallSite.java:87)", "org.jruby.RubyClass.newInstance(RubyClass.java:939)", "org.jruby.RubyClass$INVOKER$i$newInstance.call(RubyClass$INVOKER$i$newInstance.gen)", "org.jruby.ir.targets.InvokeSite.invoke(InvokeSite.java:207)", "usr.share.logstash.logstash_minus_core.lib.logstash.pipeline_action.create.RUBY$method$execute$0(/usr/share/logstash/logstash-core/lib/logstash/pipeline_action/create.rb:50)", "usr.share.logstash.logstash_minus_core.lib.logstash.pipeline_action.create.RUBY$method$execute$0$__VARARGS__(/usr/share/logstash/logstash-core/lib/logstash/pipeline_action/create.rb:49)", "org.jruby.internal.runtime.methods.CompiledIRMethod.call(CompiledIRMethod.java:80)", "org.jruby.internal.runtime.methods.MixedModeIRMethod.call(MixedModeIRMethod.java:70)", "org.jruby.ir.targets.InvokeSite.invoke(InvokeSite.java:207)", "usr.share.logstash.logstash_minus_core.lib.logstash.agent.RUBY$block$converge_state$2(/usr/share/logstash/logstash-core/lib/logstash/agent.rb:376)", "org.jruby.runtime.CompiledIRBlockBody.callDirect(CompiledIRBlockBody.java:138)", "org.jruby.runtime.IRBlockBody.call(IRBlockBody.java:58)", "org.jruby.runtime.IRBlockBody.call(IRBlockBody.java:52)", "org.jruby.runtime.Block.call(Block.java:139)", "org.jruby.RubyProc.call(RubyProc.java:318)", "org.jruby.internal.runtime.RubyRunnable.run(RubyRunnable.java:105)", "java.base/java.lang.Thread.run(Thread.java:829)"]}
All i see is the Unable to configure plugins: (ConfigurationError) Something is wrong with your configuration. But i have no idea whats wrong.
Instead of modifying logstash.yml, you can override the variables in the environment instead. Your pipeline.conf seems to be Ok. rubydebug codec is enabled by default for stdout.
So, assuming that you have a docker compose file, the configuration would be something like this:
logstash:
image: docker.elastic.co/logstash/logstash
container_name: logstash
restart: always
user: root
volumes:
- ./logstash/pipeline:/usr/share/logstash/pipeline:ro
- ./logstash/logs/:/logstash/logs/:rw
environment:
- xpack.monitoring.enabled=false
- outputs.elasticsearch=http://elasticuser:elasticuserpassword#elasticsearch:9200
depends_on:
- elasticsearch
In the ./logstash/pipeline directory, a logstash.conf file with:
input {
beats {
port => 5044
}
}
output {
elasticsearch {
hosts => "${outputs.elasticsearch}"
}
stdout {
}
}
Adapt to your needs.
The problem was that the key 'username' should be 'user'
This is the working config:
input {
beats {
port => 5044
}
}
output {
elasticsearch {
hosts => ["http://10.135.95.164:9200"]
user => "elastic"
password => ""
index => "instameister"
manage_template => false
}
stdout { codec => json_lines }
}
I have followed a tutorial to implement an observe follower notification.
exports.observeFollowing = functions.database.ref('/following/{uid}/{followingId}').onCreate((snapshot, context) => {
var uid = context.params.uid;
var followingId = context.params.followingId;
console.log('User: ' + uid + ' is following: ' + followingId);
return admin.database().ref('/users/' + followingId).once('value', snapshot => {
var userWeAreFollowing = snapshot.val();
return admin.database().ref('/users/' + uid).once('value', snapshot => {
var userDoingTheFollowing = snapshot.val();
var payload = {
notification: {
title: "You now have a new follower",
body: userDoingTheFollowing.username + "is now following you",
sound: 'default'
}
}
admin.messaging().sendToDevice(userWeAreFollowing.fcmToken, payload)
.then((response) => {
console.log('Successfully sent message:', response);
return response;
}).catch(function(error) => {
console.log('Error sending message:', error);
});
})
})
})
However, when I tried to run firebase deploy --only functions:observeFollowing I receive the following error:
npm ERR! code ELIFECYCLE
npm ERR! errno 1
npm ERR! functions# lint: `eslint .`
npm ERR! Exit status 1
npm ERR!
npm ERR! Failed at the functions# lint script.
npm ERR! This is probably not a problem with npm. There is likely additional logging output above.
I had tried to search answers from Stackoverflow but none of the answers seen to work.
I can ps-session to a remote machine, run the following, and successfully uninstall Java:
invoke-expression "msiexec /q /x '{26A24AE4-039D-4CA4-87B4-2F83218025F0}' "
I am trying to create a script that will uninstall from all domain computers:
Import-Module ActiveDirectory
function uninstallJava {
$badcomp = #()
$CompList = Get-ADComputer -Filter 'name -like "*"' | select -ExpandProperty Name
foreach ($c in $CompList) {
Try {
Enter-PSSession -ComputerName $computer
Invoke-expression "msiexec.exe /q /x '{26A24AE4-039D-4CA4-87B4-2F83218025F0}' "
}
Catch {
$badcomp += $c
}
}
}
uninstallJava
"the following servers could not be reached:"
$badcomp
I don't receive any errors, but it doesn't uninstall Java from the remote machines.
Any ideas appreciated.
Import-Module ActiveDirectory
$badcomp = #()
Function uninstallJava {
$CompList = Get-ADComputer -Filter 'name -like "*"' | Select -ExpandProperty Name
ForEach ($c In $CompList) {
Try {
Invoke-Command -ComputerName $c {
C:\Windows\System32\cmd.exe /C msiexec.exe /q /x '{26A24AE4-039D-4CA4-87B4-2F83218025F0}'
}
} Catch {
$badcomp += $c
}
}
}
uninstallJava
Write-Host "the following servers could not be reached:"
$badcomp
You should be using Invoke-Command, not Enter-PSSession. The latter is for interactively working in another machine. The former is for running a command in the other machine and getting back results (if any).
Basically, your try block should look like this:
Try {
Invoke-Command -ComputerName $c -ScriptBlock { msiexec.exe /q /x '{26A24AE4-039D-4CA4-87B4-2F83218025F0}' }
}
If you want more detailed control and error information, consider using WMI to uninstall the product instead of shelling out to msiexec.