2008-10-22 8 views
114

Dies ist eine etwas .. vergeblich Frage, aber BuildBot des Ausgang ist nicht besonders schön zu sehen .."Pretty" Continuous Integration für Python

Zum Beispiel im Vergleich zu ..

..und andere, BuildBot sieht eher .. archaischen

ich zur Zeit mit Hudson zu spielen, aber es ist sehr Java-centric (obwohl mit this guide, fand ich es einrichten leichter als BuildBot, und produziert mehr Info)

Grundsätzlich: Gibt es Continuous Integration Systeme für Python, die viele glänzende Grafiken und dergleichen produzieren?


Update: Seit dieser Zeit ist das Jenkins Projekt Hudson als Community-Version des Pakets ersetzt hat. Die ursprünglichen Autoren sind ebenfalls zu diesem Projekt übergegangen. Jenkins ist jetzt ein Standardpaket für Ubuntu/Debian, RedHat/Fedora/CentOS und andere. Das folgende Update ist immer noch im Wesentlichen korrekt. Der Ausgangspunkt, dies mit Jenkins zu tun, ist anders.

Update: ein paar Alternativen Nach dem Versuch, ich glaube, ich mit Hudson bleiben werde. Integrity war nett und einfach, aber ziemlich begrenzt. Ich denke, Buildbot ist besser dafür geeignet, zahlreiche Build-Slaves zu haben, als dass alles auf einer einzigen Maschine läuft, so wie ich es benutzt habe.

Einstellung Hudson für ein Python-Projekt war ziemlich einfach:

  • herunterladen Hudson von http://hudson-ci.org/
  • Run mit java -jar hudson.war
  • Öffnen der Web-Oberfläche auf der Standardadresse http://localhost:8080
  • Zur Hudson, Plugins, klicken Sie auf "Update" oder ähnliches
  • Installieren Sie das Git-Plugin (Ich musste git Pfad in den Hudson globalen Voreinstellungen)
  • Erstellen Sie ein neues Projekt, geben Sie das Repository, SCM Abfrageintervalle und so weiter
  • installieren nosetests über easy_install wenn es nicht bereits ist
  • Im ein Build Schritt fügen nosetests --with-xunit --verbose
  • Check „JUnit Testergebnis Bericht Publish“ und „Prüfbericht XMLs“ zu **/nosetests.xml

eingestellt, dass ist alles, was erforderlich ist.Sie können E-Mail-Benachrichtigungen einrichten, und the plugins sind einen Blick wert. Ein paar ich bin derzeit für Python-Projekte: (! Und Graph es)

  • SLOCCount plugin Zeilen Code zu zählen - Sie sloccount separat
  • Violations zu analysieren, um die PyLint Ausgabe installieren müssen (können Sie Setup Warnung Schwellenwerte, grafisch die Anzahl der Verstöße bei jedem Build)
  • Cobertura kann die Ausgabe von coverage.py analysieren. Nosetest kann Abdeckung sammeln, während die Tests ausgeführt wird, unter Verwendung von nosetests --with-coverage (dies schreibt die Ausgabe in **/coverage.xml)
+0

Große Frage, ich bin gerade in ähnlichen Dingen suchen. Wenn Sie einen Weg gehen, können Sie Ihre Erfahrung mit dem Rest von uns teilen? –

+3

Ich weiß nicht, ob es verfügbar war, als du das geschrieben hast: Benutze das Chuck Norris Plugin für Hudson, um die Kontrolle über deine Sachen weiter zu verbessern! –

+8

** Update für 2011/2012 **: Diejenigen, die Hudson in Betracht ziehen, sollten [Jenkins] (http://jenkins-ci.org/) verwenden, die Open-Source-Fortsetzung des Hudson-Projekts (Hudson wird jetzt [von Oracle kontrolliert] (http://stackoverflow.com/questions/4973981/how-to-choose-between-hudson-and-jenkins)) – mindthief

Antwort

40

Sie möchten vielleicht Nose und the Xunit output plugin auschecken. Sie können es Ihre Unit-Tests und Berichterstattung Kontrollen mit diesem Befehl ausgeführt haben:

nosetests --with-xunit --enable-cover 

Das wird hilfreich sein, wenn Sie die Jenkins Weg gehen wollen, oder wenn Sie wollen einen anderen CI-Server verwenden, die Unterstützung hat für JUnit Testberichte.

Ebenso können Sie die Ausgabe von Pylint erfassen die violations plugin for Jenkins

+36

Ah die Freuden von Open-Source-Anwendungsnamen .. – dbr

+4

Nase enthält jetzt das Xunit-Plugin standardmäßig - 'nosetests --with-xunit' – dbr

+3

Wie also kann man das Auditing von Pylint dann ausführen? Wenn ich "nosetests --with-xunit --enable-audit" mache, bekomme ich 'nosetests: error: keine solche Option: --enable-audit' –

10

Sie wissen nicht, ob es tun würde: Bitten wird von den Jungs gemacht, die Trac schreiben und ist integriert mit Trac. Apache Gump ist das CI-Tool von Apache. Es ist in Python geschrieben.

9

Wir hatten großen Erfolg mit TeamCity als unseren CI-Server und Nase als unser Testläufer verwenden. Teamcity plugin for nosetests gibt Ihnen die Zählung bestanden/nicht bestanden, lesbare Anzeige für fehlgeschlagenen Test (das kann per E-Mail). Sie können sogar Details der Testfehler anzeigen, während der Stapel ausgeführt wird.

Wenn natürlich unterstützt Dinge wie auf mehreren Maschinen laufen, und es ist viel einfacher zu Setup und Wartung als Buildbot.

0

Wir haben ein bisschen gebissen verwendet. Es ist hübsch und lässt sich gut in Trac integrieren, aber es ist ein Problem, wenn Sie einen nicht standardmäßigen Workflow haben. Es gibt auch nicht so viele Plugins wie für die populäreren Tools. Gegenwärtig bewerten wir Hudson als Ersatz.

+0

Was hast du am Ende gemacht? – Russ

2

Signal ist eine andere Option. Sie können mehr darüber erfahren und ein Video auch ansehen here.

6

Ich denke, dieser Thread ist ziemlich alt, aber hier ist mein nehmen auf sie mit hudson:

ich mit pip beschlossen zu gehen und ein Repo (die schmerzliche zum Laufen zu bringen, aber gut aussehende eggbasket) eingerichtet, der hudson Auto-Uploads mit einem erfolgreichen Tests. Hier ist mein grobes und fertiges Skript zur Verwendung mit einem hudson config execute Skript wie: /var/lib/hudson/venv/main/bin/hudson_script.py -w $ WORKSPACE -p my.package -v $ BUILD_NUMBER, einfach einfügen **/coverage.xml, pylint.txt und nosetests.xml in den Config-Bits:

#!/var/lib/hudson/venv/main/bin/python 
import os 
import re 
import subprocess 
import logging 
import optparse 

logging.basicConfig(level=logging.INFO, 
        format='%(asctime)s %(levelname)s %(message)s') 

#venvDir = "/var/lib/hudson/venv/main/bin/" 

UPLOAD_REPO = "http://ldndev01:3442" 

def call_command(command, cwd, ignore_error_code=False): 
    try: 
     logging.info("Running: %s" % command) 
     status = subprocess.call(command, cwd=cwd, shell=True) 
     if not ignore_error_code and status != 0: 
      raise Exception("Last command failed") 

     return status 

    except: 
     logging.exception("Could not run command %s" % command) 
     raise 

def main(): 
    usage = "usage: %prog [options]" 
    parser = optparse.OptionParser(usage) 
    parser.add_option("-w", "--workspace", dest="workspace", 
         help="workspace folder for the job") 
    parser.add_option("-p", "--package", dest="package", 
         help="the package name i.e., back_office.reconciler") 
    parser.add_option("-v", "--build_number", dest="build_number", 
         help="the build number, which will get put at the end of the package version") 
    options, args = parser.parse_args() 

    if not options.workspace or not options.package: 
     raise Exception("Need both args, do --help for info") 

    venvDir = options.package + "_venv/" 

    #find out if venv is there 
    if not os.path.exists(venvDir): 
     #make it 
     call_command("virtualenv %s --no-site-packages" % venvDir, 
        options.workspace) 

    #install the venv/make sure its there plus install the local package 
    call_command("%sbin/pip install -e ./ --extra-index %s" % (venvDir, UPLOAD_REPO), 
       options.workspace) 

    #make sure pylint, nose and coverage are installed 
    call_command("%sbin/pip install nose pylint coverage epydoc" % venvDir, 
       options.workspace) 

    #make sure we have an __init__.py 
    #this shouldn't be needed if the packages are set up correctly 
    #modules = options.package.split(".") 
    #if len(modules) > 1: 
    # call_command("touch '%s/__init__.py'" % modules[0], 
    #     options.workspace) 
    #do the nosetests 
    test_status = call_command("%sbin/nosetests %s --with-xunit --with-coverage --cover-package %s --cover-erase" % (venvDir, 
                        options.package.replace(".", "/"), 
                        options.package), 
       options.workspace, True) 
    #produce coverage report -i for ignore weird missing file errors 
    call_command("%sbin/coverage xml -i" % venvDir, 
       options.workspace) 
    #move it so that the code coverage plugin can find it 
    call_command("mv coverage.xml %s" % (options.package.replace(".", "/")), 
       options.workspace) 
    #run pylint 
    call_command("%sbin/pylint --rcfile ~/pylint.rc -f parseable %s > pylint.txt" % (venvDir, 
                        options.package), 
       options.workspace, True) 

    #remove old dists so we only have the newest at the end 
    call_command("rm -rfv %s" % (options.workspace + "/dist"), 
       options.workspace) 

    #if the build passes upload the result to the egg_basket 
    if test_status == 0: 
     logging.info("Success - uploading egg") 
     upload_bit = "upload -r %s/upload" % UPLOAD_REPO 
    else: 
     logging.info("Failure - not uploading egg") 
     upload_bit = "" 

    #create egg 
    call_command("%sbin/python setup.py egg_info --tag-build=.0.%s --tag-svn-revision --tag-date sdist %s" % (venvDir, 
                               options.build_number, 
                               upload_bit), 
       options.workspace) 

    call_command("%sbin/epydoc --html --graph all %s" % (venvDir, options.package), 
       options.workspace) 

    logging.info("Complete") 

if __name__ == "__main__": 
    main() 

Wenn es um Sachen bereitstellen Sie so etwas wie zu tun:

pip -E /location/of/my/venv/ install my_package==X.Y.Z --extra-index http://my_repo 

Und dann können die Leute Sachen entwickeln mit:

pip -E /location/of/my/venv/ install -e ./ --extra-index http://my_repo 

Dieses Zeug übernimmt Sie haben eine Repo-Struktur pro Paket mit einem Setup.py und Abhängigkeiten alle eingerichtet, dann können Sie nur den Kofferraum auschecken und dieses Zeug darauf ausführen.

Ich hoffe, dass dies jemand hilft.

------ Update ---------

Ich habe epydoc hinzugefügt, die mit hudson in wirklich gut passt. Fügen Sie einfach javadoc auf Ihre Konfiguration mit dem HTML-Ordner

Beachten Sie, dass Pip nicht die -E-Flag richtig in diesen Tagen nicht unterstützt, so müssen Sie Ihre Venv erstellen separat

+0

Diese Antwort ist sehr nützlich und hat viele Details in Bezug auf die Interna von Python CI, etwas, das Sie nicht kostenlos von Jenkins oder was auch immer bekommen werden. Vielen Dank! – maksimov

6

Atlassians Bamboo auch auf jeden Fall einen Besuch wert ist out. Die gesamte Atlassian-Suite (JIRA, Confluence, FishEye usw.) ist ziemlich süß.

3

Wenn Sie gehostete CI-Lösung unter Berücksichtigung und Open Source zu tun, sollten Sie in Travis CI als gut aussehen - es hat sehr schöne Integration mit GitHub. Während es als Ruby-Tool begann, haben sie vor einer Weile added Python support.

2

würde ich CircleCi betrachten - es hat große Python-Unterstützung und sehr hübsche Ausgabe.

0

Überprüfen Sie rultor.com. Wie this article erklärt, verwendet es Docker für jeden Build. Dank diesem können Sie konfigurieren, was auch immer Sie in Ihrem Docker Bild mögen, einschließlich Python.

1

continuums binstar ist jetzt in der Lage, Builds von Github auszulösen und kann für Linux, OSX und Windows (32/64) kompilieren. Das Schöne daran ist, dass es Ihnen ermöglicht, Vertrieb und kontinuierliche Integration eng miteinander zu verbinden. Das kreuzt die t's und punktet mit den Ichs der Integration. Die Site, der Workflow und die Tools sind wirklich optimiert und AFAIK conda ist die robusteste und pythonischste Methode, um komplexe Python-Module zu verteilen, wo Sie und verteilen müssen C/C++/FOTRAN-Bibliotheken.

0

Kleiner Haftungsausschluss, ich musste tatsächlich eine Lösung wie diese für einen Client, der eine Möglichkeit zum automatischen Test und Bereitstellung Code auf einem Git-Push plus eine Verwaltung der Ausgabe Tickets über Git-Notizen wollte. Dies führte auch zu meiner Arbeit an der AIMS project.

Man könnte einfach nur das Einrichten eines nackten Knoten-System, das einen Build Benutzer hat und verwalten ihre Build durch make(1), expect(1), crontab(1)/systemd.unit(5) und incrontab(1). Man könnte sogar einen Schritt weiter gehen und Ansible und Sellerie für verteilte Builds mit einem gridfs/nfs-Dateispeicher verwenden.

Obwohl, ich würde nicht erwarten, dass jemand anders als ein Graybeard UNIX-Typ oder Prinzipal-Ebene Ingenieur/Architekt tatsächlich so weit gehen.Das macht nur eine nette Idee und potentielle Lernerfahrung, da ein Build-Server nichts anderes als eine Möglichkeit ist, skriptbasierte Aufgaben automatisiert auszuführen.