stay_commerce 0.1.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 (496) hide show
  1. checksums.yaml +7 -0
  2. data/MIT-LICENSE +20 -0
  3. data/README.md +53 -0
  4. data/Rakefile +8 -0
  5. data/app/assets/config/stay_manifest.js +1 -0
  6. data/app/assets/fonts/bootstrap-icons.woff +0 -0
  7. data/app/assets/fonts/bootstrap-icons.woff2 +0 -0
  8. data/app/assets/images/chevron-down.svg +3 -0
  9. data/app/assets/images/circle-fill.svg +3 -0
  10. data/app/assets/images/circle.svg +3 -0
  11. data/app/assets/images/plus-circle.svg +4 -0
  12. data/app/assets/images/save.svg +3 -0
  13. data/app/assets/images/store.svg +3 -0
  14. data/app/assets/javascripts/stay/admin/address.js +165 -0
  15. data/app/assets/javascripts/stay/admin/ckeditor.min.js +7 -0
  16. data/app/assets/javascripts/stay/admin/flatpickr.min.js +2 -0
  17. data/app/assets/javascripts/stay/admin/index.js +28 -0
  18. data/app/assets/javascripts/stay/admin/property.js +37 -0
  19. data/app/assets/javascripts/stay/admin/select2.min.js +2 -0
  20. data/app/assets/javascripts/stay/application.js +14 -0
  21. data/app/assets/javascripts/stay/bootstrap.bundle.min.js +7 -0
  22. data/app/assets/javascripts/stay/ckeditor.js +11 -0
  23. data/app/assets/javascripts/stay/custom.js +56 -0
  24. data/app/assets/javascripts/stay/jquery-ui.min.js +13 -0
  25. data/app/assets/javascripts/stay/jquery.min.js +2 -0
  26. data/app/assets/stylesheets/stay/admin/flatpickr.min.css +13 -0
  27. data/app/assets/stylesheets/stay/admin/index.css +100 -0
  28. data/app/assets/stylesheets/stay/admin/select2.min.css +1 -0
  29. data/app/assets/stylesheets/stay/application.css +24 -0
  30. data/app/assets/stylesheets/stay/badges.css +72 -0
  31. data/app/assets/stylesheets/stay/bootstrap-icons.min.css +5 -0
  32. data/app/assets/stylesheets/stay/bootstrap-icons_fix.css +5 -0
  33. data/app/assets/stylesheets/stay/common.css +283 -0
  34. data/app/assets/stylesheets/stay/jquery-ui.css +1311 -0
  35. data/app/assets/stylesheets/stay/webpixels.css +7 -0
  36. data/app/channels/chat_channel.rb +13 -0
  37. data/app/controllers/concerns/stay/booking_validations.rb +86 -0
  38. data/app/controllers/concerns/stay/stripe_concern.rb +72 -0
  39. data/app/controllers/stay/admin/addresses_controller.rb +76 -0
  40. data/app/controllers/stay/admin/amenities_controller.rb +52 -0
  41. data/app/controllers/stay/admin/amenity_categories_controller.rb +52 -0
  42. data/app/controllers/stay/admin/base_controller.rb +38 -0
  43. data/app/controllers/stay/admin/bed_types_controller.rb +51 -0
  44. data/app/controllers/stay/admin/bookings_controller.rb +54 -0
  45. data/app/controllers/stay/admin/cancellation_policies_controller.rb +51 -0
  46. data/app/controllers/stay/admin/chats_controller.rb +53 -0
  47. data/app/controllers/stay/admin/cities_controller.rb +66 -0
  48. data/app/controllers/stay/admin/confirmations_controller.rb +30 -0
  49. data/app/controllers/stay/admin/countries_controller.rb +53 -0
  50. data/app/controllers/stay/admin/dashboard_controller.rb +8 -0
  51. data/app/controllers/stay/admin/features_controller.rb +54 -0
  52. data/app/controllers/stay/admin/home_controller.rb +15 -0
  53. data/app/controllers/stay/admin/house_rules_controller.rb +51 -0
  54. data/app/controllers/stay/admin/messages_controller.rb +53 -0
  55. data/app/controllers/stay/admin/passwords_controller.rb +32 -0
  56. data/app/controllers/stay/admin/payment_methods_controller.rb +53 -0
  57. data/app/controllers/stay/admin/payments_controller.rb +63 -0
  58. data/app/controllers/stay/admin/properties_controller.rb +118 -0
  59. data/app/controllers/stay/admin/property_categories_controller.rb +51 -0
  60. data/app/controllers/stay/admin/property_types_controller.rb +51 -0
  61. data/app/controllers/stay/admin/registrations_controller.rb +19 -0
  62. data/app/controllers/stay/admin/reviews_Controller.rb +63 -0
  63. data/app/controllers/stay/admin/roles_controller.rb +54 -0
  64. data/app/controllers/stay/admin/room_amenities_controller.rb +43 -0
  65. data/app/controllers/stay/admin/room_types_controller.rb +58 -0
  66. data/app/controllers/stay/admin/rooms_controller.rb +62 -0
  67. data/app/controllers/stay/admin/sessions_controller.rb +29 -0
  68. data/app/controllers/stay/admin/states_controller.rb +68 -0
  69. data/app/controllers/stay/admin/stores_controller.rb +132 -0
  70. data/app/controllers/stay/admin/taxes_controller.rb +51 -0
  71. data/app/controllers/stay/admin/users_controller.rb +85 -0
  72. data/app/controllers/stay/api/v1/amenities_controller.rb +13 -0
  73. data/app/controllers/stay/api/v1/amenity_categories_controller.rb +13 -0
  74. data/app/controllers/stay/api/v1/bed_types_controller.rb +9 -0
  75. data/app/controllers/stay/api/v1/booking_queries_controller.rb +205 -0
  76. data/app/controllers/stay/api/v1/bookings_controller.rb +299 -0
  77. data/app/controllers/stay/api/v1/cancellation_policies_controller.rb +10 -0
  78. data/app/controllers/stay/api/v1/chats_controller.rb +116 -0
  79. data/app/controllers/stay/api/v1/credit_cards_controller.rb +62 -0
  80. data/app/controllers/stay/api/v1/features_controller.rb +21 -0
  81. data/app/controllers/stay/api/v1/house_rules_controller.rb +9 -0
  82. data/app/controllers/stay/api/v1/invoices_controller.rb +47 -0
  83. data/app/controllers/stay/api/v1/messages_controller.rb +144 -0
  84. data/app/controllers/stay/api/v1/payments_controller.rb +61 -0
  85. data/app/controllers/stay/api/v1/profiles_controller.rb +23 -0
  86. data/app/controllers/stay/api/v1/properties_controller.rb +233 -0
  87. data/app/controllers/stay/api/v1/property_categories_controller.rb +14 -0
  88. data/app/controllers/stay/api/v1/property_types_controller.rb +14 -0
  89. data/app/controllers/stay/api/v1/room_types_controller.rb +14 -0
  90. data/app/controllers/stay/api/v1/rooms_controller.rb +23 -0
  91. data/app/controllers/stay/api/v1/user_paypal_controller.rb +53 -0
  92. data/app/controllers/stay/api/v1/users_controller.rb +17 -0
  93. data/app/controllers/stay/application_controller.rb +44 -0
  94. data/app/controllers/stay/base_api_controller.rb +14 -0
  95. data/app/controllers/stay/bookings_controller.rb +29 -0
  96. data/app/controllers/stay/payments_controller.rb +50 -0
  97. data/app/controllers/stay/profiles_controller.rb +26 -0
  98. data/app/controllers/stay/properties_controller.rb +15 -0
  99. data/app/controllers/stay/rooms_controller.rb +22 -0
  100. data/app/controllers/stay/users/confirmations_controller.rb +30 -0
  101. data/app/controllers/stay/users/omniauth_callbacks_controller.rb +30 -0
  102. data/app/controllers/stay/users/passwords_controller.rb +51 -0
  103. data/app/controllers/stay/users/registrations_controller.rb +62 -0
  104. data/app/controllers/stay/users/sessions_controller.rb +27 -0
  105. data/app/controllers/stay/users/unlocks_controller.rb +30 -0
  106. data/app/helpers/stay/admin/cities_helper.rb +4 -0
  107. data/app/helpers/stay/admin/countries_helper.rb +4 -0
  108. data/app/helpers/stay/admin/states_helper.rb +4 -0
  109. data/app/helpers/stay/admin/stores_helper.rb +25 -0
  110. data/app/helpers/stay/application_helper.rb +63 -0
  111. data/app/helpers/stay/currency_helper.rb +34 -0
  112. data/app/helpers/stay/locale_helper.rb +107 -0
  113. data/app/jobs/stay/application_job.rb +4 -0
  114. data/app/mailers/stay/application_mailer.rb +6 -0
  115. data/app/mailers/stay/user_mailer.rb +13 -0
  116. data/app/models/concerns/stay/translatable_resource.rb +25 -0
  117. data/app/models/stay/additional_rule.rb +5 -0
  118. data/app/models/stay/address.rb +40 -0
  119. data/app/models/stay/amenity.rb +13 -0
  120. data/app/models/stay/amenity_category.rb +6 -0
  121. data/app/models/stay/application_record.rb +5 -0
  122. data/app/models/stay/bed_type.rb +7 -0
  123. data/app/models/stay/booking.rb +199 -0
  124. data/app/models/stay/booking_query.rb +23 -0
  125. data/app/models/stay/cancellation_policy.rb +6 -0
  126. data/app/models/stay/chat.rb +23 -0
  127. data/app/models/stay/city.rb +9 -0
  128. data/app/models/stay/country.rb +23 -0
  129. data/app/models/stay/credit_card.rb +6 -0
  130. data/app/models/stay/discount.rb +4 -0
  131. data/app/models/stay/expense.rb +4 -0
  132. data/app/models/stay/feature.rb +11 -0
  133. data/app/models/stay/house_rule.rb +4 -0
  134. data/app/models/stay/invoice.rb +23 -0
  135. data/app/models/stay/line_item.rb +7 -0
  136. data/app/models/stay/message.rb +30 -0
  137. data/app/models/stay/payment.rb +54 -0
  138. data/app/models/stay/payment_method.rb +13 -0
  139. data/app/models/stay/price.rb +18 -0
  140. data/app/models/stay/property.rb +243 -0
  141. data/app/models/stay/property_amenity.rb +6 -0
  142. data/app/models/stay/property_category.rb +6 -0
  143. data/app/models/stay/property_feature.rb +6 -0
  144. data/app/models/stay/property_house_rule.rb +6 -0
  145. data/app/models/stay/property_tax.rb +6 -0
  146. data/app/models/stay/property_type.rb +15 -0
  147. data/app/models/stay/review.rb +5 -0
  148. data/app/models/stay/role.rb +11 -0
  149. data/app/models/stay/role_user.rb +6 -0
  150. data/app/models/stay/room.rb +93 -0
  151. data/app/models/stay/room_amenity.rb +6 -0
  152. data/app/models/stay/room_feature.rb +6 -0
  153. data/app/models/stay/room_type.rb +7 -0
  154. data/app/models/stay/state.rb +13 -0
  155. data/app/models/stay/store.rb +139 -0
  156. data/app/models/stay/store_property.rb +9 -0
  157. data/app/models/stay/tax.rb +8 -0
  158. data/app/models/stay/user.rb +111 -0
  159. data/app/models/stay/user_paypal.rb +5 -0
  160. data/app/serializers/amenity_category_serializer.rb +13 -0
  161. data/app/serializers/amenity_serializer.rb +3 -0
  162. data/app/serializers/bed_type_serializer.rb +5 -0
  163. data/app/serializers/booking_query_serializer.rb +6 -0
  164. data/app/serializers/booking_serializer.rb +68 -0
  165. data/app/serializers/cancellation_policy_serializer.rb +3 -0
  166. data/app/serializers/chat_serializer.rb +63 -0
  167. data/app/serializers/credit_card_serializer.rb +7 -0
  168. data/app/serializers/house_rules_serializer.rb +3 -0
  169. data/app/serializers/invoice_serializer.rb +41 -0
  170. data/app/serializers/last_5_messages_serializer.rb +7 -0
  171. data/app/serializers/line_item_serializer.rb +6 -0
  172. data/app/serializers/message_serializer.rb +44 -0
  173. data/app/serializers/property_category_serializer.rb +7 -0
  174. data/app/serializers/property_feature_serializer.rb +5 -0
  175. data/app/serializers/property_listing_serializer.rb +13 -0
  176. data/app/serializers/property_serializer.rb +77 -0
  177. data/app/serializers/property_type_serializer.rb +7 -0
  178. data/app/serializers/room_serializer.rb +36 -0
  179. data/app/serializers/room_type_serializer.rb +5 -0
  180. data/app/serializers/user_listing_serializer.rb +23 -0
  181. data/app/serializers/user_serializer.rb +41 -0
  182. data/app/services/stay/bookings/create_booking_service.rb +49 -0
  183. data/app/services/stay/bookings/create_line_item_service.rb +15 -0
  184. data/app/services/stay/bookings/existing_booking_service.rb +50 -0
  185. data/app/services/stay/chat/chat_messaging_service.rb +82 -0
  186. data/app/services/stay/chat/query_messaging_service.rb +56 -0
  187. data/app/services/stay/seeds/all.rb +27 -0
  188. data/app/services/stay/seeds/cancellation_policy.rb +21 -0
  189. data/app/services/stay/seeds/countries.rb +33 -0
  190. data/app/services/stay/seeds/roles.rb +9 -0
  191. data/app/services/stay/seeds/states.rb +63 -0
  192. data/app/services/stay/seeds/stores.rb +34 -0
  193. data/app/views/devise/mailer/reset_password_instructions.html.rb +10 -0
  194. data/app/views/kaminari/_first_page.html.erb +3 -0
  195. data/app/views/kaminari/_gap.html.erb +3 -0
  196. data/app/views/kaminari/_last_page.html.erb +3 -0
  197. data/app/views/kaminari/_next_page.html.erb +3 -0
  198. data/app/views/kaminari/_page.html.erb +9 -0
  199. data/app/views/kaminari/_paginator.html.erb +17 -0
  200. data/app/views/kaminari/_prev_page.html.erb +3 -0
  201. data/app/views/layouts/stay/admin.html.erb +45 -0
  202. data/app/views/layouts/stay/application.html.erb +34 -0
  203. data/app/views/stay/admin/addresses/_form.html.erb +49 -0
  204. data/app/views/stay/admin/addresses/edit.html.erb +5 -0
  205. data/app/views/stay/admin/addresses/index.html.erb +68 -0
  206. data/app/views/stay/admin/addresses/new.html.erb +5 -0
  207. data/app/views/stay/admin/addresses/show.html.erb +40 -0
  208. data/app/views/stay/admin/amenities/_form.html.erb +38 -0
  209. data/app/views/stay/admin/amenities/edit.html.erb +14 -0
  210. data/app/views/stay/admin/amenities/index.html.erb +58 -0
  211. data/app/views/stay/admin/amenities/new.html.erb +14 -0
  212. data/app/views/stay/admin/amenities/show.html.erb +19 -0
  213. data/app/views/stay/admin/amenity_categories/_form.html.erb +29 -0
  214. data/app/views/stay/admin/amenity_categories/edit.html.erb +14 -0
  215. data/app/views/stay/admin/amenity_categories/index.html.erb +53 -0
  216. data/app/views/stay/admin/amenity_categories/new.html.erb +14 -0
  217. data/app/views/stay/admin/amenity_categories/show.html.erb +18 -0
  218. data/app/views/stay/admin/bed_types/_form.html.erb +29 -0
  219. data/app/views/stay/admin/bed_types/edit.html.erb +14 -0
  220. data/app/views/stay/admin/bed_types/index.html.erb +56 -0
  221. data/app/views/stay/admin/bed_types/new.html.erb +14 -0
  222. data/app/views/stay/admin/bed_types/show.html.erb +0 -0
  223. data/app/views/stay/admin/bookings/_booking_invoice.html.erb +37 -0
  224. data/app/views/stay/admin/bookings/_booking_summary.html.erb +61 -0
  225. data/app/views/stay/admin/bookings/_form.html.erb +59 -0
  226. data/app/views/stay/admin/bookings/edit.html.erb +14 -0
  227. data/app/views/stay/admin/bookings/index.html.erb +74 -0
  228. data/app/views/stay/admin/bookings/new.html.erb +14 -0
  229. data/app/views/stay/admin/bookings/show.html.erb +80 -0
  230. data/app/views/stay/admin/cancellation_policies/_form.html.erb +38 -0
  231. data/app/views/stay/admin/cancellation_policies/edit.html.erb +14 -0
  232. data/app/views/stay/admin/cancellation_policies/index.html.erb +58 -0
  233. data/app/views/stay/admin/cancellation_policies/new.html.erb +14 -0
  234. data/app/views/stay/admin/cancellation_policies/show.html.erb +0 -0
  235. data/app/views/stay/admin/chats/_form.html.erb +31 -0
  236. data/app/views/stay/admin/chats/edit.html.erb +5 -0
  237. data/app/views/stay/admin/chats/index.html.erb +58 -0
  238. data/app/views/stay/admin/chats/new.html.erb +5 -0
  239. data/app/views/stay/admin/chats/show.html.erb +19 -0
  240. data/app/views/stay/admin/cities/_form.html.erb +30 -0
  241. data/app/views/stay/admin/cities/edit.html.erb +14 -0
  242. data/app/views/stay/admin/cities/index.html.erb +62 -0
  243. data/app/views/stay/admin/cities/new.html.erb +14 -0
  244. data/app/views/stay/admin/countries/_form.html.erb +64 -0
  245. data/app/views/stay/admin/countries/edit.html.erb +14 -0
  246. data/app/views/stay/admin/countries/index.html.erb +62 -0
  247. data/app/views/stay/admin/countries/new.html.erb +14 -0
  248. data/app/views/stay/admin/countries/show.html.erb +23 -0
  249. data/app/views/stay/admin/dashboard/index.html.erb +1 -0
  250. data/app/views/stay/admin/features/_form.html.erb +38 -0
  251. data/app/views/stay/admin/features/edit.html.erb +14 -0
  252. data/app/views/stay/admin/features/index.html.erb +58 -0
  253. data/app/views/stay/admin/features/new.html.erb +14 -0
  254. data/app/views/stay/admin/features/show.html.erb +19 -0
  255. data/app/views/stay/admin/house_rules/_form.html.erb +29 -0
  256. data/app/views/stay/admin/house_rules/edit.html.erb +14 -0
  257. data/app/views/stay/admin/house_rules/index.html.erb +54 -0
  258. data/app/views/stay/admin/house_rules/new.html.erb +14 -0
  259. data/app/views/stay/admin/house_rules/show.html.erb +18 -0
  260. data/app/views/stay/admin/mailer/confirmation_instructions.html.erb +5 -0
  261. data/app/views/stay/admin/mailer/email_changed.html.erb +7 -0
  262. data/app/views/stay/admin/mailer/password_change.html.erb +3 -0
  263. data/app/views/stay/admin/mailer/reset_password_instructions.html.erb +7 -0
  264. data/app/views/stay/admin/messages/_form.html.erb +36 -0
  265. data/app/views/stay/admin/messages/edit.html.erb +5 -0
  266. data/app/views/stay/admin/messages/index.html.erb +60 -0
  267. data/app/views/stay/admin/messages/new.html.erb +5 -0
  268. data/app/views/stay/admin/messages/show.html.erb +24 -0
  269. data/app/views/stay/admin/passwords/edit.html.erb +37 -0
  270. data/app/views/stay/admin/passwords/new.html.erb +28 -0
  271. data/app/views/stay/admin/payment_methods/_form.html.erb +22 -0
  272. data/app/views/stay/admin/payment_methods/edit.html.erb +14 -0
  273. data/app/views/stay/admin/payment_methods/index.html.erb +54 -0
  274. data/app/views/stay/admin/payment_methods/new.html.erb +14 -0
  275. data/app/views/stay/admin/payment_methods/show.html.erb +18 -0
  276. data/app/views/stay/admin/payments/_form.html.erb +36 -0
  277. data/app/views/stay/admin/payments/edit.html.erb +5 -0
  278. data/app/views/stay/admin/payments/index.html.erb +60 -0
  279. data/app/views/stay/admin/payments/new.html.erb +5 -0
  280. data/app/views/stay/admin/payments/show.html.erb +24 -0
  281. data/app/views/stay/admin/properties/_amenities.html.erb +38 -0
  282. data/app/views/stay/admin/properties/_calendar.html.erb +37 -0
  283. data/app/views/stay/admin/properties/_description.html.erb +126 -0
  284. data/app/views/stay/admin/properties/_details.html.erb +75 -0
  285. data/app/views/stay/admin/properties/_features.html.erb +39 -0
  286. data/app/views/stay/admin/properties/_form.html.erb +118 -0
  287. data/app/views/stay/admin/properties/_images.html.erb +48 -0
  288. data/app/views/stay/admin/properties/_location.html.erb +55 -0
  289. data/app/views/stay/admin/properties/_price.html.erb +88 -0
  290. data/app/views/stay/admin/properties/_sidebar.html.erb +47 -0
  291. data/app/views/stay/admin/properties/edit.html.erb +17 -0
  292. data/app/views/stay/admin/properties/index.html.erb +82 -0
  293. data/app/views/stay/admin/properties/new.html.erb +14 -0
  294. data/app/views/stay/admin/properties/show.html.erb +149 -0
  295. data/app/views/stay/admin/property_categories/_form.html.erb +29 -0
  296. data/app/views/stay/admin/property_categories/edit.html.erb +14 -0
  297. data/app/views/stay/admin/property_categories/index.html.erb +57 -0
  298. data/app/views/stay/admin/property_categories/new.html.erb +14 -0
  299. data/app/views/stay/admin/property_categories/show.html.erb +18 -0
  300. data/app/views/stay/admin/property_types/_form.html.erb +29 -0
  301. data/app/views/stay/admin/property_types/edit.html.erb +14 -0
  302. data/app/views/stay/admin/property_types/index.html.erb +56 -0
  303. data/app/views/stay/admin/property_types/new.html.erb +14 -0
  304. data/app/views/stay/admin/property_types/show.html.erb +18 -0
  305. data/app/views/stay/admin/registrations/edit.html.erb +43 -0
  306. data/app/views/stay/admin/registrations/new.html.erb +35 -0
  307. data/app/views/stay/admin/reviews/_form.html.erb +37 -0
  308. data/app/views/stay/admin/reviews/edit.html.erb +14 -0
  309. data/app/views/stay/admin/reviews/index.html.erb +58 -0
  310. data/app/views/stay/admin/reviews/new.html.erb +14 -0
  311. data/app/views/stay/admin/reviews/show.html.erb +20 -0
  312. data/app/views/stay/admin/roles/_form.html.erb +24 -0
  313. data/app/views/stay/admin/roles/edit.html.erb +14 -0
  314. data/app/views/stay/admin/roles/index.html.erb +55 -0
  315. data/app/views/stay/admin/roles/new.html.erb +14 -0
  316. data/app/views/stay/admin/roles/show.html.erb +18 -0
  317. data/app/views/stay/admin/room_types/_form.html.erb +37 -0
  318. data/app/views/stay/admin/room_types/edit.html.erb +14 -0
  319. data/app/views/stay/admin/room_types/index.html.erb +58 -0
  320. data/app/views/stay/admin/room_types/new.html.erb +14 -0
  321. data/app/views/stay/admin/room_types/show.html.erb +19 -0
  322. data/app/views/stay/admin/rooms/_form.html.erb +136 -0
  323. data/app/views/stay/admin/rooms/edit.html.erb +14 -0
  324. data/app/views/stay/admin/rooms/index.html.erb +69 -0
  325. data/app/views/stay/admin/rooms/new.html.erb +14 -0
  326. data/app/views/stay/admin/rooms/show.html.erb +25 -0
  327. data/app/views/stay/admin/sessions/new.html.erb +36 -0
  328. data/app/views/stay/admin/shared/_common-table.html.erb +334 -0
  329. data/app/views/stay/admin/shared/_error_messages.html.erb +15 -0
  330. data/app/views/stay/admin/shared/_header.html.erb +55 -0
  331. data/app/views/stay/admin/shared/_links.html.erb +15 -0
  332. data/app/views/stay/admin/shared/_sidebar.html.erb +154 -0
  333. data/app/views/stay/admin/shared/_store_switcher.html.erb +30 -0
  334. data/app/views/stay/admin/states/_form.html.erb +39 -0
  335. data/app/views/stay/admin/states/edit.html.erb +14 -0
  336. data/app/views/stay/admin/states/index.html.erb +61 -0
  337. data/app/views/stay/admin/states/new.html.erb +14 -0
  338. data/app/views/stay/admin/states/show.html.erb +0 -0
  339. data/app/views/stay/admin/stores/_form.html.erb +30 -0
  340. data/app/views/stay/admin/stores/_tabs.html.erb +17 -0
  341. data/app/views/stay/admin/stores/edit.html.erb +14 -0
  342. data/app/views/stay/admin/stores/form/_basic.html.erb +35 -0
  343. data/app/views/stay/admin/stores/form/_emails.html.erb +34 -0
  344. data/app/views/stay/admin/stores/form/_footer.html.erb +28 -0
  345. data/app/views/stay/admin/stores/form/_internationalization.html.erb +52 -0
  346. data/app/views/stay/admin/stores/form/_seo.html.erb +42 -0
  347. data/app/views/stay/admin/stores/form/_social.html.erb +34 -0
  348. data/app/views/stay/admin/stores/index.html.erb +66 -0
  349. data/app/views/stay/admin/stores/new.html.erb +14 -0
  350. data/app/views/stay/admin/stores/translations.html.erb +8 -0
  351. data/app/views/stay/admin/taxes/_form.html.erb +29 -0
  352. data/app/views/stay/admin/taxes/edit.html.erb +14 -0
  353. data/app/views/stay/admin/taxes/index.html.erb +56 -0
  354. data/app/views/stay/admin/taxes/new.html.erb +14 -0
  355. data/app/views/stay/admin/taxes/show.html.erb +18 -0
  356. data/app/views/stay/admin/users/_address.html.erb +57 -0
  357. data/app/views/stay/admin/users/_address_form.html.erb +29 -0
  358. data/app/views/stay/admin/users/_form.html.erb +73 -0
  359. data/app/views/stay/admin/users/_sidebar.html.erb +12 -0
  360. data/app/views/stay/admin/users/addresses.html.erb +17 -0
  361. data/app/views/stay/admin/users/edit.html.erb +17 -0
  362. data/app/views/stay/admin/users/index.html.erb +74 -0
  363. data/app/views/stay/admin/users/new.html.erb +14 -0
  364. data/app/views/stay/admin/users/show.html.erb +23 -0
  365. data/app/views/stay/bookings/new.html.erb +92 -0
  366. data/app/views/stay/payments/_payment.js.erb +127 -0
  367. data/app/views/stay/payments/new.html.erb +187 -0
  368. data/app/views/stay/properties/index.html.erb +56 -0
  369. data/app/views/stay/properties/show.html.erb +137 -0
  370. data/app/views/stay/shared/_navbar.html.erb +35 -0
  371. data/app/views/stay/user_mailer/new_host_signup.html.erb +12 -0
  372. data/app/views/stay/user_mailer/welcome_email.html.erb +9 -0
  373. data/app/views/stay/users/confirmations/new.html.erb +16 -0
  374. data/app/views/stay/users/mailer/confirmation_instructions.html.erb +5 -0
  375. data/app/views/stay/users/mailer/email_changed.html.erb +7 -0
  376. data/app/views/stay/users/mailer/password_change.html.erb +3 -0
  377. data/app/views/stay/users/mailer/reset_password_instructions.html.erb +7 -0
  378. data/app/views/stay/users/mailer/unlock_instructions.html.erb +7 -0
  379. data/app/views/stay/users/passwords/edit.html.erb +37 -0
  380. data/app/views/stay/users/passwords/new.html.erb +28 -0
  381. data/app/views/stay/users/registrations/edit.html.erb +43 -0
  382. data/app/views/stay/users/registrations/new.html.erb +42 -0
  383. data/app/views/stay/users/sessions/new.html.erb +43 -0
  384. data/app/views/stay/users/shared/_error_messages.html.erb +15 -0
  385. data/app/views/stay/users/shared/_links.html.erb +25 -0
  386. data/app/views/stay/users/unlocks/new.html.erb +16 -0
  387. data/config/initializers/devise.rb +358 -0
  388. data/config/initializers/friendly_id.rb +107 -0
  389. data/config/initializers/geocoder.rb +4 -0
  390. data/config/initializers/kaminari_config.rb +14 -0
  391. data/config/initializers/mobility.rb +17 -0
  392. data/config/initializers/stripe.rb +8 -0
  393. data/config/locales/devise.en.yml +65 -0
  394. data/config/locales/devise_api.en.yml +23 -0
  395. data/config/locales/en.yml +38 -0
  396. data/config/routes.rb +187 -0
  397. data/db/migrate/20240912073149_devise_create_stay_users.rb +50 -0
  398. data/db/migrate/20240912073248_create_devise_api_tables.rb +29 -0
  399. data/db/migrate/20240912092842_create_stay_roles.rb +9 -0
  400. data/db/migrate/20240912093003_create_stay_role_users.rb +10 -0
  401. data/db/migrate/20240912093151_create_stay_properties.rb +16 -0
  402. data/db/migrate/20240912093213_create_stay_rooms.rb +12 -0
  403. data/db/migrate/20240912093240_create_stay_bookings.rb +15 -0
  404. data/db/migrate/20240912093346_create_stay_payment_methods.rb +9 -0
  405. data/db/migrate/20240912093408_create_stay_payments.rb +12 -0
  406. data/db/migrate/20240912093603_create_stay_reviews.rb +11 -0
  407. data/db/migrate/20240912093644_create_stay_chats.rb +11 -0
  408. data/db/migrate/20240912093717_create_stay_messages.rb +12 -0
  409. data/db/migrate/20240912093759_create_stay_countries.rb +14 -0
  410. data/db/migrate/20240912093824_create_stay_states.rb +11 -0
  411. data/db/migrate/20240912093903_create_stay_cities.rb +10 -0
  412. data/db/migrate/20240912094149_create_stay_addresses.rb +19 -0
  413. data/db/migrate/20240916071141_create_active_storage_tables.rb +57 -0
  414. data/db/migrate/20240918080551_add_columns_to_stay_bookings.rb +12 -0
  415. data/db/migrate/20240918101502_add_columns_to_stay_payments.rb +16 -0
  416. data/db/migrate/20240918110958_create_stay_prices.rb +13 -0
  417. data/db/migrate/20240918112045_add_columns_to_stay_rooms.rb +5 -0
  418. data/db/migrate/20240918114609_add_payment_intent_in_bookings.rb +6 -0
  419. data/db/migrate/20240919045205_add_user_to_stay_addresses.rb +5 -0
  420. data/db/migrate/20240919063400_create_stay_room_types.rb +10 -0
  421. data/db/migrate/20240919070423_rename_room_type_to_room_type_id_in_stay_rooms.rb +5 -0
  422. data/db/migrate/20240919071642_rename_status_to_state_in_stay_payments.rb +5 -0
  423. data/db/migrate/20240919100508_remove_room_id_from_stay_properties.rb +5 -0
  424. data/db/migrate/20240919111801_create_stay_line_items.rb +16 -0
  425. data/db/migrate/20240919124704_remove_room_id_from_stay_bookings.rb +5 -0
  426. data/db/migrate/20240924053658_add_is_master_in_stay_rooms.rb +5 -0
  427. data/db/migrate/20240925063733_add_zipcode_required_in_countries.rb +5 -0
  428. data/db/migrate/20240926055951_remove_city_reference_from_stay_addresses.rb +5 -0
  429. data/db/migrate/20240927055935_change_price_per_night_to_decimal_in_stay_rooms.rb +5 -0
  430. data/db/migrate/20240927063023_add_first_name_to_stay_addresses.rb +8 -0
  431. data/db/migrate/20240927070538_change_description_to_text_in_stay_properties.rb +6 -0
  432. data/db/migrate/20240927111110_create_stay_stores.rb +33 -0
  433. data/db/migrate/20240930095921_create_stay_cancellation_policies.rb +9 -0
  434. data/db/migrate/20240930100157_add_cancellation_id_to_stay_properties.rb +5 -0
  435. data/db/migrate/20240930152331_create_stay_store_translations.rb +22 -0
  436. data/db/migrate/20240930162337_create_stay_store_properties.rb +10 -0
  437. data/db/migrate/20241001101816_create_stay_property_categories.rb +8 -0
  438. data/db/migrate/20241001102646_add_property_category_id_to_property.rb +5 -0
  439. data/db/migrate/20241001103758_create_stay_property_types.rb +9 -0
  440. data/db/migrate/20241001111306_add_store_id_to_stay_bookings.rb +5 -0
  441. data/db/migrate/20241001160330_add_deleted_at_to_stay_store_translations.rb +5 -0
  442. data/db/migrate/20241004061647_add_field_to_stay_properties.rb +20 -0
  443. data/db/migrate/20241004062057_create_stay_bed_types.rb +9 -0
  444. data/db/migrate/20241004062251_add_details_to_stay_rooms.rb +9 -0
  445. data/db/migrate/20241004070456_add_property_type_id_to_stay_property_categories.rb +6 -0
  446. data/db/migrate/20241004105821_create_stay_amenity_categories.rb +8 -0
  447. data/db/migrate/20241004112600_create_stay_amenities.rb +9 -0
  448. data/db/migrate/20241004115207_create_stay_house_rules.rb +8 -0
  449. data/db/migrate/20241004115317_create_stay_additional_rules.rb +9 -0
  450. data/db/migrate/20241004115608_create_stay_property_amenities.rb +9 -0
  451. data/db/migrate/20241004115615_create_stay_room_amenities.rb +9 -0
  452. data/db/migrate/20241007051646_add_preferences_to_stay_users.rb +5 -0
  453. data/db/migrate/20241007165530_create_stay_creates.rb +10 -0
  454. data/db/migrate/20241008111346_add_deleted_at_to_stay_users.rb +7 -0
  455. data/db/migrate/20241008151958_add_price_per_night_in_stay_properties.rb +5 -0
  456. data/db/migrate/20241010071855_add_zipcode_to_stay_property.rb +8 -0
  457. data/db/migrate/20241014085441_add_amenity_type_in_amenities.rb +5 -0
  458. data/db/migrate/20241015055940_create_stay_features.rb +10 -0
  459. data/db/migrate/20241015060804_create_stay_property_features.rb +9 -0
  460. data/db/migrate/20241015060854_create_stay_room_features.rb +9 -0
  461. data/db/migrate/20241016055948_create_stay_tax.rb +9 -0
  462. data/db/migrate/20241016060354_create_stay_property_tax.rb +11 -0
  463. data/db/migrate/20241016091120_remove_column_from_stay_properties_categories.rb +6 -0
  464. data/db/migrate/20241016091829_add_column_to_stay_property.rb +5 -0
  465. data/db/migrate/20241016112707_add_country_to_stay_properties.rb +6 -0
  466. data/db/migrate/20241016153847_add_state_to_properties.rb +7 -0
  467. data/db/migrate/20241016170528_up_date_price_column_in_stay_property.rb +5 -0
  468. data/db/migrate/20241017031520_add_new_field_to_stay_properties.rb +8 -0
  469. data/db/migrate/20241017051450_add_column_to_stay_chat.rb +7 -0
  470. data/db/migrate/20241018090158_create_stay_stay_credit_cards.rb +16 -0
  471. data/db/migrate/20241021090444_create_stay_stay_user_paypals.rb +9 -0
  472. data/db/migrate/20241024065949_add_stay_property_to_stay_b0okings.rb +5 -0
  473. data/db/migrate/20241027062126_add_events_to_stay_messages.rb +8 -0
  474. data/db/migrate/20241028105007_create_stay_invoices.rb +15 -0
  475. data/db/migrate/20241028105323_create_stay_expenses.rb +10 -0
  476. data/db/migrate/20241028105331_create_stay_discounts.rb +10 -0
  477. data/db/migrate/20241101044618_create_stay_booking_queries.rb +17 -0
  478. data/db/migrate/20241101093057_add_read_at_to_stay_messages.rb +5 -0
  479. data/db/migrate/20241113061248_modify_cancellation_policy_on_properties.rb +7 -0
  480. data/db/migrate/20241118064033_rename_columns_in_stay_properties.rb +7 -0
  481. data/db/migrate/20241127060541_add_new_fields_to_property.rb +11 -0
  482. data/db/migrate/20241128111832_add_name_to_stay_rooms.rb +5 -0
  483. data/db/migrate/20241129063922_change_amenity_category_null_on_stay_amenities.rb +5 -0
  484. data/db/migrate/20241205092935_add_slug_to_stay_properties.rb +6 -0
  485. data/db/migrate/20241205092943_create_friendly_id_slugs.rb +21 -0
  486. data/db/migrate/20241217044817_add_deleted_atto_stay_property.rb +6 -0
  487. data/db/migrate/20241230064432_modify_property_category_on_properties.rb +7 -0
  488. data/db/seeds.rb +1 -0
  489. data/lib/stay/controller_helpers/currency.rb +54 -0
  490. data/lib/stay/controller_helpers/store.rb +37 -0
  491. data/lib/stay/engine.rb +16 -0
  492. data/lib/stay/money.rb +77 -0
  493. data/lib/stay/version.rb +3 -0
  494. data/lib/stay.rb +16 -0
  495. data/lib/tasks/stay_tasks.rake +4 -0
  496. metadata +967 -0
@@ -0,0 +1,49 @@
1
+ module Stay
2
+ module Bookings
3
+ class CreateBookingService
4
+ def initialize(booking_query)
5
+ @booking_query = booking_query
6
+ end
7
+
8
+ def perform
9
+ user = @booking_query.user
10
+ property = @booking_query.property
11
+ room_numbers = @booking_query&.query_for.present? ? @booking_query.query_for["room_number"] : @booking_query.property.rooms.pluck(:id)
12
+ line_items_attributes = build_line_items(room_numbers)
13
+ @booking = Stay::Booking.new(
14
+ user: user,
15
+ property: property,
16
+ check_in_date: @booking_query.check_in_date,
17
+ check_out_date: @booking_query.check_out_date,
18
+ number_of_guests: @booking_query.guest_count,
19
+ line_items_attributes: line_items_attributes,
20
+ )
21
+ @booking.chat = @booking_query.chat
22
+ if @booking.save
23
+ @booking.calculate_totals
24
+ @booking_query.update(booking: @booking)
25
+ { success: true, booking: @booking }
26
+ else
27
+ { success: false, errors: @booking.errors.full_messages }
28
+ end
29
+ end
30
+
31
+ private
32
+
33
+ def build_line_items(room_numbers)
34
+ room_numbers.map do |room_number|
35
+ {
36
+ room_id: find_room_id(room_number),
37
+ price: 100,
38
+ quantity: 1,
39
+ property_id: @booking_query.property.id
40
+ }
41
+ end
42
+ end
43
+
44
+ def find_room_id(room_number)
45
+ Stay::Room.find_by(id: room_number)&.id
46
+ end
47
+ end
48
+ end
49
+ end
@@ -0,0 +1,15 @@
1
+ module Stay
2
+ module Bookings
3
+ class CreateLineItemService
4
+ def initialize(booking, room)
5
+ @booking = booking
6
+ @room = room
7
+ end
8
+
9
+ def perform
10
+ raise "Room not provided" unless @room
11
+ @room.line_items.create!(booking: @booking, price: @room.price_per_month, quantity:1)
12
+ end
13
+ end
14
+ end
15
+ end
@@ -0,0 +1,50 @@
1
+ module Stay
2
+ module Bookings
3
+ class ExistingBookingService
4
+ def initialize(booking, params)
5
+ @booking = booking
6
+ @params = params
7
+ end
8
+
9
+ def perform
10
+ user = @booking.user
11
+ property = @booking.property
12
+ unless property.shared_property
13
+ room_numbers = @booking.property.rooms.pluck(:id)
14
+ else
15
+ room_numbers = @params[:line_items_attributes].map { |r| r["room_id"] } if @params[:line_items_attributes].any?
16
+ end
17
+ if room_numbers.any?
18
+ line_items_attributes = build_line_items(room_numbers)
19
+ @booking.line_items_attributes = line_items_attributes
20
+ end
21
+
22
+ if @booking.update(
23
+ check_in_date: @params[:check_in_date],
24
+ check_out_date: @params[:check_out_date],
25
+ number_of_guests: @params[:number_of_guests]
26
+ )
27
+ @booking.calculate_totals
28
+ { success: true, booking: @booking }
29
+
30
+ else
31
+ { success: false, errors: @booking.errors.full_messages }
32
+ end
33
+ end
34
+
35
+ private
36
+
37
+ def build_line_items(room_numbers)
38
+ room_numbers.map do |room_number|
39
+ room = Stay::Room.find_by(id: room_number)
40
+ {
41
+ room_id: room.id,
42
+ price: room.price,
43
+ quantity: 1,
44
+ property_id: room.property.id
45
+ }
46
+ end
47
+ end
48
+ end
49
+ end
50
+ end
@@ -0,0 +1,82 @@
1
+ class Stay::Chat::ChatMessagingService
2
+ def initialize(booking)
3
+ @booking = booking
4
+ @user = @booking.user
5
+ @property = @booking.property
6
+ @owner = @property.user
7
+ @canceler = @booking.canceler
8
+ end
9
+
10
+ def send_initial_messages
11
+ unless @booking.chat.present?
12
+ @chat = create_chat(@booking, @user, @owner, @property)
13
+ else
14
+ @chat = @booking.chat
15
+ end
16
+ messages_by_status = {
17
+ "booking_request" => {
18
+ user_message: { text: "Your booking request was sent for property #{@property.title} for dates #{formatted_date(@booking.check_in_date.to_date)} to #{formatted_date(@booking.check_out_date.to_date)} for #{@booking.number_of_guests} guests.", event: "booking request", receiver: @owner, read_at: DateTime.now },
19
+ owner_message: { text: "You have received a new booking request for property #{@property.title} for dates #{formatted_date(@booking.check_in_date.to_date)} to #{formatted_date(@booking.check_out_date.to_date)} for #{@booking.number_of_guests} guests.", event: "booking request", receiver: @user, read_at: DateTime.now }
20
+ },
21
+ "invoice_sent" => {
22
+ user_message: { text: "You Have received a invoice for your booking for #{@property.title} for dates #{formatted_date(@booking.check_in_date.to_date)} to #{formatted_date(@booking.check_out_date.to_date)}.", event: "invoice_sent", receiver: @owner, read_at: DateTime.now },
23
+ owner_message: { text: "You have sent a new booking invoice for property #{@property.title} for dates #{formatted_date(@booking.check_in_date.to_date)} to #{formatted_date(@booking.check_out_date.to_date)}.", event: "invoice_sent", receiver: @user, read_at: DateTime.now }
24
+ },
25
+ "confirmed" => {
26
+ user_message: { text: "Your booking for property #{@property.title} from #{formatted_date(@booking.check_in_date.to_date)} to #{formatted_date(@booking.check_out_date.to_date)} has been confirmed.", event: "booking confirmed", receiver: @owner, read_at: DateTime.now },
27
+ owner_message: { text: "You have confirmed the booking for property #{@property.title} from #{formatted_date(@booking.check_in_date.to_date)} to #{formatted_date(@booking.check_out_date.to_date)}.", event: "booking confirmed", receiver: @user, read_at: DateTime.now }
28
+ },
29
+ "canceled" => {
30
+ user_message: cancellation_message_for_user,
31
+ owner_message: cancellation_message_for_owner
32
+ },
33
+ "completed" => {
34
+ user_message: { text: "Your stay at #{@property.title} from #{formatted_date(@booking.check_in_date.to_date)} to #{formatted_date(@booking.check_out_date.to_date)} is complete. Thank you for staying with us!", event: "booking completed", receiver: @owner, read_at: DateTime.now },
35
+ owner_message: { text: "The stay for property #{@property.title} from #{formatted_date(@booking.check_in_date.to_date)} to #{formatted_date(@booking.check_out_date.to_date)} has been completed.", event: "booking completed", receiver: @user, read_at: DateTime.now }
36
+ }
37
+ }
38
+
39
+ if messages_by_status.key?(@booking.status)
40
+ send_message(@chat, @user, messages_by_status[@booking.status][:user_message])
41
+ send_message(@chat, @owner, messages_by_status[@booking.status][:owner_message])
42
+ end
43
+ end
44
+
45
+ private
46
+
47
+ def create_chat(booking, user, owner, property)
48
+ Stay::Chat.create!(sender: user, receiver: owner, property: property, booking: booking)
49
+ end
50
+
51
+ def send_message(chat, sender, message_details)
52
+ chat.messages.create!(
53
+ body: message_details[:text],
54
+ sender: sender,
55
+ receiver: message_details[:receiver],
56
+ event_for: sender == @user ? 1 : 0,
57
+ event_message: message_details[:event]
58
+ )
59
+ end
60
+
61
+ def cancellation_message_for_user
62
+ if @canceler == @user
63
+ { text: "You canceled the booking for property #{@property.title} from #{formatted_date(@booking.check_in_date.to_date)} to #{formatted_date(@booking.check_out_date.to_date)}.", event: "booking canceled", receiver: @owner, read_at: DateTime.now }
64
+ else
65
+ { text: "Your booking for property #{@property.title} from #{formatted_date(@booking.check_in_date.to_date)} to #{formatted_date(@booking.check_out_date.to_date)} was canceled by the host.", event: "booking canceled", receiver: @user, read_at: DateTime.now }
66
+ end
67
+ end
68
+
69
+ def cancellation_message_for_owner
70
+ if @canceler == @user
71
+ { text: "The booking for property #{@property.title} from #{@booking.check_in_date.to_date} to #{@booking.check_out_date.to_date} was canceled by the user.", event: "booking canceled", receiver: @owner, read_at: DateTime.now }
72
+ else
73
+ { text: "You canceled the booking for property #{@property.title} from #{@booking.check_in_date.to_date} to #{@booking.check_out_date.to_date}.", event: "booking canceled", receiver: @user, read_at: DateTime.now }
74
+ end
75
+ end
76
+
77
+ def formatted_date(date)
78
+ if date.to_date.present?
79
+ date.to_date.strftime("%B %d, %Y")
80
+ end
81
+ end
82
+ end
@@ -0,0 +1,56 @@
1
+ class Stay::Chat::QueryMessagingService
2
+ def initialize(query, current_user, message = nil)
3
+ @query = query
4
+ @user = current_user
5
+ @property = @query.property
6
+ @owner = @property.user
7
+ @chat = @query.chat
8
+ @message = message
9
+ end
10
+
11
+ def perform
12
+ messages_by_status = {
13
+ "send_message" => {
14
+ user_message: { text: "#{@message} You have raised a request for the property #{@property.title} for dates #{formatted_date(@query.check_in_date.to_date)} to #{formatted_date(@query.check_out_date.to_date)} for #{@query.guest_count} guest(s).", event: "booking query", receiver: @owner },
15
+ owner_message: { text: "#{@message} A booking query has been received for the property #{@property.title} for dates #{formatted_date(@query.check_in_date.to_date)} to #{formatted_date(@query.check_out_date.to_date)} for #{@query.guest_count} guest(s).", event: "booking query", receiver: @user }
16
+ },
17
+ "booking_invitation" => {
18
+ user_message: { text: "You have received a booking invitation.", event: "booking invitation", receiver: @owner },
19
+ owner_message: { text: "You have sent a booking invitation.", event: "booking invitation", receiver: @user }
20
+ },
21
+ "request_change" => {
22
+ user_message: { text: "You have requested a change in booking dates to #{formatted_date(@query.check_in_date.to_date)} - #{formatted_date(@query.check_out_date.to_date)}.", event: "request change", receiver: @owner },
23
+ owner_message: { text: "The user has requested a change in booking dates to #{formatted_date(@query.check_in_date.to_date)} - #{formatted_date(@query.check_out_date.to_date)}.", event: "request change", receiver: @user }
24
+ },
25
+ "accepted" => {
26
+ user_message: { text: "You have sent a booking request.", event: "booking accepted", receiver: @owner },
27
+ owner_message: { text: "You have received a booking request.", event: "booking accepted", receiver: @user }
28
+ },
29
+ "rejected" => {
30
+ user_message: { text: "The booking for #{@property.title} from #{formatted_date(@query.check_in_date.to_date)} to #{formatted_date(@query.check_out_date.to_date)} has been rejected.", event: "booking rejected", receiver: @owner },
31
+ owner_message: { text: "The booking for #{@property.title} from #{formatted_date(@query.check_in_date.to_date)} to #{formatted_date(@query.check_out_date.to_date)} has been rejected.", event: "booking rejected", receiver: @user }
32
+ }
33
+ }
34
+
35
+ if messages_by_status.key?(@query.state)
36
+ messages = messages_by_status[@query.state]
37
+ send_message(@chat, @user, messages[:user_message], @owner)
38
+ send_message(@chat, @owner, messages[:owner_message], @user)
39
+ end
40
+ end
41
+
42
+ private
43
+
44
+ def send_message(chat, sender, message_details, receiver)
45
+ chat.messages.create!(
46
+ body: message_details[:text],
47
+ sender: sender,
48
+ receiver: receiver,
49
+ event_for: sender == @user ? 1 : 0,
50
+ )
51
+ end
52
+
53
+ def formatted_date(date)
54
+ date.strftime("%B %d, %Y") if date.present?
55
+ end
56
+ end
@@ -0,0 +1,27 @@
1
+ module Stay
2
+ module Seeds
3
+ class All
4
+ def self.call
5
+ # GEO
6
+ Countries.call
7
+ States.call
8
+ # Zones.call
9
+
10
+ # user roles
11
+ Roles.call
12
+
13
+ # additional data
14
+ # DefaultReimbursementTypes.call
15
+ # ShippingCategories.call
16
+ # StoreCreditCategories.call
17
+
18
+ # # store & stock location
19
+ Stores.call
20
+ # StockLocations.call
21
+
22
+ # # add store resources
23
+ # PaymentMethods.call
24
+ end
25
+ end
26
+ end
27
+ end
@@ -0,0 +1,21 @@
1
+ module Stay
2
+ module Seeds
3
+ class CancellationPolicy
4
+ def self.call
5
+ policies = {
6
+ "strict" => "Cancellation from tenant of confirmed booking; No Refund. / Cancelación del inquilino de la reserva confirmada; No hay reembolso del depósito (primer mes de renta).",
7
+ "moderate" => "*Cancellation from tenant of confirmed booking 30 days or less before check-in date; No Refund. / Cancelación del inquilino de la reserva confirmada 30 días o menos antes de la fecha del check-in; No hay reembolso del depósito (primer mes de renta).\n\n" \
8
+ "*Cancellation from tenant of confirmed booking, 31 to 60 days before check-in date; 50% refund of deposit (first month rent). / Cancelación del inquilino de la reserva confirmada, de 31 a 60 días antes de la fecha del check-in; 50% de reembolso del depósito (primer mes de renta).\n\n" \
9
+ "*Cancellation from tenant of confirmed booking, 61 days or more before check-in date; Full refund of deposit (first month rent). / Cancelación del inquilino de la reserva confirmada, 61 días o más antes de la fecha del check-in; Reembolso total del depósito (primer mes de renta).",
10
+ "flexible" => "Cancellation from tenant of confirmed booking 15 days or less before check-in date; No Refund. / Cancelación del inquilino de la reserva confirmada, 15 días o menos antes de la fecha del check-in; No hay reembolso del depósito (primer mes de renta).\n\n" \
11
+ "Cancellation from tenant of confirmed booking, 16 to 30 days before check-in date; 50% refund of deposit (first month rent). / Cancelación del inquilino de la reserva confirmada, de 16 a 30 días antes de la fecha del check-in; 50% de reembolso del depósito (primer mes de renta).\n\n" \
12
+ "Cancellation from tenant of confirmed booking, 31 days or more before check-in date; Full refund of deposit (first month rent). / Cancelación del inquilino de la reserva confirmada, 31 días o más antes de la fecha del check-in; Reembolso total del depósito (primer mes de renta)."
13
+ }
14
+
15
+ policies.each do |name, description|
16
+ Stay::CancellationPolicy.find_or_create_by!(name: name, description: description)
17
+ end
18
+ end
19
+ end
20
+ end
21
+ end
@@ -0,0 +1,33 @@
1
+ require 'carmen'
2
+
3
+ module Stay
4
+ module Seeds
5
+ class Countries
6
+ EXCLUDED_COUNTRIES = ['AQ', 'AX', 'GS', 'UM', 'HM', 'IO', 'EH', 'BV', 'TF'].freeze
7
+
8
+ def self.call
9
+ ApplicationRecord.transaction do
10
+ new_countries = Carmen::Country.all.map do |country|
11
+ # Skip the creation of some territories, uninhabited islands and the Antarctic.
12
+ next if EXCLUDED_COUNTRIES.include?(country.alpha_2_code)
13
+
14
+ Hash[
15
+ 'name': country.name,
16
+ 'iso3': country.alpha_3_code,
17
+ 'iso': country.alpha_2_code,
18
+ 'iso_name': country.name.upcase,
19
+ 'numcode': country.numeric_code,
20
+ ]
21
+ end.compact.uniq
22
+ Stay::Country.insert_all(new_countries)
23
+
24
+ # Find countries that do not use postal codes (by iso) and set 'zipcode_required' to false for them.
25
+ Stay::Country.where(iso: Stay::Address::NO_ZIPCODE_ISO_CODES).update_all(zipcode_required: false)
26
+
27
+ # Find all countries that require a state (province) at checkout and set 'states_required' to true.
28
+ Stay::Country.where(iso: Stay::Address::STATES_REQUIRED).update_all(states_required: true)
29
+ end
30
+ end
31
+ end
32
+ end
33
+ end
@@ -0,0 +1,9 @@
1
+ module Stay
2
+ module Seeds
3
+ class Roles
4
+ def self.call
5
+ Stay::Role.where(name: 'admin').first_or_create!
6
+ end
7
+ end
8
+ end
9
+ end
@@ -0,0 +1,63 @@
1
+ require 'carmen'
2
+
3
+ module Stay
4
+ module Seeds
5
+ class States
6
+ # prepend Spree::ServiceModule::Base
7
+
8
+ EXCLUDED_US_STATES = ['UM', 'AS', 'MP', 'VI', 'PR', 'GU'].freeze
9
+ EXCLUDED_CN_STATES = ['HK', 'MO', 'TW'].freeze
10
+
11
+ def self.call
12
+ Stay::Country.where(states_required: true).each do |country|
13
+ carmen_country = Carmen::Country.named(country.name)
14
+ next unless carmen_country
15
+
16
+ carmen_country.subregions.each do |subregion|
17
+ if carmen_country.alpha_2_code == 'US'
18
+ # Produces 50 states, one postal district (Washington DC)
19
+ # and 3 APO's as you would expect to see on any good U.S. states list.
20
+ next if EXCLUDED_US_STATES.include?(subregion.code)
21
+
22
+ state_level(country, subregion)
23
+ elsif carmen_country.alpha_2_code == 'CA' || carmen_country.alpha_2_code == 'MX'
24
+ # Force Canada and Mexico to use state-level data import from Carmen Gem
25
+ # else we pull in a subset of provinces that are not common at checkout.
26
+ state_level(country, subregion)
27
+ elsif carmen_country.alpha_2_code == 'CN'
28
+ # Removes 3 "States" from that list that are also listed as Countries,
29
+ # Hong Kong, Taiwan and Macao
30
+ next if EXCLUDED_CN_STATES.include?(subregion.code)
31
+
32
+ state_level(country, subregion)
33
+ elsif subregion.subregions?
34
+ province_level(country, subregion)
35
+ else
36
+ state_level(country, subregion)
37
+ end
38
+ end
39
+ end
40
+ end
41
+
42
+ protected
43
+
44
+ def self.state_level(country, subregion)
45
+ country.states.where(
46
+ name: subregion.name,
47
+ abbr: subregion.code
48
+ ).first_or_create!
49
+ end
50
+
51
+ def self.province_level(country, subregion)
52
+ new_states = subregion.subregions.map do |province|
53
+ Hash[
54
+ name: province.name,
55
+ abbr: province.code,
56
+ country_id: country.id
57
+ ]
58
+ end.compact.uniq
59
+ Stay::State.insert_all(new_states)
60
+ end
61
+ end
62
+ end
63
+ end
@@ -0,0 +1,34 @@
1
+ require 'paranoia'
2
+
3
+ module Stay
4
+ module Seeds
5
+ class Stores
6
+
7
+ def self.call
8
+ default_store = Stay::Store.default
9
+ default_country_id = Stay::Country.find_by(iso: 'US')&.id
10
+
11
+ if default_store.persisted?
12
+ default_store.update!(default_country_id: Stay::Config[:default_country_id])
13
+ else
14
+ Stay::Store.new do |s|
15
+ s.name = 'Stay Commerce'
16
+ s.code = 'Stay'
17
+ s.url = Rails.application.routes.default_url_options[:host]
18
+ s.mail_from_address = 'no-reply@example.com'
19
+ s.customer_support_email = 'support@example.com'
20
+ s.default_currency = 'USD'
21
+ s.default_country_id = default_country_id
22
+ s.default_locale = 'en'
23
+ s.default = true
24
+ s.seo_title = 'Stay Commerce Demo'
25
+ s.meta_description = 'This is the new Stay UX DEMO '
26
+ s.facebook = 'staycommerce'
27
+ s.twitter = 'staycommerce'
28
+ s.instagram = 'staycommerce'
29
+ end.save!
30
+ end
31
+ end
32
+ end
33
+ end
34
+ end
@@ -0,0 +1,10 @@
1
+ <p>Hello <%= @resource.email %>!</p>
2
+
3
+
4
+ <p>Someone has requested a link to change your password. You can do this through the link below.</p>
5
+
6
+ <p><%= link_to 'Change my password', @resource.source == 'json' ? livio.user_password_url(@resource, reset_password_token: @token) : livio.edit_user_password_url(@resource, reset_password_token: @token) %></p>
7
+
8
+
9
+ <p>If you didn't request this, please ignore this email.</p>
10
+ <p>Your password won't change until you access the link above and create a new one.</p>
@@ -0,0 +1,3 @@
1
+ <li class="page-item">
2
+ <%= link_to_unless current_page.first?, raw(t 'views.pagination.first'), url, remote: remote, class: 'page-link' %>
3
+ </li>
@@ -0,0 +1,3 @@
1
+ <li class='page-item disabled'>
2
+ <%= link_to raw(t 'views.pagination.truncate'), '#', class: 'page-link' %>
3
+ </li>
@@ -0,0 +1,3 @@
1
+ <li class="page-item">
2
+ <%= link_to_unless current_page.last?, raw(t 'views.pagination.last'), url, remote: remote, class: 'page-link' %>
3
+ </li>
@@ -0,0 +1,3 @@
1
+ <li class="page-item">
2
+ <%= link_to_unless current_page.last?, raw(t 'views.pagination.next'), url, rel: 'next', remote: remote, class: 'page-link' %>
3
+ </li>
@@ -0,0 +1,9 @@
1
+ <% if page.current? %>
2
+ <li class="page-item active">
3
+ <%= content_tag :a, page, data: { remote: remote }, rel: page.rel, class: 'page-link' %>
4
+ </li>
5
+ <% else %>
6
+ <li class="page-item">
7
+ <%= link_to page, url, remote: remote, rel: page.rel, class: 'page-link' %>
8
+ </li>
9
+ <% end %>
@@ -0,0 +1,17 @@
1
+ <%= paginator.render do %>
2
+ <nav>
3
+ <ul class="pagination">
4
+ <%= first_page_tag unless current_page.first? %>
5
+ <%= prev_page_tag unless current_page.first? %>
6
+ <% each_page do |page| %>
7
+ <% if page.left_outer? || page.right_outer? || page.inside_window? %>
8
+ <%= page_tag page %>
9
+ <% elsif !page.was_truncated? -%>
10
+ <%= gap_tag %>
11
+ <% end %>
12
+ <% end %>
13
+ <%= next_page_tag unless current_page.last? %>
14
+ <%= last_page_tag unless current_page.last? %>
15
+ </ul>
16
+ </nav>
17
+ <% end %>
@@ -0,0 +1,3 @@
1
+ <li class="page-item">
2
+ <%= link_to_unless current_page.first?, raw(t 'views.pagination.previous'), url, rel: 'prev', remote: remote, class: 'page-link' %>
3
+ </li>
@@ -0,0 +1,45 @@
1
+ <!DOCTYPE html>
2
+ <html class="h-100">
3
+ <head>
4
+ <title>Stay</title>
5
+ <%= csrf_meta_tags %>
6
+ <%= csp_meta_tag %>
7
+
8
+ <%= stylesheet_link_tag 'stay/application', media: 'all', 'data-turbolinks-track': 'reload' %>
9
+ <link href="https://unpkg.com/@webpixels/css@1.2.6/dist/index.css" rel="stylesheet">
10
+ <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/bootstrap-icons@1.11.3/font/bootstrap-icons.min.css">
11
+ <%= javascript_include_tag 'stay/application' %>
12
+ </head>
13
+ <body class="bg-surface-secondary">
14
+ <%= render 'stay/admin/shared/header' %>
15
+ <% flash.each do |type, msg| %>
16
+ <div class="flash">
17
+ <div class="flash-content">
18
+ <i class="bi <%= type == 'alert' ? 'bi-exclamation-lg' : 'bi-check-lg' %> check"></i>
19
+ <div class="message">
20
+ <span class="text text-1"><%= type.capitalize %></span>
21
+ <span class="text text-2"><%= msg %></span>
22
+ </div>
23
+ </div>
24
+ <i class="bi bi-x close"></i>
25
+ <div class="progress"></div>
26
+ </div>
27
+ <% end %>
28
+ <div class="content-wrapper">
29
+ <% if user_signed_in? %>
30
+ <div class="d-flex flex-column flex-lg-row h-lg-full">
31
+ <%= render 'stay/admin/shared/sidebar' %>
32
+ <div class="flex-grow-1 content-parent">
33
+ <main class="bg-surface-secondary">
34
+ <%= yield %>
35
+ </main>
36
+ </div>
37
+ </div>
38
+ <% else %>
39
+ <div class="main-content">
40
+ <%= yield %>
41
+ </div>
42
+ <% end %>
43
+ </div>
44
+ </body>
45
+ </html>
@@ -0,0 +1,34 @@
1
+ <!DOCTYPE html>
2
+ <html>
3
+ <head>
4
+ <title>Stay</title>
5
+ <%= csrf_meta_tags %>
6
+ <%= csp_meta_tag %>
7
+
8
+ <!-- Bootstrap CSS -->
9
+
10
+ <%= stylesheet_link_tag 'stay/application', media: 'all', 'data-turbolinks-track': 'reload' %>
11
+ <%= javascript_include_tag 'stay/application', 'data-turbolinks-track': 'reload' %>
12
+ </head>
13
+ <body>
14
+ <%= render 'stay/shared/navbar' %>
15
+ <div class="container mt-5">
16
+ <% flash.each do |type, msg| %>
17
+ <div class="flash">
18
+ <div class="flash-content">
19
+ <i class="bi <%= type == 'alert' ? 'bi-exclamation-lg' : 'bi-check-lg' %> check"></i>
20
+ <div class="message">
21
+ <span class="text text-1"><%= type.capitalize %></span>
22
+ <span class="text text-2"><%= msg %></span>
23
+ </div>
24
+ </div>
25
+ <i class="bi bi-x close"></i>
26
+ <div class="progress"></div>
27
+ </div>
28
+ <% end %>
29
+ </div>
30
+ <div class="container mt-5">
31
+ <%= yield %>
32
+ </div>
33
+ </body>
34
+ </html>
@@ -0,0 +1,49 @@
1
+ <div data-hook="stay_admin_address_form_fields">
2
+ <%= form_with(model: [:admin, address], local: true) do |f| %>
3
+
4
+ <div class="field">
5
+ <%= f.label :address1, 'Address 1' %>
6
+ <%= f.text_field :address1, class: 'form-control' %>
7
+ </div>
8
+
9
+ <div class="field">
10
+ <%= f.label :address2, 'Address 2' %>
11
+ <%= f.text_field :address2, class: 'form-control' %>
12
+ </div>
13
+
14
+ <div class="field">
15
+ <%= f.label :city, 'City' %>
16
+ <%= f.text_field :city, class: 'form-control' %>
17
+ </div>
18
+
19
+ <div class="field">
20
+ <%= f.label :state, 'State' %>
21
+ <%= f.text_field :state, class: 'form-control' %>
22
+ </div>
23
+
24
+ <div class="field">
25
+ <%= f.label :country, 'Country' %>
26
+ <%= f.text_field :country, class: 'form-control' %>
27
+ </div>
28
+
29
+ <div class="field">
30
+ <%= f.label :zipcode, 'Zipcode' %>
31
+ <%= f.text_field :zipcode, class: 'form-control' %>
32
+ </div>
33
+
34
+ <div class="field">
35
+ <%= f.label :longitude, 'Longitude' %>
36
+ <%= f.text_field :longitude, class: 'form-control' %>
37
+ </div>
38
+
39
+ <div class="field">
40
+ <%= f.label :latitude, 'Latitude' %>
41
+ <%= f.text_field :latitude, class: 'form-control' %>
42
+ </div>
43
+
44
+ <div class="actions">
45
+ <%= f.submit 'Save', class: 'btn btn-primary' %>
46
+ </div>
47
+
48
+ <% end %>
49
+ </div>
@@ -0,0 +1,5 @@
1
+ <h1>Edit Address</h1>
2
+
3
+ <%= render 'form', address: @address %>
4
+
5
+ <%= link_to 'Back', admin_addresses_path, class: 'btn btn-secondary' %>