card 1.19.6 → 1.20.0

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 (298) hide show
  1. checksums.yaml +4 -4
  2. data/VERSION +1 -1
  3. data/card.gemspec +8 -7
  4. data/config/initializers/01_core_extensions/array.rb +4 -0
  5. data/config/initializers/01_core_extensions/persistent_identifiers.rb +12 -0
  6. data/config/initializers/02_patches/better_errors.rb +56 -0
  7. data/config/initializers/core_extensions.rb +13 -18
  8. data/config/initializers/patches.rb +8 -0
  9. data/config/locales/de.yml +0 -2
  10. data/db/migrate_core_cards/20150202143810_import_bootstrap_layout.rb +22 -12
  11. data/db/migrate_core_cards/20161102202156_tweak_recaptcha_setting_cards.rb +17 -0
  12. data/db/migrate_core_cards/20161103154836_update_keys.rb +46 -0
  13. data/lib/card.rb +1 -8
  14. data/lib/card/act_manager.rb +4 -0
  15. data/lib/card/auth/permissions.rb +5 -3
  16. data/lib/card/cache.rb +1 -20
  17. data/lib/card/cache/persistent.rb +6 -0
  18. data/lib/card/content/chunk.rb +4 -3
  19. data/lib/card/content/diff.rb +2 -2
  20. data/lib/card/content/diff/result.rb +11 -0
  21. data/lib/card/env/success.rb +4 -0
  22. data/lib/card/error.rb +2 -0
  23. data/lib/card/format.rb +14 -17
  24. data/lib/card/format/content.rb +16 -8
  25. data/lib/card/format/error.rb +3 -5
  26. data/lib/card/format/names.rb +22 -16
  27. data/lib/card/format/nest.rb +67 -61
  28. data/lib/card/format/nest/fetch.rb +40 -33
  29. data/lib/card/format/nest/main.rb +39 -19
  30. data/lib/card/format/nest/subformat.rb +3 -16
  31. data/lib/card/format/nest/view.rb +23 -32
  32. data/lib/card/format/permission.rb +49 -34
  33. data/lib/card/format/registration.rb +12 -6
  34. data/lib/card/format/render.rb +62 -73
  35. data/lib/card/migration.rb +14 -10
  36. data/lib/card/migration/import.rb +20 -19
  37. data/lib/card/migration/import/import_data.rb +50 -59
  38. data/lib/card/migration/import/import_data/card_attributes.rb +56 -0
  39. data/lib/card/migration/import/import_data/card_content.rb +33 -0
  40. data/lib/card/migration/import/merger.rb +47 -0
  41. data/lib/card/mod/loader.rb +4 -4
  42. data/lib/card/model/save_helper.rb +49 -10
  43. data/lib/card/name.rb +16 -52
  44. data/lib/card/name/fields_and_traits.rb +67 -0
  45. data/lib/card/name/variants.rb +17 -0
  46. data/lib/card/query.rb +6 -2
  47. data/lib/card/query/attributes.rb +1 -1
  48. data/lib/card/query/interpretation.rb +3 -3
  49. data/lib/card/set/event.rb +2 -1
  50. data/lib/card/set/format.rb +18 -7
  51. data/lib/card/set_pattern.rb +17 -13
  52. data/lib/card/tasks/card.rake +1 -1
  53. data/lib/card/view.rb +55 -0
  54. data/lib/card/view/cache.rb +90 -0
  55. data/lib/card/view/fetch.rb +109 -0
  56. data/lib/card/view/options.rb +164 -0
  57. data/lib/card/view/stub.rb +30 -0
  58. data/lib/card/view/visibility.rb +95 -0
  59. data/lib/cardio.rb +3 -2
  60. data/lib/cardio/schema.rb +21 -8
  61. data/lib/generators/card.rb +16 -2
  62. data/lib/generators/card/format/format_generator.rb +10 -9
  63. data/lib/generators/card/migration/migration_generator.rb +10 -5
  64. data/lib/generators/card/set/USAGE +1 -1
  65. data/lib/generators/card/set/set_generator.rb +11 -9
  66. data/mod/account/set/right/account.rb +38 -40
  67. data/mod/account/set/right/token.rb +2 -1
  68. data/mod/account/set/self/account_links.rb +34 -54
  69. data/mod/account/set/self/signin.rb +107 -93
  70. data/mod/account/set/type/signup.rb +33 -32
  71. data/mod/account/set/type/user.rb +28 -21
  72. data/mod/account/spec/set/all/account_spec.rb +9 -9
  73. data/mod/account/spec/set/right/account_spec.rb +23 -14
  74. data/mod/account/spec/set/right/email_spec.rb +6 -6
  75. data/mod/account/spec/set/right/password_spec.rb +4 -4
  76. data/mod/account/spec/set/right/token_spec.rb +3 -3
  77. data/mod/account/spec/set/self/account_links_spec.rb +3 -3
  78. data/mod/account/spec/set/self/signin_spec.rb +2 -2
  79. data/mod/account/spec/set/type/signup_spec.rb +7 -8
  80. data/mod/ace_editor/set/abstract/ace_editor.rb +1 -4
  81. data/mod/admin/set/self/admin.rb +2 -2
  82. data/mod/admin/set/self/admin_info.rb +1 -1
  83. data/mod/admin/set/self/recaptcha_private_key.rb +3 -0
  84. data/mod/admin/set/self/recaptcha_proxy.rb +3 -0
  85. data/mod/admin/set/self/recaptcha_public_key.rb +3 -0
  86. data/mod/admin/set/self/trash.rb +4 -4
  87. data/mod/admin/spec/set/self/admin_spec.rb +4 -4
  88. data/mod/admin/spec/set/self/version_spec.rb +1 -1
  89. data/mod/basic_formats/set/all/all_css.rb +3 -3
  90. data/mod/basic_formats/set/all/all_csv.rb +6 -6
  91. data/mod/basic_formats/set/all/all_js.rb +4 -0
  92. data/mod/basic_formats/set/all/base.rb +40 -62
  93. data/mod/basic_formats/set/all/json.rb +34 -39
  94. data/mod/basic_formats/set/all/rss.rb +6 -6
  95. data/mod/basic_formats/set/all/text.rb +3 -2
  96. data/mod/basic_formats/set/self/01_head/javascript.rb +2 -2
  97. data/mod/basic_formats/set/self/head.rb +6 -10
  98. data/mod/basic_formats/spec/set/all/all_css_spec.rb +1 -1
  99. data/mod/basic_formats/spec/set/all/all_csv_spec.rb +1 -1
  100. data/mod/basic_formats/spec/set/all/base_spec.rb +8 -5
  101. data/mod/basic_formats/spec/set/all/json_spec.rb +2 -2
  102. data/mod/basic_formats/spec/set/all/rss_spec.rb +4 -4
  103. data/mod/basic_types/set/type/plain_text.rb +3 -5
  104. data/mod/basic_types/spec/set/type/plain_text_spec.rb +2 -2
  105. data/mod/bootstrap/lib/bootstrap.rb +16 -0
  106. data/mod/bootstrap/lib/bootstrap/basic_tags.rb +26 -0
  107. data/mod/bootstrap/lib/bootstrap/component.rb +133 -0
  108. data/mod/bootstrap/lib/bootstrap/component/form.rb +31 -0
  109. data/mod/bootstrap/lib/bootstrap/component/horizontal_form.rb +38 -0
  110. data/mod/bootstrap/lib/bootstrap/component/layout.rb +83 -0
  111. data/mod/bootstrap/lib/bootstrap/component/panel.rb +9 -0
  112. data/mod/bootstrap/lib/bootstrap/component_loader.rb +30 -0
  113. data/mod/bootstrap/lib/bootstrap/delegate.rb +16 -0
  114. data/mod/bootstrap/lib/bootstrapper.rb +16 -0
  115. data/mod/bootstrap/lib/stylesheets/bootstrap/_tables.scss +55 -52
  116. data/mod/bootstrap/lib/stylesheets/bootstrap/mixins/_table-row.scss +12 -12
  117. data/mod/bootstrap/lib/stylesheets/bootstrap_cards.scss +12 -0
  118. data/mod/bootstrap/set/all/bootstrap/accordion.rb +63 -0
  119. data/mod/bootstrap/set/all/bootstrap/helper.rb +7 -140
  120. data/mod/bootstrap/set/all/bootstrap/navbar.rb +74 -0
  121. data/mod/bootstrap/set/all/bootstrap/table.rb +76 -46
  122. data/mod/bootstrap/set/all/bootstrap/tabs.rb +58 -23
  123. data/mod/bootstrap/set/all/bootstrap/wrapper.rb +14 -8
  124. data/mod/bootstrap/set/all/rich_bootstrap.rb +5 -3
  125. data/mod/bootstrap/spec/set/all/bootstrap/bootstrap_builder_spec.rb +31 -0
  126. data/mod/bootstrap/spec/set/all/bootstrap/bootstrap_spec.rb +20 -0
  127. data/mod/bootstrap/spec/set/all/bootstrap/form_spec.rb +59 -1
  128. data/mod/bootstrap/spec/set/all/bootstrap/layout_spec.rb +104 -15
  129. data/mod/carrierwave/set/abstract/attachment.rb +4 -3
  130. data/mod/carrierwave/set/abstract/attachment/paths.rb +1 -1
  131. data/mod/carrierwave/set/abstract/attachment/storage_type.rb +5 -11
  132. data/mod/carrierwave/set/type/file.rb +39 -32
  133. data/mod/carrierwave/set/type/image.rb +59 -34
  134. data/mod/carrierwave/spec/set/type/image_spec.rb +3 -3
  135. data/mod/core/chunk/link.rb +5 -0
  136. data/mod/core/chunk/{include.rb → nest.rb} +8 -29
  137. data/mod/core/chunk/reference.rb +5 -6
  138. data/mod/core/chunk/view_stub.rb +42 -0
  139. data/mod/core/format/html_format.rb +23 -26
  140. data/mod/core/set/abstract/code_file.rb +1 -1
  141. data/mod/core/set/all/actify.rb +1 -1
  142. data/mod/core/set/all/active_card.rb +0 -1
  143. data/mod/core/set/all/{tracked_attributes.rb → assign_attributes.rb} +55 -24
  144. data/mod/core/set/all/collection.rb +136 -122
  145. data/mod/core/set/all/content.rb +8 -0
  146. data/mod/core/set/all/event.rb +5 -2
  147. data/mod/core/set/all/export.rb +7 -7
  148. data/mod/core/set/all/fetch.rb +90 -26
  149. data/mod/core/set/all/initialize.rb +17 -6
  150. data/mod/core/set/all/name.rb +2 -3
  151. data/mod/core/set/all/permissions.rb +19 -11
  152. data/mod/core/set/all/states.rb +12 -2
  153. data/mod/core/set/all/trash.rb +1 -1
  154. data/mod/core/set/all/type.rb +2 -0
  155. data/mod/core/set/all/utils.rb +4 -3
  156. data/mod/core/spec/chunk/literal_spec.rb +2 -2
  157. data/mod/core/spec/chunk/uri_spec.rb +17 -17
  158. data/mod/core/spec/format/html_format_spec.rb +11 -13
  159. data/mod/core/spec/set/all/attribute_tracking_spec.rb +2 -2
  160. data/mod/core/spec/set/all/collection_spec.rb +21 -24
  161. data/mod/core/spec/set/all/content_spec.rb +1 -1
  162. data/mod/core/spec/set/all/export_spec.rb +3 -3
  163. data/mod/core/spec/set/all/fetch_spec.rb +5 -5
  164. data/mod/core/spec/set/all/initialize_spec.rb +4 -4
  165. data/mod/core/spec/set/all/name_spec.rb +6 -6
  166. data/mod/core/spec/set/all/permissions_spec.rb +10 -10
  167. data/mod/core/spec/set/all/references_spec.rb +1 -1
  168. data/mod/core/spec/set/all/rules2_spec.rb +24 -24
  169. data/mod/core/spec/set/all/rules_spec.rb +1 -1
  170. data/mod/core/spec/set/all/templating_spec.rb +8 -8
  171. data/mod/core/spec/set/all/tracked_attributes_spec.rb +6 -6
  172. data/mod/core/spec/set/all/type_spec.rb +5 -5
  173. data/mod/developer/spec/set/all/event_viz_spec.rb +1 -1
  174. data/mod/developer/spec/set/right/debug_spec.rb +1 -1
  175. data/mod/email/set/all/email_html.rb +2 -2
  176. data/mod/email/set/all/notify.rb +8 -3
  177. data/mod/email/set/right/bcc.rb +3 -3
  178. data/mod/email/set/right/follow.rb +5 -5
  179. data/mod/email/set/right/following.rb +1 -1
  180. data/mod/email/set/self/follow_defaults.rb +27 -16
  181. data/mod/email/set/type/email_template.rb +1 -1
  182. data/mod/email/set/type_plus_right/user/follow.rb +10 -9
  183. data/mod/history/lib/card/act.rb +4 -0
  184. data/mod/history/lib/card/act/act_renderer.rb +194 -0
  185. data/mod/history/lib/card/act/act_renderer/absolute_act_renderer.rb +25 -0
  186. data/mod/history/lib/card/act/act_renderer/relative_act_renderer.rb +41 -0
  187. data/mod/history/lib/card/action.rb +1 -0
  188. data/mod/history/lib/card/action/action_renderer.rb +92 -0
  189. data/mod/history/lib/card/action/differ.rb +6 -1
  190. data/mod/history/set/all/act_view.rb +64 -0
  191. data/mod/history/set/all/action_view.rb +65 -0
  192. data/mod/history/set/all/content_history.rb +44 -37
  193. data/mod/history/set/all/history.rb +49 -263
  194. data/mod/machines/lib/stylesheets/style_cards.scss +30 -115
  195. data/mod/machines/set/abstract/script.rb +42 -7
  196. data/mod/machines/set/right/machine_input.rb +4 -0
  197. data/mod/machines/set/type/coffee_script.rb +8 -22
  198. data/mod/machines/set/type/css.rb +2 -2
  199. data/mod/machines/set/type/java_script.rb +4 -24
  200. data/mod/machines/set/type/scss.rb +1 -1
  201. data/mod/machines/spec/set/type/css_spec.rb +1 -1
  202. data/mod/machines/spec/set/type/scss_spec.rb +3 -3
  203. data/mod/machines/spec/set/type/skin_spec.rb +7 -7
  204. data/mod/pointer/set/abstract/01_pointer.rb +44 -46
  205. data/mod/pointer/set/abstract/01_pointer/edit.rb +13 -13
  206. data/mod/pointer/set/right/options.rb +4 -0
  207. data/mod/pointer/spec/set/type/pointer_spec.rb +7 -7
  208. data/mod/prosemirror_editor/set/abstract/prosemirror_editor.rb +3 -3
  209. data/mod/settings/set/abstract/permission.rb +25 -18
  210. data/mod/settings/set/right/add_help.rb +3 -3
  211. data/mod/settings/set/right/structure.rb +10 -16
  212. data/mod/settings/spec/set/right/comment_spec.rb +3 -3
  213. data/mod/settings/spec/set/right/create_spec.rb +1 -1
  214. data/mod/settings/spec/set/right/style_spec.rb +1 -1
  215. data/mod/settings/spec/set/type/setting_spec.rb +1 -1
  216. data/mod/solid_cache/set/abstract/solid_cache.rb +4 -4
  217. data/mod/solid_cache/set/right/solid_cache.rb +9 -10
  218. data/mod/standard/set/abstract/01_search_params.rb +41 -0
  219. data/mod/standard/set/abstract/search.rb +132 -0
  220. data/mod/standard/set/abstract/search/paging.rb +81 -0
  221. data/mod/standard/set/abstract/search/paging/paging_links.rb +90 -0
  222. data/mod/standard/set/abstract/wql_search.rb +67 -0
  223. data/mod/standard/set/all/error.rb +89 -82
  224. data/mod/standard/set/all/links.rb +1 -1
  225. data/mod/standard/set/all/rich_html/content.rb +125 -141
  226. data/mod/standard/set/all/rich_html/editing.rb +115 -178
  227. data/mod/standard/set/all/rich_html/form.rb +111 -131
  228. data/mod/standard/set/all/rich_html/header.rb +57 -39
  229. data/mod/standard/set/all/rich_html/menu.rb +94 -94
  230. data/mod/standard/set/all/rich_html/modal.rb +5 -10
  231. data/mod/standard/set/all/rich_html/new.rb +103 -0
  232. data/mod/standard/set/all/rich_html/toolbar.rb +54 -74
  233. data/mod/standard/set/all/rich_html/wrapper.rb +111 -138
  234. data/mod/standard/set/rstar/rules.rb +27 -38
  235. data/mod/standard/set/rstar/rules_editor.rb +298 -277
  236. data/mod/standard/set/self/navbox.rb +20 -15
  237. data/mod/standard/set/self/recent.rb +25 -17
  238. data/mod/standard/set/self/search.rb +25 -4
  239. data/mod/standard/set/type/cardtype.rb +11 -9
  240. data/mod/standard/set/type/date.rb +1 -1
  241. data/mod/standard/set/type/number.rb +1 -1
  242. data/mod/standard/set/type/phrase.rb +1 -1
  243. data/mod/standard/set/type/search_type.rb +17 -282
  244. data/mod/standard/set/type/session.rb +1 -1
  245. data/mod/standard/set/type/set.rb +155 -131
  246. data/mod/standard/set/type/toggle.rb +1 -1
  247. data/mod/standard/set/type/uri.rb +4 -4
  248. data/mod/standard/spec/chunk/include_spec.rb +13 -31
  249. data/mod/standard/spec/chunk/link_spec.rb +1 -1
  250. data/mod/standard/spec/set/all/error_spec.rb +1 -1
  251. data/mod/standard/spec/set/all/history_spec.rb +2 -2
  252. data/mod/standard/spec/set/all/rich_html/form_spec.rb +4 -4
  253. data/mod/standard/spec/set/all/rich_html/toolbar_spec.rb +22 -0
  254. data/mod/standard/spec/set/all/rich_html/wrapper_spec.rb +3 -2
  255. data/mod/standard/spec/set/right/when_created_spec.rb +1 -1
  256. data/mod/standard/spec/set/right/when_last_edited_spec.rb +1 -1
  257. data/mod/standard/spec/set/rstar/rules_spec.rb +2 -3
  258. data/mod/standard/spec/set/self/head_spec.rb +2 -2
  259. data/mod/standard/spec/set/self/navbox_spec.rb +1 -1
  260. data/mod/standard/spec/set/self/now_spec.rb +1 -1
  261. data/mod/standard/spec/set/type/date_spec.rb +1 -1
  262. data/mod/standard/spec/set/type/email_template_spec.rb +1 -1
  263. data/mod/standard/spec/set/type/layout_type_spec.rb +1 -1
  264. data/mod/standard/spec/set/type/number_spec.rb +1 -1
  265. data/mod/standard/spec/set/type/phrase_spec.rb +1 -1
  266. data/mod/standard/spec/set/type/search_type_spec.rb +2 -2
  267. data/mod/standard/spec/set/type/set_spec.rb +2 -2
  268. data/mod/standard/spec/set/type/toggle_spec.rb +2 -2
  269. data/mod/standard/spec/set/type/uri_spec.rb +3 -1
  270. data/mod/tinymce_editor/set/abstract/tinymce_editor.rb +1 -1
  271. data/spec/config/initializers/core_extensions_spec.rb +40 -10
  272. data/spec/lib/card/auth_spec.rb +8 -8
  273. data/spec/lib/card/cache_spec.rb +3 -3
  274. data/spec/lib/card/chunk_spec.rb +4 -4
  275. data/spec/lib/card/codename_spec.rb +2 -2
  276. data/spec/lib/card/content_spec.rb +23 -23
  277. data/spec/lib/card/diff_spec.rb +1 -1
  278. data/spec/lib/card/format_spec.rb +19 -24
  279. data/spec/lib/card/loader_spec.rb +4 -4
  280. data/spec/lib/card/name_spec.rb +16 -16
  281. data/spec/lib/card/query_spec.rb +80 -80
  282. data/spec/lib/card/reference_spec.rb +5 -5
  283. data/spec/lib/card/set_spec.rb +6 -6
  284. data/spec/lib/card/subcards_spec.rb +14 -0
  285. data/spec/lib/card/view_cache_spec.rb +5 -5
  286. data/spec/models/card/cardtype_spec.rb +15 -15
  287. data/spec/models/card/create_spec.rb +2 -2
  288. data/spec/models/card/trash_spec.rb +24 -24
  289. data/spec/models/card/type_transition_spec.rb +8 -8
  290. data/spec/models/card/validation_spec.rb +5 -5
  291. data/spec/models/card_spec.rb +14 -14
  292. data/spec/spec_helper.rb +6 -2
  293. data/spec/support/card_spec_helper.rb +21 -11
  294. data/spec/support/helper/card_helper.rb +11 -4
  295. metadata +73 -15
  296. data/lib/card/cache/view_cache.rb +0 -103
  297. data/mod/bootstrap/set/all/bootstrap/layout.rb +0 -58
  298. data/mod/core/set/all/view_cache.rb +0 -9
@@ -0,0 +1,109 @@
1
+ class Card
2
+ class View
3
+ # Support context-aware card view caching.
4
+ #
5
+ # View definitions can contain cache settings that guide whether and how
6
+ # the view should be cached.
7
+ module Fetch
8
+ # fetching can result in one of three things:
9
+ # - simply yielding the initial render call
10
+ # - storing or retrieving the render to/from the cache
11
+ # - creating a stub within another render
12
+ # (so that the stub may be rendered later)
13
+ def fetch &block
14
+ case cache_level
15
+ when :yield then yield
16
+ when :cache_yield then cache_fetch(&block)
17
+ when :stub then stub
18
+ end
19
+ end
20
+
21
+ # Each of the following represents an accepted value for cache
22
+ # directives on view definitions. eg:
23
+ # view :myview, cache: :standard do ...
24
+ #
25
+ # * *always* - store independent cached view, even if that means double
26
+ # caching. (eg view is inside another one already being cached)
27
+ # * *standard* (default) cache independently or dependently, but
28
+ # don't double cache
29
+ # * *never* don't ever cache this view
30
+ def cache_level
31
+ return :yield unless Cardio.config.view_cache
32
+ send "#{caching? ? 'dependent' : 'independent'}_cache_level"
33
+ end
34
+
35
+ # INDEPENDENT CACHING
36
+ # takes place on its own (not within another view being cached)
37
+
38
+ def independent_cache_level
39
+ independent_cache_ok? ? :cache_yield : :yield
40
+ end
41
+
42
+ def independent_cache_ok?
43
+ cache_setting != :never &&
44
+ foreign_live_options.empty? &&
45
+ clean_enough_to_cache?
46
+ end
47
+
48
+ # The following methods are shared by independent and dependent caching
49
+
50
+ # view-specific setting as set in view definition. (always, standard, or
51
+ # never)
52
+ def cache_setting
53
+ format.view_cache_setting requested_view
54
+ end
55
+
56
+ # altered view requests and altered cards are not cacheable
57
+ def clean_enough_to_cache?
58
+ requested_view == ok_view &&
59
+ !card.unknown? &&
60
+ !card.db_content_changed?
61
+ # FIXME: might consider other changes as disqualifying, though
62
+ # we should make sure not to disallow caching of virtual cards
63
+ end
64
+
65
+ # DEPENDENT CACHING
66
+ # handling of views rendered within another cached view.
67
+
68
+ def dependent_cache_level
69
+ level = dependent_cache_level_unvalidated
70
+ validate_stub if level == :stub
71
+ level
72
+ end
73
+
74
+ def dependent_cache_level_unvalidated
75
+ return :yield if ok_view == :too_deep
76
+ dependent_cache_ok? ? dependent_cache_setting : :stub
77
+ end
78
+
79
+ def dependent_cache_ok?
80
+ return false unless parent && clean_enough_to_cache?
81
+ return true if normalized_options[:skip_perms]
82
+ dependent_cacheable_permissible?
83
+ end
84
+
85
+ def dependent_cacheable_permissible?
86
+ case permission_task
87
+ when :none then true
88
+ when parent.permission_task then true
89
+ when Symbol then card.anyone_can?(permission_task)
90
+ else false
91
+ end
92
+ end
93
+
94
+ # task directly associated with the view in its definition via the
95
+ # "perms" directive
96
+ def permission_task
97
+ @permission_task ||= Card::Format.perms[requested_view] || :read
98
+ end
99
+
100
+ DEPENDENT_CACHE_LEVEL =
101
+ { always: :cache_yield, standard: :yield, never: :stub }.freeze
102
+
103
+ def dependent_cache_setting
104
+ level = DEPENDENT_CACHE_LEVEL[cache_setting]
105
+ level || raise("unknown cache setting: #{cache_setting}")
106
+ end
107
+ end
108
+ end
109
+ end
@@ -0,0 +1,164 @@
1
+ class Card
2
+ class View
3
+ # normalizes and manages standard view options
4
+ module Options
5
+ # option values are strings unless otherwise noted
6
+ @keymap = {
7
+ nest: [
8
+ :view, # view to render
9
+ :show, # render these views when optional
10
+ :hide, # do render these views when optional
11
+ :nest_name, # name as used in nest
12
+ :nest_syntax # full nest syntax
13
+ ],
14
+ # note: show/hide can be single view (Symbol), list of views (Array),
15
+ # or comma separated views (String)
16
+ heir: [
17
+ :main, # format object is page's "main" object (Boolean)
18
+ :home_view, # view for slot to return to when no view specified
19
+ :edit_structure # use a different structure for editing (Array)
20
+
21
+ ],
22
+ both: [
23
+ :help, # cue text when editing
24
+ :structure, # overrides the content of the card
25
+ :title, # overrides the name of the card
26
+ :variant, # override the canonical version of the name with
27
+ # a different variant
28
+ :editor, # inline_nests makes a form within standard content
29
+ # (Symbol)
30
+ :type, # set the default type of new cards
31
+ :size, # set an image size
32
+ :params, # parameters for add button. deprecate?
33
+ :items # options for items (Hash)
34
+ ],
35
+ none: [
36
+ :skip_perms, # do not check permissions for this view (Boolean)
37
+ :main_view
38
+ ] # this is main view of page (Boolean)
39
+ }
40
+
41
+ class << self
42
+ attr_reader :keymap
43
+
44
+ # all standard option keys
45
+ def all_keys
46
+ @all_keys ||= keymap.each_with_object([]) { |(_k, v), a| a.push(*v) }
47
+ end
48
+
49
+ # keys whose values can be set by Wagneers in card nests
50
+ def nest_keys
51
+ @nest_keys ||= ::Set.new(keymap[:both]) + keymap[:nest]
52
+ end
53
+
54
+ # keys that follow simple standard inheritance pattern from parent views
55
+ def heir_keys
56
+ @heir_keys ||= ::Set.new(keymap[:both]) + keymap[:heir]
57
+ end
58
+ end
59
+
60
+ # There are two primary options hashes:
61
+ # - @normalized_options are determined upon initialization and do not
62
+ # change after that.
63
+ # - @live_options are created during the "process" phase, and they can be
64
+ # altered via the "voo" API at any time
65
+
66
+ attr_reader :normalized_options
67
+
68
+ def live_options
69
+ @live_options ||= process_live_options
70
+ end
71
+
72
+ # The following methods comprise the primary voo API. They allow
73
+ # developers to read and write options dynamically
74
+
75
+ def items
76
+ live_options[:items] ||= {}
77
+ end
78
+
79
+ (heir_keys + [:nest_name, :nest_syntax] - [:items]).each do |option_key|
80
+ define_method option_key do
81
+ norm_method = "normalize_#{option_key}"
82
+ value = live_options[option_key]
83
+ try(norm_method, value) || value
84
+ end
85
+
86
+ define_method "#{option_key}=" do |value|
87
+ live_options[option_key] = value
88
+ end
89
+ end
90
+
91
+ def normalize_editor value
92
+ value && value.to_sym
93
+ end
94
+
95
+ # options to be used in data attributes of card slots (normalized options
96
+ # with standard keys)
97
+ def slot_options
98
+ normalized_options.select { |k, _v| Options.all_keys.include? k }
99
+ end
100
+
101
+ private
102
+
103
+ # option normalization includes standardizing options into a hash with
104
+ # symbols as keys, managing standard view inheritance, and special
105
+ # handling for main_views.
106
+ def normalize_options
107
+ @normalized_options = opts = options_to_hash @raw_options.clone
108
+ opts[:view] = @raw_view
109
+ inherit_from_parent if parent
110
+ opts[:main] = true if format.main?
111
+ @optional = opts.delete(:optional) || false
112
+ opts
113
+ end
114
+
115
+ # typically options are already a hash. this also handles an array of
116
+ # hashes and nil.
117
+ def options_to_hash opts
118
+ case opts
119
+ when Hash then opts
120
+ when Array then opts[0].merge opts[1]
121
+ when nil then {}
122
+ else raise Card::Error, "bad view options: #{opts}"
123
+ end.deep_symbolize_keys!
124
+ end
125
+
126
+ # standard inheritance from parent view object
127
+ def inherit_from_parent
128
+ Options.heir_keys.each do |key|
129
+ parent_value = parent.live_options[key]
130
+ normalized_options[key] ||= parent_value if parent_value
131
+ end
132
+ end
133
+
134
+ def process_live_options
135
+ opts = @live_options = normalized_options.clone
136
+ opts.merge! format.main_nest_options if opts[:main_view]
137
+ # main_view is a live_option because it is important that it NOT be
138
+ # locked in the stub. Otherwise the main card can only show one view.
139
+ process_default_options
140
+ opts
141
+ end
142
+
143
+ # This method triggers the default_X_args methods which can alter the
144
+ # @live_options hash both directly and indirectly (via the voo API)
145
+ def process_default_options
146
+ format.view_options_with_defaults requested_view, live_options
147
+ end
148
+
149
+ # "foreign" options are non-standard options. They're allowed, but they
150
+ # prevent independent caching (and thus stubbing)
151
+ def foreign_options opts
152
+ opts.reject { |k, _v| Options.all_keys.include? k }
153
+ end
154
+
155
+ def foreign_normalized_options
156
+ @foreign_normalize_options ||= foreign_options normalized_options
157
+ end
158
+
159
+ def foreign_live_options
160
+ foreign_options live_options
161
+ end
162
+ end
163
+ end
164
+ end
@@ -0,0 +1,30 @@
1
+ class Card
2
+ class View
3
+ # A "stub" is a placeholder for a card view. It can only be used in
4
+ # situations where the card identifier, known options, and nest mode
5
+ # comprise all the info needed to reproduce the view as intended
6
+ module Stub
7
+ def stub
8
+ "<card-view>#{stub_json}</card-view>"
9
+ end
10
+
11
+ def stub_json
12
+ JSON.generate stub_hash
13
+ end
14
+
15
+ def stub_hash
16
+ {
17
+ cast: card.cast,
18
+ options: normalized_options,
19
+ mode: format.mode
20
+ }
21
+ end
22
+
23
+ def validate_stub
24
+ return if foreign_normalized_options.empty?
25
+ raise "INVALID STUB: #{card.name}/#{ok_view}" \
26
+ " has foreign options: #{foreign_normalized_options}"
27
+ end
28
+ end
29
+ end
30
+ end
@@ -0,0 +1,95 @@
1
+ class Card
2
+ class View
3
+ # manages showing and hiding optional view renders
4
+ module Visibility
5
+ # tracks show/hide value for each view with an explicit setting
6
+ # eg { toggle: :hide }
7
+ def viz_hash
8
+ @viz_hash ||= {}
9
+ end
10
+
11
+ # test methods
12
+
13
+ def hide? view
14
+ viz_hash[view] == :hide
15
+ end
16
+
17
+ def show? view
18
+ !hide? view
19
+ end
20
+
21
+ # write methods
22
+
23
+ def show *views
24
+ viz views, :show
25
+ end
26
+
27
+ def hide *views
28
+ viz views, :hide
29
+ end
30
+
31
+ # force write methods
32
+
33
+ def show! *views
34
+ viz views, :show, true
35
+ end
36
+
37
+ def hide! *views
38
+ viz views, :hide, true
39
+ end
40
+
41
+ # advanced write method
42
+ VIZ_SETTING = { show: :show, true => :show,
43
+ hide: :hide, false => :hide, nil => :hide }
44
+
45
+ def viz views, setting, force=false
46
+ Array.wrap(views).each do |view|
47
+ view = view.to_sym
48
+ next if !force && viz_hash[view]
49
+ viz_hash[view] = VIZ_SETTING[setting]
50
+ end
51
+ end
52
+
53
+ def visible? view
54
+ unless viz_hash[view]
55
+ viz view, yield
56
+ end
57
+ show? view
58
+ end
59
+
60
+ # test whether main_view is optional
61
+ # (@optional is set in normalize_options
62
+ def optional?
63
+ return @optional unless @optional.nil?
64
+ @optional = detect_if_optional
65
+ end
66
+
67
+ # translate raw hide, show options (which can be strings, symbols,
68
+ # arrays, etc)
69
+ def process_visibility_options
70
+ viz_hash.reverse_merge! parent.viz_hash if parent
71
+ process_visibility live_options
72
+ viz requested_view, @optional if @optional && !viz_hash[requested_view]
73
+ end
74
+
75
+ # takes an options_hash and processes it to update viz_hash
76
+ def process_visibility options_hash
77
+ [:hide, :show].each do |setting|
78
+ list = viz_view_list options_hash.delete(setting)
79
+ viz list, setting, true
80
+ end
81
+ end
82
+
83
+ # translated show/hide setting into an array of views
84
+ def viz_view_list val
85
+ case val
86
+ when NilClass then []
87
+ when Array then val
88
+ when String then val.split(/[\s,]+/)
89
+ when Symbol then [val]
90
+ else raise Card::Error, "bad show/hide argument: #{val}"
91
+ end.map { |view| View.canonicalize view }
92
+ end
93
+ end
94
+ end
95
+ end
@@ -46,10 +46,10 @@ module Cardio
46
46
  token_expiry: 2.days,
47
47
  acts_per_page: 10,
48
48
  space_last_in_multispace: true,
49
- closed_search_limit: 50,
49
+ closed_search_limit: 10,
50
50
 
51
51
  non_createable_types: [%w(signup setting set)],
52
- view_cache: false,
52
+ view_cache: false,
53
53
 
54
54
  encoding: "utf-8",
55
55
  request_logger: false,
@@ -144,6 +144,7 @@ module Cardio
144
144
  list += Dir.glob path
145
145
  end
146
146
  end
147
+
147
148
  list.flatten
148
149
  end
149
150
  end
@@ -17,14 +17,27 @@ module Cardio
17
17
  end
18
18
 
19
19
  def schema_mode type
20
- new_suffix = Cardio.schema_suffix type
21
- original_suffix = ActiveRecord::Base.table_name_suffix
22
- ActiveRecord::Base.table_name_suffix = new_suffix
23
- ActiveRecord::SchemaMigration.reset_table_name
24
- paths = Cardio.migration_paths(type)
25
- yield(paths)
26
- ActiveRecord::Base.table_name_suffix = original_suffix
27
- ActiveRecord::SchemaMigration.reset_table_name
20
+ with_suffix type do
21
+ paths = Cardio.migration_paths(type)
22
+ yield(paths)
23
+ end
24
+ end
25
+
26
+ def with_suffix type
27
+ return yield unless (new_suffix = Cardio.schema_suffix type) &&
28
+ new_suffix.present?
29
+ original_name = ActiveRecord::Base.schema_migrations_table_name
30
+ ActiveRecord::Base.schema_migrations_table_name =
31
+ "#{original_name}#{new_suffix}"
32
+ ActiveRecord::SchemaMigration.table_name = "#{original_name}#{new_suffix}"
33
+ # ActiveRecord::Base.table_name_suffix = new_suffix
34
+ # ActiveRecord::SchemaMigration.reset_table_name
35
+ # original_suffix = ActiveRecord::Base.table_name_suffix
36
+ yield
37
+ ActiveRecord::Base.schema_migrations_table_name = original_name
38
+ ActiveRecord::SchemaMigration.table_name = original_name
39
+ # ActiveRecord::Base.table_name_suffix = original_suffix
40
+ # ActiveRecord::SchemaMigration.reset_table_name
28
41
  end
29
42
 
30
43
  def schema type=nil