shoppe 0.0.15 → 0.0.16

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 (199) hide show
  1. data/README.rdoc +1 -0
  2. data/Rakefile +21 -1
  3. data/app/assets/javascripts/shoppe/application.coffee +5 -0
  4. data/app/assets/stylesheets/shoppe/application.scss +16 -3
  5. data/app/assets/stylesheets/shoppe/elements.scss +8 -0
  6. data/app/assets/stylesheets/shoppe/printable.scss +67 -0
  7. data/app/controllers/shoppe/application_controller.rb +1 -10
  8. data/app/controllers/shoppe/orders_controller.rb +4 -0
  9. data/app/controllers/shoppe/sessions_controller.rb +1 -0
  10. data/app/controllers/shoppe/settings_controller.rb +12 -0
  11. data/app/controllers/shoppe/users_controller.rb +2 -2
  12. data/app/controllers/shoppe/variants_controller.rb +1 -1
  13. data/app/helpers/shoppe/application_helper.rb +63 -8
  14. data/app/mailers/shoppe/order_mailer.rb +5 -7
  15. data/app/mailers/shoppe/user_mailer.rb +2 -2
  16. data/app/models/shoppe/country.rb +17 -1
  17. data/app/models/shoppe/delivery_service.rb +15 -0
  18. data/app/models/shoppe/delivery_service_price.rb +17 -0
  19. data/app/models/shoppe/order.rb +82 -9
  20. data/app/models/shoppe/order_item.rb +18 -0
  21. data/app/models/shoppe/product.rb +26 -1
  22. data/app/models/shoppe/product/product_attributes.rb +1 -1
  23. data/app/models/shoppe/product/variants.rb +3 -3
  24. data/app/models/shoppe/product_attribute.rb +15 -0
  25. data/app/models/shoppe/product_category.rb +12 -0
  26. data/app/models/shoppe/setting.rb +59 -0
  27. data/app/models/shoppe/stock_level_adjustment.rb +15 -0
  28. data/app/models/shoppe/tax_rate.rb +13 -1
  29. data/app/models/shoppe/user.rb +13 -0
  30. data/app/views/layouts/shoppe/application.html.haml +2 -1
  31. data/app/views/layouts/shoppe/printable.html.haml +11 -0
  32. data/app/views/shoppe/delivery_service_prices/index.html.haml +1 -1
  33. data/app/views/shoppe/order_mailer/accepted.text.erb +2 -2
  34. data/app/views/shoppe/order_mailer/received.text.erb +2 -2
  35. data/app/views/shoppe/order_mailer/rejected.text.erb +2 -2
  36. data/app/views/shoppe/order_mailer/shipped.text.erb +2 -2
  37. data/app/views/shoppe/orders/despatch_note.html.haml +45 -0
  38. data/app/views/shoppe/orders/index.html.haml +2 -2
  39. data/app/views/shoppe/orders/show.html.haml +21 -11
  40. data/app/views/shoppe/settings/edit.html.haml +19 -0
  41. data/app/views/shoppe/user_mailer/new_password.text.erb +1 -1
  42. data/app/views/shoppe/variants/form.html.haml +4 -0
  43. data/config/locales/en.yml +34 -0
  44. data/config/routes.rb +5 -0
  45. data/db/migrate/20130926094549_create_shoppe_initial_schema.rb +92 -33
  46. data/db/seeds.rb +1 -1
  47. data/lib/shoppe.rb +13 -35
  48. data/lib/shoppe/engine.rb +6 -6
  49. data/lib/shoppe/settings.rb +28 -0
  50. data/lib/shoppe/settings_loader.rb +16 -0
  51. data/lib/shoppe/setup_generator.rb +0 -4
  52. data/lib/shoppe/version.rb +1 -1
  53. data/test/{dummy → app}/README.rdoc +0 -0
  54. data/test/{dummy → app}/Rakefile +0 -0
  55. data/test/{dummy → app}/app/assets/javascripts/application.js +0 -0
  56. data/test/{dummy → app}/app/assets/stylesheets/application.css +0 -0
  57. data/test/{dummy → app}/app/controllers/application_controller.rb +0 -0
  58. data/test/{dummy → app}/app/helpers/application_helper.rb +0 -0
  59. data/test/{dummy → app}/app/views/layouts/application.html.erb +0 -0
  60. data/test/{dummy → app}/bin/bundle +0 -0
  61. data/test/{dummy → app}/bin/rails +0 -0
  62. data/test/{dummy → app}/bin/rake +0 -0
  63. data/test/{dummy → app}/config.ru +0 -0
  64. data/test/{dummy → app}/config/application.rb +0 -0
  65. data/test/{dummy → app}/config/boot.rb +0 -0
  66. data/test/app/config/database.example.yml +30 -0
  67. data/test/{dummy → app}/config/database.yml +9 -5
  68. data/test/{dummy → app}/config/environment.rb +0 -0
  69. data/test/{dummy → app}/config/environments/development.rb +0 -0
  70. data/test/{dummy → app}/config/environments/production.rb +0 -0
  71. data/test/{dummy → app}/config/environments/test.rb +0 -0
  72. data/test/{dummy → app}/config/initializers/backtrace_silencers.rb +0 -0
  73. data/test/{dummy → app}/config/initializers/filter_parameter_logging.rb +0 -0
  74. data/test/{dummy → app}/config/initializers/inflections.rb +0 -0
  75. data/test/{dummy → app}/config/initializers/mime_types.rb +0 -0
  76. data/test/{dummy → app}/config/initializers/secret_token.rb +0 -0
  77. data/test/app/config/initializers/session_store.rb +3 -0
  78. data/test/{dummy → app}/config/initializers/wrap_parameters.rb +0 -0
  79. data/test/{dummy → app}/config/locales/en.yml +0 -0
  80. data/test/{dummy → app}/config/routes.rb +0 -0
  81. data/{config/shoppe.example.yml → test/app/config/shoppe.yml} +0 -0
  82. data/test/{dummy → app}/db/development.sqlite3 +0 -0
  83. data/test/{dummy → app}/db/migrate/20131017165217_create_nifty_attachments_table.rb +0 -0
  84. data/test/{dummy → app}/db/migrate/20131017165222_create_nifty_key_value_store_table.rb +0 -0
  85. data/test/{dummy → app}/db/schema.rb +31 -16
  86. data/test/{dummy → app}/db/test.sqlite3 +0 -0
  87. data/test/app/log/development.log +8093 -0
  88. data/test/{dummy → app}/log/test.log +0 -0
  89. data/test/{dummy → app}/public/404.html +0 -0
  90. data/test/{dummy → app}/public/422.html +0 -0
  91. data/test/{dummy → app}/public/500.html +0 -0
  92. data/test/{dummy → app}/public/favicon.ico +0 -0
  93. data/test/app/tmp/cache/assets/development/sass/7c98994848dbb534749f971b176724aa382339bb/dialog.scssc +0 -0
  94. data/test/app/tmp/cache/assets/development/sass/edac894564dae62b78e653a08d1c41f10ade93f9/application.scssc +0 -0
  95. data/test/app/tmp/cache/assets/development/sass/edac894564dae62b78e653a08d1c41f10ade93f9/dialog.scssc +0 -0
  96. data/test/app/tmp/cache/assets/development/sass/edac894564dae62b78e653a08d1c41f10ade93f9/elements.scssc +0 -0
  97. data/test/app/tmp/cache/assets/development/sass/edac894564dae62b78e653a08d1c41f10ade93f9/reset.scssc +0 -0
  98. data/test/app/tmp/cache/assets/development/sass/edac894564dae62b78e653a08d1c41f10ade93f9/sub.scssc +0 -0
  99. data/test/app/tmp/cache/assets/development/sass/edac894564dae62b78e653a08d1c41f10ade93f9/variables.scssc +0 -0
  100. data/test/app/tmp/cache/assets/development/sprockets/06d540cec125e08e63a898c35e8235d6 +0 -0
  101. data/test/app/tmp/cache/assets/development/sprockets/0a6bca3e510625f255083bd154cc470b +0 -0
  102. data/test/app/tmp/cache/assets/development/sprockets/0d8942b2279b6bc7c68b3db3e2e4c342 +0 -0
  103. data/test/app/tmp/cache/assets/development/sprockets/122a65fdcbb923c3c1cd95549ef52f43 +0 -0
  104. data/test/app/tmp/cache/assets/development/sprockets/140840b7aefa4bf5beda2c32e20374a6 +0 -0
  105. data/test/app/tmp/cache/assets/development/sprockets/160ddfa6141944c4a03757fe91643137 +0 -0
  106. data/test/app/tmp/cache/assets/development/sprockets/1bb0d399b6b81fc3b47ff794b066873f +0 -0
  107. data/test/app/tmp/cache/assets/development/sprockets/1e1679158bd397a720be46fa3a5876a3 +0 -0
  108. data/test/app/tmp/cache/assets/development/sprockets/2a75ba35f8e751887ba89a914363fefd +0 -0
  109. data/test/app/tmp/cache/assets/development/sprockets/2cc6ef740b5691af5ee246c0dbc68f14 +0 -0
  110. data/test/app/tmp/cache/assets/development/sprockets/2f80004fb2e2ce07283a83ac15cf920a +0 -0
  111. data/test/app/tmp/cache/assets/development/sprockets/322295abdd8625fcce4da08f9565cc63 +0 -0
  112. data/test/app/tmp/cache/assets/development/sprockets/421b79f445cd87f3532a5c445877cbec +0 -0
  113. data/test/app/tmp/cache/assets/development/sprockets/4528fe4a109cad1ff031659cd9eeae17 +0 -0
  114. data/test/app/tmp/cache/assets/development/sprockets/45a9c7dfe9986570daa4c972277375ec +0 -0
  115. data/test/app/tmp/cache/assets/development/sprockets/48b2cd7153bbc442eaa84c3e24e963e0 +0 -0
  116. data/test/app/tmp/cache/assets/development/sprockets/4c3fef5a3e293ed6b6df3d869f54e1d1 +0 -0
  117. data/test/app/tmp/cache/assets/development/sprockets/4c8cb5cfd87990ebddbaa5b5fd594be5 +0 -0
  118. data/test/app/tmp/cache/assets/development/sprockets/4cefa37a52d669d3ca7e6aa1e1aaf435 +0 -0
  119. data/test/app/tmp/cache/assets/development/sprockets/4ea4f5c13aaeda9a7d39684ab72fa710 +0 -0
  120. data/test/app/tmp/cache/assets/development/sprockets/4ecd1cb66cb36718daadcfba0aa42c1e +0 -0
  121. data/test/app/tmp/cache/assets/development/sprockets/4ed3cbd180c275b98627eaeea4c9c838 +0 -0
  122. data/test/app/tmp/cache/assets/development/sprockets/519aa2b3c3ab8fd8f065c56507111878 +0 -0
  123. data/test/app/tmp/cache/assets/development/sprockets/51d409a48872319ac6a731aa880e6368 +0 -0
  124. data/test/app/tmp/cache/assets/development/sprockets/55bae604bcb5ccf7d9e0ed0fd61953b6 +0 -0
  125. data/test/app/tmp/cache/assets/development/sprockets/5805d2c402f412642d86ec03a7ec4a3d +0 -0
  126. data/test/app/tmp/cache/assets/development/sprockets/5cd772b44cdeae4d3b37b62193e946eb +0 -0
  127. data/test/app/tmp/cache/assets/development/sprockets/5f32b259cbcc52156d2fe21c185d9390 +0 -0
  128. data/test/app/tmp/cache/assets/development/sprockets/656ea3403f27a33b86d5bf9e8a0c0e46 +0 -0
  129. data/test/app/tmp/cache/assets/development/sprockets/679705affe2ad274da1ad48cb5137c21 +0 -0
  130. data/test/app/tmp/cache/assets/development/sprockets/69a687de4cbb95365bf8aa2037d63726 +0 -0
  131. data/test/app/tmp/cache/assets/development/sprockets/69d5224a79e874431294e8adf04e7d65 +0 -0
  132. data/test/app/tmp/cache/assets/development/sprockets/6bc5a76ff13bc4daebb7e164a4b64196 +0 -0
  133. data/test/app/tmp/cache/assets/development/sprockets/6c1a5456c2e5d87285dd1910762fe01e +0 -0
  134. data/test/app/tmp/cache/assets/development/sprockets/6d52ff2c9298014f2d648eb9e04a61a6 +0 -0
  135. data/test/app/tmp/cache/assets/development/sprockets/7938636d16e11b754d4dd046b89863c4 +0 -0
  136. data/test/app/tmp/cache/assets/development/sprockets/7ce7981501e05438faa017eb2e197379 +0 -0
  137. data/test/app/tmp/cache/assets/development/sprockets/7e232a7b4ac10fe1350e2b9b05ab0b02 +0 -0
  138. data/test/app/tmp/cache/assets/development/sprockets/81d7800826e89041f377af8570b8324f +0 -0
  139. data/test/app/tmp/cache/assets/development/sprockets/81f524fed55fe63e95c1aeccb5d83571 +0 -0
  140. data/test/app/tmp/cache/assets/development/sprockets/85984636ee801f63af86b35d7697d4c5 +0 -0
  141. data/test/app/tmp/cache/assets/development/sprockets/88de2cf8ce5990c5fa59f7c9f4599a65 +0 -0
  142. data/test/app/tmp/cache/assets/development/sprockets/8932a78ffe18ad2e3bb7ceb90ac4b933 +0 -0
  143. data/test/app/tmp/cache/assets/development/sprockets/8d6fd863923e78438318b02bf83be1c4 +0 -0
  144. data/test/app/tmp/cache/assets/development/sprockets/8f43db1e57a90ffbae3be00a895d5a09 +0 -0
  145. data/test/app/tmp/cache/assets/development/sprockets/91e11940ab63a407af03d21720ac2951 +0 -0
  146. data/test/app/tmp/cache/assets/development/sprockets/938abfdc262a8ab42e768545640bfb2a +0 -0
  147. data/test/app/tmp/cache/assets/development/sprockets/9e760b9565b110e433b7e42f827cb5f8 +0 -0
  148. data/test/app/tmp/cache/assets/development/sprockets/9e8fbfd56e8ef705ba94bb03b5b3696e +0 -0
  149. data/test/app/tmp/cache/assets/development/sprockets/9ebbf73fb48cdf8bc07a8bfdd6d14328 +0 -0
  150. data/test/app/tmp/cache/assets/development/sprockets/9f240d481b0818a6da0b1a1aaaac2b54 +0 -0
  151. data/test/app/tmp/cache/assets/development/sprockets/a2b956b30a80f996b5aeb1b2f226775c +0 -0
  152. data/test/app/tmp/cache/assets/development/sprockets/a5b5ed9849e8019160b73aa554132b37 +0 -0
  153. data/test/app/tmp/cache/assets/development/sprockets/a692ba7ed6cff183bb840c2622233c87 +0 -0
  154. data/test/app/tmp/cache/assets/development/sprockets/a951f4ceb83ae691f002b4f6183bc1ed +0 -0
  155. data/test/app/tmp/cache/assets/development/sprockets/accc4dc17ef18d0b510917a005340da5 +0 -0
  156. data/test/app/tmp/cache/assets/development/sprockets/b2db166e9974feb35358e7fcce87cb39 +0 -0
  157. data/test/app/tmp/cache/assets/development/sprockets/b519a4f6c5b5a0d9236bdca14e0eb00d +0 -0
  158. data/test/app/tmp/cache/assets/development/sprockets/b5cbeb3def40b118469fff2d80c1b596 +0 -0
  159. data/test/app/tmp/cache/assets/development/sprockets/b6f65271a0e77b349529ce9148dd2782 +0 -0
  160. data/test/app/tmp/cache/assets/development/sprockets/b9ad7ea18b7e55c3626a15d1dae142ed +0 -0
  161. data/test/app/tmp/cache/assets/development/sprockets/bc384ea2fdcc667aa4282209caba921f +0 -0
  162. data/test/app/tmp/cache/assets/development/sprockets/bcf06bf434bb3d3a5769036d6e24b301 +0 -0
  163. data/test/app/tmp/cache/assets/development/sprockets/bd83357635155d3457747e92e47da0ed +0 -0
  164. data/test/app/tmp/cache/assets/development/sprockets/c39634555e4eba3595350eeea648ddf4 +0 -0
  165. data/test/app/tmp/cache/assets/development/sprockets/c3ef336ca8f7e64969d8bfdcf837ad10 +0 -0
  166. data/test/app/tmp/cache/assets/development/sprockets/c55037904a95162828e5d0b087677878 +0 -0
  167. data/test/app/tmp/cache/assets/development/sprockets/c733f1a2fe9d05a3a634ff64a394f64b +0 -0
  168. data/test/app/tmp/cache/assets/development/sprockets/c83a337688a52890ba93372fea6ec932 +0 -0
  169. data/test/app/tmp/cache/assets/development/sprockets/ca92d0dbc43c066af9b31f2bc26d038d +0 -0
  170. data/test/app/tmp/cache/assets/development/sprockets/cae2fc80bfbc81ec7b6c11a72be18c98 +0 -0
  171. data/test/app/tmp/cache/assets/development/sprockets/cd665363677ffcef0dde972284e8d942 +0 -0
  172. data/test/app/tmp/cache/assets/development/sprockets/d5154a1eda9cfbfe54e091d6ead1ac5f +0 -0
  173. data/test/app/tmp/cache/assets/development/sprockets/daa7fa7a610bc5951cc3c4403f290eb6 +0 -0
  174. data/test/app/tmp/cache/assets/development/sprockets/dabc0e94bc1e37007351ac756dd2dd6a +0 -0
  175. data/test/app/tmp/cache/assets/development/sprockets/edf3c55a27678996371bffe56298925b +0 -0
  176. data/test/app/tmp/cache/assets/development/sprockets/f0f04c3b2b0091fa3ca4a1edacc23a1c +0 -0
  177. data/test/app/tmp/cache/assets/development/sprockets/f8610737fbfdcb85db95ae7c6a70514e +0 -0
  178. data/test/app/tmp/restart.txt +0 -0
  179. data/test/shoppe_test.rb +0 -5
  180. data/test/test_helper.rb +1 -1
  181. metadata +298 -98
  182. data/app/helpers/shoppe/shoppe_helper.rb +0 -30
  183. data/db/migrate/20131012123829_create_shoppe_product_attributes.rb +0 -11
  184. data/db/migrate/20131012163301_add_public_boolean_to_product_attributes.rb +0 -5
  185. data/db/migrate/20131013123937_add_cost_prices_to_various_objects.rb +0 -8
  186. data/db/migrate/20131013131658_add_stock_control_boolean_to_products.rb +0 -5
  187. data/db/migrate/20131017144430_create_shoppe_stock_level_adjustments.rb +0 -18
  188. data/db/migrate/20131017180920_create_shoppe_countries.rb +0 -16
  189. data/db/migrate/20131017183211_create_shoppe_tax_rates.rb +0 -26
  190. data/db/migrate/20131020204719_add_countries_to_tax_rates_and_delivery_prices.rb +0 -6
  191. data/db/migrate/20131021135208_add_notes_to_orders.rb +0 -5
  192. data/db/migrate/20131022090919_refactor_order_items_to_allow_any_product.rb +0 -6
  193. data/db/migrate/20131022092904_rename_product_title_to_name.rb +0 -5
  194. data/db/migrate/20131022093538_stock_level_adjustments_should_be_polymorphic.rb +0 -6
  195. data/db/migrate/20131022135331_add_parent_id_to_products.rb +0 -5
  196. data/db/migrate/20131022145653_cost_price_should_be_default_to_zero.rb +0 -9
  197. data/test/dummy/config/initializers/session_store.rb +0 -3
  198. data/test/dummy/config/shoppe.yml +0 -7
  199. data/test/dummy/log/development.log +0 -1162
@@ -0,0 +1 @@
1
+ Hello.
data/Rakefile CHANGED
@@ -4,7 +4,7 @@ rescue LoadError
4
4
  puts 'You must `gem install bundler` and `bundle install` to run rake tasks'
5
5
  end
6
6
 
7
- APP_RAKEFILE = File.expand_path("../test/dummy/Rakefile", __FILE__)
7
+ APP_RAKEFILE = File.expand_path("../test/app/Rakefile", __FILE__)
8
8
  load 'rails/tasks/engine.rake'
9
9
 
10
10
  Bundler::GemHelper.install_tasks
@@ -16,3 +16,23 @@ Rake::TestTask.new(:test) do |t|
16
16
  t.pattern = 'test/**/*_test.rb'
17
17
  t.verbose = false
18
18
  end
19
+
20
+ namespace :shoppe do
21
+
22
+ desc "Generate RDoc documentation into doc/"
23
+ task :generate_docs do
24
+ system("rm -Rf doc")
25
+ system("bundle exec sdoc app/models lib README.rdoc")
26
+ end
27
+
28
+ desc "Publish RDoc documentation from doc to api.tryshoppe.com"
29
+ task :publish_docs do
30
+ if File.exist?("doc")
31
+ system "ssh root@tryshoppe.com rm -Rf /var/www/shoppe-api"
32
+ system "scp -r doc root@tryshoppe.com:/var/www/shoppe-api"
33
+ else
34
+ puts "No doc/ folder found to publish."
35
+ end
36
+ end
37
+ end
38
+
@@ -43,6 +43,11 @@ $ ->
43
43
  $('select.chosen').chosen()
44
44
  $('select.chosen-with-deselect').chosen({allow_single_deselect: true})
45
45
 
46
+ # Printables
47
+ $('a[rel=print]').on 'click', ->
48
+ window.open($(this).attr('href'), 'despatchnote', 'width=700,height=800')
49
+ false
50
+
46
51
  # Open AJAX dialogs
47
52
  $('a[rel=dialog]').on 'click', ->
48
53
  element = $(this)
@@ -81,6 +81,7 @@ header.main {
81
81
  h2.delivery_services { background-image:image-url('shoppe/icons/box.svg'); background-position: 0 3px; background-size:20px;}
82
82
  h2.tax_rates { background-image:image-url('shoppe/icons/currency.svg'); background-position: 0 2px; background-size:22px;}
83
83
  h2.users { background-image:image-url('shoppe/icons/id.svg'); background-position: 0 2px; background-size:22px;}
84
+ h2.settings { background-image:image-url('shoppe/icons/toolbox.svg'); background-position: 0 2px; background-size:22px;}
84
85
 
85
86
  }
86
87
 
@@ -154,10 +155,13 @@ header.main {
154
155
  }
155
156
  dd select { width:100%;}
156
157
  dd textarea { height:80px; }
157
- dd p.help { margin-top:15px; color:#333; background:image-url('shoppe/icons/support.svg') no-repeat 0 1px; background-size:13px; padding-left:15px;}
158
+ dd p.help { margin-top:15px; color:#333; background:image-url('shoppe/icons/support.svg') no-repeat 0 3px; line-height:1.5; background-size:13px; padding-left:18px; opacity:0.7;}
158
159
  dd.checkbox { margin-top:14px; font-size:1.1em; color:#999;}
159
160
  dd.checkbox input { float:left; margin-right:10px; margin-top:2px; }
160
-
161
+ dd div.radios {
162
+ padding-top:4px;
163
+ input,label { margin-right:10px;}
164
+ }
161
165
  &.half {
162
166
  width:49%;
163
167
  margin:0;
@@ -172,9 +176,17 @@ header.main {
172
176
  &:nth-child(2) { margin-left:2%; width:32%;}
173
177
  &:last-child { float:right; width:33%;}
174
178
  }
175
-
176
179
  }
177
180
 
181
+ dl.sided {
182
+ clear:both;
183
+ dt { float:left; width:25%; text-align:right; padding-top:4px;}
184
+ dd { margin-left:30%; }
185
+ dd p.help { margin-top:10px;}
186
+ dd div.checkbox { padding-top:5px;}
187
+ }
188
+
189
+
178
190
  //
179
191
  // margined container
180
192
  //
@@ -204,6 +216,7 @@ header.main {
204
216
  p.submit .button { margin-right:5px;}
205
217
  p.submit .right .button {margin-left:5px; margin-right:0;}
206
218
  p.submit span.right { float:right;}
219
+ p.submit.sided { padding-left:30%;}
207
220
  .errorExplanation {
208
221
  margin-bottom:25px;
209
222
  border:1px solid #EB2732;
@@ -49,6 +49,14 @@
49
49
  &:active { background:#e75d19}
50
50
  }
51
51
 
52
+ &.grey {
53
+ background-color:#777;
54
+ border-color:#777;
55
+ border-bottom-color:#777;
56
+ &:active { background:#888}
57
+ }
58
+
59
+
52
60
  &.white {
53
61
  background-color:#fff;
54
62
  color:#333 !important;
@@ -0,0 +1,67 @@
1
+ /*
2
+ *= require shoppe/reset
3
+ */
4
+ html { font-family:'Helvetica Neue', Helvetica, Arial, sans-serif; color:#000; font-size:12px;background:#efefef;}
5
+ #content {
6
+ background:#fff;
7
+ margin:5%;
8
+ outline:1px solid #ccc;
9
+ padding:35px;
10
+ }
11
+
12
+ div.despatchNote {
13
+ header {
14
+ float:left;
15
+ h1 {
16
+ font-size:1.8em;
17
+ font-weight:300;
18
+ }
19
+ h2 { margin-top:5px; font-size:2.3em; font-weight:500; }
20
+ width:40%;
21
+ }
22
+
23
+ .address {
24
+ border:1px solid #000;
25
+ padding:25px;
26
+ margin-left:45%;
27
+ line-height:1.5;
28
+ font-size:1.3em;
29
+ p.name { font-size:1.2em; font-weight:500;}
30
+ }
31
+ table.details {
32
+ width:100%;
33
+ margin:25px 0;
34
+ td, th {
35
+ border:1px solid #000;
36
+ padding:10px;
37
+ text-align:center;
38
+ }
39
+ th { background:#efefef;}
40
+ }
41
+
42
+ table.items {
43
+ width:100%;
44
+ margin:25px 0;
45
+ td, th {
46
+ border:1px solid #000;
47
+ padding:10px;
48
+ text-align:center;
49
+ &.check { width:5%;}
50
+ }
51
+ th { background:#efefef;}
52
+ }
53
+
54
+ p.footer {
55
+ font-size:1.2em;
56
+ border:1px solid #000;
57
+ padding:15px;
58
+ text-align:center;
59
+ }
60
+ }
61
+
62
+
63
+ @media print {
64
+ html { background:none;}
65
+ body {margin:5%;}
66
+ #content { margin:0; padding:0; outline:0;}
67
+ }
@@ -1,8 +1,6 @@
1
1
  module Shoppe
2
2
  class ApplicationController < ActionController::Base
3
3
 
4
- # Require that a user is logged in for all parts of the Shoppe admin
5
- # interface.
6
4
  before_filter :login_required
7
5
 
8
6
  rescue_from ActiveRecord::DeleteRestrictionError do |e|
@@ -16,39 +14,32 @@ module Shoppe
16
14
 
17
15
  private
18
16
 
19
- # If not logged in, redirect users to the login page. This should be
20
- # used in a before filter.
21
17
  def login_required
22
18
  unless logged_in?
23
19
  redirect_to login_path
24
20
  end
25
21
  end
26
22
 
27
- # Is there a user currently logged in?
28
23
  def logged_in?
29
24
  current_user.is_a?(User)
30
25
  end
31
26
 
32
- # Returns the currently logged in user
33
27
  def current_user
34
28
  @current_user ||= login_from_session || login_with_demo_mdoe || :false
35
29
  end
36
30
 
37
- # Attempt to find a user based on the value stored in the local session
38
31
  def login_from_session
39
32
  if session[:shoppe_user_id]
40
33
  @user = User.find_by_id(session[:shoppe_user_id])
41
34
  end
42
35
  end
43
36
 
44
- # Attempt to login using the demo mode
45
37
  def login_with_demo_mdoe
46
- if Shoppe.config[:demo_mode]
38
+ if Shoppe.settings.demo_mode?
47
39
  @user = User.first
48
40
  end
49
41
  end
50
42
 
51
- # Expose a current_user and logged_in? as helpers to views
52
43
  helper_method :current_user, :logged_in?
53
44
 
54
45
  end
@@ -38,6 +38,10 @@ module Shoppe
38
38
  @order.pay!(params[:payment_reference], params[:payment_method].blank? ? 'Unknown' : params[:payment_method])
39
39
  redirect_to @order, :notice => "Order has been marked as paid successfully"
40
40
  end
41
+
42
+ def despatch_note
43
+ render :layout => 'shoppe/printable'
44
+ end
41
45
 
42
46
  end
43
47
  end
@@ -1,5 +1,6 @@
1
1
  module Shoppe
2
2
  class SessionsController < Shoppe::ApplicationController
3
+
3
4
  layout 'shoppe/sub'
4
5
  skip_before_filter :login_required, :only => [:new, :create, :reset]
5
6
 
@@ -0,0 +1,12 @@
1
+ module Shoppe
2
+ class SettingsController < ApplicationController
3
+
4
+ before_filter { @active_nav = :settings }
5
+
6
+ def update
7
+ Shoppe::Setting.update_from_hash(params[:settings].permit!)
8
+ redirect_to :settings, :notice => "Settings have been updated successfully."
9
+ end
10
+
11
+ end
12
+ end
@@ -3,8 +3,8 @@ module Shoppe
3
3
 
4
4
  before_filter { @active_nav = :users }
5
5
  before_filter { params[:id] && @user = Shoppe::User.find(params[:id]) }
6
- if Shoppe.config[:demo_mode]
7
- before_filter(:only => [:create, :update, :destroy]) do
6
+ before_filter(:only => [:create, :update, :destroy]) do
7
+ if Shoppe.settings.demo_mode?
8
8
  raise Shoppe::Error, "You cannot make changes to user in demo mode. Sorry about that."
9
9
  end
10
10
  end
@@ -43,7 +43,7 @@ module Shoppe
43
43
  private
44
44
 
45
45
  def safe_params
46
- params[:product].permit(:name, :permalink, :sku, :default_image_file, :price, :cost_price, :tax_rate_id, :weight, :stock_control, :active)
46
+ params[:product].permit(:name, :permalink, :sku, :default_image_file, :price, :cost_price, :tax_rate_id, :weight, :stock_control, :active, :default)
47
47
  end
48
48
 
49
49
  end
@@ -1,10 +1,65 @@
1
- module Shoppe::ApplicationHelper
1
+ module Shoppe
2
+ module ApplicationHelper
2
3
 
3
- # Return all currencies with the currency provided by the Shoppe
4
- # configuration file.
5
- def number_to_currency(number, options = {})
6
- options[:unit] ||= Shoppe.config[:currency_unit]
7
- super
8
- end
4
+ def number_to_currency(number, options = {})
5
+ options[:unit] ||= Shoppe.settings.currency_unit
6
+ super
7
+ end
8
+
9
+ def number_to_weight(kg)
10
+ "#{kg}#{t('shoppe.helpers.number_to_weight.kg', :default => 'kg')}"
11
+ end
12
+
13
+ def status_tag(status)
14
+ content_tag :span, status, :class => "status-tag #{status}"
15
+ end
9
16
 
10
- end
17
+ def attachment_preview(attachment, options = {})
18
+ if attachment
19
+ String.new.tap do |s|
20
+ if attachment.image?
21
+ style = "style='background-image:url(#{attachment.path})'"
22
+ else
23
+ style = ''
24
+ end
25
+ s << "<div class='attachmentPreview #{attachment.image? ? 'image' : 'doc'}'>"
26
+ s << "<div class='imgContainer'><div class='img' #{style}></div></div>"
27
+ s << "<div class='desc'>"
28
+ s << "<span class='filename'><a href='#{attachment_path(attachment)}'>#{attachment.file_name}</a></span>"
29
+ s << "<span class='delete'>"
30
+ s << link_to(t('shoppe.helpers.attachment_preview.delete', :default => 'Delete this file?'), attachment_path(attachment), :method => :delete, :data => {:confirm => t('shoppe.helpers.attachment_preview.delete_confirm', :default => "Are you sure you wish to remove this attachment?")})
31
+ s << "</span>"
32
+ s << "</div>"
33
+ s << "</div>"
34
+ end.html_safe
35
+ elsif !options[:hide_if_blank]
36
+ "<div class='attachmentPreview'><div class='imgContainer'><div class='img none'></div></div><div class='desc none'>No attachment</div></div>".html_safe
37
+ end
38
+ end
39
+
40
+ def settings_label(field)
41
+ "<label for='settings_#{field}'>#{t("shoppe.settings.labels.#{field}")}</label>".html_safe
42
+ end
43
+
44
+ def settings_field(field, options = {})
45
+ default = t("shoppe.settings.defaults")[field.to_sym]
46
+ value = (params[:settings] && params[:settings][field]) || Shoppe.settings[field.to_s]
47
+ type = t("shoppe.settings.types")[field.to_sym] || 'string'
48
+ case type
49
+ when 'boolean'
50
+ String.new.tap do |s|
51
+ value = default if value.blank?
52
+ s << "<div class='radios'>"
53
+ s << radio_button_tag("settings[#{field}]", 'true', value == true, :id => "settings_#{field}_true")
54
+ s << label_tag("settings_#{field}_true", t("shoppe.settings.options.#{field}.affirmative", :default => 'Yes'))
55
+ s << radio_button_tag("settings[#{field}]", 'false', value == false, :id => "settings_#{field}_false")
56
+ s << label_tag("settings_#{field}_false", t("shoppe.settings.options.#{field}.negative", :default => 'No'))
57
+ s << "</div>"
58
+ end.html_safe
59
+ else
60
+ text_field_tag "settings[#{field}]", value, options.merge(:placeholder => default, :class => 'text')
61
+ end
62
+ end
63
+
64
+ end
65
+ end
@@ -1,27 +1,25 @@
1
1
  module Shoppe
2
2
  class OrderMailer < ActionMailer::Base
3
3
 
4
- default :from => "#{Shoppe.config[:store_name]} <#{Shoppe.config[:email_address]}>"
5
-
6
4
  def received(order)
7
5
  @order = order
8
- mail :to => order.email_address, :subject => I18n.t('shoppe.order_mailer.received.subject', :default => "Order Confirmation")
6
+ mail :from => Shoppe.settings.outbound_email_address, :to => order.email_address, :subject => I18n.t('shoppe.order_mailer.received.subject', :default => "Order Confirmation")
9
7
  end
10
8
 
11
9
  def accepted(order)
12
10
  @order = order
13
- mail :to => order.email_address, :subject => I18n.t('shoppe.order_mailer.received.accepted', :default => "Order Accepted")
11
+ mail :from => Shoppe.settings.outbound_email_address, :to => order.email_address, :subject => I18n.t('shoppe.order_mailer.received.accepted', :default => "Order Accepted")
14
12
  end
15
13
 
16
14
  def rejected(order)
17
15
  @order = order
18
- mail :to => order.email_address, :subject => I18n.t('shoppe.order_mailer.received.rejected', :default => "Order Rejected")
16
+ mail :from => Shoppe.settings.outbound_email_address, :to => order.email_address, :subject => I18n.t('shoppe.order_mailer.received.rejected', :default => "Order Rejected")
19
17
  end
20
18
 
21
19
  def shipped(order)
22
20
  @order = order
23
- mail :to => order.email_address, :subject => I18n.t('shoppe.order_mailer.received.shipped', :default => "Order Shipped")
21
+ mail :from => Shoppe.settings.outbound_email_address, :to => order.email_address, :subject => I18n.t('shoppe.order_mailer.received.shipped', :default => "Order Shipped")
24
22
  end
25
-
23
+
26
24
  end
27
25
  end
@@ -1,10 +1,10 @@
1
1
  module Shoppe
2
2
  class UserMailer < ActionMailer::Base
3
- default :from => "#{Shoppe.config[:store_name]} <#{Shoppe.config[:email_address]}>"
4
3
 
5
4
  def new_password(user)
6
5
  @user = user
7
- mail :to => user.email_address, :subject => "Your new Shoppe password"
6
+ mail :from => Shoppe.settings.outbound_email_address, :to => user.email_address, :subject => "Your new Shoppe password"
8
7
  end
8
+
9
9
  end
10
10
  end
@@ -1,3 +1,17 @@
1
+ # == Schema Information
2
+ #
3
+ # Table name: shoppe_countries
4
+ #
5
+ # id :integer not null, primary key
6
+ # name :string(255)
7
+ # code2 :string(255)
8
+ # code3 :string(255)
9
+ # continent :string(255)
10
+ # tld :string(255)
11
+ # currency :string(255)
12
+ # eu_member :boolean default(FALSE)
13
+ #
14
+
1
15
  module Shoppe
2
16
  class Country < ActiveRecord::Base
3
17
 
@@ -5,7 +19,9 @@ module Shoppe
5
19
  self.table_name = 'shoppe_countries'
6
20
 
7
21
  # Relationships
8
- has_many :orders, :dependent => :restrict_with_exception, :class_name => 'Shoppe::Order'
22
+ has_many :billed_orders, :dependent => :restrict_with_exception, :class_name => 'Shoppe::Order', :foreign_key => 'billing_country_id'
23
+ has_many :delivered_orders, :dependent => :restrict_with_exception, :class_name => 'Shoppe::Order', :foreign_key => 'delivery_country_id'
24
+
9
25
 
10
26
  # Scopes
11
27
  scope :ordered, -> { order('shoppe_countries.name asc') }
@@ -1,3 +1,18 @@
1
+ # == Schema Information
2
+ #
3
+ # Table name: shoppe_delivery_services
4
+ #
5
+ # id :integer not null, primary key
6
+ # name :string(255)
7
+ # code :string(255)
8
+ # default :boolean default(FALSE)
9
+ # active :boolean default(TRUE)
10
+ # created_at :datetime
11
+ # updated_at :datetime
12
+ # courier :string(255)
13
+ # tracking_url :string(255)
14
+ #
15
+
1
16
  module Shoppe
2
17
  class DeliveryService < ActiveRecord::Base
3
18