docks_app 0.0.1

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 (313) hide show
  1. data/.editorconfig +8 -0
  2. data/.gitignore +22 -0
  3. data/.rubocop.yml +20 -0
  4. data/.travis.yml +10 -0
  5. data/Gemfile +4 -0
  6. data/LICENSE.txt +22 -0
  7. data/README.md +35 -0
  8. data/Rakefile +3 -0
  9. data/bin/docks +5 -0
  10. data/config/json/docks_config.json +71 -0
  11. data/config/ruby/docks_config.rb +127 -0
  12. data/config/yaml/docks_config.yml +70 -0
  13. data/docks.gemspec +38 -0
  14. data/lib/docks/build.rb +300 -0
  15. data/lib/docks/cache.rb +143 -0
  16. data/lib/docks/command_line.rb +65 -0
  17. data/lib/docks/configuration.rb +217 -0
  18. data/lib/docks/containers/base_container.rb +103 -0
  19. data/lib/docks/containers/class_container.rb +39 -0
  20. data/lib/docks/containers/component_container.rb +92 -0
  21. data/lib/docks/containers/demo_container.rb +105 -0
  22. data/lib/docks/containers/factory_container.rb +12 -0
  23. data/lib/docks/containers/function_container.rb +46 -0
  24. data/lib/docks/containers/mixin_container.rb +19 -0
  25. data/lib/docks/containers/pattern_container.rb +168 -0
  26. data/lib/docks/containers/pattern_library_container.rb +77 -0
  27. data/lib/docks/containers/state_container.rb +9 -0
  28. data/lib/docks/containers/symbol_container.rb +77 -0
  29. data/lib/docks/containers/variable_container.rb +47 -0
  30. data/lib/docks/containers/variant_container.rb +9 -0
  31. data/lib/docks/containers/variation_container.rb +38 -0
  32. data/lib/docks/containers.rb +25 -0
  33. data/lib/docks/descriptor.rb +60 -0
  34. data/lib/docks/errors.rb +5 -0
  35. data/lib/docks/group.rb +66 -0
  36. data/lib/docks/helpers/github_helper.rb +29 -0
  37. data/lib/docks/helpers/path_helper.rb +94 -0
  38. data/lib/docks/helpers/render_helper.rb +87 -0
  39. data/lib/docks/helpers.rb +19 -0
  40. data/lib/docks/languages/base_language.rb +17 -0
  41. data/lib/docks/languages/coffeescript_language.rb +30 -0
  42. data/lib/docks/languages/common_types/markup_language.rb +71 -0
  43. data/lib/docks/languages/css_language.rb +13 -0
  44. data/lib/docks/languages/erb_language.rb +21 -0
  45. data/lib/docks/languages/haml_language.rb +21 -0
  46. data/lib/docks/languages/html_language.rb +10 -0
  47. data/lib/docks/languages/javascript_language.rb +42 -0
  48. data/lib/docks/languages/json_language.rb +18 -0
  49. data/lib/docks/languages/less_language.rb +33 -0
  50. data/lib/docks/languages/markdown_language.rb +10 -0
  51. data/lib/docks/languages/sass_language.rb +36 -0
  52. data/lib/docks/languages/slim_language.rb +21 -0
  53. data/lib/docks/languages/stylus_language.rb +26 -0
  54. data/lib/docks/languages/yaml_language.rb +18 -0
  55. data/lib/docks/languages.rb +103 -0
  56. data/lib/docks/markdown.rb +18 -0
  57. data/lib/docks/messenger.rb +69 -0
  58. data/lib/docks/naming_conventions/base_naming_convention.rb +9 -0
  59. data/lib/docks/naming_conventions/bem_naming_convention.rb +45 -0
  60. data/lib/docks/naming_conventions/suit_naming_convention.rb +45 -0
  61. data/lib/docks/naming_conventions.rb +21 -0
  62. data/lib/docks/ostruct.rb +17 -0
  63. data/lib/docks/parser.rb +86 -0
  64. data/lib/docks/parsers/base_parser.rb +128 -0
  65. data/lib/docks/parsers/coffeescript_parser.rb +30 -0
  66. data/lib/docks/parsers/css_parser.rb +27 -0
  67. data/lib/docks/parsers/javascript_parser.rb +30 -0
  68. data/lib/docks/parsers/less_parser.rb +22 -0
  69. data/lib/docks/parsers/sass_parser.rb +31 -0
  70. data/lib/docks/parsers/stylus_parser.rb +28 -0
  71. data/lib/docks/process.rb +60 -0
  72. data/lib/docks/processors.rb +416 -0
  73. data/lib/docks/renderers/base_renderer.rb +64 -0
  74. data/lib/docks/renderers/common_features/capturable.rb +69 -0
  75. data/lib/docks/renderers/common_features/helperable.rb +23 -0
  76. data/lib/docks/renderers/erb_renderer.rb +68 -0
  77. data/lib/docks/renderers/haml_renderer.rb +37 -0
  78. data/lib/docks/renderers/slim_renderer.rb +33 -0
  79. data/lib/docks/symbol_sources/base_symbol_source.rb +12 -0
  80. data/lib/docks/symbol_sources/jquery_symbol_source.rb +17 -0
  81. data/lib/docks/symbol_sources/mdn_symbol_source.rb +35 -0
  82. data/lib/docks/symbol_sources/sass_symbol_source.rb +27 -0
  83. data/lib/docks/symbol_sources.rb +28 -0
  84. data/lib/docks/tags/access_tag.rb +27 -0
  85. data/lib/docks/tags/activate_with_tag.rb +17 -0
  86. data/lib/docks/tags/active_tag.rb +14 -0
  87. data/lib/docks/tags/alias_tag.rb +17 -0
  88. data/lib/docks/tags/author_tag.rb +19 -0
  89. data/lib/docks/tags/base_tag.rb +52 -0
  90. data/lib/docks/tags/beta_tag.rb +26 -0
  91. data/lib/docks/tags/class_tag.rb +16 -0
  92. data/lib/docks/tags/compatibility_tag.rb +19 -0
  93. data/lib/docks/tags/demo_type_tag.rb +14 -0
  94. data/lib/docks/tags/deprecated_tag.rb +26 -0
  95. data/lib/docks/tags/description_tag.rb +99 -0
  96. data/lib/docks/tags/example_tag.rb +20 -0
  97. data/lib/docks/tags/factory_tag.rb +16 -0
  98. data/lib/docks/tags/for_tag.rb +23 -0
  99. data/lib/docks/tags/group_tag.rb +10 -0
  100. data/lib/docks/tags/helper_tag.rb +13 -0
  101. data/lib/docks/tags/include_with_tag.rb +57 -0
  102. data/lib/docks/tags/javascript_action_tag.rb +10 -0
  103. data/lib/docks/tags/link_tag.rb +18 -0
  104. data/lib/docks/tags/markup_tag.rb +106 -0
  105. data/lib/docks/tags/member_tag.rb +37 -0
  106. data/lib/docks/tags/method_tag.rb +18 -0
  107. data/lib/docks/tags/name_tag.rb +10 -0
  108. data/lib/docks/tags/object_tag.rb +15 -0
  109. data/lib/docks/tags/param_tag.rb +94 -0
  110. data/lib/docks/tags/pattern_tag.rb +21 -0
  111. data/lib/docks/tags/preclude_tag.rb +17 -0
  112. data/lib/docks/tags/private_tag.rb +15 -0
  113. data/lib/docks/tags/property_tag.rb +18 -0
  114. data/lib/docks/tags/public_tag.rb +15 -0
  115. data/lib/docks/tags/require_tag.rb +47 -0
  116. data/lib/docks/tags/returns_tag.rb +31 -0
  117. data/lib/docks/tags/set_by_tag.rb +18 -0
  118. data/lib/docks/tags/signature_tag.rb +35 -0
  119. data/lib/docks/tags/since_tag.rb +26 -0
  120. data/lib/docks/tags/source_tag.rb +12 -0
  121. data/lib/docks/tags/state_tag.rb +21 -0
  122. data/lib/docks/tags/static_tag.rb +14 -0
  123. data/lib/docks/tags/subcomponent_tag.rb +68 -0
  124. data/lib/docks/tags/subtitle_tag.rb +11 -0
  125. data/lib/docks/tags/symbol_type_tag.rb +10 -0
  126. data/lib/docks/tags/throws_tag.rb +30 -0
  127. data/lib/docks/tags/title_tag.rb +10 -0
  128. data/lib/docks/tags/type_tag.rb +10 -0
  129. data/lib/docks/tags/value_tag.rb +10 -0
  130. data/lib/docks/tags/variant_tag.rb +21 -0
  131. data/lib/docks/tags/variation_tag.rb +136 -0
  132. data/lib/docks/tags.rb +103 -0
  133. data/lib/docks/templates.rb +122 -0
  134. data/lib/docks/themes.rb +19 -0
  135. data/lib/docks/types.rb +26 -0
  136. data/lib/docks/version.rb +3 -0
  137. data/lib/docks.rb +37 -0
  138. data/spec/fixtures/build/scripts/bar/bar_2.js +1 -0
  139. data/spec/fixtures/build/scripts/bar.js +1 -0
  140. data/spec/fixtures/build/styles/foo/foo-2.css +1 -0
  141. data/spec/fixtures/build/styles/foo.css +1 -0
  142. data/spec/fixtures/build/templates/baz/baz_2.erb +1 -0
  143. data/spec/fixtures/build/templates/baz.erb +1 -0
  144. data/spec/fixtures/grouper/components/button/button.coffee +0 -0
  145. data/spec/fixtures/grouper/components/button/button.haml +0 -0
  146. data/spec/fixtures/grouper/components/button/button.scss +0 -0
  147. data/spec/fixtures/grouper/components/checkbox/_checkbox.haml +0 -0
  148. data/spec/fixtures/grouper/components/checkbox/_checkbox.scss +0 -0
  149. data/spec/fixtures/grouper/components/checkbox/checkbox.coffee +0 -0
  150. data/spec/fixtures/grouper/components/form/form.coffee +0 -0
  151. data/spec/fixtures/grouper/components/form/form.m +0 -0
  152. data/spec/fixtures/grouper/components/form/form.scss +0 -0
  153. data/spec/fixtures/grouper/components/next-expanding-textarea/_next-expanding-textarea.scss +0 -0
  154. data/spec/fixtures/grouper/components/next-expanding-textarea/_next_expanding_textarea.coffee +0 -0
  155. data/spec/fixtures/grouper/components/next-expanding-textarea/next-expanding-textarea.haml +0 -0
  156. data/spec/fixtures/grouper/components/next-tab/next-tab.coffee +0 -0
  157. data/spec/fixtures/grouper/components/next-tab/next-tab.haml +0 -0
  158. data/spec/fixtures/grouper/components/next-tab/next-tab.scss +0 -0
  159. data/spec/fixtures/grouper/components/segmented control/segmented control.coffee +0 -0
  160. data/spec/fixtures/grouper/components/segmented control/segmented control.haml +0 -0
  161. data/spec/fixtures/grouper/components/segmented control/segmented control.min.html +0 -0
  162. data/spec/fixtures/grouper/components/segmented control/segmented control.scss +0 -0
  163. data/spec/fixtures/grouper/markup/list-view.haml +0 -0
  164. data/spec/fixtures/grouper/markup/resizable/resizable.haml +0 -0
  165. data/spec/fixtures/grouper/markup/toggle.haml +0 -0
  166. data/spec/fixtures/grouper/scripts/resizable/resizable.coffee +0 -0
  167. data/spec/fixtures/grouper/scripts/toggle.coffee +0 -0
  168. data/spec/fixtures/grouper/style/_list-view.scss +0 -0
  169. data/spec/fixtures/grouper/style/_toggle.scss +0 -0
  170. data/spec/fixtures/languages/stub.json +3 -0
  171. data/spec/fixtures/languages/stub.yml +2 -0
  172. data/spec/fixtures/parsers/coffeescript_parser_fixture_basic.coffee +20 -0
  173. data/spec/fixtures/parsers/coffeescript_parser_fixture_complex.coffee +80 -0
  174. data/spec/fixtures/parsers/css_parser_fixture_basic.css +44 -0
  175. data/spec/fixtures/parsers/css_parser_fixture_complex.css +120 -0
  176. data/spec/fixtures/parsers/javascript_parser_fixture_basic.js +27 -0
  177. data/spec/fixtures/parsers/javascript_parser_fixture_complex.js +85 -0
  178. data/spec/fixtures/parsers/sass_parser_fixture_basic.scss +39 -0
  179. data/spec/fixtures/parsers/sass_parser_fixture_complex.scss +149 -0
  180. data/spec/fixtures/parsers/stylus_parser_fixture_basic.styl +34 -0
  181. data/spec/fixtures/parsers/stylus_parser_fixture_complex.styl +113 -0
  182. data/spec/fixtures/processors/join_with_smart_line_breaks/code_blocks.txt +10 -0
  183. data/spec/fixtures/processors/join_with_smart_line_breaks/headings.txt +15 -0
  184. data/spec/fixtures/processors/join_with_smart_line_breaks/lists.txt +21 -0
  185. data/spec/fixtures/processors/join_with_smart_line_breaks/lists_with_nesting.txt +13 -0
  186. data/spec/fixtures/processors/join_with_smart_line_breaks/multiple_paragraphs.txt +11 -0
  187. data/spec/fixtures/renderers/helpers.rb +37 -0
  188. data/spec/fixtures/renderers/html_output.html +7 -0
  189. data/spec/fixtures/renderers/templates/layouts/application.html.erb +0 -0
  190. data/spec/fixtures/renderers/templates/layouts/more/subdirectory.html.erb +0 -0
  191. data/spec/fixtures/renderers/templates/partials/_leading_underscore.html.erb +1 -0
  192. data/spec/fixtures/renderers/templates/partials/more/_subdirectory.html.erb +1 -0
  193. data/spec/fixtures/renderers/templates/partials/partial.html.erb +0 -0
  194. data/spec/fixtures/renderers/templates/partials/template.html.erb +1 -0
  195. data/spec/fixtures/renderers/templates/template.html.erb +1 -0
  196. data/spec/fixtures/tags/description/button.md +24 -0
  197. data/spec/fixtures/tags/description/class.md +27 -0
  198. data/spec/fixtures/tags/description/component.md +23 -0
  199. data/spec/fixtures/tags/description/function.md +30 -0
  200. data/spec/lib/build_spec.rb +467 -0
  201. data/spec/lib/cache_spec.rb +175 -0
  202. data/spec/lib/command_line_spec.rb +77 -0
  203. data/spec/lib/configuration_spec.rb +180 -0
  204. data/spec/lib/containers/base_container_spec.rb +214 -0
  205. data/spec/lib/containers/class_container_spec.rb +209 -0
  206. data/spec/lib/containers/component_container_spec.rb +158 -0
  207. data/spec/lib/containers/demo_container_spec.rb +113 -0
  208. data/spec/lib/containers/function_container_spec.rb +116 -0
  209. data/spec/lib/containers/mixin_container_spec.rb +4 -0
  210. data/spec/lib/containers/pattern_container_spec.rb +291 -0
  211. data/spec/lib/containers/pattern_library_container_spec.rb +130 -0
  212. data/spec/lib/containers/symbol_container_spec.rb +216 -0
  213. data/spec/lib/containers/variable_container_spec.rb +116 -0
  214. data/spec/lib/containers/variation_container_spec.rb +52 -0
  215. data/spec/lib/containers_spec.rb +22 -0
  216. data/spec/lib/descriptor_spec.rb +73 -0
  217. data/spec/lib/group_spec.rb +151 -0
  218. data/spec/lib/helpers/path_helper_spec.rb +202 -0
  219. data/spec/lib/helpers/render_helper_spec.rb +159 -0
  220. data/spec/lib/helpers_spec.rb +35 -0
  221. data/spec/lib/languages/base_language_spec.rb +32 -0
  222. data/spec/lib/languages/coffeescript_language_spec.rb +52 -0
  223. data/spec/lib/languages/css_language_spec.rb +13 -0
  224. data/spec/lib/languages/erb_language_spec.rb +33 -0
  225. data/spec/lib/languages/haml_language_spec.rb +32 -0
  226. data/spec/lib/languages/javascript_language_spec.rb +54 -0
  227. data/spec/lib/languages/json_language_spec.rb +24 -0
  228. data/spec/lib/languages/less_language_spec.rb +39 -0
  229. data/spec/lib/languages/markup_language_spec.rb +95 -0
  230. data/spec/lib/languages/sass_language_spec.rb +53 -0
  231. data/spec/lib/languages/slim_language_spec.rb +32 -0
  232. data/spec/lib/languages/stylus_language_spec.rb +34 -0
  233. data/spec/lib/languages/yaml_language_spec.rb +24 -0
  234. data/spec/lib/languages_spec.rb +127 -0
  235. data/spec/lib/markdown_spec.rb +63 -0
  236. data/spec/lib/messenger_spec.rb +1 -0
  237. data/spec/lib/naming_conventions/bem_naming_convention_spec.rb +112 -0
  238. data/spec/lib/naming_conventions/suit_naming_convention_spec.rb +107 -0
  239. data/spec/lib/naming_conventions_spec.rb +28 -0
  240. data/spec/lib/ostruct_spec.rb +15 -0
  241. data/spec/lib/parser_spec.rb +93 -0
  242. data/spec/lib/parsers/base_parser_spec.rb +128 -0
  243. data/spec/lib/parsers/coffeescript_parser_spec.rb +184 -0
  244. data/spec/lib/parsers/css_parser_spec.rb +136 -0
  245. data/spec/lib/parsers/javascript_parser_spec.rb +216 -0
  246. data/spec/lib/parsers/less_parser_spec.rb +111 -0
  247. data/spec/lib/parsers/sass_parser_spec.rb +233 -0
  248. data/spec/lib/parsers/stylus_parser_spec.rb +212 -0
  249. data/spec/lib/process_spec.rb +96 -0
  250. data/spec/lib/processors_spec.rb +555 -0
  251. data/spec/lib/renderers/base_renderer_spec.rb +122 -0
  252. data/spec/lib/renderers/common_features/helperable_spec.rb +30 -0
  253. data/spec/lib/renderers/erb_renderer_spec.rb +119 -0
  254. data/spec/lib/renderers/haml_renderer_spec.rb +103 -0
  255. data/spec/lib/renderers/slim_renderer_spec.rb +103 -0
  256. data/spec/lib/symbol_sources/jquery_symbol_source_spec.rb +25 -0
  257. data/spec/lib/symbol_sources/mdn_symbol_source_spec.rb +40 -0
  258. data/spec/lib/symbol_sources/sass_symbol_source_spec.rb +39 -0
  259. data/spec/lib/symbol_sources_spec.rb +19 -0
  260. data/spec/lib/tags/access_tag_spec.rb +32 -0
  261. data/spec/lib/tags/activate_with_tag_spec.rb +31 -0
  262. data/spec/lib/tags/active_tag_spec.rb +24 -0
  263. data/spec/lib/tags/alias_tag_spec.rb +31 -0
  264. data/spec/lib/tags/author_tag_spec.rb +172 -0
  265. data/spec/lib/tags/base_tag_spec.rb +21 -0
  266. data/spec/lib/tags/beta_tag_spec.rb +52 -0
  267. data/spec/lib/tags/class_tag_spec.rb +29 -0
  268. data/spec/lib/tags/compatibility_tag_spec.rb +159 -0
  269. data/spec/lib/tags/demo_type_tag_spec.rb +24 -0
  270. data/spec/lib/tags/deprecated_tag_spec.rb +50 -0
  271. data/spec/lib/tags/description_tag_spec.rb +242 -0
  272. data/spec/lib/tags/example_tag_spec.rb +37 -0
  273. data/spec/lib/tags/factory_tag_spec.rb +29 -0
  274. data/spec/lib/tags/for_tag_spec.rb +45 -0
  275. data/spec/lib/tags/group_tag_spec.rb +20 -0
  276. data/spec/lib/tags/helper_tag_spec.rb +22 -0
  277. data/spec/lib/tags/include_with_tag_spec.rb +74 -0
  278. data/spec/lib/tags/javascript_action_tag_spec.rb +20 -0
  279. data/spec/lib/tags/link_tag_spec.rb +49 -0
  280. data/spec/lib/tags/markup_tag_spec.rb +255 -0
  281. data/spec/lib/tags/member_tag_spec.rb +167 -0
  282. data/spec/lib/tags/method_tag_spec.rb +27 -0
  283. data/spec/lib/tags/name_tag_spec.rb +20 -0
  284. data/spec/lib/tags/object_tag_spec.rb +24 -0
  285. data/spec/lib/tags/param_tag_spec.rb +261 -0
  286. data/spec/lib/tags/pattern_tag_spec.rb +49 -0
  287. data/spec/lib/tags/preclude_tag_spec.rb +31 -0
  288. data/spec/lib/tags/private_tag_spec.rb +31 -0
  289. data/spec/lib/tags/property_tag_spec.rb +27 -0
  290. data/spec/lib/tags/public_tag_spec.rb +29 -0
  291. data/spec/lib/tags/require_tag_spec.rb +133 -0
  292. data/spec/lib/tags/returns_tag_spec.rb +85 -0
  293. data/spec/lib/tags/set_by_tag_spec.rb +92 -0
  294. data/spec/lib/tags/signature_tag_spec.rb +125 -0
  295. data/spec/lib/tags/since_tag_spec.rb +48 -0
  296. data/spec/lib/tags/state_tag_spec.rb +199 -0
  297. data/spec/lib/tags/static_tag_spec.rb +27 -0
  298. data/spec/lib/tags/subcomponent_tag_spec.rb +78 -0
  299. data/spec/lib/tags/subtitle_tag_spec.rb +13 -0
  300. data/spec/lib/tags/symbol_type_tag_spec.rb +20 -0
  301. data/spec/lib/tags/throws_tag_spec.rb +49 -0
  302. data/spec/lib/tags/title_tag_spec.rb +20 -0
  303. data/spec/lib/tags/type_tag_spec.rb +20 -0
  304. data/spec/lib/tags/value_tag_spec.rb +20 -0
  305. data/spec/lib/tags/variant_tag_spec.rb +13 -0
  306. data/spec/lib/tags/variation_tag_spec.rb +154 -0
  307. data/spec/lib/tags_spec.rb +264 -0
  308. data/spec/lib/templates_spec.rb +185 -0
  309. data/spec/lib/themes_spec.rb +32 -0
  310. data/spec/spec_helper.rb +34 -0
  311. data/tasks/rspec.rake +7 -0
  312. data/tasks/rubocop.rake +8 -0
  313. metadata +740 -0
@@ -0,0 +1,555 @@
1
+ require "spec_helper"
2
+
3
+ describe Docks::Processors do
4
+ subject { described_class }
5
+
6
+ before :each do
7
+ Docks::Languages.register_bundled_languages
8
+ end
9
+
10
+ describe ".split_on_characters" do
11
+ it "returns the original argument if a non-String was passed" do
12
+ content = { foo: :bar }
13
+ expect(subject.split_on_characters(content)).to eq content
14
+ end
15
+
16
+ it "returns the original content if a non-Array and non-String was passed as the `split_on` argument" do
17
+ content = "String content"
18
+ split_on = { but: "non-string split_on" }
19
+
20
+ expect(subject.split_on_characters(content, split_on)).to eq content
21
+ end
22
+
23
+ it "splits on a single character" do
24
+ target_array = %w(one two three)
25
+ expect(subject.split_on_characters("one,two,three", ",")).to eq target_array
26
+ end
27
+
28
+ it "splits on multiple characters" do
29
+ target_array = %w(one two three)
30
+ expect(subject.split_on_characters("one,two|three", ",|")).to eq target_array
31
+ end
32
+
33
+ it "splits on an array of characters" do
34
+ target_array = %w(one two three)
35
+ expect(subject.split_on_characters("one,two|three", [",", "|"])).to eq target_array
36
+ end
37
+
38
+ it "removes empty strings where they would otherwise be included" do
39
+ target_array = %w(one two three)
40
+ expect(subject.split_on_characters("one,,two,three", ",")).to eq target_array
41
+ end
42
+ end
43
+
44
+ describe ".split_on_commas_spaces_and_pipes" do
45
+ it "returns the original argument if a non-String and non-Array was passed" do
46
+ content = { foo: :bar }
47
+ expect(subject.split_on_commas_spaces_and_pipes(content)).to eq content
48
+ end
49
+
50
+ it "splits breaks apart commas" do
51
+ target_array = %w(Array String)
52
+
53
+ expect(subject.split_on_commas_spaces_and_pipes("Array, String")).to eq target_array
54
+ expect(subject.split_on_commas_spaces_and_pipes("Array ,String")).to eq target_array
55
+ expect(subject.split_on_commas_spaces_and_pipes("Array , String")).to eq target_array
56
+ expect(subject.split_on_commas_spaces_and_pipes("Array ,, String")).to eq target_array
57
+ end
58
+
59
+ it "splits breaks apart pipes" do
60
+ target_array = %w(Array String)
61
+
62
+ expect(subject.split_on_commas_spaces_and_pipes("Array| String")).to eq target_array
63
+ expect(subject.split_on_commas_spaces_and_pipes("Array |String")).to eq target_array
64
+ expect(subject.split_on_commas_spaces_and_pipes("Array | String")).to eq target_array
65
+ expect(subject.split_on_commas_spaces_and_pipes("Array || String")).to eq target_array
66
+ end
67
+
68
+ it "splits on internal spaces" do
69
+ target_array = ["Item", "1", "Item", "2"]
70
+
71
+ expect(subject.split_on_commas_spaces_and_pipes(" Item 1 , Item 2 ")).to eq target_array
72
+ end
73
+
74
+ it "joins together results of a passed array" do
75
+ target_array = %w(Array Object String Hash)
76
+ expect(subject.split_on_commas_spaces_and_pipes("Array, Object String | Hash")).to eq target_array
77
+ end
78
+ end
79
+
80
+ describe ".split_on_top_level_parens_commas_and_pipes" do
81
+ it "returns the original result as an array if it contained no parentheses" do
82
+ content = "foo bar"
83
+ expect(subject.split_on_top_level_parens_commas_and_pipes(content)).to eq [content]
84
+ end
85
+
86
+ it "does not split on unmatched opening parentheses" do
87
+ content = "This better not match... :( OR ELSE"
88
+ expect(subject.split_on_top_level_parens_commas_and_pipes(content)).to eq [content]
89
+ end
90
+
91
+ it "does not split on unmatched closing parentheses" do
92
+ content = "We got past the first one :) now to make it past here..."
93
+ expect(subject.split_on_top_level_parens_commas_and_pipes(content)).to eq [content]
94
+ end
95
+
96
+ it "does not split on reversed sets of parentheses" do
97
+ content = "I start happy :) then end sad... :("
98
+ expect(subject.split_on_top_level_parens_commas_and_pipes(content)).to eq [content]
99
+ end
100
+
101
+ it "does not split when there is only one set of parentheses" do
102
+ content = "foo (bar)"
103
+ expect(subject.split_on_top_level_parens_commas_and_pipes(content)).to eq [content]
104
+ end
105
+
106
+ it "does not split when there is a nested set of parentheses" do
107
+ content = "foo (bar (baz))"
108
+ expect(subject.split_on_top_level_parens_commas_and_pipes(content)).to eq [content]
109
+ end
110
+
111
+ it "creates a result for each set of top-level parentheses" do
112
+ content = "here's (one), and here's (two), AND HERE'S (THREE)"
113
+ expect(subject.split_on_top_level_parens_commas_and_pipes(content).length).to be 3
114
+ end
115
+
116
+ it "does not create additional results for nested parentheses" do
117
+ content = "here's (one), and here's (t(w)o), AND HERE'S (TH(R)EE)"
118
+ expect(subject.split_on_top_level_parens_commas_and_pipes(content).length).to be 3
119
+ end
120
+
121
+ it "strips spaces, pipes, and commas between the closing paren and the next character" do
122
+ content = "here's (one), and here's (t(w)o) AND HERE'S (TH(R)EE) | oh and (four)"
123
+ expect(subject.split_on_top_level_parens_commas_and_pipes(content)).to eq ["here's (one)", "and here's (t(w)o)", "AND HERE'S (TH(R)EE)", "oh and (four)"]
124
+ end
125
+
126
+ it "strips multiple commas/ pipes" do
127
+ content = "here's (one) ,, and here's (t(w)o) AND HERE'S (TH(R)EE) |||| oh and (four)"
128
+ expect(subject.split_on_top_level_parens_commas_and_pipes(content)).to eq ["here's (one)", "and here's (t(w)o)", "AND HERE'S (TH(R)EE)", "oh and (four)"]
129
+ end
130
+
131
+ it "splits even when the parentheses are directly beside each other" do
132
+ content = "(one)(two)(three)"
133
+ expect(subject.split_on_top_level_parens_commas_and_pipes(content)).to eq ["(one)", "(two)", "(three)"]
134
+ end
135
+
136
+ it "splits out the last segment even when it has no parentheses" do
137
+ content = "foo (bar), baz"
138
+ expect(subject.split_on_top_level_parens_commas_and_pipes(content)).to eq ["foo (bar)", "baz"]
139
+ end
140
+
141
+ it "does not split on a comma inside of parentheses" do
142
+ content = "foo (bar, baz)"
143
+ expect(subject.split_on_top_level_parens_commas_and_pipes(content)).to eq [content]
144
+ end
145
+
146
+ it "does not split on a pipe inside of parentheses" do
147
+ content = "foo (bar || baz)"
148
+ expect(subject.split_on_top_level_parens_commas_and_pipes(content)).to eq [content]
149
+ end
150
+
151
+ it "creates a result for each set of top-level commas" do
152
+ content = "one, two ,,three , four"
153
+ expect(subject.split_on_top_level_parens_commas_and_pipes(content)).to eq %w(one two three four)
154
+ end
155
+
156
+ it "creates a result for each set of top-level pipes" do
157
+ content = "one| two |three | four"
158
+ expect(subject.split_on_top_level_parens_commas_and_pipes(content)).to eq %w(one two three four)
159
+ end
160
+
161
+ it "creates a result for each set of top-level mixed commas and pipes" do
162
+ content = "one, two |three , four,"
163
+ expect(subject.split_on_top_level_parens_commas_and_pipes(content)).to eq %w(one two three four)
164
+ end
165
+
166
+ it "does not create additional results for nested commas and pipes" do
167
+ content = "one (one,), and here's (t|wo) || AND HERE'S (TH(R|)EE)"
168
+ expect(subject.split_on_top_level_parens_commas_and_pipes(content).length).to be 3
169
+ end
170
+ end
171
+
172
+ describe ".split_types" do
173
+ let(:target_array) { %w(Array String).map { |type| OpenStruct.new(name: type, array: false) } }
174
+
175
+ it "breaks apart commas" do
176
+ expect(subject.split_types("{Array, String}")).to eq target_array
177
+ expect(subject.split_types("{Array ,String}")).to eq target_array
178
+ expect(subject.split_types("{Array , String}")).to eq target_array
179
+ expect(subject.split_types("{Array ,, ,String}")).to eq target_array
180
+ end
181
+
182
+ it "breaks apart pipes" do
183
+ expect(subject.split_types("{Array| String}")).to eq target_array
184
+ expect(subject.split_types("{Array |String}")).to eq target_array
185
+ expect(subject.split_types("{Array | String}")).to eq target_array
186
+ expect(subject.split_types("{Array || |String}")).to eq target_array
187
+ end
188
+
189
+ it "breaks apart spaces alone" do
190
+ expect(subject.split_types("{Array String}")).to eq target_array
191
+ expect(subject.split_types("{Array String}")).to eq target_array
192
+ end
193
+
194
+ it "identifies arrays" do
195
+ expect(subject.split_types("{String[]}").first).to eq OpenStruct.new(name: "String", array: true)
196
+ end
197
+
198
+ it "converts '*' to 'Anything'" do
199
+ expect(subject.split_types("{*}").first).to eq OpenStruct.new(name: "Anything", array: false)
200
+ end
201
+ end
202
+
203
+ describe ".stringy_boolean" do
204
+ it "defaults to true for an empty string" do
205
+ expect(subject.stringy_boolean("")).to be true
206
+ end
207
+
208
+ it "defaults to false for nil" do
209
+ expect(subject.stringy_boolean("")).to be true
210
+ end
211
+
212
+ it "defaults to true a non-/false/ string" do
213
+ expect(subject.stringy_boolean("Anything!")).to be true
214
+ expect(subject.stringy_boolean("true")).to be true
215
+ expect(subject.stringy_boolean("We are the knights...")).to be true
216
+ end
217
+
218
+ it "defaults to false for a string matching /false/" do
219
+ expect(subject.stringy_boolean("false")).to be false
220
+ expect(subject.stringy_boolean(" false")).to be false
221
+ expect(subject.stringy_boolean("false ")).to be false
222
+ expect(subject.stringy_boolean(" false ")).to be false
223
+ end
224
+ end
225
+
226
+ describe ".join_with_smart_line_breaks" do
227
+ # TODO: ensure that this works:
228
+
229
+ # // @page Font Sizes
230
+ # // @group Helper
231
+ # //
232
+ # // The stylesheet exists as a single place to manage all font sizes. To use
233
+ # // a font size in your stylesheet, follow this procedure:
234
+ # //
235
+ # // 1. Add a well-named entry to the `$FONT-SIZES` map with the value set to
236
+ # // the font size for that element.
237
+ # //
238
+ # // 2. If you wish to include a `font-size` declaration in your stylesheet,
239
+ # // `@include font-size()`, passing it the name of the component to retrieve
240
+ # // the font-size for.
241
+ # //
242
+ # // 3. Retrieving the actual font-size dimension (for example, to be used in a
243
+ # // calculation to determine necessary padding) should be done by passing the
244
+ # // same argument discussed above to the `font-size` *function*.
245
+
246
+ it "returns a non-array argument" do
247
+ non_array = "I'm not an array!"
248
+ expect(subject.join_with_smart_line_breaks(non_array)).to eq non_array
249
+ end
250
+
251
+ it "returns nil for an empty array" do
252
+ expect(subject.join_with_smart_line_breaks([])).to be nil
253
+ end
254
+
255
+ it "returns nil for an array containing only whitespace strings" do
256
+ expect(subject.join_with_smart_line_breaks([" "])).to be nil
257
+ expect(subject.join_with_smart_line_breaks([" ", " "])).to be nil
258
+ end
259
+
260
+ it "identifies paragraphs as any block of text separated by at least one newline" do
261
+ content = subject.join_with_smart_line_breaks(content_for_fixture(:multiple_paragraphs))
262
+ expect(paragraph_count(content)).to eq 4
263
+ end
264
+
265
+ context "when there are lists" do
266
+ let(:content) { subject.join_with_smart_line_breaks(content_for_fixture(:lists)) }
267
+
268
+ it "separates lists by a single newline even when they are directly beside each other" do
269
+ expect(paragraph_count(content)).to eq 9
270
+ end
271
+
272
+ context "when there are nested items" do
273
+ let(:content) { subject.join_with_smart_line_breaks(content_for_fixture(:lists_with_nesting)) }
274
+
275
+ it "puts nested lists directly following one another on their own lines" do
276
+ content.sub!(/```[^`]*```\s*/, "")
277
+ expect(paragraph_count(content)).to eq 6
278
+ end
279
+
280
+ it "preserves indentation nested under lists" do
281
+ expect(content).to match /\n\n\s\sindented paragraph/i
282
+ end
283
+
284
+ it "preserves nested code block indentation" do
285
+ expect(content).to match /\n\n\s\s```/
286
+ end
287
+
288
+ it "preserves nested list indentation" do
289
+ expect(content).to match /\n\n\s\s\* items/i
290
+ end
291
+ end
292
+ end
293
+
294
+ context "when there are headers" do
295
+ let(:content) { subject.join_with_smart_line_breaks(content_for_fixture(:headings)) }
296
+
297
+ it "puts a newline between the header and its underline" do
298
+ expect(content).to match /foo\n===/i
299
+ expect(content).to match /bar\n---/i
300
+ end
301
+
302
+ it "separates paragraphs from immediately preceeding and following contents" do
303
+ content.gsub!(/\n[=\-]+\n/, "")
304
+ expect(paragraph_count(content)).to eq 8
305
+ end
306
+ end
307
+
308
+ context "when there are fenced code blocks" do
309
+ let(:content) do
310
+ subject.join_with_smart_line_breaks(content_for_fixture(:code_blocks))
311
+ end
312
+
313
+ let(:code_block) do
314
+ first_code_fence_index = content.index("```")
315
+ second_code_fence_index = content.index("```", first_code_fence_index + 1) + 2
316
+
317
+ content[first_code_fence_index..second_code_fence_index]
318
+ end
319
+
320
+ it "creates only a single line break between fenced code blocks" do
321
+ expect(code_block.split("\n").length).to eq 5
322
+ end
323
+
324
+ it "creates paragraphs when a code block is followed immediately by a paragraph" do
325
+ content.sub!(code_block, "")
326
+ paragraphs = paragraph_count(content)
327
+ expect(paragraphs).to eq 3
328
+ end
329
+ end
330
+
331
+ private
332
+
333
+ def content_for_fixture(fixture)
334
+ file = File.expand_path("../../fixtures/processors/join_with_smart_line_breaks/#{fixture}.txt", __FILE__)
335
+ File.read(file).split("\n")
336
+ end
337
+
338
+ def paragraph_count(text)
339
+ text.split(/\n+/).length
340
+ end
341
+ end
342
+
343
+ describe ".name_and_parenthetical" do
344
+ let(:basic_content) { ":checked?" }
345
+ let(:basic_result) { subject.name_and_parenthetical(basic_content) }
346
+ let(:complex_name) { "Chris Sauve" }
347
+ let(:complex_details) { "email: chrismsauve@gmail.com" }
348
+ let(:complex_content) { "#{complex_name} (#{complex_details})" }
349
+
350
+ it "sets the :name of the returned hash to the non-parenthetical part of the passed string if no custom name is passed" do
351
+ expect(basic_result[:name]).to eq basic_content
352
+ expect(subject.name_and_parenthetical(complex_content)[:name]).to eq complex_name
353
+ end
354
+
355
+ it "sets the custom name of the returned hash to the passed non-parenthetical string" do
356
+ custom_name = :setter
357
+ processed = subject.name_and_parenthetical(basic_content, custom_name)
358
+ expect(processed[custom_name]).to eq basic_content
359
+ end
360
+
361
+ it "joins the parenthetical results to the name" do
362
+ parenthetical = {
363
+ foo: "bar",
364
+ bar: "baz"
365
+ }
366
+ parenthetical_as_string = ""
367
+ parenthetical.to_a.each do |k, v|
368
+ parenthetical_as_string << "#{k} : #{v}, "
369
+ end
370
+ parenthetical_as_string.sub(/,\s$/, "")
371
+
372
+ parenthetical[:name] = basic_content
373
+
374
+ content = "#{basic_content} (#{parenthetical_as_string})"
375
+ expect(subject.name_and_parenthetical(content)).to eq parenthetical
376
+ end
377
+
378
+ it "passes along the default to the parenthetical" do
379
+ default_key, default_val = :value, "true"
380
+ content = "#{basic_content} (#{default_val})"
381
+ expect(subject.name_and_parenthetical(content, :name, default_key)[default_key]).to eq default_val
382
+ end
383
+ end
384
+
385
+ describe ".parenthetical_options" do
386
+ let(:default) { :foo }
387
+ let(:value) { "bar" }
388
+ let(:simple_result) {
389
+ result = {}
390
+ result[default] = value
391
+ result
392
+ }
393
+
394
+ it "associates a default value when no key-value pairs are found" do
395
+ expect(subject.parenthetical_options(value, default)).to eq simple_result
396
+ end
397
+
398
+ it "creates a non-default key even if it is the only one provided" do
399
+ non_default = :bar
400
+ non_default_value = "baz"
401
+ non_default_result = {}
402
+ non_default_result[non_default] = non_default_value
403
+ expect(subject.parenthetical_options("(#{non_default}: #{non_default_value})", default)).to eq non_default_result
404
+ end
405
+
406
+ it "creates a single key value pair" do
407
+ expect(subject.parenthetical_options("#{default}: #{value}")).to eq simple_result
408
+ expect(subject.parenthetical_options("#{default}: #{value}")).to eq simple_result
409
+ expect(subject.parenthetical_options("#{default} : #{value}")).to eq simple_result
410
+ expect(subject.parenthetical_options("#{default} : #{value}")).to eq simple_result
411
+ end
412
+
413
+ it "creates multiple key value pairs" do
414
+ key_2 = :bar
415
+ val_2 = "baz"
416
+ pair_1 = "#{default}: #{value}"
417
+ pair_2 = "#{key_2}: #{val_2}"
418
+ simple_result[key_2] = val_2
419
+
420
+ expect(subject.parenthetical_options("#{pair_1}, #{pair_2}")).to eq simple_result
421
+ expect(subject.parenthetical_options("#{pair_1}, #{pair_2}")).to eq simple_result
422
+ expect(subject.parenthetical_options("#{pair_1} ,#{pair_2}")).to eq simple_result
423
+ expect(subject.parenthetical_options("#{pair_1} ,#{pair_2}")).to eq simple_result
424
+ expect(subject.parenthetical_options("#{pair_1} , #{pair_2}")).to eq simple_result
425
+ expect(subject.parenthetical_options("#{pair_1} , #{pair_2}")).to eq simple_result
426
+ end
427
+
428
+ describe "multi-word keys" do
429
+ let(:key_string) { "Activate with" }
430
+ let(:key) { key_string.downcase.gsub(/\s+/, "_").to_sym }
431
+ let(:result) {
432
+ result = {}
433
+ result[key] = key_string
434
+ result
435
+ }
436
+
437
+ it "creates key-value pairs by symbolizing spaced keys" do
438
+ expect(subject.parenthetical_options("#{key_string}: #{key_string}")).to eq result
439
+ end
440
+
441
+ it "creates multiple key-value pairs that include multi-word keys" do
442
+ result.merge!(simple_result)
443
+ expect(subject.parenthetical_options("#{default}: #{value} , #{key_string} : #{key_string}")).to eq result
444
+ end
445
+ end
446
+
447
+ it "creates a default key when a non-default key-value pair is also provided" do
448
+ key_2 = :bar
449
+ val_2 = 'baz'
450
+ simple_result[key_2] = val_2
451
+ content = "#{value}, #{key_2}: #{val_2}"
452
+
453
+ expect(subject.parenthetical_options(content, default)).to eq simple_result
454
+ end
455
+ end
456
+
457
+ describe ".ensure_valid_demo_type" do
458
+ it "allows one of the included demo types" do
459
+ Docks::Types::Demo.constants.each do |const|
460
+ demo_type = Docks::Types::Demo.const_get(const)
461
+ expect(subject.ensure_valid_demo_type(demo_type)).to eq demo_type
462
+ end
463
+ end
464
+
465
+ it "returns the default type when none of the included demo types are provided" do
466
+ expect(subject.ensure_valid_demo_type("invalid")).to be Docks::Types::Demo::DEFAULT
467
+ end
468
+ end
469
+
470
+ describe ".multiline_description" do
471
+ let(:complex_content) { ['First content', 'Second content', 'Third content'] }
472
+
473
+ it "ruses the entirety of the original content as the description if the yielded block did not return a Hash" do
474
+ content = ["Hello!"]
475
+ final_content = subject.multiline_description(content) { |content| content }
476
+ expect(final_content).to eq description: content.first
477
+ end
478
+
479
+ it "uses the entirety of the original content as the description if no block was passed" do
480
+ content = ["Hello!"]
481
+ final_content = subject.multiline_description(content)
482
+ expect(final_content).to eq description: content.first
483
+ end
484
+
485
+ it "passes the first item in the array to the passed block" do
486
+ subject.multiline_description(complex_content) do |content|
487
+ expect(content).to eq complex_content.first
488
+ end
489
+ end
490
+
491
+ it "preserves the hash returned by the block in the end result" do
492
+ key = :name
493
+ value = nil
494
+ result = subject.multiline_description(complex_content) do |content|
495
+ intermediate = {}
496
+ intermediate[key] = value = content
497
+ intermediate
498
+ end
499
+
500
+ expect(result[:name]).to eq value
501
+ end
502
+
503
+ it "joins the second thru last items of the passed array as the description" do
504
+ result = subject.multiline_description(complex_content) do |content|
505
+ { foo: content }
506
+ end
507
+
508
+ expect(result[:description]).to eq subject.join_with_smart_line_breaks(["Second content", "Third content"])
509
+ end
510
+
511
+ it "joins the description portion identified in the block to the rest of the description" do
512
+ result = subject.multiline_description(complex_content) do |content|
513
+ content = content.split(" ")
514
+ intermediate = { foo: content[0] }
515
+ intermediate[:description] = content[1]
516
+ intermediate
517
+ end
518
+
519
+ expect(result[:description]).to eq subject.join_with_smart_line_breaks(["content", "Second content", "Third content"])
520
+ end
521
+ end
522
+
523
+ describe ".code_block_with_language_and_description" do
524
+ let(:description) { "The description." }
525
+ let(:language) { "scss" }
526
+ let(:code) { [".foo {", " content: 'bar';", "}"] }
527
+
528
+ it "uses the passed language if one is provided" do
529
+ expect(subject.code_block_with_language_and_description(code.unshift(language))[:language]).to eq language
530
+ end
531
+
532
+ it "has a nil description when only the language is provided" do
533
+ expect(subject.code_block_with_language_and_description(code.unshift(language))[:description]).to be nil
534
+ end
535
+
536
+ it "uses the description and language when provided" do
537
+ result = subject.code_block_with_language_and_description(code.unshift("#{language} - #{description}"))
538
+ expect(result[:description]).to eq description
539
+ expect(result[:language]).to eq language
540
+ end
541
+
542
+ it "assigns the entire passed content to the code attribute when no language is provided" do
543
+ expect(subject.code_block_with_language_and_description(code)[:code]).to eq code.join("\n")
544
+ end
545
+
546
+ it "assigns the second thru last array items to the code attribute when a valid language is provided" do
547
+ expect(subject.code_block_with_language_and_description(code.unshift(language))[:code]).to eq code.join("\n")
548
+ end
549
+
550
+ it "assigns the second thru last array items to the code attribute when a valid language and description is provided" do
551
+ result = subject.code_block_with_language_and_description(code.unshift("#{language} - #{description}"))
552
+ expect(result[:code]).to eq code.join("\n")
553
+ end
554
+ end
555
+ end
@@ -0,0 +1,122 @@
1
+ require "spec_helper"
2
+
3
+ describe Docks::Renderers::Base do
4
+ let(:fixture_dir) { File.expand_path("../../../fixtures/renderers", __FILE__) }
5
+ let(:template_dir) { Docks.config.templates }
6
+ let(:partials_dir) { File.join(template_dir, "partials") }
7
+ let(:layouts_dir) { File.join(template_dir, "layouts") }
8
+
9
+ subject { Docks::Renderers::Base.new }
10
+
11
+ around do |example|
12
+ Docks.configure do |config|
13
+ config.root = fixture_dir
14
+ config.templates = "templates"
15
+ end
16
+
17
+ example.run
18
+
19
+ subject.send(:clean)
20
+ end
21
+
22
+ describe "#normalize_content_and_locals" do
23
+ it "looks for a template if the full path is given" do
24
+ file = File.join(template_dir, "template.html.erb")
25
+ expect(subject.send(:normalize_content_and_locals, file).first).to eq File.read(file)
26
+ end
27
+
28
+ it "looks for a template in the root directory first" do
29
+ expect(subject.send(:normalize_content_and_locals, "template").first).to eq File.read(File.join(template_dir, "template.html.erb"))
30
+ end
31
+
32
+ it "looks for a template in a subdirectory of root" do
33
+ expect(subject.send(:normalize_content_and_locals, "partials/template").first).to eq File.read(File.join(partials_dir, "template.html.erb"))
34
+ end
35
+
36
+ it "looks for a template in the root directory if the template key is used" do
37
+ expect(subject.send(:normalize_content_and_locals, template: "template").first).to eq File.read(File.join(template_dir, "template.html.erb"))
38
+ end
39
+
40
+ it "looks for a template in the partials directory if none exists in the root directory" do
41
+ expect(subject.send(:normalize_content_and_locals, "partial").first).to eq File.read(File.join(partials_dir, "partial.html.erb"))
42
+ end
43
+
44
+ it "looks for a template in the partials directory if the partial key is used" do
45
+ expect(subject.send(:normalize_content_and_locals, partial: "template").first).to eq File.read(File.join(partials_dir, "template.html.erb"))
46
+ end
47
+
48
+ it "renders a template with a leading underscore" do
49
+ expect(subject.send(:normalize_content_and_locals, "leading_underscore").first).to eq File.read(File.join(partials_dir, "_leading_underscore.html.erb"))
50
+ end
51
+
52
+ it "renders a template in a subdirectory of partial" do
53
+ expect(subject.send(:normalize_content_and_locals, partial: "more/subdirectory").first).to eq File.read(File.join(partials_dir, "more/_subdirectory.html.erb"))
54
+ expect(subject.send(:normalize_content_and_locals, "more/subdirectory").first).to eq File.read(File.join(partials_dir, "more/_subdirectory.html.erb"))
55
+ end
56
+
57
+ it "finds a layout file in a layout directory" do
58
+ expect(subject.send(:normalize_content_and_locals, template: "template", layout: "application")[1]).to eq File.read(File.join(layouts_dir, "application.html.erb"))
59
+ end
60
+
61
+ it "finds a layout file in a subdirectory of the layout directory" do
62
+ expect(subject.send(:normalize_content_and_locals, template: "template", layout: "more/subdirectory")[1]).to eq File.read(File.join(layouts_dir, "more/subdirectory.html.erb"))
63
+ end
64
+
65
+ it "returns inline content" do
66
+ inline_content = "<p><%= foo %></p>"
67
+ expect(subject.send(:normalize_content_and_locals, inline: inline_content).first).to eq inline_content
68
+ end
69
+
70
+ it "caches the content of template files" do
71
+ template = "template"
72
+ expect(File).to receive(:read).once.and_call_original
73
+ subject.send(:normalize_content_and_locals, template)
74
+ subject.send(:normalize_content_and_locals, template)
75
+ end
76
+
77
+ it "provides an empty hash as locals when none are provided" do
78
+ expect(subject.send(:normalize_content_and_locals, "template").last).to eq Hash.new
79
+ expect(subject.send(:normalize_content_and_locals, partial: "template").last).to eq Hash.new
80
+ end
81
+
82
+ it "provides the second argument as locals" do
83
+ locals = { foo: "bar" }
84
+ expect(subject.send(:normalize_content_and_locals, "template", locals).last).to eq locals
85
+ end
86
+
87
+ it "provides the locals key of the first argument as locals" do
88
+ locals = { foo: "bar" }
89
+ expect(subject.send(:normalize_content_and_locals, partial: "template", locals: locals).last).to eq locals
90
+ end
91
+
92
+ it "separates the layout and locals from the second argument" do
93
+ locals = { foo: "bar" }
94
+ result = subject.send(:normalize_content_and_locals, "template", layout: "application", locals: locals)
95
+ expect(result[1]).to eq File.read(File.join(layouts_dir, "application.html.erb"))
96
+ expect(result.last).to eq locals
97
+ end
98
+
99
+ it "throws an error when no matching template is found" do
100
+ expect { subject.send(:normalize_content_and_locals, "foo") }.to raise_error(Docks::NoTemplateError)
101
+ end
102
+
103
+ it "throws an error when no matching layout is found" do
104
+ expect { subject.send(:normalize_content_and_locals, template: "template", layout: "foo") }.to raise_error(Docks::NoTemplateError)
105
+ end
106
+
107
+ it "uses no layout when the layout argument is false" do
108
+ expect(subject.send(:normalize_content_and_locals, template: "template", layout: false)[1]).to be nil
109
+ end
110
+ end
111
+
112
+ describe "#ivars=" do
113
+ it "creates an instance variable for each of the passed hash keys" do
114
+ ivars = { foo: "bar", baz: "qux" }
115
+ subject.ivars = ivars
116
+
117
+ ivars.each do |ivar, value|
118
+ expect(subject.instance_variable_get("@#{ivar}".to_sym)).to eq value
119
+ end
120
+ end
121
+ end
122
+ end