diff --git a/pom.xml b/pom.xml
index b00193d0c6..684527b2fb 100644
--- a/pom.xml
+++ b/pom.xml
@@ -56,6 +56,12 @@
4.5.1
+
+ org.apache.commons
+ commons-lang3
+ 3.5
+
+
org.jenkins-ci.plugins
durable-task
diff --git a/src/main/java/org/csanchez/jenkins/plugins/kubernetes/KubernetesCloud.java b/src/main/java/org/csanchez/jenkins/plugins/kubernetes/KubernetesCloud.java
index d89be62fd2..fa40d87cfe 100644
--- a/src/main/java/org/csanchez/jenkins/plugins/kubernetes/KubernetesCloud.java
+++ b/src/main/java/org/csanchez/jenkins/plugins/kubernetes/KubernetesCloud.java
@@ -54,7 +54,9 @@
import hudson.model.Node;
import hudson.security.ACL;
import hudson.slaves.Cloud;
+import hudson.slaves.CloudRetentionStrategy;
import hudson.slaves.NodeProvisioner;
+import hudson.slaves.RetentionStrategy;
import hudson.util.FormValidation;
import hudson.util.ListBoxModel;
import io.fabric8.kubernetes.api.model.Container;
@@ -73,6 +75,7 @@
import jenkins.model.Jenkins;
import jenkins.model.JenkinsLocationConfiguration;
import static org.csanchez.jenkins.plugins.kubernetes.PodTemplateUtils.substituteEnv;
+import org.jenkinsci.plugins.durabletask.executors.OnceRetentionStrategy;
/**
* Kubernetes cloud provider.
@@ -539,9 +542,14 @@ public ProvisioningCallback(KubernetesCloud cloud, PodTemplate t, Label label) {
public Node call() throws Exception {
KubernetesSlave slave = null;
+ RetentionStrategy retentionStrategy = null;
try {
-
- slave = new KubernetesSlave(t, t.getName(), cloud, t.getLabel());
+ if (t.getIdleMinutes() == 0) {
+ retentionStrategy = new OnceRetentionStrategy(cloud.getRetentionTimeout());
+ } else {
+ retentionStrategy = new CloudRetentionStrategy(t.getIdleMinutes());
+ }
+ slave = new KubernetesSlave(t, t.getName(), cloud, t.getLabel(), retentionStrategy);
Jenkins.getActiveInstance().addNode(slave);
Pod pod = getPodTemplate(slave, label);
diff --git a/src/main/java/org/csanchez/jenkins/plugins/kubernetes/KubernetesSlave.java b/src/main/java/org/csanchez/jenkins/plugins/kubernetes/KubernetesSlave.java
index 8a4722580a..158a1b8a46 100644
--- a/src/main/java/org/csanchez/jenkins/plugins/kubernetes/KubernetesSlave.java
+++ b/src/main/java/org/csanchez/jenkins/plugins/kubernetes/KubernetesSlave.java
@@ -19,8 +19,8 @@
import hudson.model.TaskListener;
import hudson.slaves.AbstractCloudSlave;
import hudson.slaves.JNLPLauncher;
-import hudson.slaves.NodeProperty;
import hudson.slaves.OfflineCause;
+import hudson.slaves.RetentionStrategy;
import io.fabric8.kubernetes.api.model.DoneablePod;
import io.fabric8.kubernetes.api.model.Pod;
import io.fabric8.kubernetes.client.KubernetesClient;
@@ -44,34 +44,31 @@ public class KubernetesSlave extends AbstractCloudSlave {
private transient final KubernetesCloud cloud;
- @DataBoundConstructor
public KubernetesSlave(PodTemplate template, String nodeDescription, KubernetesCloud cloud, String labelStr)
throws Descriptor.FormException, IOException {
- super(getSlaveName(template),
- nodeDescription,
- template.getRemoteFs(),
- 1,
- Node.Mode.NORMAL,
- labelStr == null ? null : labelStr,
- new JNLPLauncher(),
- new OnceRetentionStrategy(cloud.getRetentionTimeout()),
- template.getNodeProperties());
- // this.pod = pod;
- this.cloud = cloud;
+ this(template, nodeDescription, cloud, labelStr, new OnceRetentionStrategy(cloud.getRetentionTimeout()));
}
@Deprecated
public KubernetesSlave(PodTemplate template, String nodeDescription, KubernetesCloud cloud, Label label)
throws Descriptor.FormException, IOException {
+ this(template, nodeDescription, cloud, label.toString(), new OnceRetentionStrategy(cloud.getRetentionTimeout())) ;
+ }
+
+ @DataBoundConstructor
+ public KubernetesSlave(PodTemplate template, String nodeDescription, KubernetesCloud cloud, String labelStr,
+ RetentionStrategy rs)
+ throws Descriptor.FormException, IOException {
+
super(getSlaveName(template),
nodeDescription,
template.getRemoteFs(),
1,
Node.Mode.NORMAL,
- label == null ? null : label.toString(),
+ labelStr == null ? null : labelStr,
new JNLPLauncher(),
- new OnceRetentionStrategy(cloud.getRetentionTimeout()),
+ rs,
template.getNodeProperties());
// this.pod = pod;
@@ -114,7 +111,7 @@ protected void _terminate(TaskListener listener) throws IOException, Interrupted
computer.disconnect(OfflineCause.create(new Localizable(HOLDER, "offline")));
LOGGER.log(Level.INFO, "Disconnected computer {0}", name);
} catch (Exception e) {
- LOGGER.log(Level.SEVERE, "Failure to terminate instance for slave " + name, e);
+ LOGGER.log(Level.SEVERE, "Failed to terminate pod for slave " + name, e);
}
}
diff --git a/src/main/java/org/csanchez/jenkins/plugins/kubernetes/PodTemplate.java b/src/main/java/org/csanchez/jenkins/plugins/kubernetes/PodTemplate.java
index 35eca3af79..1bdde5d609 100644
--- a/src/main/java/org/csanchez/jenkins/plugins/kubernetes/PodTemplate.java
+++ b/src/main/java/org/csanchez/jenkins/plugins/kubernetes/PodTemplate.java
@@ -24,6 +24,8 @@
import hudson.model.Label;
import hudson.model.labels.LabelAtom;
+import org.apache.commons.lang3.StringUtils;
+
/**
* Kubernetes Pod Template
*
@@ -51,6 +53,8 @@ public class PodTemplate extends AbstractDescribableImpl {
private int instanceCap = Integer.MAX_VALUE;
+ private int idleMinutes;
+
private String label;
private String serviceAccount;
@@ -188,7 +192,7 @@ public int getInstanceCap() {
@DataBoundSetter
public void setInstanceCapStr(String instanceCapStr) {
- if ("".equals(instanceCapStr)) {
+ if (StringUtils.isBlank(instanceCapStr)) {
setInstanceCap(Integer.MAX_VALUE);
} else {
setInstanceCap(Integer.parseInt(instanceCapStr));
@@ -203,6 +207,31 @@ public String getInstanceCapStr() {
}
}
+ public void setIdleMinutes(int i) {
+ this.idleMinutes = i;
+ }
+
+ public int getIdleMinutes() {
+ return idleMinutes;
+ }
+
+ @DataBoundSetter
+ public void setIdleMinutesStr(String idleMinutes) {
+ if (StringUtils.isBlank(idleMinutes)) {
+ setIdleMinutes(0);
+ } else {
+ setIdleMinutes(Integer.parseInt(idleMinutes));
+ }
+ }
+
+ public String getIdleMinutesStr() {
+ if (getIdleMinutes() == 0) {
+ return "";
+ } else {
+ return String.valueOf(idleMinutes);
+ }
+ }
+
public Set getLabelSet() {
return Label.parse(label);
}
diff --git a/src/main/resources/org/csanchez/jenkins/plugins/kubernetes/PodTemplate/config.jelly b/src/main/resources/org/csanchez/jenkins/plugins/kubernetes/PodTemplate/config.jelly
index 8f585696b5..978178a206 100644
--- a/src/main/resources/org/csanchez/jenkins/plugins/kubernetes/PodTemplate/config.jelly
+++ b/src/main/resources/org/csanchez/jenkins/plugins/kubernetes/PodTemplate/config.jelly
@@ -36,6 +36,10 @@
+
+
+
+