Wie lösche ich die Builds 11 bis 1717 in Jenkins?

51

Aufgrund einer Fehlkonfiguration habe ich über 1700 fehlgeschlagene Builds in einem Jenkins-Job.

Wie kann ich sie effizient reinigen?

Aaron Digulla
quelle
2
Eine Reihe von Möglichkeiten zum Löschen von Builds über die Befehlszeile werden hier beschrieben: stackoverflow.com/questions/13052390/…
ThomasW

Antworten:

74

Sie haben mehrere Möglichkeiten:

  • Legen Sie vorübergehend die Anzahl der Builds fest, die in der Auftragskonfiguration beibehalten werden sollen ( Alte Builds verwerfen ), damit diese Builds nach Abschluss des nächsten Builds gelöscht werden. Wenn der nächste Build 1800 ist, stellen Sie ihn so ein, dass die letzten 85 oder so erhalten bleiben. Markieren Sie alle älteren Builds (dh 1 bis 10) als Keep This Build Forever, bevor Sie mit dem nächsten Build beginnen. Diese Option löscht einige Builds nicht, wenn Sie einen Downstream-Job haben, der das Löschen von Upstream-Builds verhindert (in Ihrer Situation kein Problem, wenn alle fehlgeschlagen sind).

  • Verwenden Sie die Skriptkonsole in Jenkins verwalten . Wenn es sich um einen Job der obersten Ebene handelt (nicht in einem Ordner), reicht Folgendes aus:

    Jenkins.instance.getItemByFullName('JobName').builds.findAll { it.number > 10 && it.number < 1717 }.each { it.delete() }

    Natürlich erfordert dieser Ansatz im Allgemeinen gute Backups. Es gibt eine Menge, die Sie mit der Skriptkonsole unterbrechen können.

  • Löschen Sie die Build-Ordner von der Festplatte (standardmäßig in $JENKINS_HOME/jobs/JobName/builds/, wobei der Startzeitstempel als Ordnername verwendet wird) und starten Sie Jenkins neu oder laden Sie die Konfiguration von der Festplatte neu . Diese Option lässt keine Plugins zu, die z. B. den SVN-Verlauf beibehalten, indem sie Änderungen in den nachfolgenden Build verschieben, um ihren Job zu erledigen.

Daniel Beck
quelle
10
Ich habe eine andere Lösung gefunden: Verwenden vonjenkins-cli.jar -s ... delete-builds envjs 11-1717
Aaron Digulla
Es wurde ein Gist erstellt, um alle Jobs mit einer Build-Zählung über das Terminal aufzulisten. Erleichtert das Auffinden von Jobs, die aufgeräumt werden müssen. Kann auch per Cron als E-Mail-Bericht verwendet werden.
Nick
@Nick Überprüfen Sie das Groovy-Plugin, insbesondere den Groovy-Buildschritttyp des Systems. Sie müssen dafür nicht außerhalb von Jenkins gehen, sondern müssen nur einen Job erstellen, der dies erledigt. jenkins.model.Jenkins.instance.getAllItems(hudson.model.Job.class).each { println it.fullDisplayName + " has " + it.builds.size() + " builds" } ; returnSortierung zB nach Builds ist ähnlich trivial.
Daniel Beck
Für Pipelines mit mehreren Verzweigungen können Sie die Syntax verwenden JobName/branch
waitinforatrain,
17

Machen Sie einfach einen API-Aufruf:

curl -X POST http://jenkinUser:[email protected]/job/theJob/[11-1717]/doDelete

So rufen Sie den APIToken ab: Melden Sie sich bei Jenkins> Konfiguration> API-Token anzeigen an.

Hallo Harry
quelle
Ich denke, das ist die beste Herangehensweise an das Problem. es kann remote ausgeführt werden und bietet eine breite Palette von Aktionen über REST
Alfredocambera
Beste Antwort, da Sie auf einem installierten System nicht nach dem Glas suchen müssen.
Keith Tyler
Ich meinte "Sie müssen nichts herunterladen"
Keith Tyler
"Beste Antwort, da Sie nicht müssen" - wenn Sie keine <1m-Datei herunterladen möchten, ist dies dank CLI besser. Wenn das Kriterium keine unordentlichen URLs mit Authentifizierungstoken eintippen muss, denken Sie an die Curlsyntax (vorausgesetzt, sie ist an erster Stelle installiert), und Sie bevorzugen klare Befehle und Hilfen, und vielleicht haben Sie bereits das Glas, das die CLI besser ist. Wenn Sie dort nur die Schnittstelle mit einer installierten Skriptkonsole haben, ist diese die bessere. Wie immer kommt es darauf an.
user17265
Zum Löschen für immer Builds behalten, toggleLogKeepvorher ausführen doDelete.
Fancyoung
16

Wie Aaron richtig sagte, können Sie auch die Jenkins-CLI für diesen Zweck verwenden:

java -jar jenkins-cli.jar -s http://yourserver.com delete-builds <JobName> 11-1717
jaltek
quelle
4

Vorlage für ein Skript zur Ausführung in der Jenkins Script-Console. Verwenden Sie das Flag reallyDelete, um es zu testen, bevor Sie es tatsächlich löschen:

// Jenkins job
def jobName = 'foo'
// Range of builds to delete
def rs = Fingerprint.RangeSet.fromString("11-1717", false);
// Set to true to actually delete. Use false to test the script.
def reallyDelete = false;

// ----------------------------------
def job = Jenkins.instance.getItemByFullName(jobName);
println("Job: ${job.fullName}");

def builds = Jenkins.instance.getItemByFullName(jobName).getBuilds(rs);
println("Found ${builds.size()} builds");
builds.each{ b-> 
  if (reallyDelete) {
    println("Deleting ${b}");
    b.delete();
  } else {
    println("Found match ${b}");
  }
}
Aaron Digulla
quelle
1

Die gleiche Aufgabe wurde mir gestellt, als ich einen Jenkins-Server übernahm, auf dem es etwas mehr als 150 Jobs mit bis zu 3000 alten Builds gibt. Deshalb habe ich ein kleines Bash-Skript geschrieben, das nur die letzten 10 Builds enthält:

#! /bin/bash

initialPath=$(pwd);

find /var/lib/jenkins/ -type d -name builds | while read jobs
 do

    #############################################################
    ## Enter build-directory of current job and get some numbers
    #############################################################
    cd "$jobs" ;
    ls -d [[:digit:]]* &>/dev/null ;
    rc=$? ;
    if [[ $rc -eq 0 ]] ;
     then
        buildName=$(ls -d [[:digit:]]*)  ;
        latestBuild=$(echo $buildName | awk '{print $NF}') ; # highest number
        oldestBuild=$(echo $buildName | awk '{print $1}') ; # lowest number
        amountOfBuilds=$(echo $buildName | wc -w ) ;
        lastBuildToKeep=$(echo "${latestBuild} 9" | awk '{print $1 - $2}') ;

        ############################################################
        ## Skip Folder if it contains less than 10 builds
        ############################################################
        if [ ${amountOfBuilds} -le 10 ] ;
         then
            echo "Skipping $(pwd) --> less than 10 builds";
         else
            ############################################################
            ## Delete all build-directories except the last 10
            ############################################################
            for (( i=$oldestBuild; i<$lastBuildToKeep; i++))
             do
                echo "Deleting $(pwd)/${i} ..."
                rm -r "$i" ;
            done ;
        fi ;
     else
        echo "Skipping $(pwd) --> Zero builds";
    fi ;
done ;

############################################################
## go back to $initialPath
############################################################
cd "$initialPath" ;

Es wird dringend empfohlen, Jenkins danach neu zu starten, um Probleme zu vermeiden. Vielen Dank an Aaron Digulla

Anyesto
quelle
Warum haben Sie kein Skript für die Jenkins-Konsole verwendet?
Aaron Digulla
Weil ich mich mit Bash besser auskenne. Das ist der einzige Grund.
Jedenfalls bis zum
Verstanden. Bitte bearbeiten Sie Ihre Frage und fügen Sie hinzu, dass Jenkins anschließend neu gestartet werden muss, um Probleme zu vermeiden.
Aaron Digulla
0

Ich habe ein kleines Python-Skript erstellt, das diesem Zweck dienen würde. Es folgt das Skript:

delete_jenkins_builds.py

from os import listdir, path
import shutil


job_build_fullpath = '/var/lib/jenkins/jobs/My-Jenkins-Project/builds'
print listdir(job_build_fullpath)

for build_dir in listdir(job_build_fullpath):
        if build_dir.isdigit() and int(build_dir) in range(11, 1718):
                build_dir_fullpath = path.join(job_build_fullpath, build_dir)
                print "Deleting: " + build_dir_fullpath
                shutil.rmtree(build_dir_fullpath)
  • job_build_fullpath - Pfad des Build-Verzeichnisses des Jobs

  • range (start_build_no, end_build_no) - range (11, 1718) sucht nach allen Builds ab Build-Nr. 11 zu bauen nr. 1717. Bitte stellen Sie es entsprechend ein.

  • shutil.rmtree (build_dir_fullpath) - löscht jedes Build-Verzeichnis, das sich im Bereich befindet.

Python-Version: 2.7

Shubham Soin
quelle
Müssen Sie Jenkins danach nicht neu starten? Was passiert, wenn Jenkins Informationen zu diesen Ordnern in einer Datenbank speichert?
Aaron Digulla
Ja @AaronDigulla, ein Neustart des Jenkins-Servers wäre erforderlich, um die Änderungen im Jenkins-Portal zu berücksichtigen.
Shubham Soin