http://localhost/computer/slave_name/api/json?pretty=true -- 浏览器查看
https://www.cnblogs.com/zjsupermanblog/archive/2017/07/26/7238422.html -- API 比较详细
https://javadoc.jenkins-ci.org/hudson/model/Computer.html#offlineCause -- 官方文档,详细
-
只需要将slave_name换成指定的slave名称即可,返回数据是json格式的
-
如果key offline的value为true说该slave掉线了,offlineCauseReason表面原因。
-
可以写个简单地python脚本,把脚本放到jenkins上定时执行进行监控,最好是限定这个任务在master上执行,保证任务顺利执行。shell里可以判断返回不为空时设置为exit 1,使任务失败,对于任务失败配置邮件(构建后任务里)提醒即可。
import urllib2
import json
baseapi = http://localhost/computer/%s/api/json?pretty=true
def request(slaves):
slaveapis = slaves.split(",")
offlineapi = ""
for api in slaveapis:
url = baseapi % api
ret = json.load(urllib2.urlopen(url))
if ret['offline']:
offlineapi += url
offlineapi += ","
return offlineapi
import jenkins.model.Jenkins
import hudson.model.User
import hudson.security.Permission
import hudson.EnvVars
import hudson.model.*
import jenkins.*
import jenkins.model.*
import hudson.*
import hudson.model.*
.model.*
slaves = hudson.model.Hudson.instance.slaves
offlines = []
onlines=[]
for(slave in slaves){
if(slave.getComputer().isOnline() == true){
onlines.add(slave.name)
}
if(slave.getComputer().getOfflineCause().toString().contains('Disconnected by')){
offlines.add(slave.name)
println 'offline casue is : ' + slave.getComputer().getOfflineCause()
}
}
println onlines
println offlines
简化
def offs = slaves.findAll{it.getComputer().getOfflineCause().toString().contains('Disconnected by')}
def offs_names = offs.collect{[it.name,it.getComputer().getOfflineCause().toString()]}
println offs
def ons = slaves.findAll{it.getComputer().isOnline() == true}
def ons_names = ons.collect{it.name}
println ons
《============================================》
只能做筛选,不能用于pipeline中,因为会引起序列化错误。
在pipeline中一定要使用for(slave in slaves){}结构。
《============================================》
def slaves = hudson.model.Hudson.instance.slaves
def offs = slaves.findAll{it.getComputer().getOfflineCause().toString().contains('Disconnected by')}
println offs
if(offs.size() > 0){offs.each{println it.name+ ' : '+it.getComputer().getOfflineCause().toString()}}
else{println 'no nodes to be on lines'}
def slaves = hudson.model.Hudson.instance.slaves
def ons = slaves.findAll{it.getComputer().isOnline() == true}
println ons
if(ons.size() > 0){
ons.each{
println it.name
//该指令的offline cause无效
it.getComputer().setTemporarilyOffline(true,'from off_line stage')
}
}
else{ println "No nodes to be on_line"}
for (aSlave in hudson.model.Hudson.instance.slaves) {
println('====================');
println('Name: ' + aSlave.name);
println('getLabelString: ' + aSlave.getLabelString());
println('getNumExectutors: ' + aSlave.getNumExecutors());
println('getRemoteFS: ' + aSlave.getRemoteFS());
println('getMode: ' + aSlave.getMode());
println('getRootPath: ' + aSlave.getRootPath());
println('getDescriptor: ' + aSlave.getDescriptor());
println('getComputer: ' + aSlave.getComputer());
println('computer.isAcceptingTasks: ' + aSlave.getComputer().isAcceptingTasks());
println('computer.isLaunchSupported: ' + aSlave.getComputer().isLaunchSupported());
println('computer.getConnectTime: ' + aSlave.getComputer().getConnectTime());
println('computer.getDemandStartMilliseconds: ' + aSlave.getComputer().getDemandStartMilliseconds());
println('computer.isOffline: ' + aSlave.getComputer().isOffline());
println('computer.offlineCause: ' + aSlave.getComputer().getOfflineCause());
println('computer.countBusy: ' + aSlave.getComputer().countBusy());
println('computer.getLog: ' + aSlave.getComputer().getLog());
println('computer.getBuilds: ' + aSlave.getComputer().getBuilds());
if (aSlave.name == 'NAME OF NODE TO DELETE') {
println('Shutting down node!!!!');
aSlave.getComputer().setTemporarilyOffline(true,null);
aSlave.getComputer().doDoDelete();
}
}
http://www.voidcn.com/article/p-mkxeljmv-nh.html
通过master,远程控制slave
import hudson.util.RemotingDiagnostics;
print_ip = 'println InetAddress.localHost.hostAddress';
print_hostname = 'println InetAddress.localHost.canonicalHostName';
// here it is - the shell command, uname as example
uname = 'def proc = "uname -a".execute(); proc.waitFor(); println proc.in.text';
for (slave in hudson.model.Hudson.instance.slaves) {
println slave.name;
println RemotingDiagnostics.executeGroovy(print_ip, slave.getChannel());
println RemotingDiagnostics.executeGroovy(print_hostname, slave.getChannel());
println RemotingDiagnostics.executeGroovy(uname, slave.getChannel());
}
简易方法:
for (aSlave in hudson.model.Hudson.instance.slaves) {
println('====================');
println('Name: ' + aSlave.name);
println('computer.getLog: ' + aSlave.getComputer().getLog().split('\n').toList()[0].split("/")[-2].split(' ')[-1])
}
it.getComputer().cliOnline()
it.getComputer().doDoDisconnect('temp offline') // 这个是下线,不是临时下线,offlineCause没有显示
it.getComputer().disconnect()
临时下线
it.getComputer().setTemporarilyOffline(true,null)
it.getComputer().doChangeOfflineCause('abc')
echo ???? > secret-file
java -jar agent.jar -jnlpUrl http://localhost:9000/computer/456/slave-agent.jnlp -secret @secret-file -workDir "E:\???\????"
https://github.com/jenkinsci/ssh-steps-plugin
ssh 发送命令
node {
def remote = [:]
remote.name = 'test'
remote.host = 'test.domain.com'
remote.user = 'root'
remote.password = 'password'
remote.allowAnyHosts = true
stage('Remote SSH') {
sshCommand remote: remote, command: "ls -lrt"
sshCommand remote: remote, command: "for i in {1..5}; do echo -n \"Loop \$i \"; date ; sleep 1; done"
}
}
执行脚本
node {
def remote = [:]
remote.name = 'test'
remote.host = 'test.domain.com'
remote.user = 'root'
remote.password = 'password'
remote.allowAnyHosts = true
stage('Remote SSH') {
writeFile file: 'abc.sh', text: 'ls -lrt'
sshScript remote: remote, script: "abc.sh"
}
}
https://python-jenkins.readthedocs.io/en/latest/genindex.html
pipeline { agent any stages { stage('Hello') { steps { script{ max = 4 latch = new java.util.concurrent.LinkedBlockingDeque(max) for(int i=0; i<max; i++) latch.offer("$i")
def l=(1..15).toList()
def b=[:]
l.each{
b[it]={
def thing = null
waitUntil {
script {
thing = latch.pollFirst()
return thing != null
}
}
try{
stage("$it"){
node('master'){
println it
println env.Node
sleep 10
}
}
}
finally{
latch.offer(thing)
}
}
}
timestamps{
parallel b
}
}
}
}
} }