busser-behave 0.1.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
- data/.cane +0 -0
- data/.gitignore +17 -0
- data/.tailor +4 -0
- data/.travis.yml +11 -0
- data/CHANGELOG.md +3 -0
- data/Gemfile +3 -0
- data/LICENSE +15 -0
- data/README.md +41 -0
- data/Rakefile +68 -0
- data/busser-behave.gemspec +30 -0
- data/features/plugin_install_command.feature +11 -0
- data/features/plugin_list_command.feature +8 -0
- data/features/support/env.rb +13 -0
- data/features/test_command.feature +31 -0
- data/lib/busser/behave/version.rb +26 -0
- data/lib/busser/runner_plugin/behave.rb +37 -0
- data/vendor/behave/CHANGES.rst +483 -0
- data/vendor/behave/LICENSE +23 -0
- data/vendor/behave/MANIFEST.in +37 -0
- data/vendor/behave/PROJECT_INFO.rst +21 -0
- data/vendor/behave/README.rst +112 -0
- data/vendor/behave/VERSION.txt +1 -0
- data/vendor/behave/behave.ini +22 -0
- data/vendor/behave/behave/__init__.py +30 -0
- data/vendor/behave/behave/__main__.py +187 -0
- data/vendor/behave/behave/_stepimport.py +185 -0
- data/vendor/behave/behave/_types.py +134 -0
- data/vendor/behave/behave/api/__init__.py +7 -0
- data/vendor/behave/behave/api/async_step.py +283 -0
- data/vendor/behave/behave/capture.py +227 -0
- data/vendor/behave/behave/compat/__init__.py +5 -0
- data/vendor/behave/behave/compat/collections.py +20 -0
- data/vendor/behave/behave/configuration.py +788 -0
- data/vendor/behave/behave/contrib/__init__.py +0 -0
- data/vendor/behave/behave/contrib/scenario_autoretry.py +73 -0
- data/vendor/behave/behave/formatter/__init__.py +12 -0
- data/vendor/behave/behave/formatter/_builtins.py +39 -0
- data/vendor/behave/behave/formatter/_registry.py +135 -0
- data/vendor/behave/behave/formatter/ansi_escapes.py +91 -0
- data/vendor/behave/behave/formatter/base.py +200 -0
- data/vendor/behave/behave/formatter/formatters.py +57 -0
- data/vendor/behave/behave/formatter/json.py +253 -0
- data/vendor/behave/behave/formatter/null.py +12 -0
- data/vendor/behave/behave/formatter/plain.py +158 -0
- data/vendor/behave/behave/formatter/pretty.py +351 -0
- data/vendor/behave/behave/formatter/progress.py +287 -0
- data/vendor/behave/behave/formatter/rerun.py +114 -0
- data/vendor/behave/behave/formatter/sphinx_steps.py +372 -0
- data/vendor/behave/behave/formatter/sphinx_util.py +118 -0
- data/vendor/behave/behave/formatter/steps.py +497 -0
- data/vendor/behave/behave/formatter/tags.py +178 -0
- data/vendor/behave/behave/i18n.py +614 -0
- data/vendor/behave/behave/importer.py +102 -0
- data/vendor/behave/behave/json_parser.py +264 -0
- data/vendor/behave/behave/log_capture.py +233 -0
- data/vendor/behave/behave/matchers.py +402 -0
- data/vendor/behave/behave/model.py +1737 -0
- data/vendor/behave/behave/model_core.py +416 -0
- data/vendor/behave/behave/model_describe.py +105 -0
- data/vendor/behave/behave/parser.py +615 -0
- data/vendor/behave/behave/reporter/__init__.py +0 -0
- data/vendor/behave/behave/reporter/base.py +45 -0
- data/vendor/behave/behave/reporter/junit.py +473 -0
- data/vendor/behave/behave/reporter/summary.py +94 -0
- data/vendor/behave/behave/runner.py +753 -0
- data/vendor/behave/behave/runner_util.py +417 -0
- data/vendor/behave/behave/step_registry.py +112 -0
- data/vendor/behave/behave/tag_expression.py +111 -0
- data/vendor/behave/behave/tag_matcher.py +465 -0
- data/vendor/behave/behave/textutil.py +137 -0
- data/vendor/behave/behave/userdata.py +130 -0
- data/vendor/behave/behave4cmd0/__all_steps__.py +12 -0
- data/vendor/behave/behave4cmd0/__init__.py +5 -0
- data/vendor/behave/behave4cmd0/__setup.py +11 -0
- data/vendor/behave/behave4cmd0/command_shell.py +216 -0
- data/vendor/behave/behave4cmd0/command_shell_proc.py +256 -0
- data/vendor/behave/behave4cmd0/command_steps.py +532 -0
- data/vendor/behave/behave4cmd0/command_util.py +147 -0
- data/vendor/behave/behave4cmd0/failing_steps.py +49 -0
- data/vendor/behave/behave4cmd0/log/__init__.py +1 -0
- data/vendor/behave/behave4cmd0/log/steps.py +395 -0
- data/vendor/behave/behave4cmd0/note_steps.py +29 -0
- data/vendor/behave/behave4cmd0/passing_steps.py +36 -0
- data/vendor/behave/behave4cmd0/pathutil.py +146 -0
- data/vendor/behave/behave4cmd0/setup_command_shell.py +24 -0
- data/vendor/behave/behave4cmd0/textutil.py +304 -0
- data/vendor/behave/bin/behave +44 -0
- data/vendor/behave/bin/behave.cmd +10 -0
- data/vendor/behave/bin/behave.junit_filter.py +85 -0
- data/vendor/behave/bin/behave.step_durations.py +163 -0
- data/vendor/behave/bin/behave2cucumber_json.py +63 -0
- data/vendor/behave/bin/behave_cmd.py +44 -0
- data/vendor/behave/bin/convert_i18n_yaml.py +77 -0
- data/vendor/behave/bin/explore_platform_encoding.py +24 -0
- data/vendor/behave/bin/i18n.yml +621 -0
- data/vendor/behave/bin/invoke +8 -0
- data/vendor/behave/bin/invoke.cmd +9 -0
- data/vendor/behave/bin/json.format.py +167 -0
- data/vendor/behave/bin/jsonschema_validate.py +122 -0
- data/vendor/behave/bin/make_localpi.py +279 -0
- data/vendor/behave/bin/project_bootstrap.sh +30 -0
- data/vendor/behave/bin/toxcmd.py +270 -0
- data/vendor/behave/bin/toxcmd3.py +270 -0
- data/vendor/behave/conftest.py +27 -0
- data/vendor/behave/docs/Makefile +154 -0
- data/vendor/behave/docs/_static/agogo.css +501 -0
- data/vendor/behave/docs/_static/behave_logo.png +0 -0
- data/vendor/behave/docs/_static/behave_logo1.png +0 -0
- data/vendor/behave/docs/_static/behave_logo2.png +0 -0
- data/vendor/behave/docs/_static/behave_logo3.png +0 -0
- data/vendor/behave/docs/_themes/LICENSE +45 -0
- data/vendor/behave/docs/_themes/kr/layout.html +17 -0
- data/vendor/behave/docs/_themes/kr/relations.html +19 -0
- data/vendor/behave/docs/_themes/kr/static/flasky.css_t +480 -0
- data/vendor/behave/docs/_themes/kr/static/small_flask.css +90 -0
- data/vendor/behave/docs/_themes/kr/theme.conf +7 -0
- data/vendor/behave/docs/_themes/kr_small/layout.html +22 -0
- data/vendor/behave/docs/_themes/kr_small/static/flasky.css_t +287 -0
- data/vendor/behave/docs/_themes/kr_small/theme.conf +10 -0
- data/vendor/behave/docs/api.rst +408 -0
- data/vendor/behave/docs/appendix.rst +19 -0
- data/vendor/behave/docs/behave.rst +640 -0
- data/vendor/behave/docs/behave.rst-template +86 -0
- data/vendor/behave/docs/behave_ecosystem.rst +81 -0
- data/vendor/behave/docs/comparison.rst +85 -0
- data/vendor/behave/docs/conf.py +293 -0
- data/vendor/behave/docs/context_attributes.rst +66 -0
- data/vendor/behave/docs/django.rst +192 -0
- data/vendor/behave/docs/formatters.rst +61 -0
- data/vendor/behave/docs/gherkin.rst +673 -0
- data/vendor/behave/docs/index.rst +57 -0
- data/vendor/behave/docs/install.rst +60 -0
- data/vendor/behave/docs/more_info.rst +184 -0
- data/vendor/behave/docs/new_and_noteworthy.rst +18 -0
- data/vendor/behave/docs/new_and_noteworthy_v1.2.4.rst +11 -0
- data/vendor/behave/docs/new_and_noteworthy_v1.2.5.rst +814 -0
- data/vendor/behave/docs/new_and_noteworthy_v1.2.6.rst +255 -0
- data/vendor/behave/docs/parse_builtin_types.rst +59 -0
- data/vendor/behave/docs/philosophy.rst +235 -0
- data/vendor/behave/docs/regular_expressions.rst +71 -0
- data/vendor/behave/docs/related.rst +14 -0
- data/vendor/behave/docs/test_domains.rst +62 -0
- data/vendor/behave/docs/tutorial.rst +636 -0
- data/vendor/behave/docs/update_behave_rst.py +100 -0
- data/vendor/behave/etc/json/behave.json-schema +172 -0
- data/vendor/behave/etc/junit.xml/behave_junit.xsd +103 -0
- data/vendor/behave/etc/junit.xml/junit-4.xsd +92 -0
- data/vendor/behave/examples/async_step/README.txt +8 -0
- data/vendor/behave/examples/async_step/behave.ini +14 -0
- data/vendor/behave/examples/async_step/features/async_dispatch.feature +8 -0
- data/vendor/behave/examples/async_step/features/async_run.feature +6 -0
- data/vendor/behave/examples/async_step/features/environment.py +28 -0
- data/vendor/behave/examples/async_step/features/steps/async_dispatch_steps.py +26 -0
- data/vendor/behave/examples/async_step/features/steps/async_steps34.py +10 -0
- data/vendor/behave/examples/async_step/features/steps/async_steps35.py +10 -0
- data/vendor/behave/examples/async_step/testrun_example.async_dispatch.txt +11 -0
- data/vendor/behave/examples/async_step/testrun_example.async_run.txt +9 -0
- data/vendor/behave/examples/env_vars/README.rst +26 -0
- data/vendor/behave/examples/env_vars/behave.ini +15 -0
- data/vendor/behave/examples/env_vars/behave_run.output_example.txt +12 -0
- data/vendor/behave/examples/env_vars/features/env_var.feature +6 -0
- data/vendor/behave/examples/env_vars/features/steps/env_var_steps.py +38 -0
- data/vendor/behave/features/README.txt +12 -0
- data/vendor/behave/features/background.feature +392 -0
- data/vendor/behave/features/capture_stderr.feature +172 -0
- data/vendor/behave/features/capture_stdout.feature +125 -0
- data/vendor/behave/features/cmdline.lang_list.feature +33 -0
- data/vendor/behave/features/configuration.default_paths.feature +116 -0
- data/vendor/behave/features/context.global_params.feature +35 -0
- data/vendor/behave/features/context.local_params.feature +17 -0
- data/vendor/behave/features/directory_layout.advanced.feature +147 -0
- data/vendor/behave/features/directory_layout.basic.feature +75 -0
- data/vendor/behave/features/directory_layout.basic2.feature +87 -0
- data/vendor/behave/features/environment.py +53 -0
- data/vendor/behave/features/exploratory_testing.with_table.feature +141 -0
- data/vendor/behave/features/feature.description.feature +0 -0
- data/vendor/behave/features/feature.exclude_from_run.feature +96 -0
- data/vendor/behave/features/formatter.help.feature +30 -0
- data/vendor/behave/features/formatter.json.feature +420 -0
- data/vendor/behave/features/formatter.progress3.feature +235 -0
- data/vendor/behave/features/formatter.rerun.feature +296 -0
- data/vendor/behave/features/formatter.steps.feature +181 -0
- data/vendor/behave/features/formatter.steps_catalog.feature +100 -0
- data/vendor/behave/features/formatter.steps_doc.feature +140 -0
- data/vendor/behave/features/formatter.steps_usage.feature +404 -0
- data/vendor/behave/features/formatter.tags.feature +134 -0
- data/vendor/behave/features/formatter.tags_location.feature +183 -0
- data/vendor/behave/features/formatter.user_defined.feature +196 -0
- data/vendor/behave/features/i18n.unicode_problems.feature +445 -0
- data/vendor/behave/features/logcapture.clear_handlers.feature +114 -0
- data/vendor/behave/features/logcapture.feature +188 -0
- data/vendor/behave/features/logcapture.filter.feature +130 -0
- data/vendor/behave/features/logging.no_capture.feature +99 -0
- data/vendor/behave/features/logging.setup_format.feature +157 -0
- data/vendor/behave/features/logging.setup_level.feature +168 -0
- data/vendor/behave/features/logging.setup_with_configfile.feature +137 -0
- data/vendor/behave/features/parser.background.sad_cases.feature +129 -0
- data/vendor/behave/features/parser.feature.sad_cases.feature +144 -0
- data/vendor/behave/features/runner.abort_by_user.feature +305 -0
- data/vendor/behave/features/runner.continue_after_failed_step.feature +136 -0
- data/vendor/behave/features/runner.default_format.feature +175 -0
- data/vendor/behave/features/runner.dry_run.feature +184 -0
- data/vendor/behave/features/runner.feature_listfile.feature +223 -0
- data/vendor/behave/features/runner.hook_errors.feature +382 -0
- data/vendor/behave/features/runner.multiple_formatters.feature +285 -0
- data/vendor/behave/features/runner.scenario_autoretry.feature +131 -0
- data/vendor/behave/features/runner.select_files_by_regexp.example.feature +71 -0
- data/vendor/behave/features/runner.select_files_by_regexp.feature +84 -0
- data/vendor/behave/features/runner.select_scenarios_by_file_location.feature +403 -0
- data/vendor/behave/features/runner.select_scenarios_by_name.feature +289 -0
- data/vendor/behave/features/runner.select_scenarios_by_tag.feature +225 -0
- data/vendor/behave/features/runner.stop_after_failure.feature +122 -0
- data/vendor/behave/features/runner.tag_logic.feature +67 -0
- data/vendor/behave/features/runner.unknown_formatter.feature +23 -0
- data/vendor/behave/features/runner.use_stage_implementations.feature +126 -0
- data/vendor/behave/features/scenario.description.feature +171 -0
- data/vendor/behave/features/scenario.exclude_from_run.feature +217 -0
- data/vendor/behave/features/scenario_outline.basics.feature +100 -0
- data/vendor/behave/features/scenario_outline.improved.feature +177 -0
- data/vendor/behave/features/scenario_outline.name_annotation.feature +157 -0
- data/vendor/behave/features/scenario_outline.parametrized.feature +401 -0
- data/vendor/behave/features/scenario_outline.tagged_examples.feature +118 -0
- data/vendor/behave/features/step.async_steps.feature +225 -0
- data/vendor/behave/features/step.duplicated_step.feature +106 -0
- data/vendor/behave/features/step.execute_steps.feature +59 -0
- data/vendor/behave/features/step.execute_steps.with_table.feature +65 -0
- data/vendor/behave/features/step.import_other_step_module.feature +103 -0
- data/vendor/behave/features/step.pending_steps.feature +128 -0
- data/vendor/behave/features/step.undefined_steps.feature +307 -0
- data/vendor/behave/features/step.use_step_library.feature +44 -0
- data/vendor/behave/features/step_dialect.generic_steps.feature +189 -0
- data/vendor/behave/features/step_dialect.given_when_then.feature +89 -0
- data/vendor/behave/features/step_param.builtin_types.with_float.feature +239 -0
- data/vendor/behave/features/step_param.builtin_types.with_integer.feature +305 -0
- data/vendor/behave/features/step_param.custom_types.feature +134 -0
- data/vendor/behave/features/steps/behave_active_tags_steps.py +86 -0
- data/vendor/behave/features/steps/behave_context_steps.py +67 -0
- data/vendor/behave/features/steps/behave_model_tag_logic_steps.py +105 -0
- data/vendor/behave/features/steps/behave_model_util.py +105 -0
- data/vendor/behave/features/steps/behave_select_files_steps.py +83 -0
- data/vendor/behave/features/steps/behave_tag_expression_steps.py +166 -0
- data/vendor/behave/features/steps/behave_undefined_steps.py +101 -0
- data/vendor/behave/features/steps/use_steplib_behave4cmd.py +12 -0
- data/vendor/behave/features/summary.undefined_steps.feature +114 -0
- data/vendor/behave/features/tags.active_tags.feature +385 -0
- data/vendor/behave/features/tags.default_tags.feature +104 -0
- data/vendor/behave/features/tags.tag_expression.feature +105 -0
- data/vendor/behave/features/userdata.feature +331 -0
- data/vendor/behave/invoke.yaml +21 -0
- data/vendor/behave/issue.features/README.txt +17 -0
- data/vendor/behave/issue.features/environment.py +97 -0
- data/vendor/behave/issue.features/issue0030.feature +21 -0
- data/vendor/behave/issue.features/issue0031.feature +16 -0
- data/vendor/behave/issue.features/issue0032.feature +28 -0
- data/vendor/behave/issue.features/issue0035.feature +74 -0
- data/vendor/behave/issue.features/issue0040.feature +154 -0
- data/vendor/behave/issue.features/issue0041.feature +135 -0
- data/vendor/behave/issue.features/issue0042.feature +230 -0
- data/vendor/behave/issue.features/issue0044.feature +51 -0
- data/vendor/behave/issue.features/issue0046.feature +77 -0
- data/vendor/behave/issue.features/issue0052.feature +66 -0
- data/vendor/behave/issue.features/issue0059.feature +29 -0
- data/vendor/behave/issue.features/issue0063.feature +102 -0
- data/vendor/behave/issue.features/issue0064.feature +97 -0
- data/vendor/behave/issue.features/issue0065.feature +18 -0
- data/vendor/behave/issue.features/issue0066.feature +80 -0
- data/vendor/behave/issue.features/issue0067.feature +90 -0
- data/vendor/behave/issue.features/issue0069.feature +64 -0
- data/vendor/behave/issue.features/issue0072.feature +32 -0
- data/vendor/behave/issue.features/issue0073.feature +228 -0
- data/vendor/behave/issue.features/issue0075.feature +18 -0
- data/vendor/behave/issue.features/issue0077.feature +89 -0
- data/vendor/behave/issue.features/issue0080.feature +49 -0
- data/vendor/behave/issue.features/issue0081.feature +138 -0
- data/vendor/behave/issue.features/issue0083.feature +69 -0
- data/vendor/behave/issue.features/issue0084.feature +69 -0
- data/vendor/behave/issue.features/issue0085.feature +119 -0
- data/vendor/behave/issue.features/issue0092.feature +66 -0
- data/vendor/behave/issue.features/issue0096.feature +173 -0
- data/vendor/behave/issue.features/issue0099.feature +130 -0
- data/vendor/behave/issue.features/issue0109.feature +60 -0
- data/vendor/behave/issue.features/issue0111.feature +53 -0
- data/vendor/behave/issue.features/issue0112.feature +64 -0
- data/vendor/behave/issue.features/issue0114.feature +118 -0
- data/vendor/behave/issue.features/issue0116.feature +71 -0
- data/vendor/behave/issue.features/issue0125.feature +49 -0
- data/vendor/behave/issue.features/issue0127.feature +64 -0
- data/vendor/behave/issue.features/issue0139.feature +67 -0
- data/vendor/behave/issue.features/issue0142.feature +37 -0
- data/vendor/behave/issue.features/issue0143.feature +54 -0
- data/vendor/behave/issue.features/issue0145.feature +63 -0
- data/vendor/behave/issue.features/issue0148.feature +105 -0
- data/vendor/behave/issue.features/issue0152.feature +52 -0
- data/vendor/behave/issue.features/issue0159.feature +74 -0
- data/vendor/behave/issue.features/issue0162.feature +86 -0
- data/vendor/behave/issue.features/issue0171.feature +16 -0
- data/vendor/behave/issue.features/issue0172.feature +51 -0
- data/vendor/behave/issue.features/issue0175.feature +91 -0
- data/vendor/behave/issue.features/issue0177.feature +40 -0
- data/vendor/behave/issue.features/issue0181.feature +36 -0
- data/vendor/behave/issue.features/issue0184.feature +144 -0
- data/vendor/behave/issue.features/issue0186.feature +12 -0
- data/vendor/behave/issue.features/issue0188.feature +60 -0
- data/vendor/behave/issue.features/issue0191.feature +178 -0
- data/vendor/behave/issue.features/issue0194.feature +215 -0
- data/vendor/behave/issue.features/issue0197.feature +11 -0
- data/vendor/behave/issue.features/issue0216.feature +129 -0
- data/vendor/behave/issue.features/issue0226.feature +51 -0
- data/vendor/behave/issue.features/issue0228.feature +41 -0
- data/vendor/behave/issue.features/issue0230.feature +46 -0
- data/vendor/behave/issue.features/issue0231.feature +77 -0
- data/vendor/behave/issue.features/issue0238.feature +52 -0
- data/vendor/behave/issue.features/issue0251.feature +15 -0
- data/vendor/behave/issue.features/issue0280.feature +118 -0
- data/vendor/behave/issue.features/issue0288.feature +95 -0
- data/vendor/behave/issue.features/issue0300.feature +49 -0
- data/vendor/behave/issue.features/issue0302.feature +91 -0
- data/vendor/behave/issue.features/issue0309.feature +52 -0
- data/vendor/behave/issue.features/issue0330.feature +124 -0
- data/vendor/behave/issue.features/issue0349.feature +9 -0
- data/vendor/behave/issue.features/issue0361.feature +79 -0
- data/vendor/behave/issue.features/issue0383.feature +76 -0
- data/vendor/behave/issue.features/issue0384.feature +103 -0
- data/vendor/behave/issue.features/issue0385.feature +109 -0
- data/vendor/behave/issue.features/issue0424.feature +66 -0
- data/vendor/behave/issue.features/issue0446.feature +116 -0
- data/vendor/behave/issue.features/issue0449.feature +42 -0
- data/vendor/behave/issue.features/issue0453.feature +42 -0
- data/vendor/behave/issue.features/issue0457.feature +65 -0
- data/vendor/behave/issue.features/issue0462.feature +38 -0
- data/vendor/behave/issue.features/issue0476.feature +39 -0
- data/vendor/behave/issue.features/issue0487.feature +92 -0
- data/vendor/behave/issue.features/issue0506.feature +77 -0
- data/vendor/behave/issue.features/issue0510.feature +51 -0
- data/vendor/behave/issue.features/requirements.txt +12 -0
- data/vendor/behave/issue.features/steps/ansi_steps.py +20 -0
- data/vendor/behave/issue.features/steps/behave_hooks_steps.py +10 -0
- data/vendor/behave/issue.features/steps/use_steplib_behave4cmd.py +13 -0
- data/vendor/behave/more.features/formatter.json.validate_output.feature +37 -0
- data/vendor/behave/more.features/steps/tutorial_steps.py +16 -0
- data/vendor/behave/more.features/steps/use_steplib_behave4cmd.py +7 -0
- data/vendor/behave/more.features/tutorial.feature +6 -0
- data/vendor/behave/py.requirements/README.txt +5 -0
- data/vendor/behave/py.requirements/all.txt +16 -0
- data/vendor/behave/py.requirements/basic.txt +21 -0
- data/vendor/behave/py.requirements/develop.txt +28 -0
- data/vendor/behave/py.requirements/docs.txt +6 -0
- data/vendor/behave/py.requirements/json.txt +7 -0
- data/vendor/behave/py.requirements/more_py26.txt +8 -0
- data/vendor/behave/py.requirements/testing.txt +10 -0
- data/vendor/behave/pytest.ini +24 -0
- data/vendor/behave/setup.cfg +29 -0
- data/vendor/behave/setup.py +118 -0
- data/vendor/behave/setuptools_behave.py +130 -0
- data/vendor/behave/tasks/__behave.py +45 -0
- data/vendor/behave/tasks/__init__.py +55 -0
- data/vendor/behave/tasks/__main__.py +70 -0
- data/vendor/behave/tasks/_setup.py +135 -0
- data/vendor/behave/tasks/_vendor/README.rst +35 -0
- data/vendor/behave/tasks/_vendor/invoke.zip +0 -0
- data/vendor/behave/tasks/_vendor/path.py +1725 -0
- data/vendor/behave/tasks/_vendor/pathlib.py +1280 -0
- data/vendor/behave/tasks/_vendor/six.py +868 -0
- data/vendor/behave/tasks/clean.py +246 -0
- data/vendor/behave/tasks/docs.py +97 -0
- data/vendor/behave/tasks/requirements.txt +17 -0
- data/vendor/behave/tasks/test.py +192 -0
- data/vendor/behave/test/__init__.py +0 -0
- data/vendor/behave/test/_importer_candidate.py +3 -0
- data/vendor/behave/test/reporters/__init__.py +0 -0
- data/vendor/behave/test/reporters/test_summary.py +240 -0
- data/vendor/behave/test/test_ansi_escapes.py +73 -0
- data/vendor/behave/test/test_configuration.py +172 -0
- data/vendor/behave/test/test_formatter.py +265 -0
- data/vendor/behave/test/test_formatter_progress.py +39 -0
- data/vendor/behave/test/test_formatter_rerun.py +97 -0
- data/vendor/behave/test/test_formatter_tags.py +57 -0
- data/vendor/behave/test/test_importer.py +151 -0
- data/vendor/behave/test/test_log_capture.py +29 -0
- data/vendor/behave/test/test_matchers.py +236 -0
- data/vendor/behave/test/test_model.py +871 -0
- data/vendor/behave/test/test_parser.py +1590 -0
- data/vendor/behave/test/test_runner.py +1074 -0
- data/vendor/behave/test/test_step_registry.py +96 -0
- data/vendor/behave/test/test_tag_expression.py +506 -0
- data/vendor/behave/test/test_tag_expression2.py +462 -0
- data/vendor/behave/test/test_tag_matcher.py +729 -0
- data/vendor/behave/test/test_userdata.py +184 -0
- data/vendor/behave/tests/README.txt +12 -0
- data/vendor/behave/tests/__init__.py +0 -0
- data/vendor/behave/tests/api/__ONLY_PY34_or_newer.txt +0 -0
- data/vendor/behave/tests/api/__init__.py +0 -0
- data/vendor/behave/tests/api/_test_async_step34.py +130 -0
- data/vendor/behave/tests/api/_test_async_step35.py +75 -0
- data/vendor/behave/tests/api/test_async_step.py +18 -0
- data/vendor/behave/tests/api/testing_support.py +94 -0
- data/vendor/behave/tests/api/testing_support_async.py +21 -0
- data/vendor/behave/tests/issues/test_issue0336.py +66 -0
- data/vendor/behave/tests/issues/test_issue0449.py +55 -0
- data/vendor/behave/tests/issues/test_issue0453.py +62 -0
- data/vendor/behave/tests/issues/test_issue0458.py +54 -0
- data/vendor/behave/tests/issues/test_issue0495.py +65 -0
- data/vendor/behave/tests/unit/__init__.py +0 -0
- data/vendor/behave/tests/unit/test_behave4cmd_command_shell_proc.py +135 -0
- data/vendor/behave/tests/unit/test_capture.py +280 -0
- data/vendor/behave/tests/unit/test_model_core.py +56 -0
- data/vendor/behave/tests/unit/test_textutil.py +267 -0
- data/vendor/behave/tools/test-features/background.feature +9 -0
- data/vendor/behave/tools/test-features/environment.py +8 -0
- data/vendor/behave/tools/test-features/french.feature +11 -0
- data/vendor/behave/tools/test-features/outline.feature +39 -0
- data/vendor/behave/tools/test-features/parse.feature +10 -0
- data/vendor/behave/tools/test-features/step-data.feature +60 -0
- data/vendor/behave/tools/test-features/steps/steps.py +120 -0
- data/vendor/behave/tools/test-features/tags.feature +18 -0
- data/vendor/behave/tox.ini +159 -0
- metadata +562 -0
|
@@ -0,0 +1,351 @@
|
|
|
1
|
+
# -*- coding: utf8 -*-
|
|
2
|
+
|
|
3
|
+
from __future__ import absolute_import, division
|
|
4
|
+
import sys
|
|
5
|
+
from behave.formatter.ansi_escapes import escapes, up
|
|
6
|
+
from behave.formatter.base import Formatter
|
|
7
|
+
from behave.model_core import Status
|
|
8
|
+
from behave.model_describe import escape_cell, escape_triple_quotes
|
|
9
|
+
from behave.textutil import indent, text as _text
|
|
10
|
+
import six
|
|
11
|
+
from six.moves import range, zip
|
|
12
|
+
|
|
13
|
+
|
|
14
|
+
# -----------------------------------------------------------------------------
|
|
15
|
+
# TERMINAL SUPPORT:
|
|
16
|
+
# -----------------------------------------------------------------------------
|
|
17
|
+
DEFAULT_WIDTH = 80
|
|
18
|
+
DEFAULT_HEIGHT = 24
|
|
19
|
+
|
|
20
|
+
def get_terminal_size():
|
|
21
|
+
if sys.platform == "windows":
|
|
22
|
+
# Autodetecting the size of a Windows command window is left as an
|
|
23
|
+
# exercise for the reader. Prizes may be awarded for the best answer.
|
|
24
|
+
return (DEFAULT_WIDTH, DEFAULT_HEIGHT)
|
|
25
|
+
|
|
26
|
+
try:
|
|
27
|
+
import fcntl
|
|
28
|
+
import termios
|
|
29
|
+
import struct
|
|
30
|
+
|
|
31
|
+
zero_struct = struct.pack("HHHH", 0, 0, 0, 0)
|
|
32
|
+
result = fcntl.ioctl(0, termios.TIOCGWINSZ, zero_struct)
|
|
33
|
+
h, w, hp1, wp1 = struct.unpack("HHHH", result)
|
|
34
|
+
|
|
35
|
+
return w or DEFAULT_WIDTH, h or DEFAULT_HEIGHT
|
|
36
|
+
except Exception: # pylint: disable=broad-except
|
|
37
|
+
return (DEFAULT_WIDTH, DEFAULT_HEIGHT)
|
|
38
|
+
|
|
39
|
+
|
|
40
|
+
# -----------------------------------------------------------------------------
|
|
41
|
+
# COLORING SUPPORT:
|
|
42
|
+
# -----------------------------------------------------------------------------
|
|
43
|
+
class MonochromeFormat(object):
|
|
44
|
+
def text(self, text): # pylint: disable=no-self-use
|
|
45
|
+
assert isinstance(text, six.text_type)
|
|
46
|
+
return text
|
|
47
|
+
|
|
48
|
+
class ColorFormat(object):
|
|
49
|
+
def __init__(self, status):
|
|
50
|
+
self.status = status
|
|
51
|
+
|
|
52
|
+
def text(self, text):
|
|
53
|
+
assert isinstance(text, six.text_type)
|
|
54
|
+
return escapes[self.status] + text + escapes["reset"]
|
|
55
|
+
|
|
56
|
+
|
|
57
|
+
# -----------------------------------------------------------------------------
|
|
58
|
+
# CLASS: PrettyFormatter
|
|
59
|
+
# -----------------------------------------------------------------------------
|
|
60
|
+
class PrettyFormatter(Formatter):
|
|
61
|
+
# pylint: disable=too-many-instance-attributes
|
|
62
|
+
name = "pretty"
|
|
63
|
+
description = "Standard colourised pretty formatter"
|
|
64
|
+
|
|
65
|
+
def __init__(self, stream_opener, config):
|
|
66
|
+
super(PrettyFormatter, self).__init__(stream_opener, config)
|
|
67
|
+
# -- ENSURE: Output stream is open.
|
|
68
|
+
self.stream = self.open()
|
|
69
|
+
isatty = getattr(self.stream, "isatty", lambda: True)
|
|
70
|
+
stream_supports_colors = isatty()
|
|
71
|
+
self.monochrome = not config.color or not stream_supports_colors
|
|
72
|
+
self.show_source = config.show_source
|
|
73
|
+
self.show_timings = config.show_timings
|
|
74
|
+
self.show_multiline = config.show_multiline
|
|
75
|
+
self.formats = None
|
|
76
|
+
self.display_width = get_terminal_size()[0]
|
|
77
|
+
|
|
78
|
+
# -- UNUSED: self.tag_statement = None
|
|
79
|
+
self.steps = []
|
|
80
|
+
self._uri = None
|
|
81
|
+
self._match = None
|
|
82
|
+
self.statement = None
|
|
83
|
+
self.indentations = []
|
|
84
|
+
self.step_lines = 0
|
|
85
|
+
|
|
86
|
+
|
|
87
|
+
def reset(self):
|
|
88
|
+
# -- UNUSED: self.tag_statement = None
|
|
89
|
+
self.steps = []
|
|
90
|
+
self._uri = None
|
|
91
|
+
self._match = None
|
|
92
|
+
self.statement = None
|
|
93
|
+
self.indentations = []
|
|
94
|
+
self.step_lines = 0
|
|
95
|
+
|
|
96
|
+
def uri(self, uri):
|
|
97
|
+
self.reset()
|
|
98
|
+
self._uri = uri
|
|
99
|
+
|
|
100
|
+
def feature(self, feature):
|
|
101
|
+
#self.print_comments(feature.comments, '')
|
|
102
|
+
self.print_tags(feature.tags, '')
|
|
103
|
+
self.stream.write(u"%s: %s" % (feature.keyword, feature.name))
|
|
104
|
+
if self.show_source:
|
|
105
|
+
# pylint: disable=redefined-builtin
|
|
106
|
+
format = self.format("comments")
|
|
107
|
+
self.stream.write(format.text(u" # %s" % feature.location))
|
|
108
|
+
self.stream.write("\n")
|
|
109
|
+
self.print_description(feature.description, " ", False)
|
|
110
|
+
self.stream.flush()
|
|
111
|
+
|
|
112
|
+
def background(self, background):
|
|
113
|
+
self.replay()
|
|
114
|
+
self.statement = background
|
|
115
|
+
|
|
116
|
+
def scenario(self, scenario):
|
|
117
|
+
self.replay()
|
|
118
|
+
self.statement = scenario
|
|
119
|
+
|
|
120
|
+
def replay(self):
|
|
121
|
+
self.print_statement()
|
|
122
|
+
self.print_steps()
|
|
123
|
+
self.stream.flush()
|
|
124
|
+
|
|
125
|
+
def step(self, step):
|
|
126
|
+
self.steps.append(step)
|
|
127
|
+
|
|
128
|
+
def match(self, match):
|
|
129
|
+
self._match = match
|
|
130
|
+
self.print_statement()
|
|
131
|
+
self.print_step(Status.executing, self._match.arguments,
|
|
132
|
+
self._match.location, self.monochrome)
|
|
133
|
+
self.stream.flush()
|
|
134
|
+
|
|
135
|
+
def result(self, result):
|
|
136
|
+
if not self.monochrome:
|
|
137
|
+
lines = self.step_lines + 1
|
|
138
|
+
if self.show_multiline:
|
|
139
|
+
if result.table:
|
|
140
|
+
lines += len(result.table.rows) + 1
|
|
141
|
+
if result.text:
|
|
142
|
+
lines += len(result.text.splitlines()) + 2
|
|
143
|
+
self.stream.write(up(lines))
|
|
144
|
+
arguments = []
|
|
145
|
+
location = None
|
|
146
|
+
if self._match:
|
|
147
|
+
arguments = self._match.arguments
|
|
148
|
+
location = self._match.location
|
|
149
|
+
self.print_step(result.status, arguments, location, True)
|
|
150
|
+
if result.error_message:
|
|
151
|
+
self.stream.write(indent(result.error_message.strip(), u" "))
|
|
152
|
+
self.stream.write("\n\n")
|
|
153
|
+
self.stream.flush()
|
|
154
|
+
|
|
155
|
+
def arg_format(self, key):
|
|
156
|
+
return self.format(key + "_arg")
|
|
157
|
+
|
|
158
|
+
def format(self, key):
|
|
159
|
+
if self.monochrome:
|
|
160
|
+
if self.formats is None:
|
|
161
|
+
self.formats = MonochromeFormat()
|
|
162
|
+
return self.formats
|
|
163
|
+
# -- OTHERWISE:
|
|
164
|
+
if self.formats is None:
|
|
165
|
+
self.formats = {} # pylint: disable=redefined-variable-type
|
|
166
|
+
# pylint: disable=redefined-builtin
|
|
167
|
+
format = self.formats.get(key, None)
|
|
168
|
+
if format is not None:
|
|
169
|
+
return format
|
|
170
|
+
format = self.formats[key] = ColorFormat(key)
|
|
171
|
+
return format
|
|
172
|
+
|
|
173
|
+
def eof(self):
|
|
174
|
+
self.replay()
|
|
175
|
+
self.stream.write("\n")
|
|
176
|
+
self.stream.flush()
|
|
177
|
+
|
|
178
|
+
def table(self, table):
|
|
179
|
+
cell_lengths = []
|
|
180
|
+
all_rows = [table.headings] + table.rows
|
|
181
|
+
for row in all_rows:
|
|
182
|
+
lengths = [len(escape_cell(c)) for c in row]
|
|
183
|
+
cell_lengths.append(lengths)
|
|
184
|
+
|
|
185
|
+
max_lengths = []
|
|
186
|
+
for col in range(0, len(cell_lengths[0])):
|
|
187
|
+
max_lengths.append(max([c[col] for c in cell_lengths]))
|
|
188
|
+
|
|
189
|
+
for i, row in enumerate(all_rows):
|
|
190
|
+
#for comment in row.comments:
|
|
191
|
+
# self.stream.write(" %s\n" % comment.value)
|
|
192
|
+
self.stream.write(" |")
|
|
193
|
+
for j, (cell, max_length) in enumerate(zip(row, max_lengths)):
|
|
194
|
+
self.stream.write(" ")
|
|
195
|
+
self.stream.write(self.color(cell, None, j))
|
|
196
|
+
self.stream.write(" " * (max_length - cell_lengths[i][j]))
|
|
197
|
+
self.stream.write(" |")
|
|
198
|
+
self.stream.write("\n")
|
|
199
|
+
self.stream.flush()
|
|
200
|
+
|
|
201
|
+
def doc_string(self, doc_string):
|
|
202
|
+
#self.stream.write(' """' + doc_string.content_type + '\n')
|
|
203
|
+
doc_string = _text(doc_string)
|
|
204
|
+
prefix = u" "
|
|
205
|
+
self.stream.write(u'%s"""\n' % prefix)
|
|
206
|
+
doc_string = escape_triple_quotes(indent(doc_string, prefix))
|
|
207
|
+
self.stream.write(doc_string)
|
|
208
|
+
self.stream.write(u'\n%s"""\n' % prefix)
|
|
209
|
+
self.stream.flush()
|
|
210
|
+
|
|
211
|
+
# def doc_string(self, doc_string):
|
|
212
|
+
# from behave.model_describe import ModelDescriptor
|
|
213
|
+
# prefix = " "
|
|
214
|
+
# text = ModelDescriptor.describe_docstring(doc_string, prefix)
|
|
215
|
+
# self.stream.write(text)
|
|
216
|
+
# self.stream.flush()
|
|
217
|
+
|
|
218
|
+
# -- UNUSED:
|
|
219
|
+
# def exception(self, exception):
|
|
220
|
+
# exception_text = _text(exception)
|
|
221
|
+
# self.stream.write(self.format("failed").text(exception_text) + "\n")
|
|
222
|
+
# self.stream.flush()
|
|
223
|
+
|
|
224
|
+
def color(self, cell, statuses, _color): # pylint: disable=no-self-use
|
|
225
|
+
if statuses:
|
|
226
|
+
return escapes["color"] + escapes["reset"]
|
|
227
|
+
else:
|
|
228
|
+
return escape_cell(cell)
|
|
229
|
+
|
|
230
|
+
def indented_text(self, text, proceed):
|
|
231
|
+
if not text:
|
|
232
|
+
return u""
|
|
233
|
+
|
|
234
|
+
if proceed:
|
|
235
|
+
indentation = self.indentations.pop(0)
|
|
236
|
+
else:
|
|
237
|
+
indentation = self.indentations[0]
|
|
238
|
+
|
|
239
|
+
indentation = u" " * indentation
|
|
240
|
+
return u"%s # %s" % (indentation, text)
|
|
241
|
+
|
|
242
|
+
def calculate_location_indentations(self):
|
|
243
|
+
line_widths = []
|
|
244
|
+
for s in [self.statement] + self.steps:
|
|
245
|
+
string = s.keyword + " " + s.name
|
|
246
|
+
line_widths.append(len(string))
|
|
247
|
+
max_line_width = max(line_widths)
|
|
248
|
+
self.indentations = [max_line_width - width for width in line_widths]
|
|
249
|
+
|
|
250
|
+
def print_statement(self):
|
|
251
|
+
if self.statement is None:
|
|
252
|
+
return
|
|
253
|
+
|
|
254
|
+
self.calculate_location_indentations()
|
|
255
|
+
self.stream.write(u"\n")
|
|
256
|
+
#self.print_comments(self.statement.comments, " ")
|
|
257
|
+
if hasattr(self.statement, "tags"):
|
|
258
|
+
self.print_tags(self.statement.tags, u" ")
|
|
259
|
+
self.stream.write(u" %s: %s " % (self.statement.keyword,
|
|
260
|
+
self.statement.name))
|
|
261
|
+
|
|
262
|
+
location = self.indented_text(six.text_type(self.statement.location), True)
|
|
263
|
+
if self.show_source:
|
|
264
|
+
self.stream.write(self.format("comments").text(location))
|
|
265
|
+
self.stream.write("\n")
|
|
266
|
+
#self.print_description(self.statement.description, u" ")
|
|
267
|
+
self.statement = None
|
|
268
|
+
|
|
269
|
+
def print_steps(self):
|
|
270
|
+
while self.steps:
|
|
271
|
+
self.print_step(Status.skipped, [], None, True)
|
|
272
|
+
|
|
273
|
+
def print_step(self, status, arguments, location, proceed):
|
|
274
|
+
if proceed:
|
|
275
|
+
step = self.steps.pop(0)
|
|
276
|
+
else:
|
|
277
|
+
step = self.steps[0]
|
|
278
|
+
|
|
279
|
+
text_format = self.format(status.name)
|
|
280
|
+
arg_format = self.arg_format(status.name)
|
|
281
|
+
|
|
282
|
+
#self.print_comments(step.comments, " ")
|
|
283
|
+
self.stream.write(" ")
|
|
284
|
+
self.stream.write(text_format.text(step.keyword + " "))
|
|
285
|
+
line_length = 5 + len(step.keyword)
|
|
286
|
+
|
|
287
|
+
step_name = six.text_type(step.name)
|
|
288
|
+
|
|
289
|
+
text_start = 0
|
|
290
|
+
for arg in arguments:
|
|
291
|
+
if arg.end <= text_start:
|
|
292
|
+
# -- SKIP-OVER: Optional and nested regexp args
|
|
293
|
+
# - Optional regexp args (unmatched: None).
|
|
294
|
+
# - Nested regexp args that are already processed.
|
|
295
|
+
continue
|
|
296
|
+
# -- VALID, MATCHED ARGUMENT:
|
|
297
|
+
assert arg.original is not None
|
|
298
|
+
text = step_name[text_start:arg.start]
|
|
299
|
+
self.stream.write(text_format.text(text))
|
|
300
|
+
line_length += len(text)
|
|
301
|
+
self.stream.write(arg_format.text(arg.original))
|
|
302
|
+
line_length += len(arg.original)
|
|
303
|
+
text_start = arg.end
|
|
304
|
+
|
|
305
|
+
if text_start != len(step_name):
|
|
306
|
+
text = step_name[text_start:]
|
|
307
|
+
self.stream.write(text_format.text(text))
|
|
308
|
+
line_length += (len(text))
|
|
309
|
+
|
|
310
|
+
if self.show_source:
|
|
311
|
+
location = six.text_type(location)
|
|
312
|
+
if self.show_timings and status in (Status.passed, Status.failed):
|
|
313
|
+
location += " %0.3fs" % step.duration
|
|
314
|
+
location = self.indented_text(location, proceed)
|
|
315
|
+
self.stream.write(self.format("comments").text(location))
|
|
316
|
+
line_length += len(location)
|
|
317
|
+
elif self.show_timings and status in (Status.passed, Status.failed):
|
|
318
|
+
timing = "%0.3fs" % step.duration
|
|
319
|
+
timing = self.indented_text(timing, proceed)
|
|
320
|
+
self.stream.write(self.format("comments").text(timing))
|
|
321
|
+
line_length += len(timing)
|
|
322
|
+
self.stream.write("\n")
|
|
323
|
+
|
|
324
|
+
self.step_lines = int((line_length - 1) / self.display_width)
|
|
325
|
+
|
|
326
|
+
if self.show_multiline:
|
|
327
|
+
if step.text:
|
|
328
|
+
self.doc_string(step.text)
|
|
329
|
+
if step.table:
|
|
330
|
+
self.table(step.table)
|
|
331
|
+
|
|
332
|
+
def print_tags(self, tags, indentation):
|
|
333
|
+
if not tags:
|
|
334
|
+
return
|
|
335
|
+
line = " ".join("@" + tag for tag in tags)
|
|
336
|
+
self.stream.write(indentation + line + "\n")
|
|
337
|
+
|
|
338
|
+
def print_comments(self, comments, indentation):
|
|
339
|
+
if not comments:
|
|
340
|
+
return
|
|
341
|
+
|
|
342
|
+
self.stream.write(indent([c.value for c in comments], indentation))
|
|
343
|
+
self.stream.write("\n")
|
|
344
|
+
|
|
345
|
+
def print_description(self, description, indentation, newline=True):
|
|
346
|
+
if not description:
|
|
347
|
+
return
|
|
348
|
+
|
|
349
|
+
self.stream.write(indent(description, indentation))
|
|
350
|
+
if newline:
|
|
351
|
+
self.stream.write("\n")
|
|
@@ -0,0 +1,287 @@
|
|
|
1
|
+
# -*- coding: utf-8 -*-
|
|
2
|
+
"""
|
|
3
|
+
Provides 2 dotted progress formatters:
|
|
4
|
+
|
|
5
|
+
* ScenarioProgressFormatter (scope: scenario)
|
|
6
|
+
* StepProgressFormatter (scope: step)
|
|
7
|
+
|
|
8
|
+
A "dot" character that represents the result status is printed after
|
|
9
|
+
executing a scope item.
|
|
10
|
+
"""
|
|
11
|
+
|
|
12
|
+
from __future__ import absolute_import
|
|
13
|
+
import six
|
|
14
|
+
from behave.formatter.base import Formatter
|
|
15
|
+
from behave.model_core import Status
|
|
16
|
+
from behave.textutil import text as _text
|
|
17
|
+
|
|
18
|
+
|
|
19
|
+
# -----------------------------------------------------------------------------
|
|
20
|
+
# CLASS: ProgressFormatterBase
|
|
21
|
+
# -----------------------------------------------------------------------------
|
|
22
|
+
class ProgressFormatterBase(Formatter):
|
|
23
|
+
"""
|
|
24
|
+
Provides formatter base class for different variants of progress formatters.
|
|
25
|
+
A progress formatter show an abbreviated, compact dotted progress bar,
|
|
26
|
+
similar to unittest output (in terse mode).
|
|
27
|
+
"""
|
|
28
|
+
# -- MAP: step.status to short dot_status representation.
|
|
29
|
+
dot_status = {
|
|
30
|
+
"passed": ".",
|
|
31
|
+
"failed": "F",
|
|
32
|
+
"error": "E", # Caught exception, but not an AssertionError
|
|
33
|
+
"skipped": "S",
|
|
34
|
+
"untested": "_",
|
|
35
|
+
"undefined": "U",
|
|
36
|
+
}
|
|
37
|
+
show_timings = False
|
|
38
|
+
|
|
39
|
+
def __init__(self, stream_opener, config):
|
|
40
|
+
super(ProgressFormatterBase, self).__init__(stream_opener, config)
|
|
41
|
+
# -- ENSURE: Output stream is open.
|
|
42
|
+
self.stream = self.open()
|
|
43
|
+
self.steps = []
|
|
44
|
+
self.failures = []
|
|
45
|
+
self.current_feature = None
|
|
46
|
+
self.current_scenario = None
|
|
47
|
+
self.show_timings = config.show_timings and self.show_timings
|
|
48
|
+
|
|
49
|
+
def reset(self):
|
|
50
|
+
self.steps = []
|
|
51
|
+
self.failures = []
|
|
52
|
+
self.current_feature = None
|
|
53
|
+
self.current_scenario = None
|
|
54
|
+
|
|
55
|
+
# -- FORMATTER API:
|
|
56
|
+
def feature(self, feature):
|
|
57
|
+
self.current_feature = feature
|
|
58
|
+
self.stream.write("%s " % six.text_type(feature.filename))
|
|
59
|
+
self.stream.flush()
|
|
60
|
+
|
|
61
|
+
def background(self, background):
|
|
62
|
+
pass
|
|
63
|
+
|
|
64
|
+
def scenario(self, scenario):
|
|
65
|
+
"""
|
|
66
|
+
Process the next scenario.
|
|
67
|
+
But first allow to report the status on the last scenario.
|
|
68
|
+
"""
|
|
69
|
+
self.report_scenario_completed()
|
|
70
|
+
self.current_scenario = scenario
|
|
71
|
+
|
|
72
|
+
def step(self, step):
|
|
73
|
+
self.steps.append(step)
|
|
74
|
+
|
|
75
|
+
def result(self, result):
|
|
76
|
+
self.steps.pop(0)
|
|
77
|
+
self.report_step_progress(result)
|
|
78
|
+
|
|
79
|
+
def eof(self):
|
|
80
|
+
"""
|
|
81
|
+
Called at end of a feature.
|
|
82
|
+
It would be better to have a hook that is called after all features.
|
|
83
|
+
"""
|
|
84
|
+
self.report_scenario_completed()
|
|
85
|
+
self.report_feature_completed()
|
|
86
|
+
self.report_failures()
|
|
87
|
+
self.stream.flush()
|
|
88
|
+
self.reset()
|
|
89
|
+
|
|
90
|
+
# -- SPECIFIC PART:
|
|
91
|
+
def report_step_progress(self, result):
|
|
92
|
+
"""
|
|
93
|
+
Report the progress on the current step.
|
|
94
|
+
The default implementation is empty.
|
|
95
|
+
It should be override by a concrete class.
|
|
96
|
+
"""
|
|
97
|
+
pass
|
|
98
|
+
|
|
99
|
+
def report_scenario_progress(self):
|
|
100
|
+
"""
|
|
101
|
+
Report the progress for the current/last scenario.
|
|
102
|
+
The default implementation is empty.
|
|
103
|
+
It should be override by a concrete class.
|
|
104
|
+
"""
|
|
105
|
+
pass
|
|
106
|
+
|
|
107
|
+
def report_feature_completed(self):
|
|
108
|
+
"""Hook called when a feature is completed to perform the last tasks.
|
|
109
|
+
"""
|
|
110
|
+
pass
|
|
111
|
+
|
|
112
|
+
def report_scenario_completed(self):
|
|
113
|
+
"""Hook called when a scenario is completed to perform the last tasks.
|
|
114
|
+
"""
|
|
115
|
+
self.report_scenario_progress()
|
|
116
|
+
|
|
117
|
+
def report_feature_duration(self):
|
|
118
|
+
if self.show_timings and self.current_feature:
|
|
119
|
+
self.stream.write(u" # %.3fs" % self.current_feature.duration)
|
|
120
|
+
self.stream.write("\n")
|
|
121
|
+
|
|
122
|
+
def report_scenario_duration(self):
|
|
123
|
+
if self.show_timings and self.current_scenario:
|
|
124
|
+
self.stream.write(u" # %.3fs" % self.current_scenario.duration)
|
|
125
|
+
self.stream.write("\n")
|
|
126
|
+
|
|
127
|
+
def report_failures(self):
|
|
128
|
+
if self.failures:
|
|
129
|
+
separator = "-" * 80
|
|
130
|
+
self.stream.write(u"%s\n" % separator)
|
|
131
|
+
for result in self.failures:
|
|
132
|
+
self.stream.write(u"FAILURE in step '%s':\n" % result.name)
|
|
133
|
+
self.stream.write(u" Feature: %s\n" % result.feature.name)
|
|
134
|
+
self.stream.write(u" Scenario: %s\n" % result.scenario.name)
|
|
135
|
+
self.stream.write(u"%s\n" % result.error_message)
|
|
136
|
+
if result.exception:
|
|
137
|
+
self.stream.write(u"exception: %s\n" % result.exception)
|
|
138
|
+
self.stream.write(u"%s\n" % separator)
|
|
139
|
+
|
|
140
|
+
|
|
141
|
+
# -----------------------------------------------------------------------------
|
|
142
|
+
# CLASS: ScenarioProgressFormatter
|
|
143
|
+
# -----------------------------------------------------------------------------
|
|
144
|
+
class ScenarioProgressFormatter(ProgressFormatterBase):
|
|
145
|
+
"""
|
|
146
|
+
Report dotted progress for each scenario similar to unittest.
|
|
147
|
+
"""
|
|
148
|
+
name = "progress"
|
|
149
|
+
description = "Shows dotted progress for each executed scenario."
|
|
150
|
+
|
|
151
|
+
def report_scenario_progress(self):
|
|
152
|
+
"""
|
|
153
|
+
Report the progress for the current/last scenario.
|
|
154
|
+
"""
|
|
155
|
+
if not self.current_scenario:
|
|
156
|
+
return # SKIP: No results to report for first scenario.
|
|
157
|
+
# -- NORMAL-CASE:
|
|
158
|
+
status_name = self.current_scenario.status.name
|
|
159
|
+
dot_status = self.dot_status[status_name]
|
|
160
|
+
if status_name == "failed":
|
|
161
|
+
# MAYBE TODO: self.failures.append(result)
|
|
162
|
+
pass
|
|
163
|
+
self.stream.write(dot_status)
|
|
164
|
+
self.stream.flush()
|
|
165
|
+
|
|
166
|
+
def report_feature_completed(self):
|
|
167
|
+
self.report_feature_duration()
|
|
168
|
+
|
|
169
|
+
# -----------------------------------------------------------------------------
|
|
170
|
+
# CLASS: StepProgressFormatter
|
|
171
|
+
# -----------------------------------------------------------------------------
|
|
172
|
+
class StepProgressFormatter(ProgressFormatterBase):
|
|
173
|
+
"""
|
|
174
|
+
Report dotted progress for each step similar to unittest.
|
|
175
|
+
"""
|
|
176
|
+
name = "progress2"
|
|
177
|
+
description = "Shows dotted progress for each executed step."
|
|
178
|
+
|
|
179
|
+
def report_step_progress(self, result):
|
|
180
|
+
"""
|
|
181
|
+
Report the progress for each step.
|
|
182
|
+
"""
|
|
183
|
+
dot_status = self.dot_status[result.status.name]
|
|
184
|
+
if result.status == Status.failed:
|
|
185
|
+
if (result.exception and
|
|
186
|
+
not isinstance(result.exception, AssertionError)):
|
|
187
|
+
# -- ISA-ERROR: Some Exception
|
|
188
|
+
dot_status = self.dot_status["error"]
|
|
189
|
+
result.feature = self.current_feature
|
|
190
|
+
result.scenario = self.current_scenario
|
|
191
|
+
self.failures.append(result)
|
|
192
|
+
self.stream.write(dot_status)
|
|
193
|
+
self.stream.flush()
|
|
194
|
+
|
|
195
|
+
def report_feature_completed(self):
|
|
196
|
+
self.report_feature_duration()
|
|
197
|
+
|
|
198
|
+
|
|
199
|
+
# -----------------------------------------------------------------------------
|
|
200
|
+
# CLASS: ScenarioStepProgressFormatter
|
|
201
|
+
# -----------------------------------------------------------------------------
|
|
202
|
+
class ScenarioStepProgressFormatter(StepProgressFormatter):
|
|
203
|
+
"""
|
|
204
|
+
Shows detailed dotted progress for both each step of a scenario.
|
|
205
|
+
Differs from StepProgressFormatter by:
|
|
206
|
+
|
|
207
|
+
* showing scenario names (as prefix scenario step progress)
|
|
208
|
+
* showing failures after each scenario (if necessary)
|
|
209
|
+
|
|
210
|
+
EXAMPLE:
|
|
211
|
+
$ behave -f progress3 features
|
|
212
|
+
Feature with failing scenario # features/failing_scenario.feature
|
|
213
|
+
Simple scenario with last failing step ....F
|
|
214
|
+
-----------------------------------------------------------------------
|
|
215
|
+
FAILURE in step 'last step fails' (features/failing_scenario.feature:7):
|
|
216
|
+
Assertion Failed: xxx
|
|
217
|
+
-----------------------------------------------------------------------
|
|
218
|
+
"""
|
|
219
|
+
name = "progress3"
|
|
220
|
+
description = "Shows detailed progress for each step of a scenario."
|
|
221
|
+
indent_size = 2
|
|
222
|
+
scenario_prefix = " " * indent_size
|
|
223
|
+
|
|
224
|
+
# -- FORMATTER API:
|
|
225
|
+
def feature(self, feature):
|
|
226
|
+
self.current_feature = feature
|
|
227
|
+
self.stream.write(u"%s # %s" % (feature.name, feature.filename))
|
|
228
|
+
|
|
229
|
+
def scenario(self, scenario):
|
|
230
|
+
"""Process the next scenario."""
|
|
231
|
+
# -- LAST SCENARIO: Report failures (if any).
|
|
232
|
+
self.report_scenario_completed()
|
|
233
|
+
|
|
234
|
+
# -- NEW SCENARIO:
|
|
235
|
+
assert not self.failures
|
|
236
|
+
self.current_scenario = scenario
|
|
237
|
+
scenario_name = scenario.name
|
|
238
|
+
if scenario_name:
|
|
239
|
+
scenario_name += " "
|
|
240
|
+
self.stream.write(u"%s%s " % (self.scenario_prefix, scenario_name))
|
|
241
|
+
self.stream.flush()
|
|
242
|
+
|
|
243
|
+
# -- DISABLED:
|
|
244
|
+
# def eof(self):
|
|
245
|
+
# has_scenarios = self.current_feature and self.current_scenario
|
|
246
|
+
# super(ScenarioStepProgressFormatter, self).eof()
|
|
247
|
+
# if has_scenarios:
|
|
248
|
+
# # -- EMPTY-LINE between 2 features.
|
|
249
|
+
# self.stream.write("\n")
|
|
250
|
+
|
|
251
|
+
# -- PROGRESS FORMATTER DETAILS:
|
|
252
|
+
# @overriden
|
|
253
|
+
def report_feature_completed(self):
|
|
254
|
+
# -- SKIP: self.report_feature_duration()
|
|
255
|
+
has_scenarios = self.current_feature and self.current_scenario
|
|
256
|
+
if has_scenarios:
|
|
257
|
+
# -- EMPTY-LINE between 2 features.
|
|
258
|
+
self.stream.write("\n")
|
|
259
|
+
|
|
260
|
+
def report_scenario_completed(self):
|
|
261
|
+
self.report_scenario_progress()
|
|
262
|
+
self.report_scenario_duration()
|
|
263
|
+
self.report_failures()
|
|
264
|
+
self.failures = []
|
|
265
|
+
|
|
266
|
+
def report_failures(self):
|
|
267
|
+
if self.failures:
|
|
268
|
+
separator = "-" * 80
|
|
269
|
+
self.stream.write(u"%s\n" % separator)
|
|
270
|
+
unicode_errors = 0
|
|
271
|
+
for failure in self.failures:
|
|
272
|
+
try:
|
|
273
|
+
self.stream.write(u"FAILURE in step '%s' (%s):\n" % \
|
|
274
|
+
(failure.name, failure.location))
|
|
275
|
+
self.stream.write(u"%s\n" % failure.error_message)
|
|
276
|
+
self.stream.write(u"%s\n" % separator)
|
|
277
|
+
except UnicodeError as e:
|
|
278
|
+
self.stream.write(u"%s while reporting failure in %s\n" % \
|
|
279
|
+
(e.__class__.__name__, failure.location))
|
|
280
|
+
self.stream.write(u"ERROR: %s\n" % \
|
|
281
|
+
_text(e, encoding=self.stream.encoding))
|
|
282
|
+
unicode_errors += 1
|
|
283
|
+
|
|
284
|
+
if unicode_errors:
|
|
285
|
+
msg = u"HINT: %d unicode errors occured during failure reporting.\n"
|
|
286
|
+
self.stream.write(msg % unicode_errors)
|
|
287
|
+
self.stream.flush()
|