import groovy.xml.MarkupBuilder
nodes_xmls = [:]
// ------------------------------------------------------
// ============== GENERATING NODES XMLS =================
// ------------------------------------------------------
// get all cloud nodes from openstack
cloud_nodes = [:]
for (cloud in Jenkins.instance.clouds.findAll{!it.name.contains('Compound')}) {
cloud_nodes.put(cloud.name, cloud.openstack.client.compute().servers().list(true))
}
for (dead_slave in hudson.model.Hudson.instance.slaves.findAll{!it.name.contains('Compound')}) {
// Get dead_slave available properties
slave_executors = dead_slave.getNumExecutors()
slave_retention_policy = dead_slave.getRetentionStrategy().toString().split('@')[0]
slave_cloud_name = dead_slave.cloudName
slave_labels = dead_slave.getLabelString()
slave_cred_id = dead_slave.options.credentialsId
slave_jvm_opts = dead_slave.options.jvmOptions
slave_remote_fs = dead_slave.getRemoteFS()
slave_mode = dead_slave.getMode()
cloud = Jenkins.instance.clouds.find{it.name == dead_slave.cloudName}
cloud_prefix = cloud.name.split('_')[1]
node = cloud_nodes[slave_cloud_name].find{it.name == dead_slave.name}
def writer = new StringWriter()
def xml = new MarkupBuilder(writer)
// ==== get IP addrs:
slave_addrs = [:]
node.getAddresses().getAddresses().each { k, v ->
slave_addrs.put('ipv4', v.find { it.getVersion() == 4 }.getAddr())
slave_addrs.put('ipv6', v.find { it.getVersion() == 6 }.getAddr())
}
node_template_name = slave_labels.split().find { it.toUpperCase().contains(cloud_prefix) }
node_template = cloud.getTemplate(node_template_name).getRawSlaveOptions()
// ======================== Header ================================
xml.'jenkins.plugins.openstack.compute.JCloudsSlave'(plugin: 'openstack-cloud@2.8') {
name(node.name)
remoteFS(slave_remote_fs)
numExecutors(slave_executors)
mode(slave_mode)
retentionStrategy(class: slave_retention_policy)
// ======================== Launcher ================================
launcher(class: 'jenkins.plugins.openstack.compute.JCloudsLauncher') {
launcher(class: 'hudson.plugins.sshslaves.SSHLauncher', plugin: 'ssh-s...@1.10') {
if (slave_addrs['ipv4']) {
host(slave_addrs['ipv4'])
}
else {
host(slave_addrs['ipv6'])
}
port(22)
credentialsId(slave_cred_id)
if (slave_jvm_opts) {
jvmOptions(slave_jvm_opts)
}
launchTimeoutSeconds(1200)
maxNumRetries(5)
retryWaitTime(15)
}
}
// ======================== Label ================================
label(slave_labels)
// ======================== nodeProperties ================================
nodeProperties() {
'hudson.slaves.EnvironmentVariablesNodeProperty'() {
envVars(serialization: 'custom') {
'unserializable-parents'()
'tree-map'() {
'default'() {
comparator(class: 'hudson.util.CaseInsensitiveComparator')
}
'int'(1)
string('OPENSTACK_PUBLIC_IP')
if (slave_addrs['ipv4']) {
string(slave_addrs['ipv4'])
}
else {
string(slave_addrs['ipv6'])
}
}
}
}
}
// ======================== userId ================================
userId(node.userId)
// ======================== MetaData NovaServer ================================
metadata(class: 'org.openstack4j.openstack.compute.domain.NovaServer') {
id(node.id)
name(node.name)
addresses() {
addresses() {
node.getAddresses().getAddresses().each { key, value ->
entry() {
string(key)
list() {
for (val in value) {
'org.openstack4j.openstack.compute.domain.NovaAddresses_-NovaAddress'() {
macAddr(val.getMacAddr())
version(val.getVersion())
addr(val.getAddr())
type(val.getType())
}
}
}
}
}
}
}
links() {
for (link in node.links) {
'org.openstack4j.openstack.common.GenericLink'() {
rel(link.getRel())
href(link.getHref())
}
}
}
image(class: 'linked-hash-map') {
entry() {
string('id')
string(node.image.id)
}
entry() {
string('links')
list() {
'linked-hash-map'() {
entry() {
string('href')
string(node.image.links.find { it.getRel() == 'bookmark' }.getHref())
}
entry() {
string('rel')
string('bookmark')
}
}
}
}
}
flavor() {
id(node.getFlavor().getId())
ephemeral(node.getFlavor().getEphemeral())
swap(node.getFlavor().getSwap())
rxtxFactor(node.getFlavor().getRxtxFactor())
isPublic(node.getFlavor().isPublic())
links() {
'org.openstack4j.openstack.common.GenericLink'() {
rel(node.links.find { it.getRel() == 'bookmark' }.getRel())
href(node.links.find { it.getRel() == 'bookmark' }.getHref())
}
}
}
accessIPv4(node.accessIPv4)
accessIPv6(node.accessIPv6)
configDrive(node.configDrive)
status(node.status)
progress(node.progress)
tenantId(node.tenantId)
userId(node.userId)
keyName(node.keyName)
hostId(node.hostId)
updated(node.updated)
created(node.created)
metadata(class: 'linked-hash-map') {
node.metadata.each { k, v ->
entry() {
string(k)
string(v)
}
}
}
powerstate(node.getPowerState())
vmState(node.getVmState())
diskConfig(node.getDiskConfig())
availabilityZone(node.getAvailabilityZone())
launchedAt(node.getLaunchedAt())
osExtendedVolumesAttached()
}
// ======================== CloudName ================================
cloudName(cloud.name)
// ======================== options ================================
options() {
imageId(node_template.imageId)
hardwareId(node_template.hardwareId)
networkId(node_template.networkId)
userDataId()
instanceCap(cloud.slaveOptions.instanceCap)
securityGroups(node_template.securityGroups)
startTimeout(cloud.slaveOptions.startTimeout)
keyPairName(node_template.keyPairName)
numExecutors(slave_executors)
if (slave_jvm_opts) {
jvmOptions(slave_jvm_opts)
}
fsRoot(slave_remote_fs)
credentialsId(slave_cred_id)
slaveType('SSH')
retentionTime(30)
}
// ======================== provisioningId ================================
provisioningId(plugin: 'cloud-stats@0.1') {
cloudName(cloud.name)
templateName(node_template_name)
fingerprint(System.identityHashCode(node.name) ^ (int) System.currentTimeMillis())
}
}
// ======== Put Node XML config to map `nodes_xml`
nodes_xmls.put(dead_slave.name, writer)
}
// ----------------------------------------------------------
// ============== WRITING CONFIGS TO FILESYSTEM =================
// ----------------------------------------------------------
nodes_folder = '/var/lib/jenkins/nodes_ported/'
// ----- writing nodes ----
nodes_xmls.each{nodename, xml_config ->
node_folder = nodes_folder + nodename
config_full_path = node_folder + '/config.xml'
// create folder for config
new File(node_folder).mkdirs()
// write config to folder
conf_file = new File(config_full_path)
conf_file.write("<?xml version=\'1.0\' encoding=\'UTF-8\'?>\n")
conf_file.append(xml_config)
}