zc.buildout

 zc.buildout

Обзор инструмента для автоматизации сборки программ
и подготовки окружения для их выполнения.

Ee4d18563a657e6b45c19fdce003602f?s=128

Kirill Kuzminykh

November 11, 2017
Tweet

Transcript

  1. zc.buildout Обзор инструмента для автоматизации сборки программ и подготовки окружения

    для их выполнения. Кирилл Кузьминых (Cykooz) ASD Technologies 2017
  2. 2 История создания

  3. 3 История создания Zope Corporation, начало 2000-ых: – помощь клиентам

    в соборке приложений на базе Zope; – очень большое разнообразие окружения - главная сложность в развёртывании приложения; – получение предскажуемого результата требует как то изолироваться от клиентского окружения. Решение: – собственная сборка Python в которую устанавливалось приложение; – автоматизация с помощью make.
  4. 4 История создания 2005 год: – приложения становятся сложнее –

    возникает желание использовать Python для автоматизации развёртывания; – внутренний прототип системы с конфигом на базе формата ConfigParser – секции описывали вещи, которые надо собирать; – несколько встроенных рецептов для сборки и возможность создавать сторонние рецепты; – всё ещё используется своя сборка Python для изоляции. Результат: решенно сделать zc.buildout.
  5. 5 История создания Появились setuptools и easy_install. Они автоматизировали скачивание

    и установку пакетов и их зависимостей. Результат: новая версия zc.buildout использует setuptools. Но easy_install устанавливал зависимости, но не обновлял их. Результат: следующая версия zc.buildout использует setuptools на более низком уровне, реализуя свою логику работы с пакетами.
  6. 6 Что это такое?

  7. 7 Что это такое? Инструмент для автоматизации сборки программного обеспечения

    – Запуск инструментов для сборки программ – Выполнение программ и шаблонов для создания скриптов и конфигов – Применим на всех стадиях, от разработки до выкатки
  8. 8 Что это такое? Это не совсем: – Make или

    Apache Ant Buildout – более высокоуровневый. Он сам может использовать make и ant как часть процесса сборки. – Puppet, chef и др. Buildout – сфокусирован на конкретном приложении. Puppet, chef и др. могут использовать buildout для решения своих задач.
  9. 9 Что это такое? Принципы: – Воспроизводимость – результат сборки

    должен быть одинаков в одинаковом окружении (OS и версия Python). – Автоматизация – с помощью одной/двух простых команд должна получаться готовая к работе система. – Приложение должно быть самодостаточным настолько насколько это возможно.
  10. 10 Как это выглядит?

  11. 11 Как это выглядит? $ git clone myproject.git $ cd

    myproject . ├── src/ ├── bootstrap.py └── buildout.cfg
  12. 12 Как это выглядит? $ python bootstrap.py $ ./bin/buildout

  13. 13 Как это выглядит? . ├── bin/ │ ├── buildout

    │ ├── myscript │ └── ... ├── eggs/ │ ├── requests-2.18.4-py2.7.egg/ │ └── ... ├── src/ ├── bootstrap.py └── buildout.cfg
  14. 14 Как это выглядит? . ├── bin/ │ ├── buildout

    │ ├── myscript │ └── ... ├── eggs/ │ ├── requests-2.18.4-py2.7.egg/ │ └── ... ├── src/ ├── bootstrap.py └── buildout.cfg
  15. 15 Как это выглядит? $ ./bin/myscript GET https://www.helloworld.org/data/helloworld Response body:

    #!/bin/bash echo "Hello world"
  16. 16 А что там внутри?

  17. 17 А что там внутри? . ├── bin/ │ ├──

    buildout │ ├── myscript │ └── ... ├── eggs/ │ ├── requests-2.18.4-py2.7.egg/ │ └── ... ├── src/ ├── bootstrap.py └── buildout.cfg
  18. 18 А что там внутри? . └── src/ ├── myapp/

    │ ├── __init__.py │ └── main.py └── setup.py
  19. 19 А что там внутри? . └── src/ ├── myapp/

    │ ├── __init__.py │ └── main.py └── setup.py
  20. 20 ./src/setup.py from setuptools import setup setup( name='myapp', install_requires=[ 'setuptools',

    'requests', ], entry_points={ 'console_scripts': [ 'myscript = myapp.main:main', ] } )
  21. 21 А что там внутри? . ├── src/ │ ├──

    myapp/ │ │ ├── __init__.py │ │ └── main.py │ └── setup.py ├── bootstrap.py └── buildout.cfg
  22. 22 ./buildout.cfg [buildout] develop = ./src parts = myproject [myproject]

    recipe = zc.recipe.egg:scripts eggs = myapp
  23. 23 А что там внутри? . ├── bin/ │ ├──

    buildout │ ├── myscript │ └── ... ├── eggs/ │ ├── requests-2.18.4-py2.7.egg/ │ └── ... ├── src/ ├── bootstrap.py └── buildout.cfg
  24. 24 ./bin/myscipt #!/usr/bin/python import sys sys.path[0:0] = [ '/home/user/myproject/src', '/home/user/myproject/eggs/requests-2.18.4-py2.7.egg',

    '/home/user/myproject/eggs/urllib3-1.22-py2.7.egg', ... ] import myapp.main if __name__ == '__main__': sys.exit(myapp.main.main())
  25. 25 Возможности формата конфига

  26. 26 Подстановка значений ${SECTION:OPTION} [myproject] recipe = zc.recipe.egg eggs =

    myapp initialization = import os os.environ['HOST'] = '${settings:host}' os.environ['POST'] = '${settings:port}' [settings] host = localhost port = 8080
  27. 27 Наследование [buildout] extends = base.cfg https://example.com/kgs/versions-1.2.cfg [myproject] eggs +=

    myapp[test] ipython<6.0
  28. 28 Добавление, вычитание, переопределение [buildout] extends = base.cfg parts +=

    tests build_docs parts -= nginx [myproject] eggs = myapp[test]
  29. 29 Макросы [server] recipe = zc.zdaemonrecipe port = 8080 program

    = ${buildout:bin-directory}/serve --port ${:port} --name ${:_buildout_section_name_} [server1] <= server port = 8081 [server2] <= server port = 8082
  30. 30 Зависимости [buildout] develop = . parts = run_app [run_app]

    => app recipe = collective.recipe.cmd on_install = true cmds = ${buildout:bin-directory}/app ${config:location} [app] recipe = zc.recipe.egg:scripts eggs = myapp
  31. 31 Условные секции [create_dirs] recipe = collective.recipe.cmd on_install = true

    cmds = mkdir ${buildout:directory}/var [create_dirs:windows] cmds = md ${buildout:directory}\var [buildout:os.environ.get('ALPINELINUX')] find-links += http://privat-pypi.com/simple/numpy
  32. 32 Рецепты

  33. 33 Рецепты Рецепт: – это компонент реализующий логику "части"; –

    является обычным питонячим классом с методами: • install() • update() – в одном пакете может быть несколько рецептов; – Buildout автоматически скачивает и устнаваливает пакеты с рецептами.
  34. 34 zc.recipe.egg:scripts [myproject] revipe = zc.recipe.egg:scripts eggs = myapp ipython<6.0

    interpreter = python find-links = https://domain.com/Django index = https://private-pypi.com/simple setting = myapp.production initialisation = import os os.environ.setdefault('DJANGO_SETTINGS_MODULE', '${:settings}')
  35. 35 zc.recipe.egg:scripts ./bin/manage.py #!/usr/bin/python import sys sys.path[0:0] = [ '/home/user/myproject/src',

    '/home/user/myproject/eggs/ipython-5.0.0-py2.7.egg', ... ] import os os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'myapp.production') import myapp.manage if __name__ == '__main__': sys.exit(myapp.manage.main())
  36. 36 zc.recipe.egg:custom [pillow-simd-env] CC = cc -mavx2 [pillow-simd] recipe =

    zc.recipe.egg:custom egg = Pillow-SIMD environment = pillow-simd-env
  37. 37 zc.recipe.cmmi (configure-make-make-install) [librsync] recipe = zc.recipe.cmmi url = https://domain.com/librsync-0.9.7.tar.gz

    extra_options = --enable-shared [rdiff-backup] recipe = zc.recipe.egg:custom egg = rdiff-backup rpath = ${librsync:location}/lib include-dirs = ${librsync:location}/include library-dirs = ${librsync:location}/lib
  38. 38 sact.recipe.jinjatemplate [configs] recipe = sact.recipe.jinjatemplate template-file = etc/templates/uwsgi.ini etc/templates/systemd/user/backend_uwsgi.service

    target-file = etc/uwsgi.ini etc/systemd/user/backend_uwsgi.service
  39. 39 Расширения

  40. 40 Расширения • buildout.gc • buildout.wheel • mr.developer • cykooz.buildout.basicauth

    • cykooz.buildout.venv • ...
  41. 41 mr.developer [buildout] extensions = mr.developer auto-checkout = * sources-dir

    = ext_src [sources] twisted = git git@github.com:twisted/twisted.git six = git git@github.com:benjaminp/six.git rev=1.8.0
  42. 42 mr.developer . ├── ext_src/ │ ├── twisted/ │ └──

    six/ ├── src/ └── buildout.cfg
  43. 43 Воспроизводимость

  44. 44 Воспроизводимость [buildout] allow-picked-versions = true show-picked-versions = true [versions]

    zc.buildout = 2.9.5 zc.recipe.egg = 2.0.3 setuptools = 36.6.0 six = 1.8.0 pyramid = 1.9.1
  45. 45 Воспроизводимость [buildout] extends = versions.cfg allow-picked-versions = true show-picked-versions

    = true
  46. 46 Воспроизводимость [buildout] extends = versions.cfg allow-picked-versions = true show-picked-versions

    = true update-versions-file = versions.cfg
  47. 47 Интеграция с IDE

  48. 48 PyCharm + zc.buildout

  49. 49 Eclipse + PyDev + zc.buildout [buildout] develop = ./src

    parts = myproject pydev [myproject] recipe = zc.recipe.egg:scripts eggs = myapp [pydev] recipe = pb.recipes.pydev eggs = ${myproject:eggs}
  50. 50 Other + zc.buildout [buildout] develop = ./src parts =

    myproject omelette [myproject] recipe = zc.recipe.egg:scripts eggs = myapp [omelette] recipe = collective.recipe.omelette eggs = ${myproject:eggs}
  51. 51 Other + zc.buildout . └── parts/ └── omelette/ ├──

    certifi/ ├── chardet/ ├── idna/ ├── myapp/ ├── pkg_resources/ ├── requests/ ├── setuptools/ ├── urllib3/ └── easy_install.py
  52. 52 Упссс...

  53. 53 А как же Docker, Vagrant и т.п.?

  54. 54 А как же Docker, Vagrant и т.п.? Пускай будут

    – они тоже полезные, но не заменяют Buildout.
  55. 55 Вопросы

  56. 56 Ссылки • http://docs.buildout.org • https://pypi.python.org/pypi/zc.buildout

  57. 57 Ещё примеры...

  58. 58 zc.recipe.cmmi (configure-make-make-install) [nginx] recipe = zc.recipe.cmmi url = http://sysoev.ru/nginx/nginx-0.7.65.tar.gz

    md5sum = abc4f76af450eedeb063158bd963feaa patch = ${buildout:directory}/nginx/upstream_hash.patch extra_options = --add-module=${buildout:directory}/nginx/upstream_hash