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.
Files changed (418) hide show
  1. checksums.yaml +7 -0
  2. data/.cane +0 -0
  3. data/.gitignore +17 -0
  4. data/.tailor +4 -0
  5. data/.travis.yml +11 -0
  6. data/CHANGELOG.md +3 -0
  7. data/Gemfile +3 -0
  8. data/LICENSE +15 -0
  9. data/README.md +41 -0
  10. data/Rakefile +68 -0
  11. data/busser-behave.gemspec +30 -0
  12. data/features/plugin_install_command.feature +11 -0
  13. data/features/plugin_list_command.feature +8 -0
  14. data/features/support/env.rb +13 -0
  15. data/features/test_command.feature +31 -0
  16. data/lib/busser/behave/version.rb +26 -0
  17. data/lib/busser/runner_plugin/behave.rb +37 -0
  18. data/vendor/behave/CHANGES.rst +483 -0
  19. data/vendor/behave/LICENSE +23 -0
  20. data/vendor/behave/MANIFEST.in +37 -0
  21. data/vendor/behave/PROJECT_INFO.rst +21 -0
  22. data/vendor/behave/README.rst +112 -0
  23. data/vendor/behave/VERSION.txt +1 -0
  24. data/vendor/behave/behave.ini +22 -0
  25. data/vendor/behave/behave/__init__.py +30 -0
  26. data/vendor/behave/behave/__main__.py +187 -0
  27. data/vendor/behave/behave/_stepimport.py +185 -0
  28. data/vendor/behave/behave/_types.py +134 -0
  29. data/vendor/behave/behave/api/__init__.py +7 -0
  30. data/vendor/behave/behave/api/async_step.py +283 -0
  31. data/vendor/behave/behave/capture.py +227 -0
  32. data/vendor/behave/behave/compat/__init__.py +5 -0
  33. data/vendor/behave/behave/compat/collections.py +20 -0
  34. data/vendor/behave/behave/configuration.py +788 -0
  35. data/vendor/behave/behave/contrib/__init__.py +0 -0
  36. data/vendor/behave/behave/contrib/scenario_autoretry.py +73 -0
  37. data/vendor/behave/behave/formatter/__init__.py +12 -0
  38. data/vendor/behave/behave/formatter/_builtins.py +39 -0
  39. data/vendor/behave/behave/formatter/_registry.py +135 -0
  40. data/vendor/behave/behave/formatter/ansi_escapes.py +91 -0
  41. data/vendor/behave/behave/formatter/base.py +200 -0
  42. data/vendor/behave/behave/formatter/formatters.py +57 -0
  43. data/vendor/behave/behave/formatter/json.py +253 -0
  44. data/vendor/behave/behave/formatter/null.py +12 -0
  45. data/vendor/behave/behave/formatter/plain.py +158 -0
  46. data/vendor/behave/behave/formatter/pretty.py +351 -0
  47. data/vendor/behave/behave/formatter/progress.py +287 -0
  48. data/vendor/behave/behave/formatter/rerun.py +114 -0
  49. data/vendor/behave/behave/formatter/sphinx_steps.py +372 -0
  50. data/vendor/behave/behave/formatter/sphinx_util.py +118 -0
  51. data/vendor/behave/behave/formatter/steps.py +497 -0
  52. data/vendor/behave/behave/formatter/tags.py +178 -0
  53. data/vendor/behave/behave/i18n.py +614 -0
  54. data/vendor/behave/behave/importer.py +102 -0
  55. data/vendor/behave/behave/json_parser.py +264 -0
  56. data/vendor/behave/behave/log_capture.py +233 -0
  57. data/vendor/behave/behave/matchers.py +402 -0
  58. data/vendor/behave/behave/model.py +1737 -0
  59. data/vendor/behave/behave/model_core.py +416 -0
  60. data/vendor/behave/behave/model_describe.py +105 -0
  61. data/vendor/behave/behave/parser.py +615 -0
  62. data/vendor/behave/behave/reporter/__init__.py +0 -0
  63. data/vendor/behave/behave/reporter/base.py +45 -0
  64. data/vendor/behave/behave/reporter/junit.py +473 -0
  65. data/vendor/behave/behave/reporter/summary.py +94 -0
  66. data/vendor/behave/behave/runner.py +753 -0
  67. data/vendor/behave/behave/runner_util.py +417 -0
  68. data/vendor/behave/behave/step_registry.py +112 -0
  69. data/vendor/behave/behave/tag_expression.py +111 -0
  70. data/vendor/behave/behave/tag_matcher.py +465 -0
  71. data/vendor/behave/behave/textutil.py +137 -0
  72. data/vendor/behave/behave/userdata.py +130 -0
  73. data/vendor/behave/behave4cmd0/__all_steps__.py +12 -0
  74. data/vendor/behave/behave4cmd0/__init__.py +5 -0
  75. data/vendor/behave/behave4cmd0/__setup.py +11 -0
  76. data/vendor/behave/behave4cmd0/command_shell.py +216 -0
  77. data/vendor/behave/behave4cmd0/command_shell_proc.py +256 -0
  78. data/vendor/behave/behave4cmd0/command_steps.py +532 -0
  79. data/vendor/behave/behave4cmd0/command_util.py +147 -0
  80. data/vendor/behave/behave4cmd0/failing_steps.py +49 -0
  81. data/vendor/behave/behave4cmd0/log/__init__.py +1 -0
  82. data/vendor/behave/behave4cmd0/log/steps.py +395 -0
  83. data/vendor/behave/behave4cmd0/note_steps.py +29 -0
  84. data/vendor/behave/behave4cmd0/passing_steps.py +36 -0
  85. data/vendor/behave/behave4cmd0/pathutil.py +146 -0
  86. data/vendor/behave/behave4cmd0/setup_command_shell.py +24 -0
  87. data/vendor/behave/behave4cmd0/textutil.py +304 -0
  88. data/vendor/behave/bin/behave +44 -0
  89. data/vendor/behave/bin/behave.cmd +10 -0
  90. data/vendor/behave/bin/behave.junit_filter.py +85 -0
  91. data/vendor/behave/bin/behave.step_durations.py +163 -0
  92. data/vendor/behave/bin/behave2cucumber_json.py +63 -0
  93. data/vendor/behave/bin/behave_cmd.py +44 -0
  94. data/vendor/behave/bin/convert_i18n_yaml.py +77 -0
  95. data/vendor/behave/bin/explore_platform_encoding.py +24 -0
  96. data/vendor/behave/bin/i18n.yml +621 -0
  97. data/vendor/behave/bin/invoke +8 -0
  98. data/vendor/behave/bin/invoke.cmd +9 -0
  99. data/vendor/behave/bin/json.format.py +167 -0
  100. data/vendor/behave/bin/jsonschema_validate.py +122 -0
  101. data/vendor/behave/bin/make_localpi.py +279 -0
  102. data/vendor/behave/bin/project_bootstrap.sh +30 -0
  103. data/vendor/behave/bin/toxcmd.py +270 -0
  104. data/vendor/behave/bin/toxcmd3.py +270 -0
  105. data/vendor/behave/conftest.py +27 -0
  106. data/vendor/behave/docs/Makefile +154 -0
  107. data/vendor/behave/docs/_static/agogo.css +501 -0
  108. data/vendor/behave/docs/_static/behave_logo.png +0 -0
  109. data/vendor/behave/docs/_static/behave_logo1.png +0 -0
  110. data/vendor/behave/docs/_static/behave_logo2.png +0 -0
  111. data/vendor/behave/docs/_static/behave_logo3.png +0 -0
  112. data/vendor/behave/docs/_themes/LICENSE +45 -0
  113. data/vendor/behave/docs/_themes/kr/layout.html +17 -0
  114. data/vendor/behave/docs/_themes/kr/relations.html +19 -0
  115. data/vendor/behave/docs/_themes/kr/static/flasky.css_t +480 -0
  116. data/vendor/behave/docs/_themes/kr/static/small_flask.css +90 -0
  117. data/vendor/behave/docs/_themes/kr/theme.conf +7 -0
  118. data/vendor/behave/docs/_themes/kr_small/layout.html +22 -0
  119. data/vendor/behave/docs/_themes/kr_small/static/flasky.css_t +287 -0
  120. data/vendor/behave/docs/_themes/kr_small/theme.conf +10 -0
  121. data/vendor/behave/docs/api.rst +408 -0
  122. data/vendor/behave/docs/appendix.rst +19 -0
  123. data/vendor/behave/docs/behave.rst +640 -0
  124. data/vendor/behave/docs/behave.rst-template +86 -0
  125. data/vendor/behave/docs/behave_ecosystem.rst +81 -0
  126. data/vendor/behave/docs/comparison.rst +85 -0
  127. data/vendor/behave/docs/conf.py +293 -0
  128. data/vendor/behave/docs/context_attributes.rst +66 -0
  129. data/vendor/behave/docs/django.rst +192 -0
  130. data/vendor/behave/docs/formatters.rst +61 -0
  131. data/vendor/behave/docs/gherkin.rst +673 -0
  132. data/vendor/behave/docs/index.rst +57 -0
  133. data/vendor/behave/docs/install.rst +60 -0
  134. data/vendor/behave/docs/more_info.rst +184 -0
  135. data/vendor/behave/docs/new_and_noteworthy.rst +18 -0
  136. data/vendor/behave/docs/new_and_noteworthy_v1.2.4.rst +11 -0
  137. data/vendor/behave/docs/new_and_noteworthy_v1.2.5.rst +814 -0
  138. data/vendor/behave/docs/new_and_noteworthy_v1.2.6.rst +255 -0
  139. data/vendor/behave/docs/parse_builtin_types.rst +59 -0
  140. data/vendor/behave/docs/philosophy.rst +235 -0
  141. data/vendor/behave/docs/regular_expressions.rst +71 -0
  142. data/vendor/behave/docs/related.rst +14 -0
  143. data/vendor/behave/docs/test_domains.rst +62 -0
  144. data/vendor/behave/docs/tutorial.rst +636 -0
  145. data/vendor/behave/docs/update_behave_rst.py +100 -0
  146. data/vendor/behave/etc/json/behave.json-schema +172 -0
  147. data/vendor/behave/etc/junit.xml/behave_junit.xsd +103 -0
  148. data/vendor/behave/etc/junit.xml/junit-4.xsd +92 -0
  149. data/vendor/behave/examples/async_step/README.txt +8 -0
  150. data/vendor/behave/examples/async_step/behave.ini +14 -0
  151. data/vendor/behave/examples/async_step/features/async_dispatch.feature +8 -0
  152. data/vendor/behave/examples/async_step/features/async_run.feature +6 -0
  153. data/vendor/behave/examples/async_step/features/environment.py +28 -0
  154. data/vendor/behave/examples/async_step/features/steps/async_dispatch_steps.py +26 -0
  155. data/vendor/behave/examples/async_step/features/steps/async_steps34.py +10 -0
  156. data/vendor/behave/examples/async_step/features/steps/async_steps35.py +10 -0
  157. data/vendor/behave/examples/async_step/testrun_example.async_dispatch.txt +11 -0
  158. data/vendor/behave/examples/async_step/testrun_example.async_run.txt +9 -0
  159. data/vendor/behave/examples/env_vars/README.rst +26 -0
  160. data/vendor/behave/examples/env_vars/behave.ini +15 -0
  161. data/vendor/behave/examples/env_vars/behave_run.output_example.txt +12 -0
  162. data/vendor/behave/examples/env_vars/features/env_var.feature +6 -0
  163. data/vendor/behave/examples/env_vars/features/steps/env_var_steps.py +38 -0
  164. data/vendor/behave/features/README.txt +12 -0
  165. data/vendor/behave/features/background.feature +392 -0
  166. data/vendor/behave/features/capture_stderr.feature +172 -0
  167. data/vendor/behave/features/capture_stdout.feature +125 -0
  168. data/vendor/behave/features/cmdline.lang_list.feature +33 -0
  169. data/vendor/behave/features/configuration.default_paths.feature +116 -0
  170. data/vendor/behave/features/context.global_params.feature +35 -0
  171. data/vendor/behave/features/context.local_params.feature +17 -0
  172. data/vendor/behave/features/directory_layout.advanced.feature +147 -0
  173. data/vendor/behave/features/directory_layout.basic.feature +75 -0
  174. data/vendor/behave/features/directory_layout.basic2.feature +87 -0
  175. data/vendor/behave/features/environment.py +53 -0
  176. data/vendor/behave/features/exploratory_testing.with_table.feature +141 -0
  177. data/vendor/behave/features/feature.description.feature +0 -0
  178. data/vendor/behave/features/feature.exclude_from_run.feature +96 -0
  179. data/vendor/behave/features/formatter.help.feature +30 -0
  180. data/vendor/behave/features/formatter.json.feature +420 -0
  181. data/vendor/behave/features/formatter.progress3.feature +235 -0
  182. data/vendor/behave/features/formatter.rerun.feature +296 -0
  183. data/vendor/behave/features/formatter.steps.feature +181 -0
  184. data/vendor/behave/features/formatter.steps_catalog.feature +100 -0
  185. data/vendor/behave/features/formatter.steps_doc.feature +140 -0
  186. data/vendor/behave/features/formatter.steps_usage.feature +404 -0
  187. data/vendor/behave/features/formatter.tags.feature +134 -0
  188. data/vendor/behave/features/formatter.tags_location.feature +183 -0
  189. data/vendor/behave/features/formatter.user_defined.feature +196 -0
  190. data/vendor/behave/features/i18n.unicode_problems.feature +445 -0
  191. data/vendor/behave/features/logcapture.clear_handlers.feature +114 -0
  192. data/vendor/behave/features/logcapture.feature +188 -0
  193. data/vendor/behave/features/logcapture.filter.feature +130 -0
  194. data/vendor/behave/features/logging.no_capture.feature +99 -0
  195. data/vendor/behave/features/logging.setup_format.feature +157 -0
  196. data/vendor/behave/features/logging.setup_level.feature +168 -0
  197. data/vendor/behave/features/logging.setup_with_configfile.feature +137 -0
  198. data/vendor/behave/features/parser.background.sad_cases.feature +129 -0
  199. data/vendor/behave/features/parser.feature.sad_cases.feature +144 -0
  200. data/vendor/behave/features/runner.abort_by_user.feature +305 -0
  201. data/vendor/behave/features/runner.continue_after_failed_step.feature +136 -0
  202. data/vendor/behave/features/runner.default_format.feature +175 -0
  203. data/vendor/behave/features/runner.dry_run.feature +184 -0
  204. data/vendor/behave/features/runner.feature_listfile.feature +223 -0
  205. data/vendor/behave/features/runner.hook_errors.feature +382 -0
  206. data/vendor/behave/features/runner.multiple_formatters.feature +285 -0
  207. data/vendor/behave/features/runner.scenario_autoretry.feature +131 -0
  208. data/vendor/behave/features/runner.select_files_by_regexp.example.feature +71 -0
  209. data/vendor/behave/features/runner.select_files_by_regexp.feature +84 -0
  210. data/vendor/behave/features/runner.select_scenarios_by_file_location.feature +403 -0
  211. data/vendor/behave/features/runner.select_scenarios_by_name.feature +289 -0
  212. data/vendor/behave/features/runner.select_scenarios_by_tag.feature +225 -0
  213. data/vendor/behave/features/runner.stop_after_failure.feature +122 -0
  214. data/vendor/behave/features/runner.tag_logic.feature +67 -0
  215. data/vendor/behave/features/runner.unknown_formatter.feature +23 -0
  216. data/vendor/behave/features/runner.use_stage_implementations.feature +126 -0
  217. data/vendor/behave/features/scenario.description.feature +171 -0
  218. data/vendor/behave/features/scenario.exclude_from_run.feature +217 -0
  219. data/vendor/behave/features/scenario_outline.basics.feature +100 -0
  220. data/vendor/behave/features/scenario_outline.improved.feature +177 -0
  221. data/vendor/behave/features/scenario_outline.name_annotation.feature +157 -0
  222. data/vendor/behave/features/scenario_outline.parametrized.feature +401 -0
  223. data/vendor/behave/features/scenario_outline.tagged_examples.feature +118 -0
  224. data/vendor/behave/features/step.async_steps.feature +225 -0
  225. data/vendor/behave/features/step.duplicated_step.feature +106 -0
  226. data/vendor/behave/features/step.execute_steps.feature +59 -0
  227. data/vendor/behave/features/step.execute_steps.with_table.feature +65 -0
  228. data/vendor/behave/features/step.import_other_step_module.feature +103 -0
  229. data/vendor/behave/features/step.pending_steps.feature +128 -0
  230. data/vendor/behave/features/step.undefined_steps.feature +307 -0
  231. data/vendor/behave/features/step.use_step_library.feature +44 -0
  232. data/vendor/behave/features/step_dialect.generic_steps.feature +189 -0
  233. data/vendor/behave/features/step_dialect.given_when_then.feature +89 -0
  234. data/vendor/behave/features/step_param.builtin_types.with_float.feature +239 -0
  235. data/vendor/behave/features/step_param.builtin_types.with_integer.feature +305 -0
  236. data/vendor/behave/features/step_param.custom_types.feature +134 -0
  237. data/vendor/behave/features/steps/behave_active_tags_steps.py +86 -0
  238. data/vendor/behave/features/steps/behave_context_steps.py +67 -0
  239. data/vendor/behave/features/steps/behave_model_tag_logic_steps.py +105 -0
  240. data/vendor/behave/features/steps/behave_model_util.py +105 -0
  241. data/vendor/behave/features/steps/behave_select_files_steps.py +83 -0
  242. data/vendor/behave/features/steps/behave_tag_expression_steps.py +166 -0
  243. data/vendor/behave/features/steps/behave_undefined_steps.py +101 -0
  244. data/vendor/behave/features/steps/use_steplib_behave4cmd.py +12 -0
  245. data/vendor/behave/features/summary.undefined_steps.feature +114 -0
  246. data/vendor/behave/features/tags.active_tags.feature +385 -0
  247. data/vendor/behave/features/tags.default_tags.feature +104 -0
  248. data/vendor/behave/features/tags.tag_expression.feature +105 -0
  249. data/vendor/behave/features/userdata.feature +331 -0
  250. data/vendor/behave/invoke.yaml +21 -0
  251. data/vendor/behave/issue.features/README.txt +17 -0
  252. data/vendor/behave/issue.features/environment.py +97 -0
  253. data/vendor/behave/issue.features/issue0030.feature +21 -0
  254. data/vendor/behave/issue.features/issue0031.feature +16 -0
  255. data/vendor/behave/issue.features/issue0032.feature +28 -0
  256. data/vendor/behave/issue.features/issue0035.feature +74 -0
  257. data/vendor/behave/issue.features/issue0040.feature +154 -0
  258. data/vendor/behave/issue.features/issue0041.feature +135 -0
  259. data/vendor/behave/issue.features/issue0042.feature +230 -0
  260. data/vendor/behave/issue.features/issue0044.feature +51 -0
  261. data/vendor/behave/issue.features/issue0046.feature +77 -0
  262. data/vendor/behave/issue.features/issue0052.feature +66 -0
  263. data/vendor/behave/issue.features/issue0059.feature +29 -0
  264. data/vendor/behave/issue.features/issue0063.feature +102 -0
  265. data/vendor/behave/issue.features/issue0064.feature +97 -0
  266. data/vendor/behave/issue.features/issue0065.feature +18 -0
  267. data/vendor/behave/issue.features/issue0066.feature +80 -0
  268. data/vendor/behave/issue.features/issue0067.feature +90 -0
  269. data/vendor/behave/issue.features/issue0069.feature +64 -0
  270. data/vendor/behave/issue.features/issue0072.feature +32 -0
  271. data/vendor/behave/issue.features/issue0073.feature +228 -0
  272. data/vendor/behave/issue.features/issue0075.feature +18 -0
  273. data/vendor/behave/issue.features/issue0077.feature +89 -0
  274. data/vendor/behave/issue.features/issue0080.feature +49 -0
  275. data/vendor/behave/issue.features/issue0081.feature +138 -0
  276. data/vendor/behave/issue.features/issue0083.feature +69 -0
  277. data/vendor/behave/issue.features/issue0084.feature +69 -0
  278. data/vendor/behave/issue.features/issue0085.feature +119 -0
  279. data/vendor/behave/issue.features/issue0092.feature +66 -0
  280. data/vendor/behave/issue.features/issue0096.feature +173 -0
  281. data/vendor/behave/issue.features/issue0099.feature +130 -0
  282. data/vendor/behave/issue.features/issue0109.feature +60 -0
  283. data/vendor/behave/issue.features/issue0111.feature +53 -0
  284. data/vendor/behave/issue.features/issue0112.feature +64 -0
  285. data/vendor/behave/issue.features/issue0114.feature +118 -0
  286. data/vendor/behave/issue.features/issue0116.feature +71 -0
  287. data/vendor/behave/issue.features/issue0125.feature +49 -0
  288. data/vendor/behave/issue.features/issue0127.feature +64 -0
  289. data/vendor/behave/issue.features/issue0139.feature +67 -0
  290. data/vendor/behave/issue.features/issue0142.feature +37 -0
  291. data/vendor/behave/issue.features/issue0143.feature +54 -0
  292. data/vendor/behave/issue.features/issue0145.feature +63 -0
  293. data/vendor/behave/issue.features/issue0148.feature +105 -0
  294. data/vendor/behave/issue.features/issue0152.feature +52 -0
  295. data/vendor/behave/issue.features/issue0159.feature +74 -0
  296. data/vendor/behave/issue.features/issue0162.feature +86 -0
  297. data/vendor/behave/issue.features/issue0171.feature +16 -0
  298. data/vendor/behave/issue.features/issue0172.feature +51 -0
  299. data/vendor/behave/issue.features/issue0175.feature +91 -0
  300. data/vendor/behave/issue.features/issue0177.feature +40 -0
  301. data/vendor/behave/issue.features/issue0181.feature +36 -0
  302. data/vendor/behave/issue.features/issue0184.feature +144 -0
  303. data/vendor/behave/issue.features/issue0186.feature +12 -0
  304. data/vendor/behave/issue.features/issue0188.feature +60 -0
  305. data/vendor/behave/issue.features/issue0191.feature +178 -0
  306. data/vendor/behave/issue.features/issue0194.feature +215 -0
  307. data/vendor/behave/issue.features/issue0197.feature +11 -0
  308. data/vendor/behave/issue.features/issue0216.feature +129 -0
  309. data/vendor/behave/issue.features/issue0226.feature +51 -0
  310. data/vendor/behave/issue.features/issue0228.feature +41 -0
  311. data/vendor/behave/issue.features/issue0230.feature +46 -0
  312. data/vendor/behave/issue.features/issue0231.feature +77 -0
  313. data/vendor/behave/issue.features/issue0238.feature +52 -0
  314. data/vendor/behave/issue.features/issue0251.feature +15 -0
  315. data/vendor/behave/issue.features/issue0280.feature +118 -0
  316. data/vendor/behave/issue.features/issue0288.feature +95 -0
  317. data/vendor/behave/issue.features/issue0300.feature +49 -0
  318. data/vendor/behave/issue.features/issue0302.feature +91 -0
  319. data/vendor/behave/issue.features/issue0309.feature +52 -0
  320. data/vendor/behave/issue.features/issue0330.feature +124 -0
  321. data/vendor/behave/issue.features/issue0349.feature +9 -0
  322. data/vendor/behave/issue.features/issue0361.feature +79 -0
  323. data/vendor/behave/issue.features/issue0383.feature +76 -0
  324. data/vendor/behave/issue.features/issue0384.feature +103 -0
  325. data/vendor/behave/issue.features/issue0385.feature +109 -0
  326. data/vendor/behave/issue.features/issue0424.feature +66 -0
  327. data/vendor/behave/issue.features/issue0446.feature +116 -0
  328. data/vendor/behave/issue.features/issue0449.feature +42 -0
  329. data/vendor/behave/issue.features/issue0453.feature +42 -0
  330. data/vendor/behave/issue.features/issue0457.feature +65 -0
  331. data/vendor/behave/issue.features/issue0462.feature +38 -0
  332. data/vendor/behave/issue.features/issue0476.feature +39 -0
  333. data/vendor/behave/issue.features/issue0487.feature +92 -0
  334. data/vendor/behave/issue.features/issue0506.feature +77 -0
  335. data/vendor/behave/issue.features/issue0510.feature +51 -0
  336. data/vendor/behave/issue.features/requirements.txt +12 -0
  337. data/vendor/behave/issue.features/steps/ansi_steps.py +20 -0
  338. data/vendor/behave/issue.features/steps/behave_hooks_steps.py +10 -0
  339. data/vendor/behave/issue.features/steps/use_steplib_behave4cmd.py +13 -0
  340. data/vendor/behave/more.features/formatter.json.validate_output.feature +37 -0
  341. data/vendor/behave/more.features/steps/tutorial_steps.py +16 -0
  342. data/vendor/behave/more.features/steps/use_steplib_behave4cmd.py +7 -0
  343. data/vendor/behave/more.features/tutorial.feature +6 -0
  344. data/vendor/behave/py.requirements/README.txt +5 -0
  345. data/vendor/behave/py.requirements/all.txt +16 -0
  346. data/vendor/behave/py.requirements/basic.txt +21 -0
  347. data/vendor/behave/py.requirements/develop.txt +28 -0
  348. data/vendor/behave/py.requirements/docs.txt +6 -0
  349. data/vendor/behave/py.requirements/json.txt +7 -0
  350. data/vendor/behave/py.requirements/more_py26.txt +8 -0
  351. data/vendor/behave/py.requirements/testing.txt +10 -0
  352. data/vendor/behave/pytest.ini +24 -0
  353. data/vendor/behave/setup.cfg +29 -0
  354. data/vendor/behave/setup.py +118 -0
  355. data/vendor/behave/setuptools_behave.py +130 -0
  356. data/vendor/behave/tasks/__behave.py +45 -0
  357. data/vendor/behave/tasks/__init__.py +55 -0
  358. data/vendor/behave/tasks/__main__.py +70 -0
  359. data/vendor/behave/tasks/_setup.py +135 -0
  360. data/vendor/behave/tasks/_vendor/README.rst +35 -0
  361. data/vendor/behave/tasks/_vendor/invoke.zip +0 -0
  362. data/vendor/behave/tasks/_vendor/path.py +1725 -0
  363. data/vendor/behave/tasks/_vendor/pathlib.py +1280 -0
  364. data/vendor/behave/tasks/_vendor/six.py +868 -0
  365. data/vendor/behave/tasks/clean.py +246 -0
  366. data/vendor/behave/tasks/docs.py +97 -0
  367. data/vendor/behave/tasks/requirements.txt +17 -0
  368. data/vendor/behave/tasks/test.py +192 -0
  369. data/vendor/behave/test/__init__.py +0 -0
  370. data/vendor/behave/test/_importer_candidate.py +3 -0
  371. data/vendor/behave/test/reporters/__init__.py +0 -0
  372. data/vendor/behave/test/reporters/test_summary.py +240 -0
  373. data/vendor/behave/test/test_ansi_escapes.py +73 -0
  374. data/vendor/behave/test/test_configuration.py +172 -0
  375. data/vendor/behave/test/test_formatter.py +265 -0
  376. data/vendor/behave/test/test_formatter_progress.py +39 -0
  377. data/vendor/behave/test/test_formatter_rerun.py +97 -0
  378. data/vendor/behave/test/test_formatter_tags.py +57 -0
  379. data/vendor/behave/test/test_importer.py +151 -0
  380. data/vendor/behave/test/test_log_capture.py +29 -0
  381. data/vendor/behave/test/test_matchers.py +236 -0
  382. data/vendor/behave/test/test_model.py +871 -0
  383. data/vendor/behave/test/test_parser.py +1590 -0
  384. data/vendor/behave/test/test_runner.py +1074 -0
  385. data/vendor/behave/test/test_step_registry.py +96 -0
  386. data/vendor/behave/test/test_tag_expression.py +506 -0
  387. data/vendor/behave/test/test_tag_expression2.py +462 -0
  388. data/vendor/behave/test/test_tag_matcher.py +729 -0
  389. data/vendor/behave/test/test_userdata.py +184 -0
  390. data/vendor/behave/tests/README.txt +12 -0
  391. data/vendor/behave/tests/__init__.py +0 -0
  392. data/vendor/behave/tests/api/__ONLY_PY34_or_newer.txt +0 -0
  393. data/vendor/behave/tests/api/__init__.py +0 -0
  394. data/vendor/behave/tests/api/_test_async_step34.py +130 -0
  395. data/vendor/behave/tests/api/_test_async_step35.py +75 -0
  396. data/vendor/behave/tests/api/test_async_step.py +18 -0
  397. data/vendor/behave/tests/api/testing_support.py +94 -0
  398. data/vendor/behave/tests/api/testing_support_async.py +21 -0
  399. data/vendor/behave/tests/issues/test_issue0336.py +66 -0
  400. data/vendor/behave/tests/issues/test_issue0449.py +55 -0
  401. data/vendor/behave/tests/issues/test_issue0453.py +62 -0
  402. data/vendor/behave/tests/issues/test_issue0458.py +54 -0
  403. data/vendor/behave/tests/issues/test_issue0495.py +65 -0
  404. data/vendor/behave/tests/unit/__init__.py +0 -0
  405. data/vendor/behave/tests/unit/test_behave4cmd_command_shell_proc.py +135 -0
  406. data/vendor/behave/tests/unit/test_capture.py +280 -0
  407. data/vendor/behave/tests/unit/test_model_core.py +56 -0
  408. data/vendor/behave/tests/unit/test_textutil.py +267 -0
  409. data/vendor/behave/tools/test-features/background.feature +9 -0
  410. data/vendor/behave/tools/test-features/environment.py +8 -0
  411. data/vendor/behave/tools/test-features/french.feature +11 -0
  412. data/vendor/behave/tools/test-features/outline.feature +39 -0
  413. data/vendor/behave/tools/test-features/parse.feature +10 -0
  414. data/vendor/behave/tools/test-features/step-data.feature +60 -0
  415. data/vendor/behave/tools/test-features/steps/steps.py +120 -0
  416. data/vendor/behave/tools/test-features/tags.feature +18 -0
  417. data/vendor/behave/tox.ini +159 -0
  418. metadata +562 -0
@@ -0,0 +1,729 @@
1
+ # -*- coding: utf-8 -*-
2
+
3
+ from __future__ import absolute_import
4
+ from behave.tag_matcher import *
5
+ from mock import Mock
6
+ from unittest import TestCase
7
+ import warnings
8
+ # -- REQUIRES: pytest
9
+ # import pytest
10
+
11
+
12
+ class Traits4ActiveTagMatcher(object):
13
+ TagMatcher = ActiveTagMatcher
14
+ value_provider = {
15
+ "foo": "alice",
16
+ "bar": "BOB",
17
+ }
18
+
19
+ category1_enabled_tag = TagMatcher.make_category_tag("foo", "alice")
20
+ category1_disabled_tag = TagMatcher.make_category_tag("foo", "bob")
21
+ category1_disabled_tag2 = TagMatcher.make_category_tag("foo", "charly")
22
+ category1_similar_tag = TagMatcher.make_category_tag("foo", "alice2")
23
+ category2_enabled_tag = TagMatcher.make_category_tag("bar", "BOB")
24
+ category2_disabled_tag = TagMatcher.make_category_tag("bar", "CHARLY")
25
+ category2_similar_tag = TagMatcher.make_category_tag("bar", "BOB2")
26
+ unknown_category_tag = TagMatcher.make_category_tag("UNKNOWN", "one")
27
+
28
+ # -- NEGATED TAGS:
29
+ category1_not_enabled_tag = \
30
+ TagMatcher.make_category_tag("foo", "alice", "not_active")
31
+ category1_not_enabled_tag2 = \
32
+ TagMatcher.make_category_tag("foo", "alice", "not")
33
+ category1_not_disabled_tag = \
34
+ TagMatcher.make_category_tag("foo", "bob", "not_active")
35
+ category1_negated_similar_tag1 = \
36
+ TagMatcher.make_category_tag("foo", "alice2", "not_active")
37
+
38
+
39
+ active_tags1 = [
40
+ category1_enabled_tag, category1_disabled_tag, category1_similar_tag,
41
+ category1_not_enabled_tag, category1_not_enabled_tag2,
42
+ ]
43
+ active_tags2 = [
44
+ category2_enabled_tag, category2_disabled_tag, category2_similar_tag,
45
+ ]
46
+ active_tags = active_tags1 + active_tags2
47
+
48
+ # -- REQUIRES: pytest
49
+ # class TestActiveTagMatcher2(object):
50
+ # TagMatcher = ActiveTagMatcher
51
+ # traits = Traits4ActiveTagMatcher
52
+ #
53
+ # @classmethod
54
+ # def make_tag_matcher(cls):
55
+ # value_provider = {
56
+ # "foo": "alice",
57
+ # "bar": "BOB",
58
+ # }
59
+ # tag_matcher = cls.TagMatcher(value_provider)
60
+ # return tag_matcher
61
+ #
62
+ # @pytest.mark.parametrize("case, expected_len, tags", [
63
+ # ("case: Two enabled tags", 2,
64
+ # [traits.category1_enabled_tag, traits.category2_enabled_tag]),
65
+ # ("case: Active enabled and normal tag", 1,
66
+ # [traits.category1_enabled_tag, "foo"]),
67
+ # ("case: Active disabled and normal tag", 1,
68
+ # [traits.category1_disabled_tag, "foo"]),
69
+ # ("case: Normal and active negated tag", 1,
70
+ # ["foo", traits.category1_not_enabled_tag]),
71
+ # ("case: Two normal tags", 0,
72
+ # ["foo", "bar"]),
73
+ # ])
74
+ # def test_select_active_tags__with_two_tags(self, case, expected_len, tags):
75
+ # tag_matcher = self.make_tag_matcher()
76
+ # selected = tag_matcher.select_active_tags(tags)
77
+ # selected = list(selected)
78
+ # assert len(selected) == expected_len, case
79
+ #
80
+ # @pytest.mark.parametrize("case, expected, tags", [
81
+ # # -- GROUP: With positive logic (non-negated tags)
82
+ # ("case P00: 2 disabled tags", True,
83
+ # [ traits.category1_disabled_tag, traits.category2_disabled_tag]),
84
+ # ("case P01: disabled and enabled tag", True,
85
+ # [ traits.category1_disabled_tag, traits.category2_enabled_tag]),
86
+ # ("case P10: enabled and disabled tag", True,
87
+ # [ traits.category1_enabled_tag, traits.category2_disabled_tag]),
88
+ # ("case P11: 2 enabled tags", False, # -- SHOULD-RUN
89
+ # [ traits.category1_enabled_tag, traits.category2_enabled_tag]),
90
+ # # -- GROUP: With negated tag
91
+ # ("case N00: not-enabled and disabled tag", True,
92
+ # [ traits.category1_not_enabled_tag, traits.category2_disabled_tag]),
93
+ # ("case N01: not-enabled and enabled tag", True,
94
+ # [ traits.category1_not_enabled_tag, traits.category2_enabled_tag]),
95
+ # ("case N10: not-disabled and disabled tag", True,
96
+ # [ traits.category1_not_disabled_tag, traits.category2_disabled_tag]),
97
+ # ("case N11: not-disabled and enabled tag", False, # -- SHOULD-RUN
98
+ # [ traits.category1_not_disabled_tag, traits.category2_enabled_tag]),
99
+ # # -- GROUP: With unknown category
100
+ # ("case U0x: disabled and unknown tag", True,
101
+ # [ traits.category1_disabled_tag, traits.unknown_category_tag]),
102
+ # ("case U1x: enabled and unknown tag", False, # -- SHOULD-RUN
103
+ # [ traits.category1_enabled_tag, traits.unknown_category_tag]),
104
+ # ])
105
+ # def test_should_exclude_with__combinations_of_2_categories(self, case, expected, tags):
106
+ # tag_matcher = self.make_tag_matcher()
107
+ # actual_result = tag_matcher.should_exclude_with(tags)
108
+ # assert expected == actual_result, case
109
+ #
110
+ # @pytest.mark.parametrize("case, expected, tags", [
111
+ # # -- GROUP: With positive logic (non-negated tags)
112
+ # ("case P00: 2 disabled tags", True,
113
+ # [ traits.category1_disabled_tag, traits.category1_disabled_tag2]),
114
+ # ("case P01: disabled and enabled tag", True,
115
+ # [ traits.category1_disabled_tag, traits.category1_enabled_tag]),
116
+ # ("case P10: enabled and disabled tag", True,
117
+ # [ traits.category1_enabled_tag, traits.category1_disabled_tag]),
118
+ # ("case P11: 2 enabled tags (same)", False, # -- SHOULD-RUN
119
+ # [ traits.category1_enabled_tag, traits.category1_enabled_tag]),
120
+ # # -- GROUP: With negated tag
121
+ # ("case N00: not-enabled and disabled tag", True,
122
+ # [ traits.category1_not_enabled_tag, traits.category1_disabled_tag]),
123
+ # ("case N01: not-enabled and enabled tag", True,
124
+ # [ traits.category1_not_enabled_tag, traits.category1_enabled_tag]),
125
+ # ("case N10: not-disabled and disabled tag", True,
126
+ # [ traits.category1_not_disabled_tag, traits.category1_disabled_tag]),
127
+ # ("case N11: not-disabled and enabled tag", False, # -- SHOULD-RUN
128
+ # [ traits.category1_not_disabled_tag, traits.category1_enabled_tag]),
129
+ # ])
130
+ # def test_should_exclude_with__combinations_with_same_category(self,
131
+ # case, expected, tags):
132
+ # tag_matcher = self.make_tag_matcher()
133
+ # actual_result = tag_matcher.should_exclude_with(tags)
134
+ # assert expected == actual_result, case
135
+
136
+
137
+ class TestActiveTagMatcher1(TestCase):
138
+ TagMatcher = ActiveTagMatcher
139
+ traits = Traits4ActiveTagMatcher
140
+
141
+ @classmethod
142
+ def make_tag_matcher(cls):
143
+ tag_matcher = cls.TagMatcher(cls.traits.value_provider)
144
+ return tag_matcher
145
+
146
+ def setUp(self):
147
+ self.tag_matcher = self.make_tag_matcher()
148
+
149
+ def test_select_active_tags__basics(self):
150
+ active_tag = "active.with_CATEGORY=VALUE"
151
+ tags = ["foo", active_tag, "bar"]
152
+ selected = list(self.tag_matcher.select_active_tags(tags))
153
+ self.assertEqual(len(selected), 1)
154
+ selected_tag, selected_match = selected[0]
155
+ self.assertEqual(selected_tag, active_tag)
156
+
157
+ def test_select_active_tags__matches_tag_parts(self):
158
+ tags = ["active.with_CATEGORY=VALUE"]
159
+ selected = list(self.tag_matcher.select_active_tags(tags))
160
+ self.assertEqual(len(selected), 1)
161
+ selected_tag, selected_match = selected[0]
162
+ self.assertEqual(selected_match.group("prefix"), "active")
163
+ self.assertEqual(selected_match.group("category"), "CATEGORY")
164
+ self.assertEqual(selected_match.group("value"), "VALUE")
165
+
166
+ def test_select_active_tags__finds_tag_with_any_valid_tag_prefix(self):
167
+ TagMatcher = self.TagMatcher
168
+ for tag_prefix in TagMatcher.tag_prefixes:
169
+ tag = TagMatcher.make_category_tag("foo", "alice", tag_prefix)
170
+ tags = [ tag ]
171
+ selected = self.tag_matcher.select_active_tags(tags)
172
+ selected = list(selected)
173
+ self.assertEqual(len(selected), 1)
174
+ selected_tag0 = selected[0][0]
175
+ self.assertEqual(selected_tag0, tag)
176
+ self.assertTrue(selected_tag0.startswith(tag_prefix))
177
+
178
+ def test_select_active_tags__ignores_invalid_active_tags(self):
179
+ invalid_active_tags = [
180
+ ("foo.alice", "case: Normal tag"),
181
+ ("with_foo=alice", "case: Subset of an active tag"),
182
+ ("ACTIVE.with_foo.alice", "case: Wrong tag_prefix (uppercase)"),
183
+ ("only.with_foo.alice", "case: Wrong value_separator"),
184
+ ]
185
+ for invalid_tag, case in invalid_active_tags:
186
+ tags = [ invalid_tag ]
187
+ selected = self.tag_matcher.select_active_tags(tags)
188
+ selected = list(selected)
189
+ self.assertEqual(len(selected), 0, case)
190
+
191
+ def test_select_active_tags__with_two_tags(self):
192
+ # XXX-JE-DUPLICATED:
193
+ traits = self.traits
194
+ test_patterns = [
195
+ ("case: Two enabled tags",
196
+ [traits.category1_enabled_tag, traits.category2_enabled_tag]),
197
+ ("case: Active enabled and normal tag",
198
+ [traits.category1_enabled_tag, "foo"]),
199
+ ("case: Active disabled and normal tag",
200
+ [traits.category1_disabled_tag, "foo"]),
201
+ ("case: Active negated and normal tag",
202
+ [traits.category1_not_enabled_tag, "foo"]),
203
+ ]
204
+ for case, tags in test_patterns:
205
+ selected = self.tag_matcher.select_active_tags(tags)
206
+ selected = list(selected)
207
+ self.assertTrue(len(selected) >= 1, case)
208
+
209
+
210
+ def test_should_exclude_with__returns_false_with_enabled_tag(self):
211
+ traits = self.traits
212
+ tags1 = [ traits.category1_enabled_tag ]
213
+ tags2 = [ traits.category2_enabled_tag ]
214
+ self.assertEqual(False, self.tag_matcher.should_exclude_with(tags1))
215
+ self.assertEqual(False, self.tag_matcher.should_exclude_with(tags2))
216
+
217
+ def test_should_exclude_with__returns_false_with_disabled_tag_and_more(self):
218
+ # -- NOTE: Need 1+ enabled active-tags of same category => ENABLED
219
+ traits = self.traits
220
+ test_patterns = [
221
+ ([ traits.category1_enabled_tag, traits.category1_disabled_tag ], "case: first"),
222
+ ([ traits.category1_disabled_tag, traits.category1_enabled_tag ], "case: last"),
223
+ ([ "foo", traits.category1_enabled_tag, traits.category1_disabled_tag, "bar" ], "case: middle"),
224
+ ]
225
+ enabled = True # EXPECTED
226
+ for tags, case in test_patterns:
227
+ self.assertEqual(not enabled, self.tag_matcher.should_exclude_with(tags),
228
+ "%s: tags=%s" % (case, tags))
229
+
230
+ def test_should_exclude_with__returns_true_with_other_tag(self):
231
+ traits = self.traits
232
+ tags = [ traits.category1_disabled_tag ]
233
+ self.assertEqual(True, self.tag_matcher.should_exclude_with(tags))
234
+
235
+ def test_should_exclude_with__returns_true_with_other_tag_and_more(self):
236
+ traits = self.traits
237
+ test_patterns = [
238
+ ([ traits.category1_disabled_tag, "foo" ], "case: first"),
239
+ ([ "foo", traits.category1_disabled_tag ], "case: last"),
240
+ ([ "foo", traits.category1_disabled_tag, "bar" ], "case: middle"),
241
+ ]
242
+ for tags, case in test_patterns:
243
+ self.assertEqual(True, self.tag_matcher.should_exclude_with(tags),
244
+ "%s: tags=%s" % (case, tags))
245
+
246
+ def test_should_exclude_with__returns_true_with_similar_tag(self):
247
+ traits = self.traits
248
+ tags = [ traits.category1_similar_tag ]
249
+ self.assertEqual(True, self.tag_matcher.should_exclude_with(tags))
250
+
251
+ def test_should_exclude_with__returns_true_with_similar_and_more(self):
252
+ traits = self.traits
253
+ test_patterns = [
254
+ ([ traits.category1_similar_tag, "foo" ], "case: first"),
255
+ ([ "foo", traits.category1_similar_tag ], "case: last"),
256
+ ([ "foo", traits.category1_similar_tag, "bar" ], "case: middle"),
257
+ ]
258
+ for tags, case in test_patterns:
259
+ self.assertEqual(True, self.tag_matcher.should_exclude_with(tags),
260
+ "%s: tags=%s" % (case, tags))
261
+
262
+ def test_should_exclude_with__returns_false_without_category_tag(self):
263
+ test_patterns = [
264
+ ([ ], "case: No tags"),
265
+ ([ "foo" ], "case: One tag"),
266
+ ([ "foo", "bar" ], "case: Two tags"),
267
+ ]
268
+ for tags, case in test_patterns:
269
+ self.assertEqual(False, self.tag_matcher.should_exclude_with(tags),
270
+ "%s: tags=%s" % (case, tags))
271
+
272
+ def test_should_exclude_with__returns_false_with_unknown_category_tag(self):
273
+ """Tags from unknown categories, not supported by value_provider,
274
+ should not be excluded.
275
+ """
276
+ traits = self.traits
277
+ tags = [ traits.unknown_category_tag ]
278
+ self.assertEqual("active.with_UNKNOWN=one", traits.unknown_category_tag)
279
+ self.assertEqual(None, self.tag_matcher.value_provider.get("UNKNOWN"))
280
+ self.assertEqual(False, self.tag_matcher.should_exclude_with(tags))
281
+
282
+ def test_should_exclude_with__combinations_of_2_categories(self):
283
+ # XXX-JE-DUPLICATED:
284
+ traits = self.traits
285
+ test_patterns = [
286
+ ("case P00: 2 disabled category tags", True,
287
+ [ traits.category1_disabled_tag, traits.category2_disabled_tag]),
288
+ ("case P01: disabled and enabled category tags", True,
289
+ [ traits.category1_disabled_tag, traits.category2_enabled_tag]),
290
+ ("case P10: enabled and disabled category tags", True,
291
+ [ traits.category1_enabled_tag, traits.category2_disabled_tag]),
292
+ ("case P11: 2 enabled category tags", False, # -- SHOULD-RUN
293
+ [ traits.category1_enabled_tag, traits.category2_enabled_tag]),
294
+ # -- SPECIAL CASE: With negated category
295
+ ("case N00: not-enabled and disabled category tags", True,
296
+ [ traits.category1_not_enabled_tag, traits.category2_disabled_tag]),
297
+ ("case N01: not-enabled and enabled category tags", True,
298
+ [ traits.category1_not_enabled_tag, traits.category2_enabled_tag]),
299
+ ("case N10: not-disabled and disabled category tags", True,
300
+ [ traits.category1_not_disabled_tag, traits.category2_disabled_tag]),
301
+ ("case N11: not-enabled and enabled category tags", False, # -- SHOULD-RUN
302
+ [ traits.category1_not_disabled_tag, traits.category2_enabled_tag]),
303
+ # -- SPECIAL CASE: With unknown category
304
+ ("case 0x: disabled and unknown category tags", True,
305
+ [ traits.category1_disabled_tag, traits.unknown_category_tag]),
306
+ ("case 1x: enabled and unknown category tags", False, # SHOULD-RUN
307
+ [ traits.category1_enabled_tag, traits.unknown_category_tag]),
308
+ ]
309
+ for case, expected, tags in test_patterns:
310
+ actual_result = self.tag_matcher.should_exclude_with(tags)
311
+ self.assertEqual(expected, actual_result,
312
+ "%s: tags=%s" % (case, tags))
313
+
314
+ def test_should_run_with__negates_result_of_should_exclude_with(self):
315
+ traits = self.traits
316
+ test_patterns = [
317
+ ([ ], "case: No tags"),
318
+ ([ "foo" ], "case: One non-category tag"),
319
+ ([ "foo", "bar" ], "case: Two non-category tags"),
320
+ ([ traits.category1_enabled_tag ], "case: enabled tag"),
321
+ ([ traits.category1_enabled_tag, traits.category1_disabled_tag ], "case: enabled and other tag"),
322
+ ([ traits.category1_enabled_tag, "foo" ], "case: enabled and foo tag"),
323
+ ([ traits.category1_disabled_tag ], "case: other tag"),
324
+ ([ traits.category1_disabled_tag, "foo" ], "case: other and foo tag"),
325
+ ([ traits.category1_similar_tag ], "case: similar tag"),
326
+ ([ "foo", traits.category1_similar_tag ], "case: foo and similar tag"),
327
+ ]
328
+ for tags, case in test_patterns:
329
+ result1 = self.tag_matcher.should_run_with(tags)
330
+ result2 = self.tag_matcher.should_exclude_with(tags)
331
+ self.assertEqual(result1, not result2, "%s: tags=%s" % (case, tags))
332
+ self.assertEqual(not result1, result2, "%s: tags=%s" % (case, tags))
333
+
334
+ class TestPredicateTagMatcher(TestCase):
335
+
336
+ def test_exclude_with__mechanics(self):
337
+ predicate_function_blueprint = lambda tags: False
338
+ predicate_function = Mock(predicate_function_blueprint)
339
+ predicate_function.return_value = True
340
+ tag_matcher = PredicateTagMatcher(predicate_function)
341
+ tags = [ "foo", "bar" ]
342
+ self.assertEqual(True, tag_matcher.should_exclude_with(tags))
343
+ predicate_function.assert_called_once_with(tags)
344
+ self.assertEqual(True, predicate_function(tags))
345
+
346
+ def test_should_exclude_with__returns_true_when_predicate_is_true(self):
347
+ predicate_always_true = lambda tags: True
348
+ tag_matcher1 = PredicateTagMatcher(predicate_always_true)
349
+ tags = [ "foo", "bar" ]
350
+ self.assertEqual(True, tag_matcher1.should_exclude_with(tags))
351
+ self.assertEqual(True, predicate_always_true(tags))
352
+
353
+ def test_should_exclude_with__returns_true_when_predicate_is_true2(self):
354
+ # -- CASE: Use predicate function instead of lambda.
355
+ def predicate_contains_foo(tags):
356
+ return any(x == "foo" for x in tags)
357
+ tag_matcher2 = PredicateTagMatcher(predicate_contains_foo)
358
+ tags = [ "foo", "bar" ]
359
+ self.assertEqual(True, tag_matcher2.should_exclude_with(tags))
360
+ self.assertEqual(True, predicate_contains_foo(tags))
361
+
362
+ def test_should_exclude_with__returns_false_when_predicate_is_false(self):
363
+ predicate_always_false = lambda tags: False
364
+ tag_matcher1 = PredicateTagMatcher(predicate_always_false)
365
+ tags = [ "foo", "bar" ]
366
+ self.assertEqual(False, tag_matcher1.should_exclude_with(tags))
367
+ self.assertEqual(False, predicate_always_false(tags))
368
+
369
+ class TestPredicateTagMatcher(TestCase):
370
+
371
+ def test_exclude_with__mechanics(self):
372
+ predicate_function_blueprint = lambda tags: False
373
+ predicate_function = Mock(predicate_function_blueprint)
374
+ predicate_function.return_value = True
375
+ tag_matcher = PredicateTagMatcher(predicate_function)
376
+ tags = [ "foo", "bar" ]
377
+ self.assertEqual(True, tag_matcher.should_exclude_with(tags))
378
+ predicate_function.assert_called_once_with(tags)
379
+ self.assertEqual(True, predicate_function(tags))
380
+
381
+ def test_should_exclude_with__returns_true_when_predicate_is_true(self):
382
+ predicate_always_true = lambda tags: True
383
+ tag_matcher1 = PredicateTagMatcher(predicate_always_true)
384
+ tags = [ "foo", "bar" ]
385
+ self.assertEqual(True, tag_matcher1.should_exclude_with(tags))
386
+ self.assertEqual(True, predicate_always_true(tags))
387
+
388
+ def test_should_exclude_with__returns_true_when_predicate_is_true2(self):
389
+ # -- CASE: Use predicate function instead of lambda.
390
+ def predicate_contains_foo(tags):
391
+ return any(x == "foo" for x in tags)
392
+ tag_matcher2 = PredicateTagMatcher(predicate_contains_foo)
393
+ tags = [ "foo", "bar" ]
394
+ self.assertEqual(True, tag_matcher2.should_exclude_with(tags))
395
+ self.assertEqual(True, predicate_contains_foo(tags))
396
+
397
+ def test_should_exclude_with__returns_false_when_predicate_is_false(self):
398
+ predicate_always_false = lambda tags: False
399
+ tag_matcher1 = PredicateTagMatcher(predicate_always_false)
400
+ tags = [ "foo", "bar" ]
401
+ self.assertEqual(False, tag_matcher1.should_exclude_with(tags))
402
+ self.assertEqual(False, predicate_always_false(tags))
403
+
404
+
405
+ class TestCompositeTagMatcher(TestCase):
406
+
407
+ @staticmethod
408
+ def count_tag_matcher_with_result(tag_matchers, tags, result_value):
409
+ count = 0
410
+ for tag_matcher in tag_matchers:
411
+ current_result = tag_matcher.should_exclude_with(tags)
412
+ if current_result == result_value:
413
+ count += 1
414
+ return count
415
+
416
+ def setUp(self):
417
+ predicate_false = lambda tags: False
418
+ predicate_contains_foo = lambda tags: any(x == "foo" for x in tags)
419
+ self.tag_matcher_false = PredicateTagMatcher(predicate_false)
420
+ self.tag_matcher_foo = PredicateTagMatcher(predicate_contains_foo)
421
+ tag_matchers = [
422
+ self.tag_matcher_foo,
423
+ self.tag_matcher_false
424
+ ]
425
+ self.ctag_matcher = CompositeTagMatcher(tag_matchers)
426
+
427
+ def test_should_exclude_with__returns_true_when_any_tag_matcher_returns_true(self):
428
+ test_patterns = [
429
+ ("case: with foo", ["foo", "bar"]),
430
+ ("case: with foo2", ["foozy", "foo", "bar"]),
431
+ ]
432
+ for case, tags in test_patterns:
433
+ actual_result = self.ctag_matcher.should_exclude_with(tags)
434
+ self.assertEqual(True, actual_result,
435
+ "%s: tags=%s" % (case, tags))
436
+
437
+ actual_true_count = self.count_tag_matcher_with_result(
438
+ self.ctag_matcher.tag_matchers, tags, True)
439
+ self.assertEqual(1, actual_true_count)
440
+
441
+ def test_should_exclude_with__returns_false_when_no_tag_matcher_return_true(self):
442
+ test_patterns = [
443
+ ("case: without foo", ["fool", "bar"]),
444
+ ("case: without foo2", ["foozy", "bar"]),
445
+ ]
446
+ for case, tags in test_patterns:
447
+ actual_result = self.ctag_matcher.should_exclude_with(tags)
448
+ self.assertEqual(False, actual_result,
449
+ "%s: tags=%s" % (case, tags))
450
+
451
+ actual_true_count = self.count_tag_matcher_with_result(
452
+ self.ctag_matcher.tag_matchers, tags, True)
453
+ self.assertEqual(0, actual_true_count)
454
+
455
+
456
+ # -----------------------------------------------------------------------------
457
+ # PROTOTYPING CLASSES (deprecating)
458
+ # -----------------------------------------------------------------------------
459
+ class TestOnlyWithCategoryTagMatcher(TestCase):
460
+ TagMatcher = OnlyWithCategoryTagMatcher
461
+
462
+ def setUp(self):
463
+ category = "xxx"
464
+ with warnings.catch_warnings():
465
+ warnings.simplefilter("ignore", DeprecationWarning)
466
+ self.tag_matcher = OnlyWithCategoryTagMatcher(category, "alice")
467
+ self.enabled_tag = self.TagMatcher.make_category_tag(category, "alice")
468
+ self.similar_tag = self.TagMatcher.make_category_tag(category, "alice2")
469
+ self.other_tag = self.TagMatcher.make_category_tag(category, "other")
470
+ self.category = category
471
+
472
+ def test_should_exclude_with__returns_false_with_enabled_tag(self):
473
+ tags = [ self.enabled_tag ]
474
+ self.assertEqual(False, self.tag_matcher.should_exclude_with(tags))
475
+
476
+ def test_should_exclude_with__returns_false_with_enabled_tag_and_more(self):
477
+ test_patterns = [
478
+ ([ self.enabled_tag, self.other_tag ], "case: first"),
479
+ ([ self.other_tag, self.enabled_tag ], "case: last"),
480
+ ([ "foo", self.enabled_tag, self.other_tag, "bar" ], "case: middle"),
481
+ ]
482
+ for tags, case in test_patterns:
483
+ self.assertEqual(False, self.tag_matcher.should_exclude_with(tags),
484
+ "%s: tags=%s" % (case, tags))
485
+
486
+ def test_should_exclude_with__returns_true_with_other_tag(self):
487
+ tags = [ self.other_tag ]
488
+ self.assertEqual(True, self.tag_matcher.should_exclude_with(tags))
489
+
490
+ def test_should_exclude_with__returns_true_with_other_tag_and_more(self):
491
+ test_patterns = [
492
+ ([ self.other_tag, "foo" ], "case: first"),
493
+ ([ "foo", self.other_tag ], "case: last"),
494
+ ([ "foo", self.other_tag, "bar" ], "case: middle"),
495
+ ]
496
+ for tags, case in test_patterns:
497
+ self.assertEqual(True, self.tag_matcher.should_exclude_with(tags),
498
+ "%s: tags=%s" % (case, tags))
499
+
500
+ def test_should_exclude_with__returns_true_with_similar_tag(self):
501
+ tags = [ self.similar_tag ]
502
+ self.assertEqual(True, self.tag_matcher.should_exclude_with(tags))
503
+
504
+ def test_should_exclude_with__returns_true_with_similar_and_more(self):
505
+ test_patterns = [
506
+ ([ self.similar_tag, "foo" ], "case: first"),
507
+ ([ "foo", self.similar_tag ], "case: last"),
508
+ ([ "foo", self.similar_tag, "bar" ], "case: middle"),
509
+ ]
510
+ for tags, case in test_patterns:
511
+ self.assertEqual(True, self.tag_matcher.should_exclude_with(tags),
512
+ "%s: tags=%s" % (case, tags))
513
+
514
+ def test_should_exclude_with__returns_false_without_category_tag(self):
515
+ test_patterns = [
516
+ ([ ], "case: No tags"),
517
+ ([ "foo" ], "case: One tag"),
518
+ ([ "foo", "bar" ], "case: Two tags"),
519
+ ]
520
+ for tags, case in test_patterns:
521
+ self.assertEqual(False, self.tag_matcher.should_exclude_with(tags),
522
+ "%s: tags=%s" % (case, tags))
523
+
524
+ def test_should_run_with__negates_result_of_should_exclude_with(self):
525
+ test_patterns = [
526
+ ([ ], "case: No tags"),
527
+ ([ "foo" ], "case: One non-category tag"),
528
+ ([ "foo", "bar" ], "case: Two non-category tags"),
529
+ ([ self.enabled_tag ], "case: enabled tag"),
530
+ ([ self.enabled_tag, self.other_tag ], "case: enabled and other tag"),
531
+ ([ self.enabled_tag, "foo" ], "case: enabled and foo tag"),
532
+ ([ self.other_tag ], "case: other tag"),
533
+ ([ self.other_tag, "foo" ], "case: other and foo tag"),
534
+ ([ self.similar_tag ], "case: similar tag"),
535
+ ([ "foo", self.similar_tag ], "case: foo and similar tag"),
536
+ ]
537
+ for tags, case in test_patterns:
538
+ result1 = self.tag_matcher.should_run_with(tags)
539
+ result2 = self.tag_matcher.should_exclude_with(tags)
540
+ self.assertEqual(result1, not result2, "%s: tags=%s" % (case, tags))
541
+ self.assertEqual(not result1, result2, "%s: tags=%s" % (case, tags))
542
+
543
+ def test_make_category_tag__returns_category_tag_prefix_without_value(self):
544
+ category = "xxx"
545
+ tag1 = OnlyWithCategoryTagMatcher.make_category_tag(category)
546
+ tag2 = OnlyWithCategoryTagMatcher.make_category_tag(category, None)
547
+ tag3 = OnlyWithCategoryTagMatcher.make_category_tag(category, value=None)
548
+ self.assertEqual("only.with_xxx=", tag1)
549
+ self.assertEqual("only.with_xxx=", tag2)
550
+ self.assertEqual("only.with_xxx=", tag3)
551
+ self.assertTrue(tag1.startswith(OnlyWithCategoryTagMatcher.tag_prefix))
552
+
553
+ def test_make_category_tag__returns_category_tag_with_value(self):
554
+ category = "xxx"
555
+ tag1 = OnlyWithCategoryTagMatcher.make_category_tag(category, "alice")
556
+ tag2 = OnlyWithCategoryTagMatcher.make_category_tag(category, "bob")
557
+ self.assertEqual("only.with_xxx=alice", tag1)
558
+ self.assertEqual("only.with_xxx=bob", tag2)
559
+
560
+ def test_make_category_tag__returns_category_tag_with_tag_prefix(self):
561
+ my_tag_prefix = "ONLY_WITH."
562
+ category = "xxx"
563
+ TagMatcher = OnlyWithCategoryTagMatcher
564
+ tag0 = TagMatcher.make_category_tag(category, tag_prefix=my_tag_prefix)
565
+ tag1 = TagMatcher.make_category_tag(category, "alice", my_tag_prefix)
566
+ tag2 = TagMatcher.make_category_tag(category, "bob", tag_prefix=my_tag_prefix)
567
+ self.assertEqual("ONLY_WITH.xxx=", tag0)
568
+ self.assertEqual("ONLY_WITH.xxx=alice", tag1)
569
+ self.assertEqual("ONLY_WITH.xxx=bob", tag2)
570
+ self.assertTrue(tag1.startswith(my_tag_prefix))
571
+
572
+ def test_ctor__with_tag_prefix(self):
573
+ tag_prefix = "ONLY_WITH."
574
+ tag_matcher = OnlyWithCategoryTagMatcher("xxx", "alice", tag_prefix)
575
+
576
+ tags = ["foo", "ONLY_WITH.xxx=foo", "only.with_xxx=bar", "bar"]
577
+ actual_tags = tag_matcher.select_category_tags(tags)
578
+ self.assertEqual(["ONLY_WITH.xxx=foo"], actual_tags)
579
+
580
+
581
+ class Traits4OnlyWithAnyCategoryTagMatcher(object):
582
+ """Test data for OnlyWithAnyCategoryTagMatcher."""
583
+
584
+ TagMatcher0 = OnlyWithCategoryTagMatcher
585
+ TagMatcher = OnlyWithAnyCategoryTagMatcher
586
+ category1_enabled_tag = TagMatcher0.make_category_tag("foo", "alice")
587
+ category1_similar_tag = TagMatcher0.make_category_tag("foo", "alice2")
588
+ category1_disabled_tag = TagMatcher0.make_category_tag("foo", "bob")
589
+ category2_enabled_tag = TagMatcher0.make_category_tag("bar", "BOB")
590
+ category2_similar_tag = TagMatcher0.make_category_tag("bar", "BOB2")
591
+ category2_disabled_tag = TagMatcher0.make_category_tag("bar", "CHARLY")
592
+ unknown_category_tag = TagMatcher0.make_category_tag("UNKNOWN", "one")
593
+
594
+
595
+ class TestOnlyWithAnyCategoryTagMatcher(TestCase):
596
+ TagMatcher = OnlyWithAnyCategoryTagMatcher
597
+ traits = Traits4OnlyWithAnyCategoryTagMatcher
598
+
599
+ def setUp(self):
600
+ value_provider = {
601
+ "foo": "alice",
602
+ "bar": "BOB",
603
+ }
604
+ with warnings.catch_warnings():
605
+ warnings.simplefilter("ignore", DeprecationWarning)
606
+ self.tag_matcher = self.TagMatcher(value_provider)
607
+
608
+ # def test_deprecating_warning_is_issued(self):
609
+ # value_provider = {"foo": "alice"}
610
+ # with warnings.catch_warnings(record=True) as recorder:
611
+ # warnings.simplefilter("always", DeprecationWarning)
612
+ # tag_matcher = OnlyWithAnyCategoryTagMatcher(value_provider)
613
+ # self.assertEqual(len(recorder), 1)
614
+ # last_warning = recorder[-1]
615
+ # assert issubclass(last_warning.category, DeprecationWarning)
616
+ # assert "deprecated" in str(last_warning.message)
617
+
618
+ def test_should_exclude_with__returns_false_with_enabled_tag(self):
619
+ traits = self.traits
620
+ tags1 = [ traits.category1_enabled_tag ]
621
+ tags2 = [ traits.category2_enabled_tag ]
622
+ self.assertEqual(False, self.tag_matcher.should_exclude_with(tags1))
623
+ self.assertEqual(False, self.tag_matcher.should_exclude_with(tags2))
624
+
625
+ def test_should_exclude_with__returns_false_with_enabled_tag_and_more(self):
626
+ traits = self.traits
627
+ test_patterns = [
628
+ ([ traits.category1_enabled_tag, traits.category1_disabled_tag ], "case: first"),
629
+ ([ traits.category1_disabled_tag, traits.category1_enabled_tag ], "case: last"),
630
+ ([ "foo", traits.category1_enabled_tag, traits.category1_disabled_tag, "bar" ], "case: middle"),
631
+ ]
632
+ for tags, case in test_patterns:
633
+ self.assertEqual(False, self.tag_matcher.should_exclude_with(tags),
634
+ "%s: tags=%s" % (case, tags))
635
+
636
+ def test_should_exclude_with__returns_true_with_other_tag(self):
637
+ traits = self.traits
638
+ tags = [ traits.category1_disabled_tag ]
639
+ self.assertEqual(True, self.tag_matcher.should_exclude_with(tags))
640
+
641
+ def test_should_exclude_with__returns_true_with_other_tag_and_more(self):
642
+ traits = self.traits
643
+ test_patterns = [
644
+ ([ traits.category1_disabled_tag, "foo" ], "case: first"),
645
+ ([ "foo", traits.category1_disabled_tag ], "case: last"),
646
+ ([ "foo", traits.category1_disabled_tag, "bar" ], "case: middle"),
647
+ ]
648
+ for tags, case in test_patterns:
649
+ self.assertEqual(True, self.tag_matcher.should_exclude_with(tags),
650
+ "%s: tags=%s" % (case, tags))
651
+
652
+ def test_should_exclude_with__returns_true_with_similar_tag(self):
653
+ traits = self.traits
654
+ tags = [ traits.category1_similar_tag ]
655
+ self.assertEqual(True, self.tag_matcher.should_exclude_with(tags))
656
+
657
+ def test_should_exclude_with__returns_true_with_similar_and_more(self):
658
+ traits = self.traits
659
+ test_patterns = [
660
+ ([ traits.category1_similar_tag, "foo" ], "case: first"),
661
+ ([ "foo", traits.category1_similar_tag ], "case: last"),
662
+ ([ "foo", traits.category1_similar_tag, "bar" ], "case: middle"),
663
+ ]
664
+ for tags, case in test_patterns:
665
+ self.assertEqual(True, self.tag_matcher.should_exclude_with(tags),
666
+ "%s: tags=%s" % (case, tags))
667
+
668
+ def test_should_exclude_with__returns_false_without_category_tag(self):
669
+ test_patterns = [
670
+ ([ ], "case: No tags"),
671
+ ([ "foo" ], "case: One tag"),
672
+ ([ "foo", "bar" ], "case: Two tags"),
673
+ ]
674
+ for tags, case in test_patterns:
675
+ self.assertEqual(False, self.tag_matcher.should_exclude_with(tags),
676
+ "%s: tags=%s" % (case, tags))
677
+
678
+ def test_should_exclude_with__returns_false_with_unknown_category_tag(self):
679
+ """Tags from unknown categories, not supported by value_provider,
680
+ should not be excluded.
681
+ """
682
+ traits = self.traits
683
+ tags = [ traits.unknown_category_tag ]
684
+ self.assertEqual("only.with_UNKNOWN=one", traits.unknown_category_tag)
685
+ self.assertEqual(None, self.tag_matcher.value_provider.get("UNKNOWN"))
686
+ self.assertEqual(False, self.tag_matcher.should_exclude_with(tags))
687
+
688
+ def test_should_exclude_with__combinations_of_2_categories(self):
689
+ traits = self.traits
690
+ test_patterns = [
691
+ ("case 00: 2 disabled category tags", True,
692
+ [ traits.category1_disabled_tag, traits.category2_disabled_tag]),
693
+ ("case 01: disabled and enabled category tags", True,
694
+ [ traits.category1_disabled_tag, traits.category2_enabled_tag]),
695
+ ("case 10: enabled and disabled category tags", True,
696
+ [ traits.category1_enabled_tag, traits.category2_disabled_tag]),
697
+ ("case 11: 2 enabled category tags", False, # -- SHOULD-RUN
698
+ [ traits.category1_enabled_tag, traits.category2_enabled_tag]),
699
+ # -- SPECIAL CASE: With unknown category
700
+ ("case 0x: disabled and unknown category tags", True,
701
+ [ traits.category1_disabled_tag, traits.unknown_category_tag]),
702
+ ("case 1x: enabled and unknown category tags", False, # SHOULD-RUN
703
+ [ traits.category1_enabled_tag, traits.unknown_category_tag]),
704
+ ]
705
+ for case, expected, tags in test_patterns:
706
+ actual_result = self.tag_matcher.should_exclude_with(tags)
707
+ self.assertEqual(expected, actual_result,
708
+ "%s: tags=%s" % (case, tags))
709
+
710
+ def test_should_run_with__negates_result_of_should_exclude_with(self):
711
+ traits = self.traits
712
+ test_patterns = [
713
+ ([ ], "case: No tags"),
714
+ ([ "foo" ], "case: One non-category tag"),
715
+ ([ "foo", "bar" ], "case: Two non-category tags"),
716
+ ([ traits.category1_enabled_tag ], "case: enabled tag"),
717
+ ([ traits.category1_enabled_tag, traits.category1_disabled_tag ], "case: enabled and other tag"),
718
+ ([ traits.category1_enabled_tag, "foo" ], "case: enabled and foo tag"),
719
+ ([ traits.category1_disabled_tag ], "case: other tag"),
720
+ ([ traits.category1_disabled_tag, "foo" ], "case: other and foo tag"),
721
+ ([ traits.category1_similar_tag ], "case: similar tag"),
722
+ ([ "foo", traits.category1_similar_tag ], "case: foo and similar tag"),
723
+ ]
724
+ for tags, case in test_patterns:
725
+ result1 = self.tag_matcher.should_run_with(tags)
726
+ result2 = self.tag_matcher.should_exclude_with(tags)
727
+ self.assertEqual(result1, not result2, "%s: tags=%s" % (case, tags))
728
+ self.assertEqual(not result1, result2, "%s: tags=%s" % (case, tags))
729
+