Hello community, here is the log from the commit of package python-heatclient for openSUSE:Factory checked in at 2018-01-24 15:28:25 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Comparing /work/SRC/openSUSE:Factory/python-heatclient (Old) and /work/SRC/openSUSE:Factory/.python-heatclient.new (New) ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Package is "python-heatclient" Wed Jan 24 15:28:25 2018 rev:25 rq:567543 version:1.13.0 Changes: -------- --- /work/SRC/openSUSE:Factory/python-heatclient/python-heatclient.changes 2017-08-28 15:30:32.455928954 +0200 +++ /work/SRC/openSUSE:Factory/.python-heatclient.new/python-heatclient.changes 2018-01-24 15:28:26.752138835 +0100 @@ -1,0 +2,21 @@ +Fri Jan 19 05:52:48 UTC 2018 - cloud-de...@suse.de + +- update to version 1.13.0 + - Add plug-in summary for osc doc + - Add --no-rollback option for stack cancel + - Add `--converge` argument for osc stack update + - No longer use oslotest.mockpatch + - Use generic user for both zuul v2 and v3 + - Modify error message encountered during stack update + - Decode content before checking + - Support --show-nested in openstack stack update --dry-run + - Don't override sections in deep_update + - Imported Translations from Zanata + - Don't preformat stack output show list/map values + - Remove vestigate HUDSON_PUBLISH_DOCS reference + - Allow cancelling create_in_progress stacks with --no-rollback + - Updated from global requirements + - Use Sphinx 1.5 warning-is-error +- Convert to singlespec + +------------------------------------------------------------------- Old: ---- python-heatclient-1.11.0.tar.gz New: ---- python-heatclient-1.13.0.tar.gz ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Other differences: ------------------ ++++++ python-heatclient.spec ++++++ --- /var/tmp/diff_new_pack.U33kOF/_old 2018-01-24 15:28:27.408108154 +0100 +++ /var/tmp/diff_new_pack.U33kOF/_new 2018-01-24 15:28:27.408108154 +0100 @@ -1,7 +1,7 @@ # # spec file for package python-heatclient # -# Copyright (c) 2017 SUSE LINUX GmbH, Nuernberg, Germany. +# Copyright (c) 2018 SUSE LINUX GmbH, Nuernberg, Germany. # # All modifications and additions to the file contributed by third parties # remain the property of their copyright owners, unless otherwise agreed @@ -16,96 +16,127 @@ # -%global sname python-heatclient Name: python-heatclient -Version: 1.11.0 +Version: 1.13.0 Release: 0 Summary: Python API and CLI for OpenStack Heat License: Apache-2.0 Group: Development/Languages/Python -Url: https://launchpad.net/%{sname} -Source0: https://pypi.io/packages/source/p/%{sname}/%{sname}-%{version}.tar.gz +Url: https://launchpad.net/python-heatclient +Source0: https://files.pythonhosted.org/packages/source/p/python-heatclient/python-heatclient-1.13.0.tar.gz BuildRequires: openstack-macros -BuildRequires: python-PyYAML >= 3.10.0 -BuildRequires: python-cliff >= 2.6.0 BuildRequires: python-devel -BuildRequires: python-fixtures >= 3.0.0 -BuildRequires: python-mock >= 2.0 -BuildRequires: python-mox3 >= 0.7.0 -BuildRequires: python-osc-lib >= 1.5.1 -BuildRequires: python-oslo.serialization >= 1.10.0 -BuildRequires: python-oslotest >= 1.10.0 -BuildRequires: python-pbr >= 2.0.0 -BuildRequires: python-requests-mock >= 1.1 -BuildRequires: python-swiftclient >= 3.2.0 -BuildRequires: python-testrepository >= 0.0.18 -BuildRequires: python-testscenarios >= 0.4 -BuildRequires: python-testtools >= 1.4.0 -Requires: python-Babel >= 2.3.4 -Requires: python-PrettyTable >= 0.7.1 -Requires: python-PyYAML >= 3.10.0 -Requires: python-cliff >= 2.6.0 -Requires: python-iso8601 >= 0.1.11 -Requires: python-keystoneauth1 >= 2.21.0 -Requires: python-osc-lib >= 1.5.1 -Requires: python-oslo.i18n >= 2.1.0 -Requires: python-oslo.serialization >= 1.10.0 -Requires: python-oslo.utils >= 3.20.0 -Requires: python-requests >= 2.14.2 -Requires: python-six >= 1.9.0 -Requires: python-swiftclient >= 3.2.0 +BuildRequires: python2-PyYAML +BuildRequires: python2-cliff +BuildRequires: python2-fixtures +BuildRequires: python2-mock +BuildRequires: python2-mox3 +BuildRequires: python2-osc-lib +BuildRequires: python2-oslo.serialization +BuildRequires: python2-pbr +BuildRequires: python2-requests-mock +BuildRequires: python2-swiftclient +BuildRequires: python2-testrepository +BuildRequires: python2-testscenarios +BuildRequires: python2-testtools +BuildRequires: python3-PyYAML +BuildRequires: python3-cliff +BuildRequires: python3-devel +BuildRequires: python3-fixtures +BuildRequires: python3-mock +BuildRequires: python3-mox3 +BuildRequires: python3-osc-lib +BuildRequires: python3-oslo.serialization +BuildRequires: python3-pbr +BuildRequires: python3-requests-mock +BuildRequires: python3-swiftclient +BuildRequires: python3-testrepository +BuildRequires: python3-testscenarios +BuildRequires: python3-testtools +Requires: python-Babel +Requires: python-PrettyTable +Requires: python-PyYAML +Requires: python-cliff +Requires: python-iso8601 +Requires: python-keystoneauth1 +Requires: python-osc-lib +Requires: python-oslo.i18n +Requires: python-oslo.serialization +Requires: python-oslo.utils +Requires: python-requests +Requires: python-six +Requires: python-swiftclient BuildArch: noarch +%if 0%{?suse_version} +Requires(post): update-alternatives +Requires(postun): update-alternatives +%else +# on RDO, update-alternatives is in chkconfig +Requires(post): chkconfig +Requires(postun): chkconfig +%endif +%python_subpackages %description This is a client for the OpenStack Heat API. There's a Python API (the heatclient module), and a command-line script (heat). Each implements 100% of the OpenStack Heat API. -%package doc +%package -n python-heatclient-doc Summary: Documentation for OpenStack Heat API Client -Group: Documentation +Group: Documentation/HTML BuildRequires: python-Sphinx -BuildRequires: python-openstackdocstheme >= 1.11.0 +BuildRequires: python-openstackdocstheme -%description doc +%description -n python-heatclient-doc This is a client for the OpenStack Heat API. There's a Python API (the heatclient module), and a command-line script (heat). Each implements 100% of the OpenStack Heat API. This package contains auto-generated documentation. %prep -%autosetup -n %{sname}-%{version} +%autosetup -p1 -n python-heatclient-1.13.0 %py_req_cleanup sed -i 's/^warning-is-error.*/warning-is-error = 0/g' setup.cfg %build -%{py2_build} +%{python_build} %{__python2} setup.py build_sphinx --builder=html,man # remove the sphinx-build leftovers rm -rf doc/build/html/.{doctrees,buildinfo} %install -%{py2_install} +%{python_install} # man page install -p -D -m 644 doc/build/man/heat.1 %{buildroot}%{_mandir}/man1/heat.1 # bash completion -install -p -D -m 644 tools/heat.bash_completion %{buildroot}%{_sysconfdir}/bash_completion.d/%{name} +install -p -D -m 644 tools/heat.bash_completion %{buildroot}%{_sysconfdir}/bash_completion.d/heat.bash_completion +%python_clone -a %{buildroot}%{_bindir}/heat +%python_clone -a %{buildroot}%{_mandir}/man1/heat.1 +%python_clone -a %{buildroot}%{_sysconfdir}/bash_completion.d/heat.bash_completion + +%post +%{python_install_alternative heat heat.1 %{_sysconfdir}/bash_completion.d/heat.bash_completion} + +%postun +%python_uninstall_alternative heat %check -%{__python2} setup.py testr +%{python_expand rm -rf .testrepository +$python setup.py testr +} -%files -%doc README.rst +%files %{python_files} %license LICENSE -%{python2_sitelib}/heatclient -%{python2_sitelib}/*.egg-info -%{_sysconfdir}/bash_completion.d//%{name} -%{_mandir}/man1/heat.1.gz -%{_bindir}/heat +%{python_sitelib}/heatclient +%{python_sitelib}/*.egg-info +%python_alternative %{_bindir}/heat +%python_alternative %{_mandir}/man1/heat.1 +%python_alternative %{_sysconfdir}/bash_completion.d/heat.bash_completion -%files doc +%files -n python-heatclient-doc %license LICENSE -%doc doc/build/html +%doc doc/build/html README.rst %changelog ++++++ _service ++++++ --- /var/tmp/diff_new_pack.U33kOF/_old 2018-01-24 15:28:27.440106657 +0100 +++ /var/tmp/diff_new_pack.U33kOF/_new 2018-01-24 15:28:27.440106657 +0100 @@ -1,8 +1,8 @@ <services> <service mode="disabled" name="renderspec"> - <param name="input-template">https://raw.githubusercontent.com/openstack/rpm-packaging/stable/pike/openstack/python-heatclient/python-heatclient.spec.j2</param> + <param name="input-template">https://raw.githubusercontent.com/openstack/rpm-packaging/master/openstack/python-heatclient/python-heatclient.spec.j2</param> <param name="output-name">python-heatclient.spec</param> - <param name="requirements">https://raw.githubusercontent.com/openstack/rpm-packaging/stable/pike/global-requirements.txt</param> + <param name="requirements">https://raw.githubusercontent.com/openstack/rpm-packaging/master/global-requirements.txt</param> <param name="changelog-email">cloud-de...@suse.de</param> <param name="changelog-provider">gh,openstack,python-heatclient</param> </service> ++++++ python-heatclient-1.11.0.tar.gz -> python-heatclient-1.13.0.tar.gz ++++++ diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/python-heatclient-1.11.0/AUTHORS new/python-heatclient-1.13.0/AUTHORS --- old/python-heatclient-1.11.0/AUTHORS 2017-07-28 21:00:53.000000000 +0200 +++ new/python-heatclient-1.13.0/AUTHORS 2017-12-07 15:48:55.000000000 +0100 @@ -51,6 +51,7 @@ Jianing YANG <jiani...@unitedstack.com> Joe Borg <j...@josephb.org> JordanP <jordan.pittier-...@cloudwatt.com> +KATO Tomoyuki <kato.tomoy...@jp.fujitsu.com> Kanagaraj Manickam <kanagaraj.manic...@hp.com> Kanagaraj Manickam <mkr1...@gmail.com> Kevin_Zheng <zhengzhe...@huawei.com> @@ -64,6 +65,7 @@ Masahito Muroi <muroi.masah...@lab.ntt.co.jp> Monty Taylor <mord...@inaugust.com> Nachi Ueno <na...@ntti3.com> +Nam Nguyen Hoai <na...@vn.fujitsu.com> Naohiro Tamura <naohi...@jp.fujitsu.com> Oleg Khavroshin <okhavros...@mirantis.com> Oleksii Chuprykov <ochupry...@mirantis.com> @@ -76,6 +78,7 @@ Paul Van Eck <pvan...@us.ibm.com> Pavlo Shchelokovskyy <pshchelokovs...@mirantis.com> Peter Razumovsky <prazumov...@mirantis.com> +PriyaDuggirala <priyaduggiral...@gmail.com> Rabi Mishra <ramis...@redhat.com> Rahul Nair <rahulun...@gmail.com> Rakesh H S <r...@hp.com> @@ -84,6 +87,7 @@ Rico Lin <rico.lin.gua...@gmail.com> Rob Cresswell <robert.cressw...@outlook.com> Rob Crittenden <rcrit...@redhat.com> +Roberto Polli <robipo...@gmail.com> Ronald Bradford <ronald.bradf...@gmail.com> Rui Chen <chenrui.m...@gmail.com> Russell Bryant <rbry...@redhat.com> @@ -125,6 +129,7 @@ Zhang Yang <neil.zhangy...@huawei.com> ZhiQiang Fan <aji.zq...@gmail.com> ZhiQiang Fan <zhiqiang....@huawei.com> +Zuul <z...@review.openstack.org> anusha-rayani-7 <anusha.ray...@tcs.com> bhagyashris <bhagyashri.shew...@nttdata.com> cedric.brandily <cedric.brand...@thalesgroup.com> diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/python-heatclient-1.11.0/ChangeLog new/python-heatclient-1.13.0/ChangeLog --- old/python-heatclient-1.11.0/ChangeLog 2017-07-28 21:00:53.000000000 +0200 +++ new/python-heatclient-1.13.0/ChangeLog 2017-12-07 15:48:55.000000000 +0100 @@ -1,10 +1,37 @@ CHANGES ======= +1.13.0 +------ + +* Don't preformat stack output show list/map values +* Updated from global requirements +* Updated from global requirements +* Allow cancelling create\_in\_progress stacks with --no-rollback +* Add --no-rollback option for stack cancel +* Modify error message encountered during stack update + +1.12.0 +------ + +* Add \`--converge\` argument for osc stack update +* Use generic user for both zuul v2 and v3 +* No longer use oslotest.mockpatch +* Don't override sections in deep\_update +* Updated from global requirements +* Support --show-nested in openstack stack update --dry-run +* Use Sphinx 1.5 warning-is-error +* Updated from global requirements +* Remove vestigate HUDSON\_PUBLISH\_DOCS reference +* Updated from global requirements +* Imported Translations from Zanata +* Updated from global requirements + 1.11.0 ------ * Fixing read before prompt bug +* Decode content before checking * Updated from global requirements * Updated from global requirements * Updated from global requirements @@ -15,6 +42,7 @@ 1.10.0 ------ +* Add plug-in summary for osc doc * Updated from global requirements * Add optional arguments '-y' in CLI:snapshot-delete * Updated from global requirements diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/python-heatclient-1.11.0/PKG-INFO new/python-heatclient-1.13.0/PKG-INFO --- old/python-heatclient-1.11.0/PKG-INFO 2017-07-28 21:00:54.000000000 +0200 +++ new/python-heatclient-1.13.0/PKG-INFO 2017-12-07 15:48:57.000000000 +0100 @@ -1,11 +1,12 @@ Metadata-Version: 1.1 Name: python-heatclient -Version: 1.11.0 +Version: 1.13.0 Summary: OpenStack Orchestration API Client Library Home-page: http://docs.openstack.org/developer/python-heatclient/ Author: OpenStack Author-email: openstack-...@lists.openstack.org License: UNKNOWN +Description-Content-Type: UNKNOWN Description: ======================== Team and repository tags ======================== diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/python-heatclient-1.11.0/doc/source/conf.py new/python-heatclient-1.13.0/doc/source/conf.py --- old/python-heatclient-1.11.0/doc/source/conf.py 2017-07-28 20:57:57.000000000 +0200 +++ new/python-heatclient-1.13.0/doc/source/conf.py 2017-12-07 15:45:22.000000000 +0100 @@ -39,10 +39,7 @@ extensions = ['sphinx.ext.autodoc', 'openstackdocstheme'] # Add any paths that contain templates here, relative to this directory. -if os.getenv('HUDSON_PUBLISH_DOCS'): - templates_path = ['_ga', '_templates'] -else: - templates_path = ['_templates'] +templates_path = [] # The suffix of source filenames. source_suffix = '.rst' diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/python-heatclient-1.11.0/heatclient/common/http.py new/python-heatclient-1.13.0/heatclient/common/http.py --- old/python-heatclient-1.11.0/heatclient/common/http.py 2017-07-28 20:57:57.000000000 +0200 +++ new/python-heatclient-1.13.0/heatclient/common/http.py 2017-12-07 15:45:22.000000000 +0100 @@ -221,10 +221,10 @@ raise exc.CommunicationError(message=message) self.log_http_response(resp) - + txt_content = encodeutils.safe_decode(resp.content, 'utf-8') if not ('X-Auth-Key' in kwargs['headers']) and ( resp.status_code == 401 or - (resp.status_code == 500 and "(HTTP 401)" in resp.content)): + (resp.status_code == 500 and "(HTTP 401)" in txt_content)): raise exc.HTTPUnauthorized(_("Authentication failed: %s") % resp.content) elif 400 <= resp.status_code < 600: diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/python-heatclient-1.11.0/heatclient/common/template_utils.py new/python-heatclient-1.13.0/heatclient/common/template_utils.py --- old/python-heatclient-1.11.0/heatclient/common/template_utils.py 2017-07-28 20:57:57.000000000 +0200 +++ new/python-heatclient-1.13.0/heatclient/common/template_utils.py 2017-12-07 15:45:22.000000000 +0100 @@ -74,11 +74,13 @@ return {}, None else: raise exc.CommandError(_('Need to specify exactly one of ' - '%(arg1)s, %(arg2)s or %(arg3)s') % + '[%(arg1)s, %(arg2)s or %(arg3)s]' + ' or %(arg4)s') % { 'arg1': '--template-file', 'arg2': '--template-url', - 'arg3': '--template-object'}) + 'arg3': '--template-object', + 'arg4': '--existing'}) if not tpl: raise exc.CommandError(_('Could not fetch template from %s') @@ -198,6 +200,9 @@ if isinstance(v, collections.Mapping): r = deep_update(old.get(k, {}), v) old[k] = r + elif v is None and isinstance(old.get(k), collections.Mapping): + # Don't override empty data, to work around yaml syntax issue + pass else: old[k] = new[k] return old diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/python-heatclient-1.11.0/heatclient/locale/zh_CN/LC_MESSAGES/heatclient-log-error.po new/python-heatclient-1.13.0/heatclient/locale/zh_CN/LC_MESSAGES/heatclient-log-error.po --- old/python-heatclient-1.11.0/heatclient/locale/zh_CN/LC_MESSAGES/heatclient-log-error.po 2017-07-28 20:57:57.000000000 +0200 +++ new/python-heatclient-1.13.0/heatclient/locale/zh_CN/LC_MESSAGES/heatclient-log-error.po 1970-01-01 01:00:00.000000000 +0100 @@ -1,25 +0,0 @@ -# zzxwill <zzxw...@gmail.com>, 2016. #zanata -msgid "" -msgstr "" -"Project-Id-Version: python-heatclient 1.2.1.dev53\n" -"Report-Msgid-Bugs-To: https://bugs.launchpad.net/openstack-i18n/\n" -"POT-Creation-Date: 2016-06-27 08:52+0000\n" -"MIME-Version: 1.0\n" -"Content-Type: text/plain; charset=UTF-8\n" -"Content-Transfer-Encoding: 8bit\n" -"PO-Revision-Date: 2016-06-27 11:57+0000\n" -"Last-Translator: zzxwill <zzxw...@gmail.com>\n" -"Language-Team: Chinese (China)\n" -"Language: zh-CN\n" -"X-Generator: Zanata 3.7.3\n" -"Plural-Forms: nplurals=1; plural=0\n" - -msgid "Could not decode response body as JSON" -msgstr "无法将响应主题编码为JSON" - -#, python-format -msgid "Stack %(stack)s or resource %(resource)snot found for hook %(hook_type)" -msgstr "" -"Postpone to translate this message as we Need to add a space between " -"'%(resource)s' and 'not'. Submitted a fix for the original string. (https://" -"review.openstack.org/334428)" diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/python-heatclient-1.11.0/heatclient/locale/zh_CN/LC_MESSAGES/heatclient-log-info.po new/python-heatclient-1.13.0/heatclient/locale/zh_CN/LC_MESSAGES/heatclient-log-info.po --- old/python-heatclient-1.11.0/heatclient/locale/zh_CN/LC_MESSAGES/heatclient-log-info.po 2017-07-28 20:57:57.000000000 +0200 +++ new/python-heatclient-1.13.0/heatclient/locale/zh_CN/LC_MESSAGES/heatclient-log-info.po 1970-01-01 01:00:00.000000000 +0100 @@ -1,24 +0,0 @@ -# zzxwill <zzxw...@gmail.com>, 2016. #zanata -msgid "" -msgstr "" -"Project-Id-Version: python-heatclient 1.2.1.dev53\n" -"Report-Msgid-Bugs-To: https://bugs.launchpad.net/openstack-i18n/\n" -"POT-Creation-Date: 2016-06-27 08:52+0000\n" -"MIME-Version: 1.0\n" -"Content-Type: text/plain; charset=UTF-8\n" -"Content-Transfer-Encoding: 8bit\n" -"PO-Revision-Date: 2016-06-27 11:59+0000\n" -"Last-Translator: zzxwill <zzxw...@gmail.com>\n" -"Language-Team: Chinese (China)\n" -"Language: zh-CN\n" -"X-Generator: Zanata 3.7.3\n" -"Plural-Forms: nplurals=1; plural=0\n" - -msgid "User did not confirm stack delete (ctrl-c) so taking no action." -msgstr "因为用户没有确认栈删除操作(ctrl-c),所以不执行任何动作。" - -msgid "User did not confirm stack delete (ctrl-d) so taking no action." -msgstr "因为用户没有确认栈删除操作(ctrl-d),所以不执行任何动作。" - -msgid "User did not confirm stack delete so taking no action." -msgstr "因为用户没有确认栈删除操作,所以不执行任何动作。" diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/python-heatclient-1.11.0/heatclient/locale/zh_CN/LC_MESSAGES/heatclient-log-warning.po new/python-heatclient-1.13.0/heatclient/locale/zh_CN/LC_MESSAGES/heatclient-log-warning.po --- old/python-heatclient-1.11.0/heatclient/locale/zh_CN/LC_MESSAGES/heatclient-log-warning.po 2017-07-28 20:57:57.000000000 +0200 +++ new/python-heatclient-1.13.0/heatclient/locale/zh_CN/LC_MESSAGES/heatclient-log-warning.po 1970-01-01 01:00:00.000000000 +0100 @@ -1,26 +0,0 @@ -# zzxwill <zzxw...@gmail.com>, 2016. #zanata -msgid "" -msgstr "" -"Project-Id-Version: python-heatclient 1.2.1.dev53\n" -"Report-Msgid-Bugs-To: https://bugs.launchpad.net/openstack-i18n/\n" -"POT-Creation-Date: 2016-06-27 08:52+0000\n" -"MIME-Version: 1.0\n" -"Content-Type: text/plain; charset=UTF-8\n" -"Content-Transfer-Encoding: 8bit\n" -"PO-Revision-Date: 2016-06-27 12:01+0000\n" -"Last-Translator: zzxwill <zzxw...@gmail.com>\n" -"Language-Team: Chinese (China)\n" -"Language: zh-CN\n" -"X-Generator: Zanata 3.7.3\n" -"Plural-Forms: nplurals=1; plural=0\n" - -#, python-format -msgid "\"%(old)s\" is deprecated, please use \"%(new)s\" instead" -msgstr "\"%(old)s\"已弃用,请使用\"%(new)s\"。" - -#, python-format -msgid "%(arg1)s is deprecated, please use %(arg2)s instead" -msgstr "\"%(arg1)s\"已弃用,请使用\"%(arg2)s\"。" - -msgid "System ca file could not be found." -msgstr "找不到系统CA文件。" diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/python-heatclient-1.11.0/heatclient/osc/plugin.py new/python-heatclient-1.13.0/heatclient/osc/plugin.py --- old/python-heatclient-1.11.0/heatclient/osc/plugin.py 2017-07-28 20:57:57.000000000 +0200 +++ new/python-heatclient-1.13.0/heatclient/osc/plugin.py 2017-12-07 15:45:22.000000000 +0100 @@ -11,6 +11,8 @@ # under the License. # +"""OpenStackClient plugin for Orchestration service.""" + import logging from osc_lib import utils diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/python-heatclient-1.11.0/heatclient/osc/v1/stack.py new/python-heatclient-1.13.0/heatclient/osc/v1/stack.py --- old/python-heatclient-1.11.0/heatclient/osc/v1/stack.py 2017-07-28 20:57:57.000000000 +0200 +++ new/python-heatclient-1.13.0/heatclient/osc/v1/stack.py 2017-12-07 15:45:22.000000000 +0100 @@ -233,6 +233,10 @@ 'would be changed') ) parser.add_argument( + '--show-nested', default=False, action="store_true", + help=_('Show nested stacks when performing --dry-run') + ) + parser.add_argument( '--parameter', metavar='<key=value>', help=_('Parameter values used to create the stack. ' 'This can be specified multiple times'), @@ -278,6 +282,11 @@ help=_('Wait until stack goes to UPDATE_COMPLETE or ' 'UPDATE_FAILED') ) + parser.add_argument( + '--converge', + action='store_true', + help=_('Stack update with observe on reality.') + ) return parser @@ -335,6 +344,9 @@ fields['disable_rollback'] = rollback == 'disabled' if parsed_args.dry_run: + if parsed_args.show_nested: + fields['show_nested'] = parsed_args.show_nested + changes = client.stacks.preview_update(**fields) fields = ['state', 'resource_name', 'resource_type', @@ -354,6 +366,9 @@ limit=1) marker = events[0].id if events else None + if parsed_args.converge: + fields['converge'] = True + client.stacks.update(**fields) if parsed_args.wait: @@ -994,11 +1009,6 @@ msg = _('Output error: %s') % output['output_error'] raise exc.CommandError(msg) - if (isinstance(output['output_value'], list) or - isinstance(output['output_value'], dict)): - output['output_value'] = heat_utils.json_formatter( - output['output_value']) - return self.dict2columns(output) @@ -1208,16 +1218,23 @@ Supported tasks for cancellation: * update + * create """ log = logging.getLogger(__name__ + '.CancelStack') def get_parser(self, prog_name): - return self._get_parser( + parser = self._get_parser( prog_name, _('Stack(s) to cancel (name or ID)'), - _('Wait for check to complete') + _('Wait for cancel to complete') + ) + parser.add_argument( + '--no-rollback', + action='store_true', + help=_('Cancel without rollback') ) + return parser def take_action(self, parsed_args): self.log.debug("take_action(%s)", parsed_args) @@ -1230,20 +1247,25 @@ 'Updated Time' ] heat_client = self.app.client_manager.orchestration - + if parsed_args.no_rollback: + action = heat_client.actions.cancel_without_rollback + allowed_statuses = ['create_in_progress', + 'update_in_progress'] + else: + action = heat_client.actions.cancel_update + allowed_statuses = ['update_in_progress'] for stack in parsed_args.stack: try: data = heat_client.stacks.get(stack_id=stack) except heat_exc.HTTPNotFound: raise exc.CommandError('Stack not found: %s' % stack) - status = getattr(data, 'stack_status').lower() - if status == 'update_in_progress': + if status in allowed_statuses: data = _stack_action( stack, parsed_args, heat_client, - heat_client.actions.cancel_update + action ) rows += [utils.get_dict_properties(data.to_dict(), columns)] else: diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/python-heatclient-1.11.0/heatclient/tests/functional/hooks/post_test_hook.sh new/python-heatclient-1.13.0/heatclient/tests/functional/hooks/post_test_hook.sh --- old/python-heatclient-1.11.0/heatclient/tests/functional/hooks/post_test_hook.sh 2017-07-28 20:57:57.000000000 +0200 +++ new/python-heatclient-1.13.0/heatclient/tests/functional/hooks/post_test_hook.sh 2017-12-07 15:45:22.000000000 +0100 @@ -21,7 +21,7 @@ sudo /usr/os-testr-env/bin/subunit2html $BASE/logs/testrepository.subunit $BASE/logs/testr_results.html sudo gzip -9 $BASE/logs/testrepository.subunit sudo gzip -9 $BASE/logs/testr_results.html - sudo chown jenkins:jenkins $BASE/logs/testrepository.subunit.gz $BASE/logs/testr_results.html.gz + sudo chown $USER:$USER $BASE/logs/testrepository.subunit.gz $BASE/logs/testr_results.html.gz sudo chmod a+r $BASE/logs/testrepository.subunit.gz $BASE/logs/testr_results.html.gz fi } @@ -35,13 +35,13 @@ # Go to the heatclient dir cd $HEATCLIENT_DIR -sudo chown -R jenkins:stack $HEATCLIENT_DIR +sudo chown -R $USER:stack $HEATCLIENT_DIR # Run tests echo "Running heatclient functional test suite" set +e # Preserve env for OS_ credentials -sudo -E -H -u jenkins tox -efunctional +sudo -E -H -u $USER tox -efunctional EXIT_CODE=$? set -e diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/python-heatclient-1.11.0/heatclient/tests/unit/osc/v1/test_stack.py new/python-heatclient-1.13.0/heatclient/tests/unit/osc/v1/test_stack.py --- old/python-heatclient-1.11.0/heatclient/tests/unit/osc/v1/test_stack.py 2017-07-28 20:57:57.000000000 +0200 +++ new/python-heatclient-1.13.0/heatclient/tests/unit/osc/v1/test_stack.py 2017-12-07 15:45:22.000000000 +0100 @@ -304,6 +304,16 @@ self.stack_client.update.assert_called_with(**kwargs) + def test_stack_update_converge(self): + arglist = ['my_stack', '-t', self.template_path, '--converge'] + kwargs = copy.deepcopy(self.defaults) + kwargs['converge'] = True + parsed_args = self.check_parser(self.cmd, arglist, []) + + self.cmd.take_action(parsed_args) + + self.stack_client.update.assert_called_with(**kwargs) + def test_stack_update_pre_update(self): arglist = ['my_stack', '-t', self.template_path, '--pre-update', 'a'] kwargs = copy.deepcopy(self.defaults) @@ -335,6 +345,17 @@ self.stack_client.preview_update.assert_called_with(**self.defaults) self.stack_client.update.assert_not_called() + def test_stack_update_dry_run_show_nested(self): + arglist = ['my_stack', '-t', self.template_path, '--dry-run', + '--show-nested'] + parsed_args = self.check_parser(self.cmd, arglist, []) + + self.cmd.take_action(parsed_args) + + self.stack_client.preview_update.assert_called_with( + show_nested=True, **self.defaults) + self.stack_client.update.assert_not_called() + @mock.patch('heatclient.common.event_utils.poll_for_events', return_value=('UPDATE_COMPLETE', 'Stack my_stack UPDATE_COMPLETE')) @@ -1210,6 +1231,21 @@ def test_stack_cancel(self): self._test_stack_action(2) + def _test_stack_cancel_no_rollback(self, call_count): + self.action = self.mock_client.actions.cancel_without_rollback + arglist = ['my_stack', '--no-rollback'] + parsed_args = self.check_parser(self.cmd, arglist, []) + columns, rows = self.cmd.take_action(parsed_args) + self.action.assert_called_once_with('my_stack') + self.mock_client.stacks.get.assert_called_with('my_stack') + self.assertEqual(call_count, + self.mock_client.stacks.get.call_count) + self.assertEqual(self.columns, columns) + self.assertEqual(1, len(rows)) + + def test_stack_cancel_no_rollback(self): + self._test_stack_cancel_no_rollback(2) + def test_stack_cancel_multi(self): self._test_stack_action_multi(4) @@ -1223,6 +1259,7 @@ self._test_stack_action_exception() def test_stack_cancel_unsupported_state(self): + self.stack.stack_status = "CREATE_COMPLETE" self.mock_client.stacks.get.return_value = self.stack error = self.assertRaises(exc.CommandError, self._test_stack_action, @@ -1231,6 +1268,17 @@ 'not in cancelable state', str(error)) + def test_stack_cancel_create_in_progress(self): + self.stack.stack_status = "CREATE_IN_PROGRESS" + self.mock_client.stacks.get.return_value = self.stack + error = self.assertRaises(exc.CommandError, + self._test_stack_action, + 2) + self.assertEqual('Stack my_stack with status \'create_in_progress\' ' + 'not in cancelable state', + str(error)) + self._test_stack_cancel_no_rollback(3) + class TestStackCheck(_TestStackCheckBase, TestStack): diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/python-heatclient-1.11.0/heatclient/tests/unit/test_actions.py new/python-heatclient-1.13.0/heatclient/tests/unit/test_actions.py --- old/python-heatclient-1.11.0/heatclient/tests/unit/test_actions.py 2017-07-28 20:57:57.000000000 +0200 +++ new/python-heatclient-1.13.0/heatclient/tests/unit/test_actions.py 2017-12-07 15:45:22.000000000 +0100 @@ -98,6 +98,15 @@ manager = self._base_test(expect_args, expect_kwargs) manager.cancel_update(**fields) + def test_cancel_without_rollback(self): + fields = {'stack_id': 'teststack%2Fabcd1234'} + expect_args = ('POST', + '/stacks/teststack%2Fabcd1234/actions') + expect_kwargs = {'data': {'cancel_without_rollback': None}} + + manager = self._base_test(expect_args, expect_kwargs) + manager.cancel_without_rollback(**fields) + def test_check(self): fields = {'stack_id': 'teststack%2Fabcd1234'} expect_args = ('POST', diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/python-heatclient-1.11.0/heatclient/tests/unit/test_common_http.py new/python-heatclient-1.13.0/heatclient/tests/unit/test_common_http.py --- old/python-heatclient-1.11.0/heatclient/tests/unit/test_common_http.py 2017-07-28 20:57:57.000000000 +0200 +++ new/python-heatclient-1.13.0/heatclient/tests/unit/test_common_http.py 2017-12-07 15:45:22.000000000 +0100 @@ -132,7 +132,7 @@ fake500 = fakes.FakeHTTPResponse( 500, 'ERROR', {'content-type': 'application/octet-stream'}, - '(HTTP 401)') + b'(HTTP 401)') # no token or credentials mock_request.return_value = fake500 diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/python-heatclient-1.11.0/heatclient/tests/unit/test_shell.py new/python-heatclient-1.13.0/heatclient/tests/unit/test_shell.py --- old/python-heatclient-1.11.0/heatclient/tests/unit/test_shell.py 2017-07-28 20:57:57.000000000 +0200 +++ new/python-heatclient-1.13.0/heatclient/tests/unit/test_shell.py 2017-12-07 15:45:22.000000000 +0100 @@ -22,7 +22,6 @@ import mox from oslo_serialization import jsonutils from oslo_utils import encodeutils -from oslotest import mockpatch import requests from requests_mock.contrib import fixture as rm_fixture import six @@ -124,7 +123,7 @@ # NOTE(tlashchova): this overrides the testtools.TestCase.patch method # that does simple monkey-patching in favor of mock's patching def patch(self, target, **kwargs): - mockfixture = self.useFixture(mockpatch.Patch(target, **kwargs)) + mockfixture = self.useFixture(fixtures.MockPatch(target, **kwargs)) return mockfixture.mock def stack_list_resp_dict(self, show_nested=False, include_project=False): diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/python-heatclient-1.11.0/heatclient/tests/unit/test_template_utils.py new/python-heatclient-1.13.0/heatclient/tests/unit/test_template_utils.py --- old/python-heatclient-1.11.0/heatclient/tests/unit/test_template_utils.py 2017-07-28 20:57:57.000000000 +0200 +++ new/python-heatclient-1.13.0/heatclient/tests/unit/test_template_utils.py 2017-12-07 15:45:22.000000000 +0100 @@ -448,6 +448,51 @@ ]) + @mock.patch('six.moves.urllib.request.urlopen') + def test_process_multiple_environments_empty_registry(self, mock_url): + # Setup + env_file1 = '/home/my/dir/env1.yaml' + env_file2 = '/home/my/dir/env2.yaml' + + env1 = b''' + resource_registry: + "OS::Thingy1": "file:///home/b/a.yaml" + ''' + env2 = b''' + resource_registry: + ''' + mock_url.side_effect = [six.BytesIO(env1), + six.BytesIO(self.template_a), + six.BytesIO(self.template_a), + six.BytesIO(env2)] + + # Test + env_file_list = [] + files, env = template_utils.process_multiple_environments_and_files( + [env_file1, env_file2], env_list_tracker=env_file_list) + + # Verify + expected_env = { + 'resource_registry': {'OS::Thingy1': 'file:///home/b/a.yaml'}} + self.assertEqual(expected_env, env) + + self.assertEqual(self.template_a.decode('utf-8'), + files['file:///home/b/a.yaml']) + + self.assertEqual(['file:///home/my/dir/env1.yaml', + 'file:///home/my/dir/env2.yaml'], env_file_list) + self.assertIn('file:///home/my/dir/env1.yaml', files) + self.assertIn('file:///home/my/dir/env2.yaml', files) + self.assertEqual(expected_env, + json.loads(files['file:///home/my/dir/env1.yaml'])) + mock_url.assert_has_calls([ + mock.call('file://%s' % env_file1), + mock.call('file:///home/b/a.yaml'), + mock.call('file:///home/b/a.yaml'), + mock.call('file://%s' % env_file2), + + ]) + def test_global_files(self): url = 'file:///home/b/a.yaml' env = ''' @@ -571,8 +616,8 @@ exc.CommandError, template_utils.get_template_contents) self.assertEqual( - ('Need to specify exactly one of --template-file, ' - '--template-url or --template-object'), + ('Need to specify exactly one of [--template-file, ' + '--template-url or --template-object] or --existing'), str(ex)) def test_get_template_contents_file_none_existing(self): diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/python-heatclient-1.11.0/heatclient/v1/actions.py new/python-heatclient-1.13.0/heatclient/v1/actions.py --- old/python-heatclient-1.11.0/heatclient/v1/actions.py 2017-07-28 20:57:57.000000000 +0200 +++ new/python-heatclient-1.13.0/heatclient/v1/actions.py 2017-12-07 15:45:22.000000000 +0100 @@ -48,6 +48,11 @@ body = {'cancel_update': None} self.client.post('/stacks/%s/actions' % stack_id, data=body) + def cancel_without_rollback(self, stack_id): + """Cancel running update of a stack.""" + body = {'cancel_without_rollback': None} + self.client.post('/stacks/%s/actions' % stack_id, data=body) + def check(self, stack_id): """Check a stack.""" body = {'check': None} diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/python-heatclient-1.11.0/python_heatclient.egg-info/PKG-INFO new/python-heatclient-1.13.0/python_heatclient.egg-info/PKG-INFO --- old/python-heatclient-1.11.0/python_heatclient.egg-info/PKG-INFO 2017-07-28 21:00:53.000000000 +0200 +++ new/python-heatclient-1.13.0/python_heatclient.egg-info/PKG-INFO 2017-12-07 15:48:55.000000000 +0100 @@ -1,11 +1,12 @@ Metadata-Version: 1.1 Name: python-heatclient -Version: 1.11.0 +Version: 1.13.0 Summary: OpenStack Orchestration API Client Library Home-page: http://docs.openstack.org/developer/python-heatclient/ Author: OpenStack Author-email: openstack-...@lists.openstack.org License: UNKNOWN +Description-Content-Type: UNKNOWN Description: ======================== Team and repository tags ======================== diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/python-heatclient-1.11.0/python_heatclient.egg-info/SOURCES.txt new/python-heatclient-1.13.0/python_heatclient.egg-info/SOURCES.txt --- old/python-heatclient-1.11.0/python_heatclient.egg-info/SOURCES.txt 2017-07-28 21:00:54.000000000 +0200 +++ new/python-heatclient-1.13.0/python_heatclient.egg-info/SOURCES.txt 2017-12-07 15:48:57.000000000 +0100 @@ -34,9 +34,6 @@ heatclient/common/template_format.py heatclient/common/template_utils.py heatclient/common/utils.py -heatclient/locale/zh_CN/LC_MESSAGES/heatclient-log-error.po -heatclient/locale/zh_CN/LC_MESSAGES/heatclient-log-info.po -heatclient/locale/zh_CN/LC_MESSAGES/heatclient-log-warning.po heatclient/osc/__init__.py heatclient/osc/plugin.py heatclient/osc/v1/__init__.py @@ -134,6 +131,7 @@ python_heatclient.egg-info/pbr.json python_heatclient.egg-info/requires.txt python_heatclient.egg-info/top_level.txt +releasenotes/notes/add-converge-in-osc-stack-update-10f256589f628d13.yaml releasenotes/notes/bug-1643492-2d7537b55f347722.yaml tools/heat.bash_completion tools/tox_install.sh \ No newline at end of file diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/python-heatclient-1.11.0/python_heatclient.egg-info/pbr.json new/python-heatclient-1.13.0/python_heatclient.egg-info/pbr.json --- old/python-heatclient-1.11.0/python_heatclient.egg-info/pbr.json 2017-07-28 21:00:53.000000000 +0200 +++ new/python-heatclient-1.13.0/python_heatclient.egg-info/pbr.json 2017-12-07 15:48:55.000000000 +0100 @@ -1 +1 @@ -{"git_version": "804ab3e", "is_release": true} \ No newline at end of file +{"git_version": "fbff3c6", "is_release": true} \ No newline at end of file diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/python-heatclient-1.11.0/python_heatclient.egg-info/requires.txt new/python-heatclient-1.13.0/python_heatclient.egg-info/requires.txt --- old/python-heatclient-1.11.0/python_heatclient.egg-info/requires.txt 2017-07-28 21:00:53.000000000 +0200 +++ new/python-heatclient-1.13.0/python_heatclient.egg-info/requires.txt 2017-12-07 15:48:55.000000000 +0100 @@ -1,14 +1,14 @@ Babel!=2.4.0,>=2.3.4 pbr!=2.1.0,>=2.0.0 -cliff>=2.8.0 +cliff!=2.9.0,>=2.8.0 iso8601>=0.1.11 osc-lib>=1.7.0 PrettyTable<0.8,>=0.7.1 -oslo.i18n!=3.15.2,>=2.1.0 -oslo.serialization!=2.19.1,>=1.10.0 -oslo.utils>=3.20.0 -keystoneauth1>=3.0.1 +oslo.i18n>=3.15.3 +oslo.serialization!=2.19.1,>=2.18.0 +oslo.utils>=3.31.0 +keystoneauth1>=3.2.0 python-swiftclient>=3.2.0 -PyYAML>=3.10.0 +PyYAML>=3.10 requests>=2.14.2 -six>=1.9.0 +six>=1.10.0 diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/python-heatclient-1.11.0/releasenotes/notes/add-converge-in-osc-stack-update-10f256589f628d13.yaml new/python-heatclient-1.13.0/releasenotes/notes/add-converge-in-osc-stack-update-10f256589f628d13.yaml --- old/python-heatclient-1.11.0/releasenotes/notes/add-converge-in-osc-stack-update-10f256589f628d13.yaml 1970-01-01 01:00:00.000000000 +0100 +++ new/python-heatclient-1.13.0/releasenotes/notes/add-converge-in-osc-stack-update-10f256589f628d13.yaml 2017-12-07 15:45:22.000000000 +0100 @@ -0,0 +1,8 @@ +--- +features: + - Adds '--converge' option for stack update with openstackclient. If + specified, existing resource attributes (which may have diverged) are + compared with the resource properties in the template used for update. + + Usage: + # openstack stack update --converge ... <stack_name> \ No newline at end of file diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/python-heatclient-1.11.0/requirements.txt new/python-heatclient-1.13.0/requirements.txt --- old/python-heatclient-1.11.0/requirements.txt 2017-07-28 20:57:57.000000000 +0200 +++ new/python-heatclient-1.13.0/requirements.txt 2017-12-07 15:45:22.000000000 +0100 @@ -4,15 +4,15 @@ Babel!=2.4.0,>=2.3.4 # BSD pbr!=2.1.0,>=2.0.0 # Apache-2.0 -cliff>=2.8.0 # Apache-2.0 +cliff!=2.9.0,>=2.8.0 # Apache-2.0 iso8601>=0.1.11 # MIT osc-lib>=1.7.0 # Apache-2.0 PrettyTable<0.8,>=0.7.1 # BSD -oslo.i18n!=3.15.2,>=2.1.0 # Apache-2.0 -oslo.serialization!=2.19.1,>=1.10.0 # Apache-2.0 -oslo.utils>=3.20.0 # Apache-2.0 -keystoneauth1>=3.0.1 # Apache-2.0 +oslo.i18n>=3.15.3 # Apache-2.0 +oslo.serialization!=2.19.1,>=2.18.0 # Apache-2.0 +oslo.utils>=3.31.0 # Apache-2.0 +keystoneauth1>=3.2.0 # Apache-2.0 python-swiftclient>=3.2.0 # Apache-2.0 -PyYAML>=3.10.0 # MIT +PyYAML>=3.10 # MIT requests>=2.14.2 # Apache-2.0 -six>=1.9.0 # MIT +six>=1.10.0 # MIT diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/python-heatclient-1.11.0/setup.cfg new/python-heatclient-1.13.0/setup.cfg --- old/python-heatclient-1.11.0/setup.cfg 2017-07-28 21:00:54.000000000 +0200 +++ new/python-heatclient-1.13.0/setup.cfg 2017-12-07 15:48:57.000000000 +0100 @@ -99,9 +99,10 @@ [build_sphinx] builders = html,man +all-files = 1 +warning-is-error = 1 source-dir = doc/source build-dir = doc/build -all_files = 1 [upload_sphinx] upload-dir = doc/build/html diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/python-heatclient-1.11.0/test-requirements.txt new/python-heatclient-1.13.0/test-requirements.txt --- old/python-heatclient-1.11.0/test-requirements.txt 2017-07-28 20:57:57.000000000 +0200 +++ new/python-heatclient-1.13.0/test-requirements.txt 2017-12-07 15:45:22.000000000 +0100 @@ -6,14 +6,13 @@ hacking!=0.13.0,<0.14,>=0.12.0 # Apache-2.0 coverage!=4.4,>=4.0 # Apache-2.0 fixtures>=3.0.0 # Apache-2.0/BSD -requests-mock>=1.1 # Apache-2.0 -mock>=2.0 # BSD -mox3!=0.19.0,>=0.7.0 # Apache-2.0 -openstackdocstheme>=1.11.0 # Apache-2.0 -oslotest>=1.10.0 # Apache-2.0 -python-openstackclient!=3.10.0,>=3.3.0 # Apache-2.0 +requests-mock>=1.1.0 # Apache-2.0 +mock>=2.0.0 # BSD +mox3>=0.20.0 # Apache-2.0 +openstackdocstheme>=1.17.0 # Apache-2.0 +python-openstackclient>=3.12.0 # Apache-2.0 sphinx>=1.6.2 # BSD -tempest>=16.1.0 # Apache-2.0 +tempest>=17.1.0 # Apache-2.0 testrepository>=0.0.18 # Apache-2.0/BSD testscenarios>=0.4 # Apache-2.0/BSD -testtools>=1.4.0 # MIT +testtools>=2.2.0 # MIT