droom 0.0.1 → 0.2.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 (459) hide show
  1. data/README.md +2 -2
  2. data/app/assets/images/droom/Untitled-1.png +0 -0
  3. data/app/assets/images/droom/acceptance.png +0 -0
  4. data/app/assets/images/droom/add.png +0 -0
  5. data/app/assets/images/droom/asterisk.png +0 -0
  6. data/app/assets/images/droom/asterisk_up.png +0 -0
  7. data/app/assets/images/droom/checkboxes.png +0 -0
  8. data/app/assets/images/droom/clear.png +0 -0
  9. data/app/assets/images/droom/cog.png +0 -0
  10. data/app/assets/images/droom/copy.png +0 -0
  11. data/app/assets/images/droom/copy_to_dropbox.png +0 -0
  12. data/app/assets/images/droom/crosses.png +0 -0
  13. data/app/assets/images/droom/dark_scrap_icons.png +0 -0
  14. data/app/assets/images/droom/defilter.png +0 -0
  15. data/app/assets/images/droom/delete.png +0 -0
  16. data/app/assets/images/droom/dropbox.png +0 -0
  17. data/app/assets/images/droom/dropbox_button.png +0 -0
  18. data/app/assets/images/droom/dropbox_button_small.png +0 -0
  19. data/app/assets/images/droom/edit.png +0 -0
  20. data/app/assets/images/droom/expand.png +0 -0
  21. data/app/assets/images/droom/expander.png +0 -0
  22. data/app/assets/images/droom/folder.png +0 -0
  23. data/app/assets/images/droom/image_box.png +0 -0
  24. data/app/assets/images/droom/in_dropbox.png +0 -0
  25. data/app/assets/images/droom/integration_buttons.png +0 -0
  26. data/app/assets/images/droom/leftright.png +0 -0
  27. data/app/assets/images/droom/manage.png +0 -0
  28. data/app/assets/images/droom/medium_object_icons.png +0 -0
  29. data/app/assets/images/droom/object_icons.png +0 -0
  30. data/app/assets/images/droom/playable.png +0 -0
  31. data/app/assets/images/droom/revoke.png +0 -0
  32. data/app/assets/images/droom/scrap_icons.png +0 -0
  33. data/app/assets/images/droom/search.png +0 -0
  34. data/app/assets/images/droom/small_asterisk.png +0 -0
  35. data/app/assets/images/droom/small_cog.png +0 -0
  36. data/app/assets/images/droom/small_download.png +0 -0
  37. data/app/assets/images/droom/small_image_box.png +0 -0
  38. data/app/assets/images/droom/smalladd.png +0 -0
  39. data/app/assets/images/droom/smallarrows.png +0 -0
  40. data/app/assets/images/droom/smallcopy.png +0 -0
  41. data/app/assets/images/droom/smalldelete.png +0 -0
  42. data/app/assets/images/droom/smalldownload.png +0 -0
  43. data/app/assets/images/droom/smalledit.png +0 -0
  44. data/app/assets/images/droom/smallmanage.png +0 -0
  45. data/app/assets/images/droom/star.png +0 -0
  46. data/app/assets/images/droom/symbols.png +0 -0
  47. data/app/assets/images/droom/tinyarrows.png +0 -0
  48. data/app/assets/images/droom/to_dropbox.png +0 -0
  49. data/app/assets/images/droom/twisty.png +0 -0
  50. data/app/assets/images/droom/youtube_icon.png +0 -0
  51. data/app/assets/javascripts/droom.js.coffee +62 -65
  52. data/app/assets/javascripts/droom/actions.js.coffee +492 -0
  53. data/app/assets/javascripts/droom/ajax.js.coffee +84 -0
  54. data/app/assets/javascripts/droom/{lib/extensions.js.coffee → extensions.js.coffee} +22 -15
  55. data/app/assets/javascripts/droom/lib/ZeroClipboard.js +334 -0
  56. data/app/assets/javascripts/droom/lib/ZeroClipboard.swf +0 -0
  57. data/app/assets/javascripts/droom/lib/ZeroClipboard10.swf +0 -0
  58. data/app/assets/javascripts/droom/map.js.coffee +124 -86
  59. data/app/assets/javascripts/droom/popups.js.coffee +252 -0
  60. data/app/assets/javascripts/droom/stream.js.coffee +92 -0
  61. data/app/assets/javascripts/droom/utilities.js.coffee +120 -0
  62. data/app/assets/javascripts/droom/widgets.js.coffee +1209 -0
  63. data/app/assets/stylesheets/_definitions.css.sass +189 -0
  64. data/app/assets/stylesheets/droom.css.sass +1429 -376
  65. data/app/assets/stylesheets/lib/_kalendae.css.sass +2 -5
  66. data/app/assets/stylesheets/lib/_popups.css.sass +86 -0
  67. data/app/assets/stylesheets/lib/_toolbar.css.sass +17 -11
  68. data/app/controllers/droom/agenda_categories_controller.rb +24 -0
  69. data/app/controllers/droom/calendars_controller.rb +29 -0
  70. data/app/controllers/droom/confirmations_controller.rb +38 -0
  71. data/app/controllers/droom/dashboard_controller.rb +2 -0
  72. data/app/controllers/droom/documents_controller.rb +42 -51
  73. data/app/controllers/droom/dropbox_tokens_controller.rb +61 -0
  74. data/app/controllers/droom/engine_controller.rb +8 -23
  75. data/app/controllers/droom/events_controller.rb +39 -27
  76. data/app/controllers/droom/folders_controller.rb +106 -0
  77. data/app/controllers/droom/group_invitations_controller.rb +15 -7
  78. data/app/controllers/droom/groups_controller.rb +4 -4
  79. data/app/controllers/droom/invitations_controller.rb +37 -9
  80. data/app/controllers/droom/memberships_controller.rb +5 -3
  81. data/app/controllers/droom/organisations_controller.rb +53 -0
  82. data/app/controllers/droom/people_controller.rb +46 -27
  83. data/app/controllers/droom/preferences_controller.rb +34 -0
  84. data/app/controllers/droom/scraps_controller.rb +77 -0
  85. data/app/controllers/droom/search_controller.rb +66 -0
  86. data/app/controllers/droom/suggestions_controller.rb +22 -35
  87. data/app/controllers/droom/users_controller.rb +69 -0
  88. data/app/controllers/droom/venues_controller.rb +1 -2
  89. data/app/controllers/droom/youtube_controller.rb +22 -0
  90. data/app/helpers/droom/droom_helper.rb +93 -5
  91. data/app/models/droom/agenda_category.rb +8 -1
  92. data/app/models/droom/calendar.rb +19 -0
  93. data/app/models/droom/category.rb +4 -6
  94. data/app/models/droom/document.rb +103 -64
  95. data/app/models/droom/document_attachment.rb +13 -47
  96. data/app/models/droom/dropbox_document.rb +41 -0
  97. data/app/models/droom/dropbox_token.rb +29 -0
  98. data/app/models/droom/event.rb +125 -90
  99. data/app/models/droom/folder.rb +134 -0
  100. data/app/models/droom/group.rb +68 -27
  101. data/app/models/droom/group_invitation.rb +12 -3
  102. data/app/models/droom/invitation.rb +50 -8
  103. data/app/models/droom/mailing_list_membership.rb +128 -0
  104. data/app/models/droom/membership.rb +71 -9
  105. data/app/models/droom/organisation.rb +22 -0
  106. data/app/models/droom/page.rb +3 -3
  107. data/app/models/droom/person.rb +180 -166
  108. data/app/models/droom/personal_folder.rb +31 -0
  109. data/app/models/droom/preference.rb +35 -0
  110. data/app/models/droom/recurrence_rule.rb +1 -1
  111. data/app/models/droom/scrap.rb +110 -0
  112. data/app/models/droom/tag.rb +120 -0
  113. data/app/models/droom/tagging.rb +13 -0
  114. data/app/models/droom/user.rb +211 -0
  115. data/app/models/droom/user_action_observer.rb +12 -0
  116. data/app/models/droom/venue.rb +56 -39
  117. data/app/views/cropper/uploads/_crop.html.haml +46 -0
  118. data/app/views/devise/mailer/confirmation_instructions.en.html.haml +24 -0
  119. data/app/views/devise/mailer/reset_password_instructions.en.html.haml +21 -0
  120. data/app/views/devise/passwords/edit.html.haml +31 -0
  121. data/app/views/devise/passwords/new.html.haml +21 -0
  122. data/app/views/devise/sessions/new.html.haml +33 -0
  123. data/app/views/droom/agenda_categories/_form.html.haml +22 -0
  124. data/app/views/droom/agenda_categories/new.html.haml +6 -0
  125. data/app/views/droom/calendars/_action_menu.html.haml +6 -0
  126. data/app/views/droom/calendars/index.html.haml +12 -0
  127. data/app/views/droom/calendars/show.rss.builder +0 -0
  128. data/app/views/droom/confirmations/show.html.haml +40 -0
  129. data/app/views/droom/dashboard/_calendar.html.haml +1 -0
  130. data/app/views/droom/dashboard/_folders.html.haml +5 -0
  131. data/app/views/droom/dashboard/_future_events.html.haml +18 -0
  132. data/app/views/droom/dashboard/_invitations.html.haml +1 -0
  133. data/app/views/droom/dashboard/_past_events.haml +14 -0
  134. data/app/views/droom/dashboard/_quicksearch.html.haml +6 -0
  135. data/app/views/droom/dashboard/_stream.html.haml +9 -0
  136. data/app/views/droom/dashboard/index.html.haml +5 -3
  137. data/app/views/droom/documents/_action_menu.html.haml +7 -0
  138. data/app/views/droom/documents/_documents.html.haml +5 -0
  139. data/app/views/droom/documents/_documents_list.html.haml +6 -6
  140. data/app/views/droom/documents/_documents_table.html.haml +29 -10
  141. data/app/views/droom/documents/_form.html.haml +3 -7
  142. data/app/views/droom/documents/_listing.html.haml +5 -6
  143. data/app/views/droom/documents/_pagination.html.haml +8 -0
  144. data/app/views/droom/documents/_search_result.html.haml +14 -0
  145. data/app/views/droom/documents/_suggested.html.haml +0 -5
  146. data/app/views/droom/documents/_table_document.html.haml +2 -8
  147. data/app/views/droom/documents/edit.html.haml +7 -1
  148. data/app/views/droom/documents/index.html.haml +10 -27
  149. data/app/views/droom/documents/new.html.haml +10 -1
  150. data/app/views/droom/dropbox_tokens/new.html.haml +6 -0
  151. data/app/views/droom/events/_action_menu.html.haml +15 -0
  152. data/app/views/droom/events/_event.html.haml +67 -57
  153. data/app/views/droom/events/_form.html.haml +15 -4
  154. data/app/views/droom/events/_invitations.html.haml +4 -19
  155. data/app/views/droom/events/_search_result.html.haml +19 -0
  156. data/app/views/droom/events/_views.html.haml +2 -2
  157. data/app/views/droom/events/edit.html.haml +7 -1
  158. data/app/views/droom/events/index.html.haml +27 -10
  159. data/app/views/droom/events/index.rss.builder +1 -1
  160. data/app/views/droom/events/new.html.haml +6 -1
  161. data/app/views/droom/events/show.html.haml +5 -1
  162. data/app/views/droom/folders/_action_menu.html.haml +14 -0
  163. data/app/views/droom/folders/_attachments.html.haml +3 -0
  164. data/app/views/droom/folders/_contents.html.haml +6 -0
  165. data/app/views/droom/folders/_folder.html.haml +20 -0
  166. data/app/views/droom/folders/_folders.html.haml +2 -0
  167. data/app/views/droom/folders/_form.html.haml +18 -0
  168. data/app/views/droom/folders/edit.html.haml +6 -0
  169. data/app/views/droom/folders/index.html.haml +32 -0
  170. data/app/views/droom/folders/new.html.haml +6 -0
  171. data/app/views/droom/folders/show.html.haml +1 -0
  172. data/app/views/droom/group_invitations/_form.html.haml +15 -4
  173. data/app/views/droom/group_invitations/new.html.haml +6 -1
  174. data/app/views/droom/groups/_action_menu.haml +11 -0
  175. data/app/views/droom/groups/_form.html.haml +10 -11
  176. data/app/views/droom/groups/_group.html.haml +9 -10
  177. data/app/views/droom/groups/_groups.html.haml +2 -3
  178. data/app/views/droom/groups/_search_result.html.haml +16 -0
  179. data/app/views/droom/groups/_suggested.html.haml +7 -0
  180. data/app/views/droom/groups/edit.html.haml +7 -1
  181. data/app/views/droom/groups/index.html.haml +6 -3
  182. data/app/views/droom/groups/new.html.haml +7 -0
  183. data/app/views/droom/groups/show.html.haml +1 -1
  184. data/app/views/droom/invitations/_created.html.haml +1 -1
  185. data/app/views/droom/invitations/_form.html.haml +9 -5
  186. data/app/views/droom/invitations/_invitation.html.haml +9 -0
  187. data/app/views/droom/invitations/_invitations.html.haml +8 -0
  188. data/app/views/droom/invitations/new.html.haml +6 -1
  189. data/app/views/droom/memberships/_member.html.haml +1 -1
  190. data/app/views/droom/memberships/_membership_toggle.html.haml +10 -0
  191. data/app/views/droom/memberships/new.html.haml +10 -0
  192. data/app/views/droom/organisations/_action_menu.html.haml +7 -0
  193. data/app/views/droom/organisations/_form.html.haml +25 -0
  194. data/app/views/droom/organisations/_organisation.html.haml +23 -0
  195. data/app/views/droom/organisations/_organisations.html.haml +2 -0
  196. data/app/views/droom/organisations/_suggested.html.haml +7 -0
  197. data/app/views/droom/organisations/edit.html.haml +6 -0
  198. data/app/views/droom/organisations/index.html.haml +20 -0
  199. data/app/views/droom/organisations/new.html.haml +6 -0
  200. data/app/views/droom/organisations/show.html.haml +1 -0
  201. data/app/views/droom/pages/_full_page.html.haml +1 -1
  202. data/app/views/droom/pages/index.html.haml +1 -1
  203. data/app/views/droom/panels/_account.html.haml +16 -0
  204. data/app/views/droom/panels/_admin.html.haml +23 -0
  205. data/app/views/droom/panels/_devices.html.haml +19 -0
  206. data/app/views/droom/panels/_dropbox.html.haml +17 -0
  207. data/app/views/droom/panels/_email.html.haml +16 -0
  208. data/app/views/droom/panels/_keywords.html.haml +3 -0
  209. data/app/views/droom/panels/_networks.html.haml +3 -0
  210. data/app/views/droom/panels/_readers.html.haml +18 -0
  211. data/app/views/droom/panels/_rss.html.haml +10 -0
  212. data/app/views/droom/panels/_search.html.haml +16 -0
  213. data/app/views/droom/panels/_vcal.html.haml +3 -0
  214. data/app/views/droom/people/_action_menu.html.haml +22 -0
  215. data/app/views/droom/people/_form.html.haml +69 -39
  216. data/app/views/droom/people/_listing.html.haml +19 -0
  217. data/app/views/droom/people/_memberships.html.haml +24 -0
  218. data/app/views/droom/people/_people.html.haml +5 -29
  219. data/app/views/droom/people/_person.html.haml +30 -32
  220. data/app/views/droom/people/_search_result.html.haml +14 -0
  221. data/app/views/droom/people/_suggested.html.haml +10 -5
  222. data/app/views/droom/people/edit.html.haml +9 -1
  223. data/app/views/droom/people/index.html.haml +6 -9
  224. data/app/views/droom/people/new.html.haml +6 -1
  225. data/app/views/droom/people/show.html.haml +1 -1
  226. data/app/views/droom/preferences/_checkbox.html.haml +7 -0
  227. data/app/views/droom/preferences/_radio_set.html.haml +9 -0
  228. data/app/views/droom/scraps/_action_menu.html.haml +9 -0
  229. data/app/views/droom/scraps/_caption.html.haml +9 -0
  230. data/app/views/droom/scraps/_credit.html.haml +10 -0
  231. data/app/views/droom/scraps/_form.html.haml +77 -0
  232. data/app/views/droom/scraps/_heading.html.haml +16 -0
  233. data/app/views/droom/scraps/_scrap.html.haml +17 -0
  234. data/app/views/droom/scraps/_search_result.html.haml +5 -0
  235. data/app/views/droom/scraps/_stream.html.haml +4 -0
  236. data/app/views/droom/scraps/_suggested.html.haml +5 -0
  237. data/app/views/droom/scraps/_thumb.html.haml +5 -0
  238. data/app/views/droom/scraps/edit.html.haml +2 -0
  239. data/app/views/droom/scraps/full/_document.html.haml +6 -0
  240. data/app/views/droom/scraps/full/_event.html.haml +20 -0
  241. data/app/views/droom/scraps/full/_image.html.haml +4 -0
  242. data/app/views/droom/scraps/full/_link.html.haml +5 -0
  243. data/app/views/droom/scraps/full/_quote.html.haml +8 -0
  244. data/app/views/droom/scraps/full/_text.html.haml +4 -0
  245. data/app/views/droom/scraps/full/_video.html.haml +4 -0
  246. data/app/views/droom/scraps/index.atom.builder +26 -0
  247. data/app/views/droom/scraps/index.html.haml +15 -0
  248. data/app/views/droom/scraps/new.html.haml +2 -0
  249. data/app/views/droom/scraps/show.html.haml +4 -0
  250. data/app/views/droom/scraps/thumbs/_document.html.haml +9 -0
  251. data/app/views/droom/scraps/thumbs/_event.html.haml +17 -0
  252. data/app/views/droom/scraps/thumbs/_image.html.haml +6 -0
  253. data/app/views/droom/scraps/thumbs/_link.html.haml +10 -0
  254. data/app/views/droom/scraps/thumbs/_quote.html.haml +8 -0
  255. data/app/views/droom/scraps/thumbs/_text.html.haml +8 -0
  256. data/app/views/droom/scraps/thumbs/_video.html.haml +6 -0
  257. data/app/views/droom/shared/_controls.html.haml +5 -3
  258. data/app/views/droom/shared/_excerpt.html.haml +2 -0
  259. data/app/views/droom/shared/_navigation.html.haml +4 -4
  260. data/app/views/droom/shared/_panels.html.haml +4 -0
  261. data/app/views/droom/shared/_quicklinks.html.haml +5 -0
  262. data/app/views/droom/shared/_search_form.html.haml +2 -1
  263. data/app/views/droom/shared/_search_results.html.haml +9 -0
  264. data/app/views/droom/shared/_suggestions.html.haml +13 -9
  265. data/app/views/droom/shared/_title_excerpt.haml +2 -0
  266. data/app/views/droom/shared/search.html.haml +18 -0
  267. data/app/views/droom/users/_confirmation.html.haml +2 -0
  268. data/app/views/droom/users/_dropbox_status.html.haml +2 -0
  269. data/app/views/droom/users/_form.html.haml +34 -0
  270. data/app/views/droom/users/_user.html.haml +2 -0
  271. data/app/views/droom/users/_user_or_person.html.haml +63 -0
  272. data/app/views/droom/users/_users_table.html.haml +17 -0
  273. data/app/views/droom/users/edit.html.haml +10 -0
  274. data/app/views/droom/users/index.html.haml +42 -0
  275. data/app/views/droom/users/unwelcome.en.html.haml +17 -0
  276. data/app/views/droom/venues/_search_result.html.haml +17 -0
  277. data/app/views/droom/youtube/show.html.haml +12 -0
  278. data/app/views/kaminari/_paginator.html.haml +16 -0
  279. data/app/views/layouts/droom/application.html.haml +17 -17
  280. data/app/views/layouts/droom/email.html.haml +59 -0
  281. data/config/cucumber.yml +8 -0
  282. data/config/initializers/devise.rb +240 -0
  283. data/config/locales/devise.en.yml +58 -0
  284. data/config/locales/en.yml +203 -32
  285. data/config/routes.rb +55 -16
  286. data/config/sunspot.yml +17 -0
  287. data/db/migrate/20121120115447_tags.rb +18 -0
  288. data/db/migrate/20130116155331_dropbox_tokens.rb +9 -0
  289. data/db/migrate/20130118103540_folders.rb +47 -0
  290. data/db/migrate/20130124113715_preferences.rb +10 -0
  291. data/db/migrate/20130125132427_users_in_droom.rb +58 -0
  292. data/db/migrate/20130129142307_mobile_phones.rb +7 -0
  293. data/db/migrate/20130130120124_folder_ancestry_to_parents.rb +7 -0
  294. data/db/migrate/20130131161430_mailing_lists.rb +37 -0
  295. data/db/migrate/20130207091903_preference_uuids.rb +5 -0
  296. data/db/migrate/20130207123614_stream.rb +13 -0
  297. data/db/migrate/20130208035113_access_token_secret.rb +5 -0
  298. data/db/migrate/20130214145014_person_image.rb +9 -0
  299. data/db/migrate/20130217152644_devise_confirmable.rb +13 -0
  300. data/db/migrate/20130225095328_create_droom_calendars.rb +20 -0
  301. data/db/migrate/20130226092944_give_scraps_document.rb +5 -0
  302. data/db/migrate/20130228083509_privateness.rb +9 -0
  303. data/db/migrate/20130228134143_store_metadata.rb +5 -0
  304. data/db/migrate/20130305150648_folders_nicely.rb +6 -0
  305. data/db/migrate/20130305151936_niceties.rb +7 -0
  306. data/db/migrate/20130308103807_create_droom_dropbox_documents.rb +11 -0
  307. data/db/migrate/20130308154552_dropbox_documents_changed.rb +5 -0
  308. data/db/migrate/20130326135738_user_titles.rb +5 -0
  309. data/lib/droom.rb +189 -22
  310. data/lib/droom/engine.rb +6 -1
  311. data/lib/droom/folders.rb +106 -0
  312. data/lib/droom/lazy_hash.rb +73 -0
  313. data/lib/droom/{helpers.rb → model_helpers.rb} +1 -1
  314. data/lib/droom/monkeys.rb +21 -2
  315. data/lib/droom/routing.rb +13 -0
  316. data/lib/droom/searchability.rb +25 -0
  317. data/lib/droom/taggability.rb +60 -0
  318. data/lib/droom/title_case.rb +101 -0
  319. data/lib/droom/user_config.rb +67 -0
  320. data/lib/droom/validators.rb +6 -0
  321. data/lib/droom/version.rb +1 -1
  322. data/lib/generators/droom/install/templates/droom_initializer.rb +0 -1
  323. data/lib/tasks/cucumber.rake +65 -0
  324. data/spec/datasets/calendar_events_dataset.rb +44 -0
  325. data/spec/datasets/calendar_pages_dataset.rb +8 -0
  326. data/spec/datasets/calendar_sites_dataset.rb +6 -0
  327. data/spec/datasets/calendars_dataset.rb +34 -0
  328. data/spec/datasets/documents_dataset.rb +28 -0
  329. data/spec/datasets/recurrence_dataset.rb +7 -0
  330. data/spec/dummy/README.rdoc +261 -0
  331. data/spec/dummy/Rakefile +7 -0
  332. data/spec/dummy/app/assets/javascripts/application.js +15 -0
  333. data/spec/dummy/app/assets/stylesheets/application.css +13 -0
  334. data/spec/dummy/app/controllers/application_controller.rb +3 -0
  335. data/spec/dummy/app/helpers/application_helper.rb +2 -0
  336. data/spec/dummy/app/views/layouts/application.html.erb +14 -0
  337. data/spec/dummy/config.ru +4 -0
  338. data/spec/dummy/config/application.rb +65 -0
  339. data/spec/dummy/config/boot.rb +10 -0
  340. data/spec/dummy/config/database.yml +21 -0
  341. data/spec/dummy/config/environment.rb +5 -0
  342. data/spec/dummy/config/environments/development.rb +38 -0
  343. data/spec/dummy/config/environments/production.rb +67 -0
  344. data/spec/dummy/config/environments/test.rb +38 -0
  345. data/spec/dummy/config/initializers/backtrace_silencers.rb +7 -0
  346. data/spec/dummy/config/initializers/inflections.rb +15 -0
  347. data/spec/dummy/config/initializers/mime_types.rb +5 -0
  348. data/spec/dummy/config/initializers/secret_token.rb +7 -0
  349. data/spec/dummy/config/initializers/session_store.rb +8 -0
  350. data/spec/dummy/config/initializers/wrap_parameters.rb +14 -0
  351. data/spec/dummy/config/locales/en.yml +7 -0
  352. data/spec/dummy/config/routes.rb +3 -0
  353. data/spec/dummy/config/sunspot.yml +17 -0
  354. data/spec/dummy/db/migrate/20120911070124_create_droom_data.droom.rb +135 -0
  355. data/spec/dummy/db/migrate/20120921094604_agenda_sections.droom.rb +14 -0
  356. data/spec/dummy/db/migrate/20120921094605_add_postal_address_to_people.droom.rb +11 -0
  357. data/spec/dummy/db/migrate/20121102064845_give_groups_descriptions.droom.rb +6 -0
  358. data/spec/dummy/db/migrate/20121102064846_more_names.droom.rb +6 -0
  359. data/spec/dummy/db/migrate/20121102064847_event_agenda_sections.droom.rb +14 -0
  360. data/spec/dummy/db/migrate/20121102064848_create_group_invitations.droom.rb +11 -0
  361. data/spec/dummy/db/migrate/20121102064849_give_people_positions.droom.rb +6 -0
  362. data/spec/dummy/db/migrate/20121102064850_help_pages.droom.rb +14 -0
  363. data/spec/dummy/db/migrate/20121102064851_category_slugs.droom.rb +6 -0
  364. data/spec/dummy/db/migrate/20121102064852_document_links.droom.rb +15 -0
  365. data/spec/dummy/db/migrate/20121102064853_people_visibility.droom.rb +8 -0
  366. data/spec/dummy/db/migrate/20121102094820_shy_people.droom.rb +6 -0
  367. data/spec/dummy/db/migrate/20121102095927_visibility_defaults.droom.rb +10 -0
  368. data/spec/dummy/db/migrate/20130121122352_tags.droom.rb +19 -0
  369. data/spec/dummy/db/migrate/20130121122353_dropbox.droom.rb +10 -0
  370. data/spec/dummy/db/migrate/20130121122354_folders.droom.rb +48 -0
  371. data/spec/dummy/db/migrate/20130128142902_memberships_expire.droom.rb +6 -0
  372. data/spec/dummy/db/migrate/20130128142903_give_documents_extracted_text.droom.rb +6 -0
  373. data/spec/dummy/db/migrate/20130128142904_preferences.droom.rb +11 -0
  374. data/spec/dummy/db/migrate/20130128142905_users_in_droom.droom.rb +59 -0
  375. data/spec/dummy/db/migrate/20130130120631_folder_ancestry_to_parents.droom.rb +8 -0
  376. data/spec/dummy/db/migrate/20130201103737_mobile_phones.droom.rb +8 -0
  377. data/spec/dummy/db/migrate/20130201103738_mailing_lists.droom.rb +38 -0
  378. data/spec/dummy/db/schema.rb +327 -0
  379. data/spec/dummy/log/sunspot-solr-test.log.1 +222 -0
  380. data/spec/dummy/public/404.html +26 -0
  381. data/spec/dummy/public/422.html +26 -0
  382. data/spec/dummy/public/500.html +25 -0
  383. data/spec/dummy/public/favicon.ico +0 -0
  384. data/spec/dummy/public/system/droom/documents/files/000/000/001/original/frog.png +0 -0
  385. data/spec/dummy/public/system/droom/documents/files/000/000/001/original/rat.png +0 -0
  386. data/spec/dummy/script/rails +6 -0
  387. data/spec/dummy/solr/conf/admin-extra.html +31 -0
  388. data/spec/dummy/solr/conf/elevate.xml +36 -0
  389. data/spec/dummy/solr/conf/mapping-ISOLatin1Accent.txt +246 -0
  390. data/spec/dummy/solr/conf/protwords.txt +21 -0
  391. data/spec/dummy/solr/conf/schema.xml +238 -0
  392. data/spec/dummy/solr/conf/scripts.conf +24 -0
  393. data/spec/dummy/solr/conf/solrconfig.xml +934 -0
  394. data/spec/dummy/solr/conf/spellings.txt +2 -0
  395. data/spec/dummy/solr/conf/stopwords.txt +58 -0
  396. data/spec/dummy/solr/conf/synonyms.txt +31 -0
  397. data/spec/dummy/solr/data/development/index/segments.gen +0 -0
  398. data/spec/dummy/solr/data/development/index/segments_1 +0 -0
  399. data/spec/dummy/solr/data/development/spellchecker/segments.gen +0 -0
  400. data/spec/dummy/solr/data/development/spellchecker/segments_1 +0 -0
  401. data/spec/dummy/solr/data/test/index/segments.gen +0 -0
  402. data/spec/dummy/solr/data/test/index/segments_3nu +0 -0
  403. data/spec/dummy/solr/data/test/spellchecker/segments.gen +0 -0
  404. data/spec/dummy/solr/data/test/spellchecker/segments_1 +0 -0
  405. data/spec/dummy/webdav/1/group/rat.png +0 -0
  406. data/spec/dummy/webdav/1/unattached/rat.png +0 -0
  407. data/spec/dummy/webdav/group/rat.png +0 -0
  408. data/spec/dummy/webdav/unattached/rat.png +0 -0
  409. data/spec/dummy/webdav/unattached/rat_v1.png +0 -0
  410. data/spec/factories/agenda_categories.rb +5 -0
  411. data/spec/factories/categories.rb +5 -0
  412. data/spec/factories/documents.rb +16 -0
  413. data/spec/factories/events.rb +41 -0
  414. data/spec/factories/folders.rb +5 -0
  415. data/spec/factories/groups.rb +6 -0
  416. data/spec/factories/memberships.rb +5 -0
  417. data/spec/factories/people.rb +16 -0
  418. data/spec/factories/recurrence_rules.rb +25 -0
  419. data/spec/factories/user.rb +6 -0
  420. data/spec/fixtures/dummy.ics +59 -0
  421. data/spec/fixtures/images/frog.png +0 -0
  422. data/spec/fixtures/images/rat.png +0 -0
  423. data/spec/fixtures/ny.ics +36 -0
  424. data/spec/lib/droom/folders_spec.rb +46 -0
  425. data/spec/lib/droom/lazy_hash_spec.rb +33 -0
  426. data/spec/models/droom/agenda_category_spec.rb +15 -0
  427. data/spec/models/droom/document_spec.rb +76 -0
  428. data/spec/models/droom/event_spec.rb +154 -0
  429. data/spec/models/droom/folder_spec.rb +5 -0
  430. data/spec/models/droom/ical_spec.rb +62 -0
  431. data/spec/models/droom/mailing_list_membership_spec.rb +81 -0
  432. data/spec/models/droom/membership_spec.rb +22 -0
  433. data/spec/models/droom/person_spec.rb +72 -0
  434. data/spec/models/droom/recurrence_rule_spec.rb +81 -0
  435. data/spec/models/droom/user_spec.rb +27 -0
  436. data/spec/models/droom/visibility_spec.rb +6 -0
  437. data/spec/spec_helper.rb +119 -0
  438. data/spec/support/matchers/content_type_matcher.rb +17 -0
  439. metadata +591 -36
  440. data/app/assets/javascripts/droom/calendar.js.coffee +0 -121
  441. data/app/assets/javascripts/droom/drag_sort.js.coffee +0 -22
  442. data/app/assets/javascripts/droom/forms.js.coffee +0 -746
  443. data/app/assets/javascripts/droom/sort.js.coffee +0 -126
  444. data/app/assets/javascripts/droom/suggester.js.coffee +0 -230
  445. data/app/controllers/droom/document_attachments_controller.rb +0 -19
  446. data/app/models/droom/document_link.rb +0 -31
  447. data/app/models/droom/personal_document.rb +0 -98
  448. data/app/views/droom/dashboard/_marginalia.html.haml +0 -3
  449. data/app/views/droom/dashboard/_my_future_events.html.haml +0 -9
  450. data/app/views/droom/dashboard/_my_group_documents.html.haml +0 -6
  451. data/app/views/droom/dashboard/_my_past_events.haml +0 -6
  452. data/app/views/droom/documents/_event_document_form.html.haml +0 -15
  453. data/app/views/droom/errors/bang.html.haml +0 -12
  454. data/app/views/droom/errors/not_allowed.html.haml +0 -12
  455. data/app/views/droom/errors/not_found.html.haml +0 -12
  456. data/app/views/droom/events/_attachment.html.haml +0 -1
  457. data/app/views/droom/events/_attachment_list.html.haml +0 -4
  458. data/app/views/droom/invitations/_attending_people.html.haml +0 -8
  459. data/config/initializers/dav.rb +0 -2
@@ -5,42 +5,8 @@ module Droom
5
5
  belongs_to :document
6
6
  belongs_to :attachee, :polymorphic => true
7
7
  belongs_to :category
8
- belongs_to :created_by, :class_name => "User"
8
+ belongs_to :created_by, :class_name => "Droom::User"
9
9
 
10
- has_many :document_links, :dependent => :destroy
11
- has_many :people, :through => :document_links
12
-
13
- after_destroy :remove_private_document_if_unattached
14
- after_create :link_people
15
-
16
- default_scope order("(CASE WHEN droom_document_attachments.category_id IS NULL THEN 0 ELSE 1 END), droom_documents.updated_at ASC, droom_documents.created_at ASC").includes(:document)
17
-
18
- scope :unfiled, where("category_id IS NULL")
19
-
20
- scope :attached_to, lambda { |attachee|
21
- where(["droom_document_attachments.attachee_type = :class AND droom_document_attachments.attachee_id = :id", :class => attachee.class.to_s, :id => attachee.id])
22
- }
23
-
24
- scope :to_event, lambda { |event|
25
- where(["droom_document_attachments.attachee_type = 'Droom::Event' AND droom_document_attachments.attachee_id = ?", event.id])
26
- }
27
-
28
- scope :to_group, lambda { |group|
29
- where(["droom_document_attachments.attachee_type = 'Droom::Group' AND droom_document_attachments.attachee_id = ?", group.id])
30
- }
31
-
32
- scope :to_events, lambda { |events|
33
- placeholders = events.map{'?'}.join(',')
34
- ids = events.map(&:id)
35
- where(["droom_document_attachments.attachee_type = 'Droom::Event' AND droom_document_attachments.attachee_id IN (#{placeholders})", *ids])
36
- }
37
-
38
- scope :to_groups, lambda { |groups|
39
- placeholders = groups.map{'?'}.join(',')
40
- ids = groups.map(&:id)
41
- where(["droom_document_attachments.attachee_type = 'Droom::Group' AND droom_document_attachments.attachee_id IN (#{placeholders})", *ids])
42
- }
43
-
44
10
  def slug
45
11
  if attachee
46
12
  attachee.slug
@@ -53,19 +19,19 @@ module Droom
53
19
  category ? category.name : "uncategorised"
54
20
  end
55
21
 
56
- protected
57
-
58
- def remove_private_document_if_unattached
59
- unless document.public? || document.document_attachments.count > 0
60
- document.destroy
22
+ def move_document_to_folder
23
+ recipient = if category
24
+ # attachee will be an event
25
+ attachee.find_or_create_agenda_category(category)
26
+ else
27
+ attachee
28
+ end
29
+ if document
30
+ document.folder = nil
31
+ recipient.receive_document(document)
32
+ document.save
61
33
  end
62
34
  end
63
-
64
- # Upon creation we create document links to all the people who are newly entitled to see the document.
65
- # Deletion takes care of itself, as document_links are :dependent => :destroy.
66
- #
67
- def link_people
68
- people << attachee.people if attachee
69
- end
35
+
70
36
  end
71
37
  end
@@ -0,0 +1,41 @@
1
+ module Droom
2
+ class DropboxDocument < ActiveRecord::Base
3
+ attr_accessible :person_id
4
+
5
+ belongs_to :person
6
+ belongs_to :document
7
+
8
+ validates_uniqueness_of :person_id, :scope => :document_id
9
+
10
+ after_save :get_file
11
+
12
+ after_destroy :remove_dropbox_document
13
+
14
+ def get_file
15
+ bucket = Droom.aws_bucket
16
+ file = bucket.files.get(document.file.path)
17
+ dropbox_client.put_file(document.full_path, file)
18
+ end
19
+
20
+ def update
21
+ get_file
22
+ end
23
+
24
+ def dropbox_client
25
+ person.user.dropbox_client
26
+ end
27
+
28
+ def deleted=(boolean)
29
+ deleted = boolean
30
+ end
31
+
32
+ def remove_dropbox_document
33
+ dropbox_client.file_delete(document.full_path)
34
+ end
35
+
36
+ def changed?
37
+ modified?# || dropbox_client.get_file_and_metadata(document.full_path)#dropbox file has revisions
38
+ end
39
+
40
+ end
41
+ end
@@ -0,0 +1,29 @@
1
+ module Droom
2
+ class DropboxToken < ActiveRecord::Base
3
+ attr_accessible :access_token, :access_token_secret, :created_by
4
+ belongs_to :created_by, :class_name => "Droom::User"
5
+ after_create :delete_previous
6
+
7
+ scope :by_date, order("created_at DESC")
8
+ scope :other_than, lambda { |token| where "id <> ?", token.id }
9
+
10
+ def dropbox_session
11
+ unless @dbsession
12
+ @dbsession = DropboxSession.new(Droom.dropbox_app_key, Droom.dropbox_app_secret)
13
+ @dbsession.set_access_token(access_token, access_token_secret)
14
+ end
15
+ @dbsession
16
+ end
17
+
18
+ def dropbox_client
19
+ @dbclient ||= DropboxClient.new(dropbox_session)
20
+ end
21
+
22
+ protected
23
+
24
+ def delete_previous
25
+ self.created_by.dropbox_tokens.other_than(self).destroy_all
26
+ end
27
+
28
+ end
29
+ end
@@ -1,14 +1,15 @@
1
1
  require 'open-uri'
2
- require 'zip/zip'
3
2
  require 'uuidtools'
4
3
  require 'chronic'
5
4
  require 'ri_cal'
6
5
 
7
6
  module Droom
8
7
  class Event < ActiveRecord::Base
9
- attr_accessible :start, :finish, :name, :description, :event_set_id, :created_by_id, :uuid, :all_day, :master_id, :url, :start_date, :start_time, :finish_date, :finish_time, :venue, :private, :public, :venue_name
8
+ attr_accessible :start, :finish, :name, :description, :event_set_id, :created_by_id, :uuid, :all_day, :master_id, :url, :start_date, :start_time, :finish_date, :finish_time, :venue, :venue_id, :private, :public, :venue_name, :calendar_id
10
9
 
11
- belongs_to :created_by, :class_name => 'User'
10
+ belongs_to :created_by, :class_name => "Droom::User"
11
+
12
+ has_folder #... and subfolders via agenda_categories
12
13
 
13
14
  has_many :invitations, :dependent => :destroy
14
15
  has_many :people, :through => :invitations
@@ -16,18 +17,19 @@ module Droom
16
17
  has_many :group_invitations, :dependent => :destroy
17
18
  has_many :groups, :through => :group_invitations
18
19
 
19
- has_many :document_attachments, :as => :attachee, :dependent => :destroy
20
- has_many :documents, :through => :document_attachments
21
-
22
20
  has_many :agenda_categories, :dependent => :destroy
23
21
  has_many :categories, :through => :agenda_categories
24
-
22
+
25
23
  belongs_to :venue
26
24
  accepts_nested_attributes_for :venue
27
25
 
28
26
  belongs_to :event_set
29
27
  accepts_nested_attributes_for :event_set
30
-
28
+
29
+ belongs_to :calendar
30
+
31
+ has_many :scraps
32
+
31
33
  belongs_to :master, :class_name => 'Event'
32
34
  has_many :occurrences, :class_name => 'Event', :foreign_key => 'master_id', :dependent => :destroy
33
35
  has_many :recurrence_rules, :dependent => :destroy, :conditions => {:active => true}
@@ -39,20 +41,42 @@ module Droom
39
41
  validates :name, :presence => true
40
42
 
41
43
  before_validation :set_uuid
42
- before_save :check_slug
44
+ before_save :ensure_slug
43
45
  after_save :update_occurrences
44
-
46
+ after_save :index
47
+
45
48
  scope :primary, where("master_id IS NULL")
46
49
  scope :recurrent, where(:conditions => "master_id IS NOT NULL")
47
- default_scope order('start ASC').includes(:venue)
48
-
50
+
51
+ searchable do
52
+ text :name, :boost => 10, :stored => true
53
+ text :description, :stored => true
54
+ end
55
+
56
+ handle_asynchronously :solr_index
57
+
58
+ def self.highlight_fields
59
+ [:name, :description]
60
+ end
61
+
49
62
  ## Event retrieval in various ways
50
63
  #
64
+ # Events differ from other models in that they are visible to all unless marked 'private'.
65
+ # The documents attached to them are only visible to all if marked 'public'.
66
+ #
67
+ scope :all_private, where("private = 1")
68
+ scope :not_private, where("private <> 1 OR private IS NULL")
69
+ scope :all_public, where("public = 1 AND private <> 1 OR private IS NULL")
70
+ scope :not_public, where("public <> 1 OR private = 1)")
71
+
72
+ # events are visible by default. Private events are made invisible except to the people
73
+ # invited to them.
74
+
51
75
  scope :visible_to, lambda { |person|
52
76
  if person
53
77
  select('droom_events.*')
54
78
  .joins('LEFT OUTER JOIN droom_invitations ON droom_events.id = droom_invitations.event_id')
55
- .where(["(droom_events.public = 1 OR droom_invitations.person_id = ?)", person.id])
79
+ .where(["(NOT(droom_events.private = 1) OR droom_invitations.person_id = ?)", person.id])
56
80
  .group('droom_events.id')
57
81
  else
58
82
  all_public
@@ -62,25 +86,29 @@ module Droom
62
86
  scope :after, lambda { |datetime| # datetime. eg calendar.occurrences.after(Time.now)
63
87
  where(['start > ?', datetime])
64
88
  }
65
-
89
+
66
90
  scope :before, lambda { |datetime| # datetime. eg calendar.occurrences.before(Time.now)
67
91
  where(['start < :date AND (finish IS NULL or finish < :date)', :date => datetime])
68
92
  }
69
-
93
+
70
94
  scope :between, lambda { |start, finish| # datetimable objects. eg. Event.between(reader.last_login, Time.now)
71
95
  where(['start > :start AND start < :finish AND (finish IS NULL or finish < :finish)', :start => start, :finish => finish])
72
96
  }
73
-
97
+
74
98
  scope :future_and_current, lambda {
75
99
  where(['(finish > :now) OR (finish IS NULL AND start > :now)', :now => Time.now])
76
100
  }
77
-
78
- scope :unfinished, lambda { |start| # datetimable object.
79
- where(['start < :start AND finish > :start', :start => start])
101
+
102
+ scope :finished, lambda {
103
+ where(['(finish < :now) OR (finish IS NULL AND start < :now)', :now => Time.now])
80
104
  }
81
105
 
106
+ scope :unbegun, lambda {
107
+ where(['start > :now', :now => Time.now])
108
+ }
109
+
82
110
  scope :by_finish, order("finish ASC")
83
-
111
+
84
112
  scope :coincident_with, lambda { |start, finish| # datetimable objects.
85
113
  where(['(start < :finish AND finish > :start) OR (finish IS NULL AND start > :start AND start < :finish)', {:start => start, :finish => finish}])
86
114
  }
@@ -88,37 +116,31 @@ module Droom
88
116
  scope :limited_to, lambda { |limit|
89
117
  limit(limit)
90
118
  }
91
-
119
+
92
120
  scope :at_venue, lambda { |venue| # EventVenue object
93
121
  where(["venue_id = ?", venue.id])
94
122
  }
95
-
123
+
96
124
  scope :except_these_uuids, lambda { |uuids| # array of uuid strings
97
125
  placeholders = uuids.map{'?'}.join(',')
98
126
  where(["uuid NOT IN (#{placeholders})", *uuids])
99
127
  }
100
-
128
+
101
129
  scope :without_invitations_to, lambda { |person| # Person object
102
130
  select("droom_events.*")
103
131
  .joins("LEFT OUTER JOIN droom_invitations ON droom_events.id = droom_invitations.event_id AND droom_invitations.person_id = #{sanitize(person.id)}")
104
132
  .group("droom_events.id")
105
133
  .having("COUNT(droom_invitations.id) = 0")
106
134
  }
107
-
135
+
108
136
  scope :with_documents,
109
137
  select("droom_events.*")
110
138
  .joins("INNER JOIN droom_document_attachments ON droom_events.id = droom_document_attachments.attachee_id AND droom_document_attachments.attachee_type = 'Droom::Event'")
111
139
  .group("droom_events.id")
112
-
113
-
114
- scope :all_private, where("private = 1 OR private = 't'")
115
- scope :not_private, where("private = 0 OR private = 'f'")
116
- scope :all_public, where("public = 1 OR public = 't'")
117
- scope :not_public, where("public = 0 OR public = 'f'")
118
140
 
119
- scope :name_matching, lambda { |fragment|
141
+ scope :matching, lambda { |fragment|
120
142
  fragment = "%#{fragment}%"
121
- where('droom_events.name like ?', fragment)
143
+ where('droom_events.name like :f OR droom_events.description like :f', :f => fragment)
122
144
  }
123
145
 
124
146
  # All of these class methods also return scopes.
@@ -162,11 +184,11 @@ module Droom
162
184
  end
163
185
 
164
186
  def self.future
165
- after(Time.now)
187
+ unbegun.order('start ASC')
166
188
  end
167
189
 
168
190
  def self.past
169
- before(Time.now)
191
+ finished.order('start DESC')
170
192
  end
171
193
 
172
194
  ## Instance methods
@@ -174,15 +196,11 @@ module Droom
174
196
  def invite(person)
175
197
  self.people << person
176
198
  end
177
-
199
+
178
200
  def attach(doc)
179
201
  self.documents << doc
180
202
  end
181
203
 
182
- def identifier
183
- 'event'
184
- end
185
-
186
204
  # We store the start and end points of the event as a single DateTime value to make comparison simple.
187
205
  # The setters for date and time are overridden to pass strings through chronic's natural language parser
188
206
  # and to treat numbers as epoch seconds. These should all work as you'd expect:
@@ -235,15 +253,18 @@ module Droom
235
253
  def start_time=(value)
236
254
  self.start = (start_date || Date.today).to_time + parse_date(value).seconds_since_midnight
237
255
  end
238
-
256
+
239
257
  def start_date=(value)
240
258
  self.start = parse_date(value).to_date# + start_time
241
259
  end
242
-
260
+
243
261
  def finish_time=(value)
244
- self.finish = (finish_date || start_date || Date.today).to_time + parse_date(value).seconds_since_midnight
262
+ if value && !value.blank?
263
+ time_portion = parse_date(value).seconds_since_midnight
264
+ self.finish = (finish_date || start_date || Date.today).to_time + time_portion
265
+ end
245
266
  end
246
-
267
+
247
268
  def finish_date=(value)
248
269
  self.finish = parse_date(value).to_date# + finish_time
249
270
  end
@@ -259,57 +280,57 @@ module Droom
259
280
  def venue_name
260
281
  venue.name if venue
261
282
  end
262
-
283
+
263
284
  def venue_name=(name)
264
285
  self.venue = Droom::Venue.find_or_create_by_name(name)
265
286
  end
266
287
 
267
- # Agenda sections are global, and we don't want to have to manage the extra workload of associating a section with an event.
268
- # This call retrieves all the agenda sections that are associated with any of our document attachments, and is suitable for looping
269
- # on a template to display attachments per section.
270
- #
271
- def agenda_sections
272
- Droom::AgendaSection.associated_with_event(self)
288
+ def find_or_create_agenda_category(category)
289
+ agenda_categories.find_or_create_by_category_id(category.id)
273
290
  end
274
-
275
- # and this sorts our attachment list into agenda section buckets so that we don't have to go back to the database for each section.
276
- def attachments_by_category
277
- cats = {}
278
- document_attachments.each_with_object({}) do |att, hash|
279
- key = att.category_name
280
- cats[key] ||= []
281
- cats[key].push(att)
282
- end
283
- categories.each do |category|
284
- key = category.name
285
- cats[key] ||= []
286
- end
287
- cats
288
- end
289
-
291
+
290
292
  def categories_for_selection
291
293
  cats = categories.map{|c| [c.name, c.id] }
292
294
  cats.unshift(['', ''])
293
295
  cats
294
296
  end
295
-
297
+
298
+ def attended_by?(person)
299
+ person && person.invited_to?(self)
300
+ end
301
+
296
302
  def visible_to?(user_or_person)
303
+ return true if self.public?
304
+ return false if self.private?# || Droom.events_private_by_default?
305
+ return true
306
+ end
307
+
308
+ def detail_visible_to?(user_or_person)
297
309
  return true if self.public?
298
310
  return false unless user_or_person
299
311
  return true if user_or_person.admin?
312
+ return true if user_or_person.privileged?
300
313
  return true if user_or_person.person.invited_to?(self)
301
314
  return false if self.private?
302
315
  return true
303
316
  end
317
+
318
+ def has_people?
319
+ invitations.any?
320
+ end
321
+
322
+ def has_documents?
323
+ all_documents.any?
324
+ end
304
325
 
305
326
  def one_day?
306
327
  all_day? && within_day?
307
328
  end
308
-
329
+
309
330
  def within_day?
310
331
  (!finish || start.to.jd == finish.to.jd || finish == start + 1.day)
311
332
  end
312
-
333
+
313
334
  def continuing?
314
335
  finish && start < Time.now && finish > Time.now
315
336
  end
@@ -317,29 +338,25 @@ module Droom
317
338
  def finished?
318
339
  start < Time.now && (!finish || finish < Time.now)
319
340
  end
320
-
341
+
321
342
  def recurs?
322
343
  master || occurrences.any?
323
344
  end
324
-
345
+
325
346
  def recurrence
326
347
  recurrence_rules.first.to_s
327
348
  end
328
-
349
+
329
350
  def add_recurrence(rule)
330
351
  self.recurrence_rules << Droom::RecurrenceRule.from(rule)
331
352
  end
332
353
 
333
- def documents_zipped
334
- if self.documents.any?
335
- tempfile = Tempfile.new("droom-temp-#{slug}-#{Time.now}.zip")
336
- Zip::ZipOutputStream.open(tempfile.path) do |z|
337
- self.documents.each do |doc|
338
- z.add(doc.file_file_name, open(doc.file.url))
339
- end
340
- end
341
- tempfile
342
- end
354
+ def url_with_protocol
355
+ url =~ /^https?:\/\// ? url : "http://#{url}"
356
+ end
357
+
358
+ def url_without_protocol
359
+ url.sub(/^https?:\/\//, '')
343
360
  end
344
361
 
345
362
  def to_rical
@@ -349,28 +366,46 @@ module Droom
349
366
  cal_event.description = description if description
350
367
  cal_event.dtstart = (all_day? ? start_date : start) if start
351
368
  cal_event.dtend = (all_day? ? finish_date : finish) if finish
352
- cal_event.url = url if url
369
+ cal_event.url = url_with_protocol if url
353
370
  cal_event.rrules = recurrence_rules.map(&:to_rical) if recurrence_rules.any?
354
371
  cal_event.location = venue.name if venue
355
372
  end
356
373
  end
357
-
374
+
358
375
  def to_ics
359
376
  to_rical.to_s
360
377
  end
361
-
378
+
362
379
  def as_json(options={})
363
380
  json = super
364
381
  json[:datestring] = I18n.l start, :format => :natural_with_date
365
382
  json
366
383
  end
367
384
 
385
+ def as_suggestion
386
+ {
387
+ :type => 'event',
388
+ :prompt => name,
389
+ :value => name,
390
+ :id => id
391
+ }
392
+ end
393
+
394
+ def as_search_result
395
+ {
396
+ :type => 'event',
397
+ :prompt => name,
398
+ :value => name,
399
+ :id => id
400
+ }
401
+ end
402
+
368
403
  protected
369
-
370
- def check_slug
404
+
405
+ def ensure_slug
371
406
  ensure_presence_and_uniqueness_of(:slug, "#{start.strftime("%Y %m %d")} #{name}".parameterize)
372
407
  end
373
-
408
+
374
409
  def set_uuid
375
410
  self.uuid = UUIDTools::UUID.timestamp_create.to_s if uuid.blank?
376
411
  end
@@ -383,7 +418,7 @@ module Droom
383
418
  to_rical.occurrences(:before => recurrence_horizon).each do |occ|
384
419
  occurrences.create!({
385
420
  :name => self.name,
386
- :url => self.url,
421
+ :url => self.url_with_protocol,
387
422
  :description => self.description,
388
423
  :venue => self.venue,
389
424
  :start => occ.dtstart,
@@ -404,6 +439,6 @@ module Droom
404
439
  value
405
440
  end
406
441
  end
407
-
442
+
408
443
  end
409
444
  end