meetup python nantes - les tests en python

Post on 11-Feb-2017

170 Views

Category:

Internet

8 Downloads

Preview:

Click to see full reader

TRANSCRIPT

PythonMeetupoctobre2016lestestsenpython

IntroductionMeetupPythonNantes-mai2016

( ) ArthurLutz Logilab @arthurlutz @logilab

Planintroductionauxtestsunittaireslancerlestests:unittestdebase,py.test,nose,pytest,etc.toxpourlancerlestestdansdesvirtualenvsl'intégrationcontinueavecpython(jenkins,travis,etc.)lestestsenprod:healthchecksaucœurdel'application

introductionauxtestsunitaires

TDD-testdrivendeveloppement-dévelopementpilotéparlestests

testunitaire

passerdesprintsetvérificationhumaineàunpointOK/notOKdocumenterdesexemplesd'usagedesoncode

https://en.wikipedia.org/wiki/Test-driven_developmenthttps://fr.wikipedia.org/wiki/Test_driven_development

https://fr.wikipedia.org/wiki/Test_unitaire

Enpythonmoduleunittest

nepasutiliserassert(assertTrueàlaplace)

https://docs.python.org/3.5/library/unittest.htmlassertEqual(a,b)assertNotEqual(a,b)assertTrue(x)assertFalse(x)

Écrireuntestclasseshéritantdeunittest.TestCasetouteslesmethodescommencantpartestsontconsidéréescommeuntestunittaire

Exemple(deladoc)importunittest

classTestStringMethods(unittest.TestCase):

deftest_upper(self):self.assertEqual('foo'.upper(),'FOO')

deftest_isupper(self):self.assertTrue('FOO'.isupper())self.assertFalse('Foo'.isupper())

deftest_split(self):s='helloworld'self.assertEqual(s.split(),['hello','world'])#checkthats.splitfailswhentheseparatorisnotastringwithself.assertRaises(TypeError):s.split(2)

if__name__=='__main__':unittest.main()

Avant/aprèslestests

defsetUp()deftearDown()setUpClassettearDownClasssetup_methodetteardown_methodsetup_functionetteardown_function

https://en.wikipedia.org/wiki/Test_fixture#Software

Extensionscouverturesdetests(pycoverage,python-coverage,etc.)linters(pychecker,pylint,flake8,etc.)doctestshttps://docs.python.org/2/library/doctest.htmlhttps://en.wikipedia.org/wiki/Fuzz_testing

Mockmockornottomock(orwheretomock?)

unittest.mock:

https://en.wikipedia.org/wiki/Mock_object

https://docs.python.org/3/library/unittest.mock.html

>>>fromunittest.mockimportMagicMock>>>thing=ProductionClass()>>>thing.method=MagicMock(return_value=3)>>>thing.method(3,4,5,key='value')3>>>thing.method.assert_called_with(3,4,5,key='value')

Mockencoredecorator@patchcontextmanagerwithPatch...quelquesexemplesd'assertions

assert_called_withassert_called_once_withassert_any_callassert_has_callsassert_not_calledreset_mock

Nepasmockerpostgresqlàlademande:Pythonfixturesanddaemonmanagingtoolsforfunctionaltesting:

http://faitout.fedorainfracloud.org/

https://github.com/jd/pifpaf

platformspecific1/2django

cubicweb-populateDB

testwithreallivedatabase

https://docs.djangoproject.com/en/1.10/topics/testing/https://factoryboy.readthedocs.io/en/latest/

https://docs.cubicweb.org/book/devrepo/testing.html

https://docs.cubicweb.org/book/devrepo/testing.html#testing-on-a-real-life-database

platformspecific2/2saltfromsalttestingimportTestCase

infrastructure:testinfra:

https://docs.saltstack.com/en/latest/topics/development/tests/unit.html

http://testinfra.readthedocs.io/en/latest/

Seleniumhttp://www.seleniumhq.org/https://github.com/SeleniumHQ/selenium/tree/master/py

pipinstallselenium

Seleniumexempleimportunittestfromseleniumimportwebdriver

classAfpyTestCase(unittest.TestCase):

defsetUp(self):self.browser=webdriver.Firefox()self.addCleanup(self.browser.quit)

deftestPageTitle(self):self.browser.get('http://nantes.afpy.org/')self.assertIn('Python-Nantes',self.browser.title)

if__name__=='__main__':unittest.main(verbosity=2)

lancerlestests

unittestdebaseunit2pytest(logilab-common)py.test(nextpytest)nose&nose2etc

https://wiki.python.org/moin/PythonTestingToolsTaxonomy

unittest.mainEnbasdechaquefichierpython:

Pourlelancer:

if__name__=='__main__':unittest.main()

#pythontest_this.py

pytest(logilab-common)historique

testlib-extensiondeunittestpytest-lanceurdetestsselectiontagsavecdesdecorateurs(tags)suppriméauprofitdenouveauxprojets

unit2unittest2estunbackportpython2dunouveauunittestpython3

unit2==python-munittest2unit2discover

py.test

py.test(bientôtpytest)http://docs.pytest.org/en/latest/

$pipinstallpytest

py.testpy.testpy.test-x:s'arrêteàlapremièreerreurpy.test--maxfail=3:s'arrêteauboutde3erreurs

py.testselectionpy.testtest_module.pypy.testtest_mod.py::test_funcpy.testtest_mod.py::TestClass::test_method

py.testaffichagepy.test--tb=long#thedefaultinformativetracebackformattingpy.test--tb=native#thePythonstandardlibraryformattingpy.test--tb=short#ashortertracebackformatpy.test--tb=line#onlyonelineperfailure

py.testavancémarkersfixturesparametrisationpy.test--fixturespluginspipsearchpytest(ouapt-cachesearchpytest)

http://docs.pytest.org/en/latest/mark.htmlhttp://docs.pytest.org/en/latest/fixture.html

http://docs.pytest.org/en/latest/parametrize.html

nose&nose2

Commandes:

nosetestsnose2

https://nose.readthedocs.io/en/latest/https://github.com/nose-devs/nose2

toxpourlancerlestestdansdesvirtualenvshttps://tox.readthedocs.io/en/latest/

#contentof:tox.ini,putinsamedirassetup.py[tox]envlist=py26,py27[testenv]deps=pytest#installpytestinthevenvscommands=py.test#or'nosetests'or...

toxestamourSlides:Vidéo:

http://tox.jehaisleprintemps.net/#/http://video-pyconfr2015.paulla.asso.fr/108_-

_Bruno_Bord_-_tox_est_amour.html

Accélerertox:cachesserverpypilocal:dansdocker(avecapt-cacher-ngetsquid)

http://doc.devpi.net/latest/

https://github.com/ebar0n/proxy-cache

L'intégrationcontinueavecpython

(monopoleavecgithub?)

(testssouswindows)etc.

hudsonjenkinsapycottravisbitbucketpipelinesdrone.ioappveyor

JenkinsPythonPlugin:

ShiningPanda:

https://wiki.jenkins-ci.org/display/JENKINS/Python+Plugin

https://wiki.jenkins-ci.org/display/JENKINS/ShiningPanda+Plugin

MatrixProjectMatrixProjectpourplusieursenvironnements:

jenkins-job-builder(descriptiondevosprojetsenYAML):https://wiki.jenkins-ci.org/display/JENKINS/Matrix+Project+Plugin

http://docs.openstack.org/infra/jenkins-job-builder/project_matrix.html

Junit/xUnitfichiersXMLdedescriptiondestestsréussisounon

ilexisteaussidesformatsxmlpourlacouverturedetests(Corbetura,etc.)

https://en.wikipedia.org/wiki/XUnit

Quandlancerlestests?Surchaquepullrequest?surchaquetêteavantunpush?avantuncommit?surl'ensemble?surquelsous-ensemble?

lestestsenprod:healthchecksaucœurde

l'application

Inspirationspyconfr2015:BenoitBryon,Peopledoc

KelseyHightower-healthz:Stopreverseengineeringapplicationsandstartmonitoringfromtheinside

Vidéo:Code:

https://blog.notmyidea.org/pyconfr-2015-hospital-des-tests-en-prod.html

https://vimeo.com/173610242https://github.com/kelseyhightower/app-healthz

healthchecks-principelancerdestestsdirectementaucoeurdel'applicationenproductioncomplémentdelasupervisiontraditionnellepermetdedifférentierentre"leprocesstourne"et"leservicerépond"

particulièrementutilepourledéploiementcontinueetlarépartissiondechargedynamique

healthchecksenpythonhttps://github.com/python-hospital/hospitalhttps://github.com/danielfrg/django-hospitalhttps://github.com/healthchecks/healthcheckshttps://github.com/ludia/pyramid_health

FinDesquestions?Desajouts?Présentation:Contact:

http://slides.logilab.fr/2016/meetup_python_nantes_tests/@arthurlutz @logilab

top related