Compare commits

...

287 Commits

Author SHA1 Message Date
Luis Ramos
26cd0f4a9d Merge pull request #5023 from mkllnk/5019-invoice-bill-address
Display shipping and billing address on invoices
2020-03-21 20:38:00 +00:00
Luis Ramos
17c2f7b138 Merge pull request #4889 from luisramos0/3-0-prod-set
[Spree 2.1] Fix ProductSet spec (1 broken spec)
2020-03-20 19:33:19 +00:00
Matt-Yorkley
70643a84b2 Update all locales with the latest Transifex translations 2020-03-20 18:44:23 +01:00
Matt-Yorkley
62a00b17a2 Merge pull request #5026 from Matt-Yorkley/checkout_display
Temporarily hide OC selector in checkout page
2020-03-20 18:33:47 +01:00
Pau Pérez Fabregat
c4f96a1dcf Merge pull request #4972 from mkllnk/4810-tab-navigation
4810 Shop tab / page navigation with browser buttons
2020-03-20 15:24:50 +01:00
Pau Pérez Fabregat
6f4f3d42cc Merge pull request #5012 from openfoodfoundation/dependabot/bundler/rack-mini-profiler-2.0.1
Bump rack-mini-profiler from 2.0.0 to 2.0.1
2020-03-20 15:22:43 +01:00
Matt-Yorkley
e8692fec4c Temporarily hide OC selector in checkout page 2020-03-20 12:08:58 +01:00
Luis Ramos
3b2c10526d Merge pull request #4838 from openfoodfoundation/dependabot/bundler/jquery-rails-3.1.5
[Security] Bump jquery-rails from 3.0.4 to 3.1.5
2020-03-20 09:49:22 +00:00
Maikel Linke
b1a274ea27 Update translations 2020-03-20 16:20:21 +11:00
Maikel
00c7b9986b Merge pull request #5020 from openfoodfoundation/transifex
Transifex
2020-03-20 16:15:54 +11:00
Maikel Linke
25b11f1f4b Display delivery details in the header 2020-03-20 15:51:49 +11:00
Maikel Linke
22384cb4da Display shipping and billing address on invoices 2020-03-20 15:14:24 +11:00
Transifex-Openfoodnetwork
9dc18afef0 Updating translations for config/locales/pt_BR.yml 2020-03-20 12:20:04 +11:00
Transifex-Openfoodnetwork
d2d3d767ac Updating translations for config/locales/en_GB.yml 2020-03-19 23:53:09 +11:00
Transifex-Openfoodnetwork
a4ff74272b Updating translations for config/locales/nb.yml 2020-03-19 22:47:36 +11:00
Transifex-Openfoodnetwork
1000dc52bf Updating translations for config/locales/en_FR.yml 2020-03-19 19:37:32 +11:00
Transifex-Openfoodnetwork
54b8d22e0d Updating translations for config/locales/fr.yml 2020-03-19 19:37:21 +11:00
Maikel Linke
7e00f78a77 Highlight menu item only when active or hovered
The `:focus` selector meant that every link that was clicked on was
still highlighted after going back or forward in the browser history. We
don't need that selector because tabs you click on are then active and
are highlighted anyway.
2020-03-19 15:49:29 +11:00
Maikel Linke
5a9b5660f1 Simplify logic in PageSelectionCtrl 2020-03-19 15:38:00 +11:00
Maikel Linke
1d42ce885b Stay on shop page when opening login modal
The login modal changes the URL to `#/login` which interfers with our
shop pages. In order to show the right shop page, we need to know which
pages are valid and where we have been before we clicked on Login.
2020-03-19 15:38:00 +11:00
Maikel Linke
17751c448f Rename PageSelectionCtrl for clarity 2020-03-19 15:37:13 +11:00
Maikel Linke
4b8d9d18d7 Simplify PagesetCtrl 2020-03-19 15:37:13 +11:00
Maikel Linke
a21ef19529 Render only shop tabs within shop
The include directive was listening to all $location paths including
`#login` which is unrelated to the shop tabs. Angular tried to load the
template `shop/login.html` which doesn't exist.

We now whitelist the templates that can be included by having an include
tag for each shop tab/page.
2020-03-19 15:37:13 +11:00
Maikel Linke
ea80ae3832 Enable page navigation via URL fragment
The broadcasting of notifications didn't update properly and I couldn't
find a way to listen to $location updates. I replaced the three
intertwined directives with one controller and a bit more HTML code. Now
we have only one scope that listens to $location and all browser actions
like the back button is reflected in the page.

As nice side-effect, the menu links have now the right destination so
that you can copy the link and paste it into another browser window.

40 lines less code.
2020-03-19 15:37:13 +11:00
Maikel Linke
bf26a26743 Reduce complexity by removing unused code branch 2020-03-19 15:36:24 +11:00
Maikel Linke
e3f840f48c Remove dependency to Tabsets 2020-03-19 15:36:23 +11:00
Maikel Linke
42ca7888c0 Simplify by reducing unused options 2020-03-19 15:36:23 +11:00
Maikel Linke
8aa892136e Duplicate shop tab code for rewrite
The old code is still used on the user page.
2020-03-19 15:36:23 +11:00
Maikel Linke
2d21341183 Update all locales with the latest Transifex translations 2020-03-19 14:06:04 +11:00
Maikel
5cabf59015 Merge pull request #5016 from openfoodfoundation/revert-4879-inner-join-visible-orders
Revert "Inner join visible orders"
2020-03-19 12:37:20 +11:00
Maikel
289dff5b91 Merge pull request #4988 from openfoodfoundation/transifex
Transifex
2020-03-19 12:06:37 +11:00
Maikel
c4e4beb912 Revert "Inner join visible orders" 2020-03-19 12:01:00 +11:00
Maikel
27d8951add Merge pull request #5013 from openfoodfoundation/mobile-ux-3
Merge mobile-ux-3 branch into master
2020-03-19 11:51:41 +11:00
Transifex-Openfoodnetwork
f7720f1b1f Updating translations for config/locales/en_FR.yml 2020-03-19 05:18:19 +11:00
Transifex-Openfoodnetwork
c46ae4354d Updating translations for config/locales/en_FR.yml 2020-03-19 05:15:09 +11:00
Transifex-Openfoodnetwork
5f00323cbb Updating translations for config/locales/fr.yml 2020-03-19 05:14:27 +11:00
Transifex-Openfoodnetwork
c52f29706b Updating translations for config/locales/en_CA.yml 2020-03-19 03:47:42 +11:00
Luis Ramos
2590745b2e Merge pull request #4954 from luisramos0/dead_temp
Delete templates that are not used
2020-03-18 13:52:15 +00:00
Matt-Yorkley
6db0421347 Merge pull request #4764 from Matt-Yorkley/mobile-tabs-styling
[mobile ux] Mobile tabs styling
2020-03-18 08:42:44 +01:00
Maikel
b63c47cca2 Merge pull request #4816 from mkllnk/1860-copy-paste
1860 Remove style from pasted text for shopfront messages
2020-03-18 16:23:50 +11:00
Maikel
2b9f57f4e0 Merge pull request #4998 from mkllnk/4277-signup-flow
Direct new enterprise users to their dashboard
2020-03-18 16:17:41 +11:00
Matt-Yorkley
8a1de72542 Center order cycle select elements in tablet view 2020-03-17 20:32:18 +01:00
Matt-Yorkley
2cb3a0cd99 Adjust padding, size, colour (transparency), caret size and position, border-radius, etc 2020-03-17 20:32:18 +01:00
Matt-Yorkley
b0637a24ff Adjust padding, size, colour transparency, caret size 2020-03-17 20:32:18 +01:00
Matt-Yorkley
d969b68c8c Add placeholder to order cycle selector 2020-03-17 20:32:18 +01:00
Matt-Yorkley
a89d4266d5 Update ordercycleselector to show message in red and remove powertip. 2020-03-17 20:32:18 +01:00
Matt-Yorkley
4b8ced5fc0 Add right-margin on bullet points in groups tab 2020-03-17 20:32:18 +01:00
Matt-Yorkley
2678342122 Reduce padding on ordercycle selector 2020-03-17 20:32:18 +01:00
Matt-Yorkley
b33c819863 Reduce rounding on ordercycle edges (box-radius) 2020-03-17 20:32:18 +01:00
Matt-Yorkley
97d7e27786 Update social icon colours 2020-03-17 20:32:18 +01:00
Matt-Yorkley
e73e43838c Add 2px margin under Contact subheadings 2020-03-17 20:32:18 +01:00
Matt-Yorkley
cdc40fbc38 Update Contact tab subheading text colour 2020-03-17 20:32:18 +01:00
Matt-Yorkley
3430cc617a Maximise space for tabs to fit on small screens 2020-03-17 20:32:18 +01:00
Matt-Yorkley
ed6f042446 Adjust tab widths/spacing on mobile and tablet 2020-03-17 20:32:18 +01:00
Matt-Yorkley
80a8c436d6 Update box-shadow underneath tab buttons 2020-03-17 20:32:18 +01:00
Matt-Yorkley
049a87e8a9 Remove defunct text-shadow from tab text 2020-03-17 20:32:18 +01:00
Matt-Yorkley
deb5b8e74c Fix minor display issue where "Ready For" option with lots of characters is too big to fit on screen on mobile.
The layout was breaking in some specific cases where the content didn't fit on very small screens.
2020-03-17 20:32:18 +01:00
Matt-Yorkley
a5dd14d902 Adjust new colour variables to match Zeplin 2020-03-17 20:32:18 +01:00
Matt-Yorkley
9a6859edc0 Fix CodeClimate issue with SCSS variable naming 2020-03-17 20:32:18 +01:00
Matt-Yorkley
c0c53113d3 Change font on shop tab titles 2020-03-17 20:32:18 +01:00
Matt-Yorkley
26688409a1 Use alternate dots in <ul> display 2020-03-17 20:32:18 +01:00
Matt-Yorkley
0893d14025 Add new shop link colours 2020-03-17 20:32:18 +01:00
Matt-Yorkley
efd314e3b1 Restyle contact tab 2020-03-17 20:23:45 +01:00
Matt-Yorkley
bd7549c57f Update layout for producers and groups tabs 2020-03-17 20:23:45 +01:00
Matt-Yorkley
45cf54408d Readjust layout after rebase 2020-03-17 20:23:45 +01:00
Matt-Yorkley
15360740b1 Add ng-cloak to ordercycle box to improve appearance whilst page loads 2020-03-17 20:23:45 +01:00
Matt-Yorkley
5ce5072f26 Adjust position of OC popover tip to not cover up the "ready for" label 2020-03-17 20:23:45 +01:00
Matt-Yorkley
35133f7ee8 Adjust height of ordercycle selector on desktop 2020-03-17 20:23:45 +01:00
Matt-Yorkley
5becbc2a11 Move caret svg to /app/assets/images 2020-03-17 20:23:45 +01:00
Matt-Yorkley
390d80f0eb Update order cycle selector positioning 2020-03-17 20:23:45 +01:00
Matt-Yorkley
6da43850d1 Restyle order cycle dropdown 2020-03-17 20:23:45 +01:00
Matt-Yorkley
a146bdacc8 Realign ordercycle text on tablet downwards 2020-03-17 20:23:45 +01:00
Matt-Yorkley
43cadb00c4 Recolour order cycle selector 2020-03-17 20:23:45 +01:00
Matt-Yorkley
2e616a9e31 Fix conditional display of order cycle selection element 2020-03-17 20:23:45 +01:00
Matt-Yorkley
1927e2883e Move brackets inside conditionals for rendering last closed / next open message 2020-03-17 20:23:45 +01:00
Matt-Yorkley
a4b94cf39f Add dividing line on tabs
Shows a thin grey line when the tab view content is white, but doesn't interfere when the content below is a full-width colour image.
2020-03-17 20:23:45 +01:00
Matt-Yorkley
a35f3c130e Recolour shop tab buttons 2020-03-17 20:23:45 +01:00
Matt-Yorkley
a93243a8b7 Change vertical position of shop name in relation to logo 2020-03-17 20:23:45 +01:00
Matt-Yorkley
de4402457a Improve layout and positioning on mobile and tablet 2020-03-17 20:23:45 +01:00
Matt-Yorkley
bf9f7309f7 Adapt style definitions to altered layout 2020-03-17 20:23:45 +01:00
Matt-Yorkley
4b0e1610ec Update order cycle selection box 2020-03-17 20:23:45 +01:00
dependabot-preview[bot]
0c6fe20e82 Bump rack-mini-profiler from 2.0.0 to 2.0.1
Bumps [rack-mini-profiler](https://github.com/MiniProfiler/rack-mini-profiler) from 2.0.0 to 2.0.1.
- [Release notes](https://github.com/MiniProfiler/rack-mini-profiler/releases)
- [Changelog](https://github.com/MiniProfiler/rack-mini-profiler/blob/master/CHANGELOG.md)
- [Commits](https://github.com/MiniProfiler/rack-mini-profiler/compare/v2.0.0...v2.0.1)

Signed-off-by: dependabot-preview[bot] <support@dependabot.com>
2020-03-17 19:19:22 +00:00
Luis Ramos
0f2e23d225 Merge pull request #4968 from lin-d-hop/customer-balances
Revert changes that broke existing usage of this report
2020-03-17 18:06:35 +00:00
Pau Pérez Fabregat
129de8fd57 Merge pull request #5006 from Matt-Yorkley/loggageddon
Logageddon Hotfix
2020-03-17 14:48:12 +01:00
Matt-Yorkley
e24d858af9 Ensure log level is the default :info for staging and production
The default was being ignored in our new logging configuration, and the actual log output was way too high. This was causing serious disk space issues.
2020-03-17 12:25:25 +01:00
Matt-Yorkley
d2cacf5330 Add comments for unusable log_level setting 2020-03-17 12:22:58 +01:00
Transifex-Openfoodnetwork
af231d2ebe Updating translations for config/locales/fr.yml 2020-03-17 20:32:15 +11:00
Pau Pérez Fabregat
711a3debe7 Merge pull request #4990 from openfoodfoundation/dependabot/bundler/webmock-3.8.3
Bump webmock from 3.8.2 to 3.8.3
2020-03-17 09:59:10 +01:00
Pau Pérez Fabregat
d09b0849e4 Merge pull request #4936 from luisramos0/fix_order_syncer
Fixes spec/services/order_syncer_spec in rails 4
2020-03-17 09:56:17 +01:00
Pau Pérez Fabregat
c639821dc3 Merge pull request #4931 from luisramos0/fix_ent_ser
Fix serializers/api/enterprise_shopfront_serializer_spec in rails 4
2020-03-17 09:53:31 +01:00
Maikel
d9b643d795 Merge pull request #4799 from mkllnk/4771-back-to-shop-button
4771 Back to shop button
2020-03-17 19:51:02 +11:00
Maikel Linke
6b8b3be524 Show "Back To Store" button when no shop has been selected yet 2020-03-17 10:28:03 +11:00
Maikel Linke
1db8283e98 Link "Back To Store" button to products page 2020-03-17 10:28:03 +11:00
Maikel Linke
5fce40ee71 Link "Continue shopping" to products tab 2020-03-17 10:28:03 +11:00
Maikel Linke
c64493ca77 Continue shopping with the products list 2020-03-17 10:28:03 +11:00
Maikel Linke
5b942e6933 Add spec for "continue shopping" from cart
https://github.com/openfoodfoundation/openfoodnetwork/issues/4771
2020-03-17 10:28:03 +11:00
Luis Ramos
ffbb5934d7 Merge pull request #4989 from luisramos0/specs_in_engines
Adapt task that runs engine specs
2020-03-16 19:17:04 +00:00
Luis Ramos
bae9df8214 Merge pull request #4787 from luisramos0/catalog_domain
Add new domain/engine Catalog
2020-03-16 18:47:55 +00:00
Luis Ramos
5da47b3f19 Merge pull request #4757 from luisramos0/stripe_sca_extra
StripeSCA - Handle further SCA auth request when checking out
2020-03-16 16:45:28 +00:00
Luis Ramos
b14e4237cc Make the task that runs engines specs run from the main app, not inside the engine
Right now and for some time the engines are not independent of the main_app. We should aim for that but it will naturally take a while to disentangle the code
2020-03-16 16:20:36 +00:00
Pau Pérez Fabregat
3e7685193f Merge pull request #4996 from luisramos0/fix_build
Fix broken master build
2020-03-16 16:37:09 +01:00
Luis Ramos
8558000c22 Merge pull request #5 from coopdevs/fix-suppliers-report-test-case
Fix suppliers report test case
2020-03-16 13:47:03 +00:00
Pau Perez
6486e5f908 Provide a non-zero amount for ship/pay calculator
This way the adjustment's total_amount is not 0 and thus, not filtered
out but the report service.
2020-03-16 13:56:52 +01:00
Maikel Linke
9244a95472 Direct new enterprise users to their dashboard
People were directed to the home page and had to do several more clicks
to continue with their enterprise setup.
2020-03-16 11:18:32 +11:00
Transifex-Openfoodnetwork
bd237ef257 Updating translations for config/locales/fr_CA.yml 2020-03-15 07:22:12 +11:00
Transifex-Openfoodnetwork
bc06e10146 Updating translations for config/locales/en_CA.yml 2020-03-15 07:21:33 +11:00
Pau Perez
05eadac935 Fix some filtering test cases for fee report
The calculators of the adjustments related to the enterprise fees
created in the test setup have a preferred_amount of 0. So, when
computed, the adjustments' amounts end up being `0 = 0 * 1 line_item`.

Then, the ReportService filters these out in
`#exclude_groups_with_zero_total` from the result set. This is why the
assertions can't find them in `totals`.
2020-03-14 11:19:35 +01:00
Pau Perez
5a83b12c66 Make EnterpriseFee report SQL readable 2020-03-14 11:04:49 +01:00
Pau Perez
71576fd7db Refactor PerItem calculator to ease readability 2020-03-14 11:04:16 +01:00
Luis Ramos
63a1d4145a Adapt order factories to work with enterprise fees summaries report specs 2020-03-13 12:36:01 +00:00
Luis Ramos
1049525e50 Merge pull request #4963 from luisramos0/variants_fix
Fix 2 broken buttons in the product variants list page
2020-03-12 23:48:50 +00:00
Luis Ramos
bd32510837 Merge pull request #4860 from mkllnk/3395-remove-unused-assets
3395 remove unused assets
2020-03-12 22:44:41 +00:00
dependabot-preview[bot]
f0b40eea1e Bump webmock from 3.8.2 to 3.8.3
Bumps [webmock](https://github.com/bblimke/webmock) from 3.8.2 to 3.8.3.
- [Release notes](https://github.com/bblimke/webmock/releases)
- [Changelog](https://github.com/bblimke/webmock/blob/master/CHANGELOG.md)
- [Commits](https://github.com/bblimke/webmock/compare/v3.8.2...v3.8.3)

Signed-off-by: dependabot-preview[bot] <support@dependabot.com>
2020-03-12 19:20:17 +00:00
Transifex-Openfoodnetwork
ed790ab65d Updating translations for config/locales/en_GB.yml 2020-03-13 05:26:37 +11:00
Luis Ramos
46e23b28fd Merge pull request #4975 from openfoodfoundation/dependabot/bundler/rspec-rails-3.9.1
Bump rspec-rails from 3.9.0 to 3.9.1
2020-03-12 16:47:14 +00:00
Luis Ramos
bc904a7afa Merge pull request #4976 from openfoodfoundation/dependabot/bundler/rack-mini-profiler-2.0.0
Bump rack-mini-profiler from 1.1.6 to 2.0.0
2020-03-12 16:46:43 +00:00
Pau Perez
8ccc8dfaf6 Update all locales with the latest Transifex translations 2020-03-12 13:33:42 +01:00
Luis Ramos
55b32c828c Merge pull request #4978 from Matt-Yorkley/dev-env-reload
Fix reloading issue in dev environment
2020-03-12 12:22:00 +00:00
Pau Pérez Fabregat
25dfd8ad40 Merge pull request #4939 from openfoodfoundation/transifex
Transifex
2020-03-12 13:19:59 +01:00
Pau Pérez Fabregat
2a5311493f Merge pull request #4969 from luisramos0/oc_apli
Fix spec in rails 4 branch by making code in OrderCycleFormApplicator a bit more resilient
2020-03-12 12:51:23 +01:00
Pau Pérez Fabregat
57ac28cfbd Merge pull request #4970 from openfoodfoundation/dependabot/bundler/ddtrace-0.33.1
Bump ddtrace from 0.33.0 to 0.33.1
2020-03-12 12:50:01 +01:00
Pau Pérez Fabregat
fb02043e6e Merge pull request #4926 from luisramos0/prod_api
Fix products api spec in rails 4
2020-03-12 12:46:45 +01:00
Transifex-Openfoodnetwork
30d7cc89fa Updating translations for config/locales/pt_BR.yml 2020-03-12 09:25:51 +11:00
Transifex-Openfoodnetwork
d14b5eb46b Updating translations for config/locales/pt_BR.yml 2020-03-12 09:22:44 +11:00
dependabot-preview[bot]
8eb60388fd Bump rack-mini-profiler from 1.1.6 to 2.0.0
Bumps [rack-mini-profiler](https://github.com/MiniProfiler/rack-mini-profiler) from 1.1.6 to 2.0.0.
- [Release notes](https://github.com/MiniProfiler/rack-mini-profiler/releases)
- [Changelog](https://github.com/MiniProfiler/rack-mini-profiler/blob/master/CHANGELOG.md)
- [Commits](https://github.com/MiniProfiler/rack-mini-profiler/compare/v1.1.6...v2.0.0)

Signed-off-by: dependabot-preview[bot] <support@dependabot.com>
2020-03-11 19:19:24 +00:00
dependabot-preview[bot]
633f1bd7cf Bump rspec-rails from 3.9.0 to 3.9.1
Bumps [rspec-rails](https://github.com/rspec/rspec-rails) from 3.9.0 to 3.9.1.
- [Release notes](https://github.com/rspec/rspec-rails/releases)
- [Changelog](https://github.com/rspec/rspec-rails/blob/master/Changelog.md)
- [Commits](https://github.com/rspec/rspec-rails/compare/v3.9.0...v3.9.1)

Signed-off-by: dependabot-preview[bot] <support@dependabot.com>
2020-03-11 19:15:51 +00:00
Matt-Yorkley
933b5f1606 Fix reloading issue in dev environment
I constantly get `NameError: uninitialized constant Spree::AuthenticationHelpers` when touching local files and then reloading a page, and have to restart my rails server every time (in development). I read the other day that this is the best way to fix the issue, and it seems to work...
2020-03-11 15:31:25 +01:00
Transifex-Openfoodnetwork
4c7b8209b9 Updating translations for config/locales/nb.yml 2020-03-11 19:49:14 +11:00
Pau Pérez Fabregat
802ac647e3 Merge pull request #4879 from coopdevs/inner-join-visible-orders
Inner join visible orders
2020-03-10 22:54:03 +01:00
dependabot-preview[bot]
c83bded763 Bump ddtrace from 0.33.0 to 0.33.1
Bumps [ddtrace](https://github.com/DataDog/dd-trace-rb) from 0.33.0 to 0.33.1.
- [Release notes](https://github.com/DataDog/dd-trace-rb/releases)
- [Changelog](https://github.com/DataDog/dd-trace-rb/blob/master/CHANGELOG.md)
- [Commits](https://github.com/DataDog/dd-trace-rb/compare/v0.33.0...v0.33.1)

Signed-off-by: dependabot-preview[bot] <support@dependabot.com>
2020-03-10 19:19:31 +00:00
Luis Ramos
03246d425d Make this method handle the case where the variants hash passed is nil
This fixes a spec in the rails 4 branch
2020-03-10 18:41:26 +00:00
Luis Ramos
7585e3d1d6 The variants_to_a method was dead but actually we can use it to make the code simpler 2020-03-10 18:40:46 +00:00
Luis Ramos
bc1430c984 Make new_variant button work again by making a normal call to the server, isntead of an ajax call that was no longer working 2020-03-10 14:21:26 +00:00
Luis Ramos
676d949972 Make variants collection show deleted again by bypassing the default scope that removed deleted variants 2020-03-10 14:21:20 +00:00
lin-d-hop
e4bd7c4e30 Revert changes that broke existing usage of this report 2020-03-10 10:59:18 +00:00
Pau Pérez Fabregat
50cdda7c63 Merge pull request #4802 from luisramos0/too_many
Last batch to fix error "subquery with too many columns" in rails 4 branch
2020-03-10 09:20:44 +01:00
Pau Pérez Fabregat
d0af046e59 Merge pull request #4908 from luisramos0/package_spec
Make package spec work in rails 4
2020-03-10 09:17:53 +01:00
Pau Pérez Fabregat
5811f3ead1 Merge pull request #4905 from luisramos0/untouch
Remove some live but elderly debug code
2020-03-10 09:17:13 +01:00
Pau Pérez Fabregat
d7d3c9ea53 Merge pull request #4938 from openfoodfoundation/dependabot/bundler/ddtrace-0.33.0
Bump ddtrace from 0.32.0 to 0.33.0
2020-03-10 08:48:31 +01:00
Pau Pérez Fabregat
a02cc1de34 Merge pull request #4857 from luisramos0/schedules_ctrl
Remove dead spec in SchedulesController
2020-03-10 08:38:46 +01:00
Luis Ramos
94783f44f9 Delete templates that are not used 2020-03-09 15:30:37 +00:00
Luis Ramos
2184c7c06b Merge pull request #4856 from Matt-Yorkley/dead-code
Delete some dead code in Product Import (fixes 1 broken spec)
2020-03-07 15:26:39 +00:00
Transifex-Openfoodnetwork
928bf0d9c7 Updating translations for config/locales/fr.yml 2020-03-08 01:24:08 +11:00
Transifex-Openfoodnetwork
0d02b2afcf Updating translations for config/locales/en_FR.yml 2020-03-08 01:21:12 +11:00
Transifex-Openfoodnetwork
1e76f3f744 Updating translations for config/locales/fr.yml 2020-03-08 01:20:57 +11:00
dependabot-preview[bot]
7c3a0a292f Bump ddtrace from 0.32.0 to 0.33.0
Bumps [ddtrace](https://github.com/DataDog/dd-trace-rb) from 0.32.0 to 0.33.0.
- [Release notes](https://github.com/DataDog/dd-trace-rb/releases)
- [Changelog](https://github.com/DataDog/dd-trace-rb/blob/master/CHANGELOG.md)
- [Commits](https://github.com/DataDog/dd-trace-rb/compare/v0.32.0...v0.33.0)

Signed-off-by: dependabot-preview[bot] <support@dependabot.com>
2020-03-06 19:31:47 +00:00
Luis Ramos
c5ca0976a5 Merge pull request #4873 from jeduardo824/ampersand-not-showing-correctly
fix ampersand problem using ng-bind-html
2020-03-06 17:40:54 +00:00
Pau Pérez Fabregat
be7b3d5a12 Merge pull request #4809 from jeduardo824/redirect-to-shops-when-shop-does-not-exist
redirect to shops list when an enterprise is not found
2020-03-06 18:39:00 +01:00
Luis Ramos
d3f498f5b1 The shipping rates refresh process changed a little in spree 2.1 and the selection is and was random, it picks the first acceptable
In this case we need to specifically select one shipping method so that the test is valid
2020-03-06 16:39:20 +00:00
Luis Ramos
55941a1206 Round time values to make spec green as in rails 4, for unknown reason, the timestamps are differing in some miliseconds 2020-03-06 10:16:58 +00:00
Luis Ramos
6304a085c0 Update all locales with the latest Transifex translations 2020-03-06 08:30:04 +00:00
Luis Ramos
7c708de937 Merge pull request #4928 from openfoodfoundation/transifex
Transifex
2020-03-06 08:28:09 +00:00
Transifex-Openfoodnetwork
5d51e5d393 Updating translations for config/locales/pt_BR.yml 2020-03-06 07:41:46 +11:00
Transifex-Openfoodnetwork
464717dec5 Updating translations for config/locales/pt_BR.yml 2020-03-06 07:38:36 +11:00
Pau Pérez Fabregat
7a06018c3e Merge pull request #4874 from openfoodfoundation/transifex
Transifex
2020-03-05 19:29:21 +01:00
Pau Pérez Fabregat
b8c76ff633 Merge pull request #4906 from luisramos0/ent_caching
Fix enterprise_caching_spec in rails 4
2020-03-05 19:28:54 +01:00
Pau Pérez Fabregat
1ecc0bfe07 Merge pull request #4927 from luisramos0/variants_delete
Fix spree/admin/variants_controller_spec.rb in rails 4
2020-03-05 19:24:35 +01:00
Pau Pérez Fabregat
600d2d23c8 Merge pull request #4912 from luisramos0/cart_serv_fix
Make cart_service spec green in rails 4 branch
2020-03-05 19:11:58 +01:00
Pau Pérez Fabregat
bf3211fd01 Merge pull request #4918 from luisramos0/bulk_lis
Fix spec/controllers/admin/bulk_line_items_controller_spec in rails 4
2020-03-05 19:07:37 +01:00
Pau Pérez Fabregat
5fd0d9406d Merge pull request #4923 from openfoodfoundation/dependabot/bundler/oj-3.10.5
Bump oj from 3.10.3 to 3.10.5
2020-03-05 19:06:20 +01:00
Pau Pérez Fabregat
c78a6bea91 Merge pull request #4921 from luisramos0/li_ctrl
Fix line_items_controller_spec in the rails 4 branch
2020-03-05 19:05:46 +01:00
Pau Pérez Fabregat
be9f33312b Merge pull request #4904 from luisramos0/tax_rates_match
Move TaxRate#match to OFN to avoid having to adapt to the spree 2.1 version
2020-03-05 18:55:55 +01:00
Luis Ramos
f23575302b In rails 4 variant.destroy is removing the variants from the exchanges as needed and variant.exchange_variants becomes immediatly empty but variant.exchanges is not automatically updated anymore and needs a refresh to become empty 2020-03-05 17:07:08 +00:00
Pau Perez
0042ab2f28 Rewrite INNER JOIN in ActiveRecord's DSL 2020-03-05 17:45:06 +01:00
Pau Perez
53a63775fe Replace LEFT JOIN with INNER JOIN
I see no reason why a LEFT might be needed and its the root cause of the
awful performance.
2020-03-05 17:45:06 +01:00
Pau Perez
461b1b26f3 Add controller tests to cover totals by supplier 2020-03-05 17:45:06 +01:00
Luis Ramos
f13d7d6845 Fix products api spec in rails 4 2020-03-05 15:20:45 +00:00
dependabot-preview[bot]
e4d09b5404 Bump oj from 3.10.3 to 3.10.5
Bumps [oj](https://github.com/ohler55/oj) from 3.10.3 to 3.10.5.
- [Release notes](https://github.com/ohler55/oj/releases)
- [Changelog](https://github.com/ohler55/oj/blob/develop/CHANGELOG.md)
- [Commits](https://github.com/ohler55/oj/compare/v3.10.3...v3.10.5)

Signed-off-by: dependabot-preview[bot] <support@dependabot.com>
2020-03-04 19:16:40 +00:00
Luis Ramos
415415273c In rails 4 we need to update the stub after we update the order.user otherwise the stub will return the previous value 2020-03-04 15:50:52 +00:00
Luis Ramos
d969190ca5 Bypass problem with quick_login_as_admin in rails 4 and just user simple factory 2020-03-04 14:29:11 +00:00
Luis Ramos
a180576c0a Make cart_service spec green in rails 4 branch 2020-03-03 17:29:38 +00:00
Luis Ramos
7fdaa0f0c7 Make package spec work in rails 4 by persisting the test enterprises so that the copnnection between shipping methods and enterprises works 2020-03-03 14:46:12 +00:00
Luis Ramos
ba750547a2 The touch process in 'belongs_to :supplier, class_name: 'Enterprise', touch: true' must have changed in rails 4 and now we need to reload the enterprise to get the new updated_at value 2020-03-03 12:26:18 +00:00
Luis Ramos
af8369ae1b Remove 5 years old debug code
This reverts ab9bc7b1dc, it can be added if the issue happens again
2020-03-03 10:56:57 +00:00
Luis Ramos
829a73c58d Merge pull request #4886 from openfoodfoundation/dependabot/bundler/oj-3.10.3
Bump oj from 3.10.2 to 3.10.3
2020-03-03 09:57:46 +00:00
Luis Ramos
a2691df64e Merge pull request #4887 from openfoodfoundation/dependabot/bundler/rubocop-0.80.1
Bump rubocop from 0.80.0 to 0.80.1
2020-03-03 09:56:37 +00:00
Luis Ramos
6c8b175344 Merge match and its alias method 2020-03-03 09:29:02 +00:00
Pau Pérez Fabregat
ad10053271 Merge pull request #4903 from luisramos0/address_finder
[Spree 2.1] Adapt address finder spec to work with spree 2.1 code
2020-03-03 10:27:13 +01:00
Luis Ramos
a508c55700 Bring TaxRate.match to OFN
The version of this method in spree 2.1 will break our build

This way we simply bypass this fix in spree: https://github.com/spree/spree/pull/3669

We can get back to this in the future if we ever experience the mentioned bug
2020-03-03 09:27:04 +00:00
Transifex-Openfoodnetwork
2712be3fa4 Updating translations for config/locales/fr.yml 2020-03-03 14:14:38 +11:00
Transifex-Openfoodnetwork
484326561f Updating translations for config/locales/en_GB.yml 2020-03-03 14:11:28 +11:00
Transifex-Openfoodnetwork
7ea96f88e8 Updating translations for config/locales/en_CA.yml 2020-03-03 14:08:26 +11:00
Transifex-Openfoodnetwork
de752b05a7 Updating translations for config/locales/fr_CA.yml 2020-03-03 14:08:17 +11:00
Maikel
0b18344572 Merge pull request #4790 from mkllnk/4779-payment-method-display
4779 payment method display
2020-03-03 10:10:51 +11:00
Luis Ramos
690474c01a Adapt address finder spec to work with spree 2.1 code
Order ship address is required to get have an order with shipping rates
2020-03-02 21:55:21 +00:00
Luis Ramos
777754f8a9 Remove dead code that creates products in product_set 2020-03-02 19:41:51 +00:00
dependabot-preview[bot]
e4c5893c1e Bump rubocop from 0.80.0 to 0.80.1
Bumps [rubocop](https://github.com/rubocop-hq/rubocop) from 0.80.0 to 0.80.1.
- [Release notes](https://github.com/rubocop-hq/rubocop/releases)
- [Changelog](https://github.com/rubocop-hq/rubocop/blob/master/CHANGELOG.md)
- [Commits](https://github.com/rubocop-hq/rubocop/compare/v0.80.0...v0.80.1)

Signed-off-by: dependabot-preview[bot] <support@dependabot.com>
2020-03-02 19:36:43 +00:00
dependabot-preview[bot]
67aeae4a6d Bump oj from 3.10.2 to 3.10.3
Bumps [oj](https://github.com/ohler55/oj) from 3.10.2 to 3.10.3.
- [Release notes](https://github.com/ohler55/oj/releases)
- [Changelog](https://github.com/ohler55/oj/blob/develop/CHANGELOG.md)
- [Commits](https://github.com/ohler55/oj/compare/v3.10.2...v3.10.3)

Signed-off-by: dependabot-preview[bot] <support@dependabot.com>
2020-03-02 19:34:09 +00:00
Luis Ramos
02008769e9 Make spree_payment.cvv_response_message without size limit so that long stripe redirect URLs can be stored there 2020-03-02 17:31:01 +00:00
Luis Ramos
65dd9f51cf Add spec to cover update request where a stripe redirect must happen 2020-03-02 17:30:12 +00:00
Luis Ramos
a224c53200 Add spec to test receiving a redirect from stripe with a valid payment intent id 2020-03-02 17:30:12 +00:00
Luis Ramos
66f07c0d1c Make checkout controller spec test both extracted payment redirects 2020-03-02 17:30:12 +00:00
Luis Ramos
d5287026f8 Add spec for Checkout::PostCheckoutActions 2020-03-02 17:30:12 +00:00
Luis Ramos
6b80eb2c16 Add spec for AuthorizeResponsePatcher 2020-03-02 17:30:12 +00:00
Luis Ramos
b54b981740 Improve readability of PaymentIntentValidator and cover with specs 2020-03-02 17:30:12 +00:00
Luis Ramos
895032fe6a Move stubbed requests to the top as they are the same for every test 2020-03-02 17:30:12 +00:00
Luis Ramos
531c385aae Adapt stripe sca spec to new double step auth+capture payment process 2020-03-02 17:30:12 +00:00
Luis Ramos
d0a3ab68f3 Make processing payments also pending payments 2020-03-02 17:30:12 +00:00
luisramos0
b5038c5745 Adapt subscriptionPaymentUpdater to include pending payments as pending payments! Pending payments of credit cards are payments already authorized, ready to be captured
This is problably what will happen with subscriptions credit cards where payments will be authorized by the customer and the confirmation process on process_payments! will just capture the payment
2020-03-02 17:30:12 +00:00
luisramos0
6877485c90 Extract AuthorizeResponsePatcher from stripeSCA gateway 2020-03-02 17:30:12 +00:00
luisramos0
95c1b7f7a6 Extract PaymentIntentValidator from StripeSCA gateway 2020-03-02 17:30:12 +00:00
luisramos0
3fcf286516 Extract PostCheckoutActions from checkout controller 2020-03-02 17:30:12 +00:00
luisramos0
e2cdb01a28 Improve readability of stripe sca gateway code 2020-03-02 17:30:12 +00:00
luisramos0
08e729673f Move stripe sca gateway error messages to translatable keys 2020-03-02 17:30:12 +00:00
luisramos0
c0bf09131f Make order.pending_payments include payments in pending state so that these payments (pending is the state after authorization for credit cards) are also processed as part of the normal order workflow 2020-03-02 17:30:12 +00:00
luisramos0
19042e0d37 Make checkout controller able to receive a redirect from stripe with a payment_intent as parameter 2020-03-02 17:30:12 +00:00
luisramos0
4b3b4e00ff Add authorize action to the stripe_sca gateway and make it fetch the redirect url if provided
Change the purchase action to only capture the alrteady authorized payment intent
2020-03-02 17:30:12 +00:00
luisramos0
e3ffe8fe6b Add Checkout Stripe redirect logic to get users redirected to stripe authentication pages provided by the stripe API 2020-03-02 17:30:12 +00:00
luisramos0
d91578ab80 Rename checkout payment redirect to checkout paypal redirect 2020-03-02 17:30:12 +00:00
luisramos0
873dcc373f Small refactoring to make next commit easier 2020-03-02 17:30:12 +00:00
luisramos0
1289c3f1a2 Fix rubocop issues in credit_cards_controller 2020-03-02 17:29:30 +00:00
Luis Ramos
c37218fdc5 Merge pull request #4719 from luisramos0/stripe_card_to_pm
Make StripeSCA payment method work with existing credit cards (the ones saved through the Stripe Charges API)
2020-03-02 17:22:07 +00:00
Luis Ramos
dad21a52b2 Merge pull request #4672 from luisramos0/stripe_sca_method
Add new Stripe payment method compatible with the new Stripe Payment Intents API
2020-03-02 17:19:05 +00:00
Pau Pérez Fabregat
97a65d760f Merge pull request #4527 from luisramos0/subs_logs
Improve Subscriptions logging
2020-03-02 15:48:45 +01:00
Transifex-Openfoodnetwork
63e92197f5 Updating translations for config/locales/pt_BR.yml 2020-03-02 09:40:20 +11:00
Transifex-Openfoodnetwork
fd534bf629 Updating translations for config/locales/pt_BR.yml 2020-03-02 09:37:10 +11:00
Eduardo
64d83bfc4d fix ampersand problem using ng-bind-html 2020-03-01 17:54:36 -03:00
Pau Pérez Fabregat
83065a798e Merge pull request #4814 from luisramos0/rubop_rules
Add new cops (disabled) to rubocop config
2020-02-28 11:15:34 +01:00
Matt-Yorkley
b661b3ee40 Merge pull request #4823 from luisramos0/require_specs
Add some require statements to specs
2020-02-28 10:46:29 +01:00
Luis Ramos
b528903aa8 Remove spec covering html format in SchedulesController#index, this is not used anywhere 2020-02-27 19:05:36 +00:00
Matt-Yorkley
38215c2a88 Delete some dead code
This feature for assigning defaults via the UI was previously removed
2020-02-27 19:28:25 +01:00
Eduardo
4c3916a93d redirect to shops list when an enterprise is not found 2020-02-26 19:25:38 -03:00
Luis Ramos
677f31ffa8 Make payment source_views/gateway work with nil credit card
This will happen if user deletes a saved credit card used previously. In this case, the admin payment details page will render empty details and the payment amount
2020-02-26 11:55:17 +00:00
Luis Ramos
5848a46149 Add missing template to render stripeSCA payment and add spec to verify it's presence 2020-02-26 11:38:42 +00:00
Luis Ramos
6b6cdf07fb Remove inactive confirm
The new version of jquery is picking up a confirm in the ship action that was not being triggered in the previous version

The orders_spec was not expecting this confirm to appear so we are removing here to keep the behaviour and the spec green
2020-02-25 11:56:23 +00:00
Maikel Linke
8432dab142 Remove unused Javascript manifest
It reduces compilation from 25s to 24s.
2020-02-25 11:43:53 +11:00
Maikel Linke
0b0263a605 Remove unused stylesheet manifest
Compiling assets with application.css: 40s
Compiling assets without application.css: 25s
2020-02-25 11:43:39 +11:00
dependabot-preview[bot]
51dd55c5b9 [Security] Bump jquery-rails from 3.0.4 to 3.1.5
Bumps [jquery-rails](https://github.com/rails/jquery-rails) from 3.0.4 to 3.1.5. **This update includes a security fix.**
- [Release notes](https://github.com/rails/jquery-rails/releases)
- [Changelog](https://github.com/rails/jquery-rails/blob/v3.1.5/CHANGELOG.md)
- [Commits](https://github.com/rails/jquery-rails/compare/v3.0.4...v3.1.5)

Signed-off-by: dependabot-preview[bot] <support@dependabot.com>
2020-02-24 19:14:38 +00:00
Maikel Linke
17ea2cd510 Clean up JS assets comments 2020-02-24 11:22:47 +11:00
Maikel Linke
325c427219 Remove style from pasted HTML in editor 2020-02-24 11:22:47 +11:00
Maikel Linke
a3e87d893a Remove obsolete angular-sanitize
Our TextAngular module supplies that code.
2020-02-24 11:22:47 +11:00
Maikel Linke
480a629349 Bump textAngular to latest v1.5.16
I'm not sure which version we had previously. This update should come
with lots of minor improvements even though we didn't have anyone
complain.
2020-02-24 11:22:47 +11:00
Luis Ramos
03fac6f285 Avoid subquery with too many columns error by specifying the selected column 2020-02-23 20:05:13 +00:00
Luis Ramos
2108a282c8 Add some require statements to specs 2020-02-22 11:49:52 +00:00
luisramos0
404e7c1f37 Make credit card cloner clone the payment method even if the customer is not given
This makes the payments without saving card work again in the frontoffice as well as the payments taken by the seller in the backoffice
2020-02-21 14:11:13 +00:00
Luis Ramos
47916f823f Add spec to credit card cloner. No customer given. 2020-02-21 10:56:32 +00:00
Luis Ramos
ab4add1954 Fix CreditCardCloner basic spec 2020-02-21 10:56:32 +00:00
Luis Ramos
10fff31dca Fix stripe_sca spec 2020-02-21 10:56:32 +00:00
Luis Ramos
7fb85092ce Remove duplicate customers stubs 2020-02-21 10:56:32 +00:00
Luis Ramos
7584e96759 Make customer stub always return the same customer id
I cant make stripe customers stub return different customer_ids based on the stripe_account header
2020-02-21 10:56:32 +00:00
Luis Ramos
f8ab64d71e Move specs around in stripe_sca_spec so we can re-use the cloning stubs when storing a new card and when re-using a new card 2020-02-21 10:56:32 +00:00
Luis Ramos
ccb4c77d1f Adapt credit card cloner to not clone card if it's a card to be used only once
Adapt stripe_sca specs to new cloner logic
2020-02-21 10:56:32 +00:00
luisramos0
5ef1510fc7 Adapt CreditCard cloner to clone not 'cards of the platform account to payment_methods of the connected accounts' but instead 'cards or payment_methods of the platform account to payment_methods of the connected accounts'
This process mimicks the existing process of generating a token on the connected account from a card on the platform account. In the Payment Intents API we need to create a payment method in the connected account, a token is not enough
2020-02-21 10:56:32 +00:00
luisramos0
1afd712ff4 Make StripeSCA store cards (and delete them) on the Stripe platform account and not the Stripe Connected account (the sellers accounts)
This is important so that cards can be re-used across sellers in OFN
2020-02-21 10:56:32 +00:00
luisramos0
699110258b Add spec for credit_card_cloner 2020-02-21 10:56:32 +00:00
luisramos0
3fb1df9bb3 Rename CardCloner to CreditCardCloner because it's dependent on Spree:CreditCard attributes 2020-02-21 10:56:32 +00:00
luisramos0
14c03ead31 Extract CardCloner to separate class 2020-02-21 10:56:32 +00:00
luisramos0
4480c2f0f0 Add logic to stripe_sca gateway to handle cards stored in the platform account with the stripe Charges API: card_* 2020-02-21 10:56:32 +00:00
luisramos0
b3ac5d8f41 Improve code readability a little 2020-02-21 10:52:56 +00:00
luisramos0
6fb74c88cd Fix a typo 2020-02-21 10:52:56 +00:00
luisramos0
38fd028a9f Fix some rubocop issues from previous commit 2020-02-21 10:52:56 +00:00
luisramos0
4e84310d63 Add StripeSCA where StripeConnect is treated as an exception in the setting up of process of a payment method and subscriptions
Here we are copy pasting and adding stripe SCA because we are planning to delete the StripeConnect that will be replaced by the stripe sca implementation
2020-02-21 10:52:56 +00:00
luisramos0
66440f9e4c Add missing translations for new payment method stripe sca 2020-02-21 10:52:56 +00:00
luisramos0
b8457ebece Make profile storer a bit easier to read 2020-02-21 10:52:56 +00:00
Luis Ramos
668fd1c7c0 Add spec for profile storer to cover happy path for both response attribute cases: existin stripe integration and new stripe sca 2020-02-21 10:52:55 +00:00
Luis Ramos
aff934c814 Remove unnecessary test setup code 2020-02-21 10:52:55 +00:00
Luis Ramos
6bb04f6cc6 Adapt stripe_sca_spec to actual stripe SCA API 2020-02-21 10:52:55 +00:00
luisramos0
0e815439b3 Duplicate stripe_connect_spec and adapt to new stripe_sca
stripe_connect_spec will be deleted at some point when all users are migrated to the sca api
2020-02-21 10:52:55 +00:00
luisramos0
c7b01c37af Fix a problem in credit cards controller spec and test case where stripe_account_id must be included in the stripe api call 2020-02-21 10:52:55 +00:00
luisramos0
ac8f3c811f Fix rubocop issues in some stripe integration related files 2020-02-21 10:52:55 +00:00
luisramos0
1b820ea85c Fix rubocop issues in credit_cards_controller 2020-02-21 10:52:55 +00:00
luisramos0
ec7b91bb68 Make ProfileStorer a bit easier to read 2020-02-21 10:52:29 +00:00
luisramos0
c773cde191 Add admin payment template for stripe sca and respective js code to make it work 2020-02-21 10:52:29 +00:00
luisramos0
db1065a69e Make saving a card on checkout work with the payment intents api by making profile storer work with the slightly different api responses from stripe 2020-02-21 10:52:29 +00:00
luisramos0
9fa4bad0b4 Add stripe SCA checkotu payment template and move stripe object definition to it and the other stripe template
We need to set the stripe object with the stripe account id to work with the payment intents api but we cannot set it to work with the stripe charges api

This makes the two payment methods incompatible: a given enterprise cannot use both the old stripe integration and this new one at the same time.
2020-02-21 10:52:29 +00:00
luisramos0
a52c4b542c Make destroy stored cards work for stripe SCA by setting stripe account id before making the call to the stripe api
This account id cannot be sent when dealing with the old StripeConnect gateway
2020-02-21 10:52:29 +00:00
luisramos0
283abf9a88 Remove dead code from Stripe connect gateway
Update Source is dead since a74c502fd9
2020-02-21 10:52:29 +00:00
luisramos0
f691d1aafd Add new payment method StripeSCA that will use the Stripe Payment Intents API instead of the Stripe Charges API that the current StripeConnect gatreway uses 2020-02-21 10:52:29 +00:00
luisramos0
5724c3bb0a Add code from ActiveMerchant v1.98.0 that supports the Stripe Payment Intents API
This commit can be reverted once we upgrade to v1.98.0
2020-02-21 10:52:29 +00:00
Luis Ramos
06200c9d3c Add new cops (disabled) to rubocop config 2020-02-20 18:04:43 +00:00
Luis Ramos
2412658e51 Update db/schema timestamp according to last change 2020-02-20 11:41:49 +00:00
Maikel Linke
03fa3e2269 Find last payment deterministically 2020-02-20 15:59:57 +11:00
Maikel Linke
11fbe7d5c9 Show last payment method in order confirmations 2020-02-20 15:59:57 +11:00
Maikel Linke
799c1f08de Optimise finding last payment
Suggested by Rubocop.
2020-02-20 15:59:56 +11:00
Maikel Linke
6b66458bfd Replace andand with new Ruby syntax 2020-02-20 15:59:56 +11:00
Maikel Linke
3e0a5bac6a Move helper to service for re-use 2020-02-20 15:59:56 +11:00
Maikel Linke
2c2023df03 Show last payment method in order confirmation
If we had multiple failed payments and then a successful payment, the
order confirmation was displaying the payment method of the first failed
payment. That was confusing and is now changed to the last payment
method.
2020-02-20 15:59:56 +11:00
Maikel Linke
7306d379a5 Display payment method literally
Don't allow for HTML and potentially bad scripts. But this also prevents
accidental display errors. If someone wrote, "We only take <cash>", it
would mess with the site.
2020-02-20 15:59:56 +11:00
Maikel Linke
e15c61d862 Add spec for order confirmation view 2020-02-20 15:59:56 +11:00
Luis Ramos
1eba17f048 Make select column explicit to avoid too many columns sql error 2020-02-18 18:32:52 +00:00
Luis Ramos
00e57c8a55 Add module definition in the recently moved service and adapt all it's usages to refer to the new namespace 2020-02-13 20:17:09 +00:00
Luis Ramos
2e74e64e22 Move Product Reset Strategy to the catalog domain 2020-02-13 20:17:09 +00:00
Luis Ramos
fc5d623465 Add new domain structure Catalog 2020-02-13 20:17:06 +00:00
luisramos0
3b399b899c Extract methods in subscription_placement_job to fix rubocop complexity issues 2020-02-07 10:06:59 +00:00
luisramos0
01d69c89aa Add some log messages to help debug problems in subscription placement and subscription confirmation processes 2020-02-07 10:06:58 +00:00
luisramos0
a2801e40a2 Improve readability of proxy_order_syncer and add some log messages 2020-02-07 10:06:58 +00:00
luisramos0
abd4f0b923 Add custom_data column to paper_trail versions table so we can track a specific list of ids in a model
Activate paper_trail in order_cycles and schedules and track each others ids

An alternative way of doing this would be to use a gem for paper_trail associations but this way we avoid adding a new dependency to the app
2020-02-07 10:06:58 +00:00
211 changed files with 5573 additions and 951 deletions

View File

@@ -386,7 +386,6 @@ Metrics/AbcSize:
- app/helpers/spree/admin/base_helper.rb
- app/helpers/spree/admin/zones_helper.rb
- app/helpers/spree/orders_helper.rb
- app/jobs/subscription_placement_job.rb
- app/mailers/producer_mailer.rb
- app/models/calculator/flat_percent_per_item.rb
- app/models/column_preference.rb
@@ -413,6 +412,8 @@ Metrics/AbcSize:
- app/services/create_order_cycle.rb
- app/services/order_syncer.rb
- app/services/subscription_validator.rb
- lib/active_merchant/billing/gateways/stripe_decorator.rb
- lib/active_merchant/billing/gateways/stripe_payment_intents.rb
- lib/discourse/single_sign_on.rb
- lib/open_food_network/bulk_coop_report.rb
- lib/open_food_network/customers_report.rb
@@ -506,6 +507,7 @@ Metrics/CyclomaticComplexity:
- app/models/spree/product_decorator.rb
- app/models/variant_override_set.rb
- app/services/cart_service.rb
- lib/active_merchant/billing/gateways/stripe_payment_intents.rb
- lib/discourse/single_sign_on.rb
- lib/open_food_network/bulk_coop_report.rb
- lib/open_food_network/enterprise_issue_validator.rb
@@ -531,6 +533,7 @@ Metrics/PerceivedComplexity:
- app/models/spree/ability_decorator.rb
- app/models/spree/order_decorator.rb
- app/models/spree/product_decorator.rb
- lib/active_merchant/billing/gateways/stripe_payment_intents.rb
- lib/discourse/single_sign_on.rb
- lib/open_food_network/bulk_coop_report.rb
- lib/open_food_network/enterprise_issue_validator.rb
@@ -600,6 +603,7 @@ Metrics/MethodLength:
- app/serializers/api/cached_enterprise_serializer.rb
- app/services/order_cycle_form.rb
- engines/order_management/app/services/order_management/reports/enterprise_fee_summary/scope.rb
- lib/active_merchant/billing/gateways/stripe_payment_intents.rb
- lib/discourse/single_sign_on.rb
- lib/open_food_network/bulk_coop_report.rb
- lib/open_food_network/column_preference_defaults.rb
@@ -663,6 +667,7 @@ Metrics/ClassLength:
- app/serializers/api/enterprise_shopfront_serializer.rb
- app/services/cart_service.rb
- engines/order_management/app/services/order_management/reports/enterprise_fee_summary/scope.rb
- lib/active_merchant/billing/gateways/stripe_payment_intents.rb
- lib/open_food_network/bulk_coop_report.rb
- lib/open_food_network/enterprise_fee_calculator.rb
- lib/open_food_network/order_cycle_form_applicator.rb

View File

@@ -117,6 +117,15 @@ Style/FormatString:
Enabled: false
StyleGuide: http://relaxed.ruby.style/#styleformatstring
Style/HashEachMethods:
Enabled: false
Style/HashTransformKeys:
Enabled: false
Style/HashTransformValues:
Enabled: false
Style/IfUnlessModifier:
Enabled: false
StyleGuide: http://relaxed.ruby.style/#styleifunlessmodifier

View File

@@ -681,7 +681,6 @@ Style/FrozenStringLiteralComment:
- 'app/models/product_import/entry_validator.rb'
- 'app/models/product_import/inventory_reset_strategy.rb'
- 'app/models/product_import/product_importer.rb'
- 'app/models/product_import/products_reset_strategy.rb'
- 'app/models/product_import/reset_absent.rb'
- 'app/models/product_import/settings.rb'
- 'app/models/product_import/spreadsheet_data.rb'
@@ -1257,7 +1256,6 @@ Style/FrozenStringLiteralComment:
- 'spec/models/producer_property_spec.rb'
- 'spec/models/product_import/entry_processor_spec.rb'
- 'spec/models/product_import/inventory_reset_strategy_spec.rb'
- 'spec/models/product_import/products_reset_strategy_spec.rb'
- 'spec/models/product_import/reset_absent_spec.rb'
- 'spec/models/product_import/settings_spec.rb'
- 'spec/models/product_importer_spec.rb'

View File

@@ -12,6 +12,7 @@ gem "activerecord-import"
# Patched version. See http://rubysec.com/advisories/CVE-2015-5312/.
gem 'nokogiri', '>= 1.6.7.1'
gem "catalog", path: "./engines/catalog"
gem "order_management", path: "./engines/order_management"
gem 'web', path: './engines/web'
@@ -114,7 +115,7 @@ gem "foundation-rails"
gem 'foundation_rails_helper', github: 'willrjmarshall/foundation_rails_helper', branch: "rails3"
gem 'jquery-migrate-rails'
gem 'jquery-rails', '3.0.4'
gem 'jquery-rails', '3.1.5'
gem 'jquery-ui-rails', '~> 4.0.0'
gem 'select2-rails', '~> 3.4.7'
@@ -166,5 +167,5 @@ group :development do
# greater than 1.0.9, so we just required the latest available version here.
gem 'eventmachine', '>= 1.2.3'
gem 'rack-mini-profiler', '< 2.0.0'
gem 'rack-mini-profiler', '< 3.0.0'
end

View File

@@ -75,6 +75,11 @@ GIT
activemodel (>= 3.0)
railties (>= 3.0)
PATH
remote: engines/catalog
specs:
catalog (0.0.1)
PATH
remote: engines/order_management
specs:
@@ -211,7 +216,7 @@ GEM
activerecord (>= 3.2.0, < 5.0)
fog (~> 1.0)
rails (>= 3.2.0, < 5.0)
ddtrace (0.32.0)
ddtrace (0.33.1)
msgpack
debugger-linecache (1.2.0)
deface (1.0.2)
@@ -419,7 +424,7 @@ GEM
gmaps4rails (1.5.6)
haml (4.0.7)
tilt
hashdiff (1.0.0)
hashdiff (1.0.1)
highline (1.6.18)
hike (1.2.3)
httparty (0.16.2)
@@ -433,7 +438,7 @@ GEM
jaro_winkler (1.5.4)
journey (1.0.4)
jquery-migrate-rails (1.2.1)
jquery-rails (3.0.4)
jquery-rails (3.1.5)
railties (>= 3.0, < 5.0)
thor (>= 0.14, < 2.0)
jquery-ui-rails (4.0.5)
@@ -467,7 +472,7 @@ GEM
railties (>= 3.1)
money (5.1.1)
i18n (~> 0.6.0)
msgpack (1.3.1)
msgpack (1.3.3)
multi_json (1.14.1)
multi_xml (0.6.0)
multipart-post (2.1.1)
@@ -480,7 +485,7 @@ GEM
multi_json (~> 1.3)
multi_xml (~> 0.5)
rack (>= 1.2, < 3)
oj (3.10.2)
oj (3.10.5)
orm_adapter (0.5.0)
paper_trail (5.2.3)
activerecord (>= 3.0, < 6.0)
@@ -494,7 +499,7 @@ GEM
parallel (1.19.1)
paranoia (1.3.4)
activerecord (~> 3.1)
parser (2.7.0.2)
parser (2.7.0.4)
ast (~> 2.4.0)
paypal-sdk-core (0.2.10)
multi_json (~> 1.0)
@@ -516,9 +521,9 @@ GEM
rabl (0.8.4)
activesupport (>= 2.3.14)
rack (1.4.7)
rack-cache (1.9.0)
rack-cache (1.11.0)
rack (>= 0.4)
rack-mini-profiler (1.1.6)
rack-mini-profiler (2.0.1)
rack (>= 1.2.0)
rack-protection (1.5.5)
rack
@@ -548,7 +553,7 @@ GEM
thor (>= 0.14.6, < 2.0)
rainbow (3.0.0)
raindrops (0.19.1)
rake (13.0.0)
rake (13.0.1)
ransack (0.7.2)
actionpack (~> 3.0)
activerecord (~> 3.0)
@@ -580,15 +585,15 @@ GEM
rspec-core (~> 3.9.0)
rspec-expectations (~> 3.9.0)
rspec-mocks (~> 3.9.0)
rspec-core (3.9.0)
rspec-support (~> 3.9.0)
rspec-core (3.9.1)
rspec-support (~> 3.9.1)
rspec-expectations (3.9.0)
diff-lcs (>= 1.2.0, < 2.0)
rspec-support (~> 3.9.0)
rspec-mocks (3.9.0)
rspec-mocks (3.9.1)
diff-lcs (>= 1.2.0, < 2.0)
rspec-support (~> 3.9.0)
rspec-rails (3.9.0)
rspec-rails (3.9.1)
actionpack (>= 3.0)
activesupport (>= 3.0)
railties (>= 3.0)
@@ -598,8 +603,8 @@ GEM
rspec-support (~> 3.9.0)
rspec-retry (0.6.2)
rspec-core (> 3.3)
rspec-support (3.9.0)
rubocop (0.80.0)
rspec-support (3.9.2)
rubocop (0.80.1)
jaro_winkler (~> 1.5.1)
parallel (~> 1.10)
parser (>= 2.7.0.1)
@@ -679,7 +684,7 @@ GEM
nokogiri (~> 1.6)
rubyzip (>= 1.3.0)
selenium-webdriver (>= 3.0, < 4.0)
webmock (3.8.2)
webmock (3.8.3)
addressable (>= 2.3.6)
crack (>= 0.3.2)
hashdiff (>= 0.4.0, < 2.0.0)
@@ -711,6 +716,7 @@ DEPENDENCIES
bugsnag
byebug (~> 9.0.0)
capybara (>= 2.18.0)
catalog!
coffee-rails (~> 3.2.1)
combine_pdf
compass-rails
@@ -742,7 +748,7 @@ DEPENDENCIES
i18n-js (~> 3.6.0)
immigrant
jquery-migrate-rails
jquery-rails (= 3.0.4)
jquery-rails (= 3.1.5)
jquery-ui-rails (~> 4.0.0)
json_spec (~> 1.1.4)
jwt (~> 2.2)
@@ -762,7 +768,7 @@ DEPENDENCIES
pg (~> 0.21.0)
pry-byebug (>= 3.4.3)
rabl
rack-mini-profiler (< 2.0.0)
rack-mini-profiler (< 3.0.0)
rack-rewrite
rack-ssl
rails (~> 3.2.22)

View File

@@ -0,0 +1,23 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
id="svg4"
xml:space="preserve"
enable-background="new 0 0 6 3"
viewBox="0 0 6 3"
height="3px"
width="24px"
y="0px"
x="12px"
version="1.1"><metadata
id="metadata10"><rdf:RDF><cc:Work
rdf:about=""><dc:format>image/svg+xml</dc:format><dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" /><dc:title></dc:title></cc:Work></rdf:RDF></metadata><defs
id="defs8" /><polygon
style="fill:#000000;fill-opacity:1"
id="polygon2"
points="5.992,0 2.992,3 -0.008,0 " /></svg>

After

Width:  |  Height:  |  Size: 832 B

View File

@@ -0,0 +1,23 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
id="svg4"
xml:space="preserve"
enable-background="new 0 0 6 3"
viewBox="0 0 6 3"
height="3px"
width="24px"
y="0px"
x="12px"
version="1.1"><metadata
id="metadata10"><rdf:RDF><cc:Work
rdf:about=""><dc:format>image/svg+xml</dc:format><dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" /><dc:title></dc:title></cc:Work></rdf:RDF></metadata><defs
id="defs8" /><polygon
style="fill:#ffffff;fill-opacity:1"
id="polygon2"
points="5.992,0 2.992,3 -0.008,0 " /></svg>

After

Width:  |  Height:  |  Size: 832 B

View File

@@ -20,7 +20,6 @@
//= require angular
//= require angular-resource
//= require angular-animate
//= require angular-sanitize
//= require angularjs-file-upload
//= require ../shared/ng-infinite-scroll.min.js
//= require ../shared/ng-tags-input.min.js
@@ -67,6 +66,8 @@
// text, dates and translations
//= require textAngular-rangy.min.js
// This replaces angular-sanitize. We should include only one.
// https://github.com/textAngular/textAngular#where-to-get-it
//= require textAngular-sanitize.min.js
//= require textAngular.min.js
//= require i18n/translations

View File

@@ -21,7 +21,7 @@ angular.module('admin.payments').factory 'Payment', (AdminStripeElements, curren
year: @form_data.card_year
verification_value: @form_data.card_verification_value
}
when 'stripe'
when 'stripe', 'stripe_sca'
angular.extend munged_payment.payment, {
source_attributes:
gateway_payment_profile_id: @form_data.token
@@ -35,6 +35,8 @@ angular.module('admin.payments').factory 'Payment', (AdminStripeElements, curren
purchase: ->
if @paymentMethodType() == 'stripe'
AdminStripeElements.requestToken(@form_data, @submit)
else if @paymentMethodType() == 'stripe_sca'
AdminStripeElements.createPaymentMethod(@form_data, @submit)
else
@submit()

View File

@@ -5,7 +5,7 @@ angular.module("admin.payments").factory 'AdminStripeElements', ($rootScope, Sta
stripe: null
card: null
# New Stripe Elements method
# Create Token to be used with the Stripe Charges API
requestToken: (secrets, submit) ->
return unless @stripe? && @card?
@@ -20,6 +20,21 @@ angular.module("admin.payments").factory 'AdminStripeElements', ($rootScope, Sta
secrets.card = response.token.card
submit()
# Create Payment Method to be used with the Stripe Payment Intents API
createPaymentMethod: (secrets, submit) ->
return unless @stripe? && @card?
cardData = @makeCardData(secrets)
@stripe.createPaymentMethod({ type: 'card', card: @card }, @card, cardData).then (response) =>
if(response.error)
StatusMessage.display 'error', response.error.message
else
secrets.token = response.paymentMethod.id
secrets.cc_type = response.paymentMethod.card.brand
secrets.card = response.paymentMethod.card
submit()
# Maps the brand returned by Stripe to that required by activemerchant
mapCC: (ccType) ->
switch ccType

View File

@@ -16,7 +16,7 @@ angular.module("admin.subscriptions").controller "DetailsController", ($scope, $
return if !newValue?
paymentMethod = ($scope.paymentMethods.filter (pm) -> pm.id == newValue)[0]
return unless paymentMethod?
$scope.cardRequired = (paymentMethod.type == "Spree::Gateway::StripeConnect")
$scope.cardRequired = (paymentMethod.type == "Spree::Gateway::StripeConnect" || paymentMethod.type == "Spree::Gateway::StripeSCA")
$scope.loadCustomer() if $scope.cardRequired && !$scope.customer
$scope.loadCustomer = ->

View File

@@ -2,4 +2,10 @@ angular.module("admin.utils").directive "textangularStrip", () ->
restrict: 'CA'
link: (scope, element, attrs) ->
scope.stripFormatting = ($html) ->
return String($html).replace(/<[^>]+>/gm, '')
element = document.createElement("div")
element.innerHTML = String($html)
allTags = element.getElementsByTagName("*")
for child in allTags
child.removeAttribute("style")
child.removeAttribute("class")
return element.innerHTML

View File

@@ -1,9 +0,0 @@
// This is a manifest file that'll be compiled into including all the files listed below.
// Add new JavaScript/Coffee code in separate files in this directory and they'll automatically
// be included in the compiled file accessible from http://example.com/assets/application.js
// It's not advisable to add code directly here, but if you do, it'll appear at the bottom of the
// the compiled file.
//
//= require jquery
//= require jquery_ujs
//= require_tree .

View File

@@ -0,0 +1,17 @@
Darkswarm.controller "PageSelectionCtrl", ($scope, $location) ->
$scope.selectedPage = ->
# The path looks like `/contact` for the URL `https://ofn.org/shop#/contact`.
# We remove the slash at the beginning.
page = $location.path()[1..]
return $scope.whitelist[0] unless page
# If the path points to an unrelated path like `/login`, stay where we were.
return $scope.lastPage unless page in $scope.whitelist
$scope.lastPage = page
page
$scope.whitelistPages = (pages) ->
$scope.whitelist = pages
$scope.lastPage = pages[0]

View File

@@ -7,6 +7,8 @@ Darkswarm.factory 'Checkout', ($injector, CurrentOrder, ShippingMethods, StripeE
purchase: ->
if @paymentMethod()?.method_type == 'stripe' && !@secrets.selected_card
StripeElements.requestToken(@secrets, @submit)
else if @paymentMethod()?.method_type == 'stripe_sca' && !@secrets.selected_card
StripeElements.createPaymentMethod(@secrets, @submit)
else
@submit()
@@ -59,7 +61,7 @@ Darkswarm.factory 'Checkout', ($injector, CurrentOrder, ShippingMethods, StripeE
last_name: @order.bill_address.lastname
}
if @paymentMethod()?.method_type == 'stripe'
if @paymentMethod()?.method_type == 'stripe' || @paymentMethod()?.method_type == 'stripe_sca'
if @secrets.selected_card
angular.extend munged_order, {
existing_card_id: @secrets.selected_card

View File

@@ -1,12 +1,10 @@
Darkswarm.factory 'StripeElements', ($rootScope, Loading, RailsFlashLoader) ->
new class StripeElements
# TODO: add locale here for translations of error messages etc. from Stripe
# These are both set from the StripeElements directive
stripe: null
card: null
# New Stripe Elements method
# Create Token to be used with the Stripe Charges API
requestToken: (secrets, submit, loading_message = t("processing_payment")) ->
return unless @stripe? && @card?
@@ -23,6 +21,23 @@ Darkswarm.factory 'StripeElements', ($rootScope, Loading, RailsFlashLoader) ->
secrets.card = response.token.card
submit()
# Create Payment Method to be used with the Stripe Payment Intents API
createPaymentMethod: (secrets, submit, loading_message = t("processing_payment")) ->
return unless @stripe? && @card?
Loading.message = loading_message
cardData = @makeCardData(secrets)
@stripe.createPaymentMethod({ type: 'card', card: @card }, @card, cardData).then (response) =>
if(response.error)
Loading.clear()
RailsFlashLoader.loadFlash({error: t("error") + ": #{response.error.message}"})
else
secrets.token = response.paymentMethod.id
secrets.cc_type = response.paymentMethod.card.brand
secrets.card = response.paymentMethod.card
submit()
# Maps the brand returned by Stripe to that required by activemerchant
mapCC: (ccType) ->
switch ccType

View File

@@ -1,7 +0,0 @@
/*
* This is a manifest file that'll automatically include all the stylesheets available in this directory
* and any sub-directories. You're free to add application-wide styles to this file and they'll appear at
* the top of the compiled file, but it's generally better to create a new file per style scope.
*= require_self
*= require_tree .
*/

View File

@@ -2,7 +2,7 @@
.darkswarm navigation {
display: block;
background: #f7f7f7;
background: $white;
distributor.details {
box-sizing: border-box;
@@ -10,9 +10,11 @@
min-height: 150px;
padding: 30px 0 20px 0;
position: relative;
select {
width: 200px;
}
img {
display: block;
height: 100px;
@@ -31,72 +33,158 @@
#distributor_title h3 {
margin-top: 0;
padding-top: 0.45em;
@media all and (max-width: 768px) {
margin-bottom: 8px;
}
}
}
}
ordercycle {
float: right;
background: $teal-400;
color: $white;
width: 100%;
border-radius: 0.5em 0.5em 0 0;
position: absolute;
right: 1em;
padding: 1em;
margin-top: 3em;
height: 7.6em;
&.requires-selection {
background-color: $red-700;
ordercycle {
text-align: right;
float: right;
p {
max-width: 400px;
.order-cycle-select {
border: 1px solid $red-500;
.select-label {
background-color: rgba($red-500, 0.5);
}
h4 i {
margin-right: 0.3rem;
select {
background-color: $white;
background-image: url('/assets/black-caret.svg');
color: $grey-500;
font-style: italic;
}
@media all and (max-width: 640px) {
float: left;
clear: left;
text-align: left;
padding: 12px 10px;
width: 100%;
margin-top: 10px;
background: #e5e5e5;
p {
max-width: 100%;
}
}
form.custom {
text-align: right;
& > strong {
line-height: 2.5;
font-size: 1.29em;
padding-right: 14px;
}
select {
width: inherit;
display: inline-block;
border: 1px #999;
color: #666;
font-size: 1em;
margin-bottom: 0;
padding: 8px 20px 8px 12px;
@media all and (max-width: 768px) {
font-size: 0.875em;
}
@media screen and (-webkit-min-device-pixel-ratio: 0) {
font-size: 16px;
}
}
}
closing {
@include headingFont;
color: black;
font-size: 1.5em;
}
}
p {
max-width: 400px;
}
h4 i {
margin-right: 0.3rem;
}
@media all and (max-width: 1024px) {
float: none;
padding: 0.5em 1em;
width: 100%;
margin-top: 0;
display: inline-block;
border-radius: 0;
position: relative;
right: 0;
height: auto;
p {
max-width: 100%;
}
}
@media all and (max-width: 768px) {
padding: 0.5em 1em 0.75em;
}
form.custom {
text-align: center;
}
.order-cycle-select {
border: 1px solid $teal-300;
display: inline-block;
font-size: 1em;
border-radius: 0.25em;
.select-label {
background-color: rgba($teal-300, 0.5);
display: inline-block;
border-radius: 0.25em 0 0 0.25em;
float: left;
font-size: 1em;
line-height: 1.5em;
padding: 0.5em 0.75em;
height: 2.35em;
span {
width: max-content;
display: block;
padding-bottom: 12px;
@media all and (max-width: 768px) {
font-size: 1.2em;
padding-bottom: 10px;
}
span {
@media all and (max-width: 768px) {
font-size: 0.875em;
}
}
}
}
select {
width: inherit;
display: inline-block;
color: $white;
background-color: transparent;
border: 0;
margin-bottom: 0;
font-size: 1em;
line-height: 1.5em;
padding: 0.5em 1.25em 0.5em 0.75em;
height: 2.35em;
background-image: url('/assets/white-caret.svg');
background-size: 30px auto;
border-radius: 0 0.25em 0.25em 0;
min-width: 13em;
@media all and (max-width: 480px) {
width: 100%;
}
}
@media all and (max-width: 1024px) {
float: none;
margin-right: 1em;
}
@media all and (max-width: 768px) {
float: none;
}
@media all and (max-width: 480px) {
display: flex;
}
}
closing {
@include headingFont;
color: $white;
font-size: 1.25rem;
display: block;
padding: 0 0 12px;
@media all and (max-width: 1024px) {
float: none;
display: inline-block;
padding: 0.2em 0 0;
font-size: 1.2em;
margin-right: 1em;
}
@media all and (max-width: 768px) {
float: none;
padding: 0 0 10px;
}
span {
@media all and (max-width: 768px) {
font-size: 0.875em;
}
}
}

View File

@@ -38,3 +38,25 @@ $light-grey: #ddd;
$light-grey-transparency: rgba(0, 0, 0, .1);
$black: #000;
$white: #fff;
$grey-400: #bbb;
$grey-500: #999;
$grey-600: #777;
$grey-700: #555;
$grey-800: #333;
$teal-300: #80d3df;
$teal-400: #4cb5c5;
$teal-500: #0096ad;
$orange-400: #ff9466;
$orange-500: #f27052;
$orange-600: #d7583a;
$red-500: #e54e47;
$red-700: #c1122b;
$social-facebook: #3b5998;
$social-instagram: #e1306c;
$social-linkedin: #0e76a8;
$social-twitter: #00acee;

View File

@@ -111,6 +111,22 @@
i {
font-size: 2rem;
&.facebook {
color: $social-facebook;
}
&.twitter {
color: $social-twitter;
}
&.linkedin {
color: $social-linkedin;
}
&.instagram {
color: $social-instagram;
}
}
a {

View File

@@ -3,22 +3,27 @@
@import "branding";
// Tabs styling
.tabset-ctrl#shop-tabs {
#shop-tabs {
.tab-buttons {
background: url("/assets/gray_jean.png") top left repeat;
@include box-shadow(inset 0 2px 3px 0 rgba(0, 0, 0, 0.15));
color: $dark-grey;
box-shadow: 0 1px 0 rgba(0,0,0,0.05), 0 8px 6px -6px rgba(0, 0, 0, 0.2);
.row:first-child {
.columns {
display: flex;
justify-content: space-between;
@media all and (max-width: 1024px) {
display: table;
width: 100%;
}
@media all and (max-width: 480px) {
padding: 0;
}
}
}
.tab {
.page {
text-align: center;
border-top: 4px solid transparent;
display: inline-block;
@@ -27,8 +32,7 @@
>a {
outline: none;
display: block;
background-color: #efefef;
color: #222;
color: $grey-500;
font-family: "Oswald", sans-serif;
}
@@ -39,12 +43,11 @@
text-transform: uppercase;
line-height: 1;
font-size: 0.875em;
text-shadow: 0 -1px 1px #ffffff;
padding: 1em 2em;
border: none;
&:hover, &:focus, &:active {
color: $clr-brick-bright;
&:hover, &:active {
color: $teal-500;
}
&, &:hover {
@@ -53,29 +56,41 @@
@media all and (max-width: 640px) {
padding: 0.35em 0 0.65em 0;
text-shadow: none;
}
}
&.selected {
border-bottom: 4px solid $clr-brick;
border-bottom: 4px solid $teal-500;
a {
color: $clr-brick;
color: $teal-500;
}
}
@media all and (max-width: 1024px) {
display: table-cell;
width: auto;
}
}
// content revealed in accordion
.tab-view {
.page-view {
margin-bottom: 5em;
background: none;
border: none;
.content {
padding: 1.25em 0;
background-color: $white;
background-color: transparent;
a {
color: $orange-500;
&:hover {
color: $orange-600;
}
}
img {
margin: 0px 0px 0px 40px;
@@ -83,6 +98,7 @@
h5 {
margin-bottom: 1em;
font-family: $body-font;
}
p {
@@ -100,13 +116,9 @@
.header {
text-align: center;
text-transform: uppercase;
color: $dark-grey;
border-bottom: 1px solid $disabled-dark;
color: $grey-600;
margin-top: 0.75rem;
margin-bottom: 0.75rem;
padding-bottom: 0.25rem;
font-size: 0.875rem;
margin-bottom: 2px;
}
}
}

View File

@@ -9,7 +9,7 @@
}
$headingFont: "Oswald";
$bodyFont: "Roboto";
$body-font: "Roboto", Arial, sans-serif;
body {
@include bodyFont;
@@ -43,7 +43,7 @@ small, .small {
.text-small {
font-size: 0.875rem;
margin-bottom: 0.5rem;
font-family: $bodyFont;
font-family: $body-font;
&, & * {
font-size: 0.875rem;
@@ -52,12 +52,12 @@ small, .small {
.text-normal {
font-weight: 400;
font-family: $bodyFont;
font-family: $body-font;
}
.text-skinny {
font-weight: 300;
font-family: $bodyFont;
font-family: $body-font;
}
.word-wrap {
@@ -114,9 +114,9 @@ ul.bullet-list, ul.check-list {
}
li:before {
content: "";
content: "";
font-family: "OFN";
margin-left: -1.25em;
margin: 0 0.25em 0 -1.25em;
display: inline-block;
font-weight: normal;
font-style: normal;

View File

@@ -10,7 +10,7 @@
@include border-radius(0.5em);
font-family: $bodyFont;
font-family: $body-font;
background-color: transparent;
border: 2px solid rgba(200, 200, 200, 1);
color: #999;
@@ -63,7 +63,7 @@
}
.button.primary, button.primary {
font-family: $bodyFont;
font-family: $body-font;
background: $clr-brick;
color: white;
}

View File

@@ -23,7 +23,6 @@ module Admin
before_filter :setup_property, only: [:edit]
helper 'spree/products'
include ActionView::Helpers::TextHelper
include OrderCyclesHelper
def index
@@ -77,19 +76,12 @@ module Admin
def bulk_update
@enterprise_set = EnterpriseSet.new(collection, params[:enterprise_set])
touched_enterprises = @enterprise_set.collection.select(&:changed?)
if @enterprise_set.save
flash[:success] = I18n.t(:enterprise_bulk_update_success_notice)
# 18-3-2015: It seems that the form for this action sometimes loads bogus values for
# the 'sells' field, and submitting that form results in a bunch of enterprises with
# values that have mysteriously changed. This statement is here to help debug that
# issue, and should be removed (along with its display in index.html.haml) when the
# issue has been resolved.
flash[:action] = "#{I18n.t(:updated)} #{pluralize(touched_enterprises.count, 'enterprise')}: #{touched_enterprises.map(&:name).join(', ')}"
redirect_to main_app.admin_enterprises_path
else
touched_enterprises = @enterprise_set.collection.select(&:changed?)
@enterprise_set.collection.select! { |e| touched_enterprises.include? e }
flash[:error] = I18n.t(:enterprise_bulk_update_error)
render :index

View File

@@ -1,5 +1,5 @@
require 'open_food_network/referer_parser'
require 'spree/authentication_helpers'
require_dependency 'spree/authentication_helpers'
class ApplicationController < ActionController::Base
protect_from_forgery

View File

@@ -35,6 +35,8 @@ class CheckoutController < Spree::StoreController
rescue_from Spree::Core::GatewayError, with: :rescue_from_spree_gateway_error
def edit
return handle_redirect_from_stripe if valid_payment_intent_provided?
# This is only required because of spree_paypal_express. If we implement
# a version of paypal that uses this controller, and more specifically
# the #update_failed method, then we can remove this call
@@ -151,6 +153,23 @@ class CheckoutController < Spree::StoreController
end
end
def valid_payment_intent_provided?
params["payment_intent"]&.starts_with?("pi_") &&
@order.state == "payment" &&
@order.payments.last.state == "pending" &&
@order.payments.last.response_code == params["payment_intent"]
end
def handle_redirect_from_stripe
if advance_order_state(@order) && order_complete?
checkout_succeeded
redirect_to(order_path(@order)) && return
else
flash[:error] = order_workflow_error
checkout_failed
end
end
def checkout_workflow(shipping_method_id)
while @order.state != "complete"
if @order.state == "payment"
@@ -165,11 +184,12 @@ class CheckoutController < Spree::StoreController
return update_failed
end
update_result
update_response
end
def redirect_to_payment_gateway
redirect_path = Checkout::PaymentRedirect.new(params).path
redirect_path = Checkout::PaypalRedirect.new(params).path
redirect_path = Checkout::StripeRedirect.new(params, @order).path if redirect_path.blank?
return if redirect_path.blank?
render json: { path: redirect_path }, status: :ok
@@ -193,27 +213,27 @@ class CheckoutController < Spree::StoreController
end
end
def update_result
if @order.state == "complete" || @order.completed?
save_order_addresses_as_user_default
ResetOrderService.new(self, current_order).call
update_succeeded
def update_response
if order_complete?
checkout_succeeded
update_succeeded_response
else
update_failed
end
end
def save_order_addresses_as_user_default
user_default_address_setter = UserDefaultAddressSetter.new(@order, spree_current_user)
user_default_address_setter.set_default_bill_address if params[:order][:default_bill_address]
user_default_address_setter.set_default_ship_address if params[:order][:default_ship_address]
def order_complete?
@order.state == "complete" || @order.completed?
end
def update_succeeded
def checkout_succeeded
Checkout::PostCheckoutActions.new(@order).success(self, params, spree_current_user)
session[:access_token] = current_order.token
flash[:notice] = t(:order_processed_successfully)
end
def update_succeeded_response
respond_to do |format|
format.html do
respond_with(@order, location: order_path(@order))
@@ -225,9 +245,15 @@ class CheckoutController < Spree::StoreController
end
def update_failed
current_order.updater.shipping_address_from_distributor
RestartCheckout.new(@order).call
checkout_failed
update_failed_response
end
def checkout_failed
Checkout::PostCheckoutActions.new(@order).failure
end
def update_failed_response
respond_to do |format|
format.html do
render :edit

View File

@@ -63,8 +63,6 @@ class EnterprisesController < BaseController
end
def reset_order
distributor = Enterprise.is_distributor.find_by_permalink(params[:id]) ||
Enterprise.is_distributor.find(params[:id])
order = current_order(true)
reset_distributor(order, distributor)
@@ -74,6 +72,14 @@ class EnterprisesController < BaseController
reset_order_cycle(order, distributor)
order.save!
rescue ActiveRecord::RecordNotFound
flash[:error] = I18n.t(:enterprise_shop_show_error)
redirect_to shops_path
end
def distributor
@distributor ||= Enterprise.is_distributor.find_by_permalink(params[:id]) ||
Enterprise.is_distributor.find(params[:id])
end
def reset_distributor(order, distributor)

View File

@@ -110,7 +110,7 @@ module Spree
else
Gateway.providers.reject{ |p| p.name.include? "Bogus" }.sort_by(&:name)
end
@providers.reject!{ |p| p.name.ends_with? "StripeConnect" } unless show_stripe?
@providers.reject!{ |provider| stripe_provider?(provider) } unless show_stripe?
@calculators = PaymentMethod.calculators.sort_by(&:name)
end
@@ -134,12 +134,12 @@ module Spree
# current payment_method is already a Stripe method
def show_stripe?
Spree::Config.stripe_connect_enabled ||
@payment_method.try(:type) == "Spree::Gateway::StripeConnect"
stripe_payment_method?
end
def restrict_stripe_account_change
return unless @payment_method
return unless @payment_method.type == "Spree::Gateway::StripeConnect"
return unless stripe_payment_method?
return unless @payment_method.preferred_enterprise_id.andand > 0
@stripe_account_holder = Enterprise.find(@payment_method.preferred_enterprise_id)
@@ -147,6 +147,15 @@ module Spree
params[:payment_method][:preferred_enterprise_id] = @stripe_account_holder.id
end
def stripe_payment_method?
["Spree::Gateway::StripeConnect",
"Spree::Gateway::StripeSCA"].include? @payment_method.try(:type)
end
def stripe_provider?(provider)
provider.name.ends_with?("StripeConnect", "StripeSCA")
end
end
end
end

View File

@@ -59,7 +59,7 @@ module Spree
@collection ||= if @deleted.blank?
super
else
Variant.where(product_id: parent.id).deleted
Variant.unscoped.where(product_id: parent.id).deleted
end
@collection
end

View File

@@ -10,10 +10,14 @@ module Spree
render json: @credit_card, serializer: ::Api::CreditCardSerializer, status: :ok
else
message = t(:card_could_not_be_saved)
render json: { flash: { error: I18n.t(:spree_gateway_error_flash_for_checkout, error: message) } }, status: :bad_request
render json: { flash: { error: I18n.t(:spree_gateway_error_flash_for_checkout,
error: message) } },
status: :bad_request
end
rescue Stripe::CardError => e
render json: { flash: { error: I18n.t(:spree_gateway_error_flash_for_checkout, error: e.message) } }, status: :bad_request
render json: { flash: { error: I18n.t(:spree_gateway_error_flash_for_checkout,
error: e.message) } },
status: :bad_request
end
def update
@@ -52,12 +56,20 @@ module Spree
private
# Currently can only destroy the whole customer object
# It destroys the whole customer object
def destroy_at_stripe
stripe_customer = Stripe::Customer.retrieve(@credit_card.gateway_customer_profile_id)
stripe_customer = Stripe::Customer.retrieve(@credit_card.gateway_customer_profile_id, {})
stripe_customer.delete if stripe_customer
end
def stripe_account_id
StripeAccount.
find_by_enterprise_id(@credit_card.payment_method.preferred_enterprise_id).
andand.
stripe_user_id
end
def create_customer(token)
Stripe::Customer.create(email: spree_current_user.email, source: token)
end

View File

@@ -16,4 +16,8 @@ module SharedHelper
def admin_user?
spree_current_user.andand.has_spree_role? 'admin'
end
def current_shop_products_path
"#{main_app.enterprise_shop_path(current_distributor)}#/shop"
end
end

View File

@@ -8,6 +8,10 @@ module ShopHelper
end
end
def oc_select_options
@order_cycles.map { |oc| { time: pickup_time(oc), id: oc.id } }
end
def require_customer?
current_distributor.require_login? && !user_is_related_to_distributor?
end
@@ -31,6 +35,10 @@ module ShopHelper
].select{ |tab| tab[:show] }
end
def shop_tab_names
shop_tabs.map { |tab| tab[:name] }
end
def show_home_tab?
require_customer? || current_distributor.preferred_shopfront_message.present?
end

View File

@@ -6,6 +6,7 @@ class SubscriptionConfirmJob
ids = proxy_orders.pluck(:id)
proxy_orders.update_all(confirmed_at: Time.zone.now)
ProxyOrder.where(id: ids).each do |proxy_order|
Rails.logger.info "Confirming Order for Proxy Order #{proxy_order.id}"
@order = proxy_order.order
process!
end

View File

@@ -5,8 +5,7 @@ class SubscriptionPlacementJob
ids = proxy_orders.pluck(:id)
proxy_orders.update_all(placed_at: Time.zone.now)
ProxyOrder.where(id: ids).each do |proxy_order|
proxy_order.initialise_order!
process(proxy_order.order)
place_order_for(proxy_order)
end
send_placement_summary_emails
@@ -28,16 +27,18 @@ class SubscriptionPlacementJob
.joins(:subscription).merge(Subscription.not_canceled.not_paused)
end
def process(order)
def place_order_for(proxy_order)
Rails.logger.info "Placing Order for Proxy Order #{proxy_order.id}"
proxy_order.initialise_order!
place_order(proxy_order.order)
end
def place_order(order)
record_order(order)
return record_issue(:complete, order) if order.completed?
changes = cap_quantity_and_store_changes(order)
if order.line_items.where('quantity > 0').empty?
order.reload.adjustments.destroy_all
order.update!
return send_empty_email(order, changes)
end
return handle_empty_order(order, changes) if order.line_items.where('quantity > 0').empty?
move_to_completion(order)
send_placement_email(order, changes)
@@ -58,12 +59,18 @@ class SubscriptionPlacementJob
changes
end
def handle_empty_order(order, changes)
order.reload.adjustments.destroy_all
order.update!
send_empty_email(order, changes)
end
def move_to_completion(order)
AdvanceOrderService.new(order).call!
end
def unavailable_stock_lines_for(order)
order.line_items.where('variant_id NOT IN (?)', available_variants_for(order))
order.line_items.where('variant_id NOT IN (?)', available_variants_for(order).select(&:id))
end
def available_variants_for(order)

View File

@@ -321,7 +321,7 @@ class Enterprise < ActiveRecord::Base
def distributed_taxons
Spree::Taxon.
joins(:products).
where('spree_products.id IN (?)', Spree::Product.in_distributor(self)).
where('spree_products.id IN (?)', Spree::Product.in_distributor(self).select(&:id)).
select('DISTINCT spree_taxons.*')
end
@@ -337,7 +337,7 @@ class Enterprise < ActiveRecord::Base
def supplied_taxons
Spree::Taxon.
joins(:products).
where('spree_products.id IN (?)', Spree::Product.in_supplier(self)).
where('spree_products.id IN (?)', Spree::Product.in_supplier(self).select(&:id)).
select('DISTINCT spree_taxons.*')
end

View File

@@ -27,7 +27,7 @@ class EnterpriseFee < ActiveRecord::Base
if user.has_spree_role?('admin')
scoped
else
where('enterprise_id IN (?)', user.enterprises)
where('enterprise_id IN (?)', user.enterprises.select(&:id))
end
}

View File

@@ -22,7 +22,7 @@ class EnterpriseRelationship < ActiveRecord::Base
}
scope :involving_enterprises, ->(enterprises) {
where('parent_id IN (?) OR child_id IN (?)', enterprises, enterprises)
where('parent_id IN (?) OR child_id IN (?)', enterprises.select(&:id), enterprises.select(&:id))
}
scope :permitting, ->(enterprise_ids) { where('child_id IN (?)', enterprise_ids) }

View File

@@ -49,7 +49,7 @@ class Exchange < ActiveRecord::Base
}
scope :with_product, lambda { |product|
joins(:exchange_variants).
where('exchange_variants.variant_id IN (?)', product.variants_including_master)
where('exchange_variants.variant_id IN (?)', product.variants_including_master.select(&:id))
}
scope :by_enterprise_name, -> {
joins('INNER JOIN enterprises AS sender ON (sender.id = exchanges.sender_id)').

View File

@@ -17,6 +17,7 @@ class OrderCycle < ActiveRecord::Base
has_many :distributors, source: :receiver, through: :cached_outgoing_exchanges, uniq: true
has_and_belongs_to_many :schedules, join_table: 'order_cycle_schedules'
has_paper_trail meta: { custom_data: :schedule_ids }
attr_accessor :incoming_exchanges, :outgoing_exchanges

View File

@@ -74,7 +74,7 @@ module ProductImport
if settings.importing_into_inventory?
InventoryResetStrategy
else
ProductsResetStrategy
Catalog::ProductImport::ProductsResetStrategy
end
end
@@ -122,7 +122,6 @@ module ProductImport
def save_new_inventory_item(entry)
new_item = entry.product_object
assign_defaults(new_item, entry)
new_item.import_date = @import_time
if new_item.valid? && new_item.save
@@ -136,7 +135,6 @@ module ProductImport
def save_existing_inventory_item(entry)
existing_item = entry.product_object
assign_defaults(existing_item, entry)
existing_item.import_date = @import_time
if existing_item.valid? && existing_item.save
@@ -164,7 +162,6 @@ module ProductImport
product = Spree::Product.new
product.assign_attributes(entry.attributes.except('id', 'on_hand', 'on_demand'))
product.supplier_id = entry.producer_id
assign_defaults(product, entry)
if product.save
ensure_variant_updated(product, entry)
@@ -179,7 +176,6 @@ module ProductImport
def save_variant(entry)
variant = entry.product_object
assign_defaults(variant, entry)
variant.import_date = @import_time
if variant.valid? && variant.save
@@ -199,37 +195,6 @@ module ProductImport
)
end
def assign_defaults(object, entry)
# Assigns a default value for a specified field e.g. category='Vegetables', setting this value
# either for all entries (overwrite_all), or only for those entries where the field was blank
# in the spreadsheet (overwrite_empty), depending on selected import settings
return unless settings.defaults(entry)
settings.defaults(entry).each do |attribute, setting|
next unless setting['active']
case setting['mode']
when 'overwrite_all'
object.assign_attributes(attribute => setting['value'])
# In case of new products, some attributes are saved on the variant.
# We write them to the entry here to be copied to the variant later.
if entry.respond_to? "#{attribute}="
entry.public_send("#{attribute}=", setting['value'])
end
when 'overwrite_empty'
if object.public_send(attribute).blank? ||
((attribute == 'on_hand') &&
entry.on_hand_nil)
object.assign_attributes(attribute => setting['value'])
if entry.respond_to? "#{attribute}="
entry.public_send("#{attribute}=", setting['value'])
end
end
end
end
end
def display_in_inventory(variant_override, is_new = false)
unless is_new
existing_item = InventoryItem.where(

View File

@@ -1,45 +0,0 @@
module ProductImport
class ProductsResetStrategy
def initialize(excluded_items_ids)
@excluded_items_ids = excluded_items_ids
end
def reset(enterprise_ids)
@enterprise_ids = enterprise_ids
return 0 if enterprise_ids.blank?
reset_variants_on_hand(enterprise_variants_relation)
end
private
attr_reader :excluded_items_ids, :enterprise_ids
def enterprise_variants_relation
relation = Spree::Variant
.joins(:product)
.where(
spree_products: { supplier_id: enterprise_ids },
spree_variants: { is_master: false, deleted_at: nil }
)
return relation if excluded_items_ids.blank?
relation.where('spree_variants.id NOT IN (?)', excluded_items_ids)
end
def reset_variants_on_hand(variants)
updated_records_count = 0
variants.each do |variant|
updated_records_count += 1 if reset_variant_on_hand(variant)
end
updated_records_count
end
def reset_variant_on_hand(variant)
variant.on_hand = 0
variant.on_hand.zero?
end
end
end

View File

@@ -1,5 +1,7 @@
class Schedule < ActiveRecord::Base
has_and_belongs_to_many :order_cycles, join_table: 'order_cycle_schedules'
has_paper_trail meta: { custom_data: :order_cycle_ids }
has_many :coordinators, uniq: true, through: :order_cycles
attr_accessible :name, :order_cycle_ids

View File

@@ -13,14 +13,15 @@ module Spree
def compute(object = nil)
return 0 if object.nil?
preferred_amount * line_items_for(object).reduce(0) do |sum, value|
value_to_add = if matching_products.blank? || matching_products.include?(value.product)
value.quantity
number_of_line_items = line_items_for(object).reduce(0) do |sum, line_item|
value_to_add = if matching_products.blank? || matching_products.include?(line_item.product)
line_item.quantity
else
0
end
sum + value_to_add
end
preferred_amount * number_of_line_items
end
end
end

View File

@@ -9,12 +9,6 @@ module Spree
attr_accessible :preferred_enterprise_id
CARD_TYPE_MAPPING = {
'American Express' => 'american_express',
'Diners Club' => 'diners_club',
'Visa' => 'visa'
}.freeze
def method_type
'stripe'
end
@@ -77,11 +71,6 @@ module Spree
[money, creditcard, options]
end
def update_source!(source)
source.cc_type = CARD_TYPE_MAPPING[source.cc_type] if CARD_TYPE_MAPPING.include?(source.cc_type)
source
end
def token_from_card_profile_ids(creditcard)
token_or_card_id = creditcard.gateway_payment_profile_id
customer = creditcard.gateway_customer_profile_id

View File

@@ -0,0 +1,139 @@
# frozen_string_literal: true
require 'stripe/profile_storer'
require 'stripe/credit_card_cloner'
require 'stripe/authorize_response_patcher'
require 'stripe/payment_intent_validator'
require 'active_merchant/billing/gateways/stripe_payment_intents'
require 'active_merchant/billing/gateways/stripe_decorator'
module Spree
class Gateway
class StripeSCA < Gateway
preference :enterprise_id, :integer
validate :ensure_enterprise_selected
attr_accessible :preferred_enterprise_id
def method_type
'stripe_sca'
end
def provider_class
ActiveMerchant::Billing::StripePaymentIntentsGateway
end
def payment_profiles_supported?
true
end
def stripe_account_id
StripeAccount.find_by_enterprise_id(preferred_enterprise_id).andand.stripe_user_id
end
# NOTE: the name of this method is determined by Spree::Payment::Processing
def purchase(money, creditcard, gateway_options)
begin
payment_intent_id = fetch_payment_intent(creditcard, gateway_options)
rescue Stripe::StripeError => e
return failed_activemerchant_billing_response(e.message)
end
options = basic_options(gateway_options)
options[:customer] = creditcard.gateway_customer_profile_id
provider.capture(money, payment_intent_id, options)
rescue Stripe::StripeError => e
failed_activemerchant_billing_response(e.message)
end
# NOTE: the name of this method is determined by Spree::Payment::Processing
def authorize(money, creditcard, gateway_options)
authorize_response = provider.authorize(*options_for_authorize(money,
creditcard,
gateway_options))
Stripe::AuthorizeResponsePatcher.new(authorize_response).call!
rescue Stripe::StripeError => e
failed_activemerchant_billing_response(e.message)
end
# NOTE: the name of this method is determined by Spree::Payment::Processing
def void(response_code, _creditcard, gateway_options)
gateway_options[:stripe_account] = stripe_account_id
provider.void(response_code, gateway_options)
end
# NOTE: the name of this method is determined by Spree::Payment::Processing
def credit(money, _creditcard, response_code, gateway_options)
gateway_options[:stripe_account] = stripe_account_id
provider.refund(money, response_code, gateway_options)
end
def create_profile(payment)
return unless payment.source.gateway_customer_profile_id.nil?
profile_storer = Stripe::ProfileStorer.new(payment, provider)
profile_storer.create_customer_from_token
end
private
# In this gateway, what we call 'secret_key' is the 'login'
def options
options = super
options.merge(login: Stripe.api_key)
end
def basic_options(gateway_options)
options = {}
options[:description] = "Spree Order ID: #{gateway_options[:order_id]}"
options[:currency] = gateway_options[:currency]
options[:stripe_account] = stripe_account_id
options
end
def options_for_authorize(money, creditcard, gateway_options)
options = basic_options(gateway_options)
options[:return_url] = full_checkout_path
customer_id, payment_method_id = Stripe::CreditCardCloner.new.clone(creditcard,
stripe_account_id)
options[:customer] = customer_id
[money, payment_method_id, options]
end
def fetch_payment_intent(creditcard, gateway_options)
payment = fetch_payment(creditcard, gateway_options)
raise Stripe::StripeError, I18n.t(:no_pending_payments) unless payment&.response_code
Stripe::PaymentIntentValidator.new.call(payment.response_code, stripe_account_id)
end
def fetch_payment(creditcard, gateway_options)
order_number = gateway_options[:order_id].split('-').first
Spree::Order.find_by_number(order_number).payments.merge(creditcard.payments).last
end
def failed_activemerchant_billing_response(error_message)
ActiveMerchant::Billing::Response.new(false, error_message)
end
def ensure_enterprise_selected
return if preferred_enterprise_id.andand.positive?
errors.add(:stripe_account_owner, I18n.t(:error_required))
end
def full_checkout_path
URI.join(url_helpers.root_url, url_helpers.checkout_path).to_s
end
def url_helpers
# This is how we can get the helpers with a usable root_url outside the controllers
Rails.application.routes.default_url_options = ActionMailer::Base.default_url_options
Rails.application.routes.url_helpers
end
end
end
end

View File

@@ -56,7 +56,9 @@ Spree::Order.class_eval do
# Find orders that are distributed by the user or have products supplied by the user
# WARNING: This only filters orders, you'll need to filter line items separately using LineItem.managed_by
with_line_items_variants_and_products_outer.
where('spree_orders.distributor_id IN (?) OR spree_products.supplier_id IN (?)', user.enterprises, user.enterprises).
where('spree_orders.distributor_id IN (?) OR spree_products.supplier_id IN (?)',
user.enterprises.select(&:id),
user.enterprises.select(&:id)).
select('DISTINCT spree_orders.*')
end
}
@@ -65,7 +67,7 @@ Spree::Order.class_eval do
if user.has_spree_role?('admin')
scoped
else
where('spree_orders.distributor_id IN (?)', user.enterprises)
where('spree_orders.distributor_id IN (?)', user.enterprises.select(&:id))
end
}
@@ -115,6 +117,12 @@ Spree::Order.class_eval do
end
end
# "Checkout" is the initial state and, for card payments, "pending" is the state after authorization
# These are both valid states to process the payment
def pending_payments
(payments.select(&:pending?) + payments.select(&:processing?) + payments.select(&:checkout?)).uniq
end
def remove_variant(variant)
line_items(:reload)
current_item = find_line_item_by_variant(variant)

View File

@@ -20,7 +20,7 @@ Spree::PaymentMethod.class_eval do
scoped
else
joins(:distributors).
where('distributors_payment_methods.distributor_id IN (?)', user.enterprises).
where('distributors_payment_methods.distributor_id IN (?)', user.enterprises.select(&:id)).
select('DISTINCT spree_payment_methods.*')
end
}
@@ -68,6 +68,8 @@ Spree::PaymentMethod.class_eval do
"Pin Payments"
when "Spree::Gateway::StripeConnect"
"Stripe"
when "Spree::Gateway::StripeSCA"
"Stripe SCA"
when "Spree::Gateway::PayPalExpress"
"PayPal Express"
else

View File

@@ -1,6 +1,6 @@
class Spree::ProductSet < ModelSet
def initialize(attributes = {})
super(Spree::Product, [], attributes, proc { |attrs| attrs[:product_id].blank? })
super(Spree::Product, [], attributes)
end
def save
@@ -34,11 +34,9 @@ class Spree::ProductSet < ModelSet
split_taxon_ids!(attributes)
product = find_model(@collection, attributes[:id])
if product.nil?
@klass.new(attributes).save unless @reject_if.andand.call(attributes)
else
update_product(product, attributes)
end
return if product.nil?
update_product(product, attributes)
end
def split_taxon_ids!(attributes)

View File

@@ -15,7 +15,7 @@ Spree::ShippingMethod.class_eval do
scoped
else
joins(:distributors).
where('distributors_shipping_methods.distributor_id IN (?)', user.enterprises).
where('distributors_shipping_methods.distributor_id IN (?)', user.enterprises.select(&:id)).
select('DISTINCT spree_shipping_methods.*')
end
}

View File

@@ -1,12 +1,14 @@
module Spree
TaxRate.class_eval do
class << self
def match_with_sales_tax_registration(order)
def match(order)
return [] if order.distributor && !order.distributor.charges_sales_tax
return [] unless order.tax_zone
match_without_sales_tax_registration(order)
all.select do |rate|
rate.zone == order.tax_zone || rate.zone.contains?(order.tax_zone) || rate.zone.default_tax
end
end
alias_method_chain :match, :sales_tax_registration
end
def adjust_with_included_tax(order)

View File

@@ -49,7 +49,7 @@ Spree::Variant.class_eval do
}
scope :for_distribution, lambda { |order_cycle, distributor|
where('spree_variants.id IN (?)', order_cycle.variants_distributed_by(distributor))
where('spree_variants.id IN (?)', order_cycle.variants_distributed_by(distributor).select(&:id))
}
scope :visible_for, lambda { |enterprise|

View File

@@ -1,5 +1,7 @@
class Subscription < ActiveRecord::Base
ALLOWED_PAYMENT_METHOD_TYPES = ["Spree::PaymentMethod::Check", "Spree::Gateway::StripeConnect"].freeze
ALLOWED_PAYMENT_METHOD_TYPES = ["Spree::PaymentMethod::Check",
"Spree::Gateway::StripeConnect",
"Spree::Gateway::StripeSCA"].freeze
belongs_to :shop, class_name: 'Enterprise'
belongs_to :customer

View File

@@ -4,7 +4,8 @@ module Api
delegate :serializable_hash, to: :method_serializer
def method_serializer
if object.type == 'Spree::Gateway::StripeConnect'
if object.type == 'Spree::Gateway::StripeConnect' ||
object.type == 'Spree::Gateway::StripeSCA'
Api::Admin::PaymentMethod::StripeSerializer.new(object)
else
Api::Admin::PaymentMethod::BaseSerializer.new(object)

View File

@@ -2,7 +2,7 @@
# Provides the redirect path if a redirect to the payment gateway is needed
module Checkout
class PaymentRedirect
class PaypalRedirect
def initialize(params)
@params = params
end

View File

@@ -0,0 +1,30 @@
# frozen_string_literal: true
# Executes actions after checkout
module Checkout
class PostCheckoutActions
def initialize(order)
@order = order
end
def success(controller, params, current_user)
save_order_addresses_as_user_default(params, current_user)
ResetOrderService.new(controller, @order).call
end
def failure
@order.updater.shipping_address_from_distributor
RestartCheckout.new(@order).call
end
private
def save_order_addresses_as_user_default(params, current_user)
return unless params[:order]
user_default_address_setter = UserDefaultAddressSetter.new(@order, current_user)
user_default_address_setter.set_default_bill_address if params[:order][:default_bill_address]
user_default_address_setter.set_default_ship_address if params[:order][:default_ship_address]
end
end
end

View File

@@ -0,0 +1,46 @@
# frozen_string_literal: true
# Provides the redirect path if a redirect to the payment gateway is needed
module Checkout
class StripeRedirect
def initialize(params, order)
@params = params
@order = order
end
# Returns the path to the authentication form if a redirect is needed
def path
return unless stripe_payment_method?
payment = @order.pending_payments.last
return unless payment&.checkout?
payment.authorize!
raise unless payment.pending?
field_with_url(payment) if url?(field_with_url(payment))
end
private
def stripe_payment_method?
return unless @params[:order][:payments_attributes]
payment_method_id = @params[:order][:payments_attributes].first[:payment_method_id]
payment_method = Spree::PaymentMethod.find(payment_method_id)
payment_method.is_a?(Spree::Gateway::StripeSCA)
end
def url?(string)
return false if string.blank?
string.starts_with?("http")
end
# Stripe::AuthorizeResponsePatcher patches the Stripe authorization response
# so that this field stores the redirect URL
def field_with_url(payment)
payment.cvv_response_message
end
end
end

View File

@@ -0,0 +1,14 @@
# frozen_string_literal: true
module OrderPaymentFinder
def self.last_payment_method(order)
# `max_by` avoids additional database queries when payments are loaded
# already. There is usually only one payment and this shouldn't cause
# any overhead compared to `order(:created_at).last`. Using `last`
# without order is not deterministic.
#
# We are not using `updated_at` because all payments are touched when the
# order is updated and then all payments have the same `updated_at` value.
order.payments.max_by(&:created_at)&.payment_method
end
end

View File

@@ -82,13 +82,18 @@ class SubscriptionValidator
def credit_card_ok?
return unless customer && payment_method
return unless payment_method.type == "Spree::Gateway::StripeConnect"
return unless stripe_payment_method?(payment_method)
return errors.add(:payment_method, :charges_not_allowed) unless customer.allow_charges
return if customer.user.andand.default_card.present?
errors.add(:payment_method, :no_default_card)
end
def stripe_payment_method?(payment_method)
payment_method.type == "Spree::Gateway::StripeConnect" ||
payment_method.type == "Spree::Gateway::StripeSCA"
end
def subscription_line_items_present?
return if subscription_line_items.reject(&:marked_for_destruction?).any?

View File

@@ -1,7 +1,3 @@
-# For purposes of debugging bulk_update. See Admin/Enterprises#bulk_update.
- if flash[:action]
%p= flash[:action]
= form_for @enterprise_set, url: main_app.bulk_update_admin_enterprises_path do |f|
%table#listing_enterprises.index
%colgroup

View File

@@ -3,7 +3,7 @@
.three.columns.alpha
= f.label "enterprise_preferred_shopfront_message", t('.shopfront_message')
.eight.columns.omega
%text-angular{'ng-model' => 'Enterprise.preferred_shopfront_message', 'id' => 'enterprise_preferred_shopfront_message', 'name' => 'enterprise[preferred_shopfront_message]', 'class' => 'text-angular', "textangular-links-target-blank" => true,
%text-angular{'ng-model' => 'Enterprise.preferred_shopfront_message', 'id' => 'enterprise_preferred_shopfront_message', 'name' => 'enterprise[preferred_shopfront_message]', 'class' => 'text-angular textangular-strip', 'ta-paste' => "stripFormatting($html)", "textangular-links-target-blank" => true,
'ta-toolbar' => "[['h1','h2','h3','h4','p'],['bold','italics','underline','clear'],['insertLink']]",
'placeholder' => t('.shopfront_message_placeholder')}
.row
@@ -11,7 +11,7 @@
.three.columns.alpha
= f.label "enterprise_preferred_shopfront_closed_message", t('.shopfront_closed_message')
.eight.columns.omega
%text-angular{'ng-model' => 'Enterprise.preferred_shopfront_closed_message', 'id' => 'enterprise_preferred_shopfront_closed_message', 'name' => 'enterprise[preferred_shopfront_closed_message]', 'class' => 'text-angular', "textangular-links-target-blank" => true,
%text-angular{'ng-model' => 'Enterprise.preferred_shopfront_closed_message', 'id' => 'enterprise_preferred_shopfront_closed_message', 'name' => 'enterprise[preferred_shopfront_closed_message]', 'class' => 'text-angular textangular-strip', 'ta-paste' => "stripFormatting($html)", "textangular-links-target-blank" => true,
'ta-toolbar' => "[['h1','h2','h3','h4','p'],['bold','italics','underline','clear'],['insertLink']]",
'placeholder' => t('.shopfront_closed_message_placeholder')}
.row

View File

@@ -19,8 +19,7 @@
{{ orderCycle.producers.length }}
= t('.suppliers')
%span{ ng: { hide: 'orderCycle.producers.length > 3', bind: 'orderCycle.producerNames' } }
%td.coordinator{ ng: { show: 'columns.coordinator.visible' } }
{{ orderCycle.coordinator.name }}
%td.coordinator{ ng: { show: 'columns.coordinator.visible', bind: { html: 'orderCycle.coordinator.name'} } }
%td.shops{ ng: { show: 'columns.shops.visible' } }
%span{'ofn-with-tip' => '{{ orderCycle.shopNames }}', ng: { show: 'orderCycle.shops.length > 3' } }
{{ orderCycle.shops.length }}

View File

@@ -13,7 +13,7 @@
%th.hide=t('admin.variant_overrides.index.hide')
%tbody{ ng: { repeat: 'product in filteredProducts | limitTo:productLimit' } }
%tr{ id: "v_{{variant.id}}", ng: { repeat: 'variant in product.variants | inventoryVariants:hub_id:views' } }
%td.producer{ ng: { bind: '::producersByID[product.producer_id].name'} }
%td.producer{ ng: { bind: { html: '::producersByID[product.producer_id].name'} } }
%td.product{ ng: { bind: '::product.name'} }
%td.variant
%span{ ng: { bind: '::variant.display_name || ""'} }

View File

@@ -1,5 +1,5 @@
%tr.product.even
%td.producer{ ng: { show: 'columns.producer.visible', bind: '::producersByID[product.producer_id].name'} }
%td.producer{ ng: { show: 'columns.producer.visible', bind: { html: '::producersByID[product.producer_id].name'} } }
%td.product{ ng: { show: 'columns.product.visible', bind: '::product.name'} }
%td.sku{ ng: { show: 'columns.sku.visible' } }
%td.price{ ng: { show: 'columns.price.visible' } }

View File

@@ -1,8 +1,3 @@
- content_for :injection_data do
- if Stripe.publishable_key
:javascript
angular.module('Darkswarm').value("stripeObject", Stripe("#{Stripe.publishable_key}"))
%fieldset#payment
%ng-form{"ng-controller" => "PaymentCtrl", name: "payment"}

View File

@@ -15,7 +15,7 @@
%strong
= pickup_time current_order_cycle
= render partial: "shopping_shared/header"
= render partial: "shopping_shared/header", locals: { hide_oc_selector: true }
%accordion{"close-others" => "false"}
%checkout.row{"ng-controller" => "CheckoutCtrl"}

View File

@@ -19,22 +19,24 @@
- content_for :order_cycle_form do
%div{"ng-controller" => "OrderCycleChangeCtrl", "ng-cloak" => true}
%closing{"ng-if" => "OrderCycle.selected()"}
= t :enterprises_next_closing
%strong {{ OrderCycle.orders_close_at() | date_in_words }}
%closing
%div{"ng-if" => "OrderCycle.selected()"}
= t :enterprises_next_closing
%strong {{ OrderCycle.orders_close_at() | date_in_words }}
%div{"ng-if" => "!OrderCycle.selected()"}
= t :enterprises_choose
%span
= t :enterprises_ready_for
/ Will this label should be a variable to reflect 'Ready for pickup / delivery' as appropriate
%select.avenir#order_cycle_id{"ng-model" => "order_cycle.order_cycle_id",
"ofn-change-order-cycle" => true,
"disabled" => require_customer?,
"ng-options" => "oc.id as oc.time for oc in #{@order_cycles.map {|oc| {time: pickup_time(oc), id: oc.id}}.to_json}",
"popover-placement" => "left", "popover" => t(:enterprises_choose), "popover-trigger" => "openTrigger"}
.order-cycle-select
.select-label
%span= t :enterprises_ready_for
%select.select2.avenir#order_cycle_id{"ng-model" => "order_cycle.order_cycle_id",
"ofn-change-order-cycle" => true,
"disabled" => require_customer?,
"ng-options" => "oc.id as oc.time for oc in #{oc_select_options.to_json}"}
- if oc_select_options.count > 1
%option{value: "", disabled: "", selected: ""}= t :shopping_oc_select
= render partial: "shopping_shared/header"
= render partial: "shopping_shared/tabs"

View File

@@ -1,19 +0,0 @@
.row
.large-12.large-centered.columns
%h2
= t :label_login
= form_for Spree::User.new, :remote => true, :html => {'data-type' => :json}, :as => :spree_user, :url => spree.spree_user_session_path do |f|
#password-credentials
#login-error-alert.alert-box.alert.hide
= t :login_invalid
%p
= f.label :email, t(:email)
= f.email_field :email, :class => 'title', :tabindex => 1, :id => "login_spree_user_email"
%p
= f.label :password, t(:password)
= f.password_field :password, :class => 'title', :tabindex => 2, :id => "login_spree_user_password"
%p
%label
= f.check_box :remember_me
= f.label :remember_me, t(:remember_me)
%p= f.submit t(:login), :class => 'button primary', :tabindex => 3, :id => "login_spree_user_remember_me"

View File

@@ -1,18 +0,0 @@
.row
.large-12.large-centered.columns
%h2
= t :label_signup
= form_for Spree::User.new, :as => :spree_user, :url => spree.spree_user_registration_path(@spree_user) do |f|
%p
= f.label :email, t(:email)
= f.email_field :email, :class => 'title', :id => "signup_spree_user_email"
#password-credentials
%p
= f.label :password, t(:password)
= f.password_field :password, :class => 'title', :id => "signup_spree_user_password"
%p
= f.label :password_confirmation, t(:confirm_password)
= f.password_field :password_confirmation, :class => 'title', :id => "signup_spree_user_password_confirmation"
= f.submit t(:create), :class => 'button'

View File

@@ -9,4 +9,4 @@
%p= t(".login")
.row
.small-12.columns.text-center
%a.button.primary{ type: "button", href: "/" }= "#{t(".action")} >"
%a.button.primary{ type: "button", href: spree.admin_dashboard_path }= t(".action")

View File

@@ -2,14 +2,14 @@
%navigation
%distributor.details.row
.small-12.medium-6.large-6.columns
.small-12.medium-12.large-8.columns
#distributor_title
- if distributor.logo?
%img.left{src: distributor.logo.url(:thumb)}
%h3
= distributor.name
%location= distributor.address.city
/ Will this needs to be a drop-down to choose either pick-up point or delivery once shipping methods are implemented
.small-12.medium-6.large-6.columns
= render partial: "shopping_shared/order_cycles"
- unless defined? hide_oc_selector
.show-for-large-up.large-4.columns
= render partial: "shopping_shared/order_cycles"

View File

@@ -1,2 +1,4 @@
- if most_recently_closed = OrderCycle.most_recently_closed_for(@distributor)
(
= t :shopping_oc_last_closed, distance_of_time: distance_of_time_in_words_to_now(most_recently_closed.orders_close_at)
)

View File

@@ -1,2 +1,4 @@
- if next_oc = OrderCycle.first_opening_for(@distributor)
(
= t :shopping_oc_next_open, distance_of_time: distance_of_time_in_words_to_now(next_oc.orders_open_at)
)

View File

@@ -1,8 +1,8 @@
- content_for :injection_data do
= inject_current_order_cycle
%ordercycle{"ng-controller" => "OrderCycleCtrl"}
- unless no_open_order_cycles?
- unless no_open_order_cycles?
%ordercycle{"ng-controller" => "OrderCycleCtrl", "ng-cloak" => true,
"ng-class" => "{'requires-selection': !OrderCycle.selected()}"}
%form.custom
= yield :order_cycle_form

View File

@@ -3,11 +3,12 @@
- shop_tabs.each do |tab|
= render "shopping_shared/tabs/#{tab[:name]}"
.tabset-ctrl#shop-tabs{ navigate: 'true', alwaysopen: 'true', selected: shop_tabs.first[:name], prefix: 'shop', ng: { cloak: true } }
#shop-tabs{ ng: { controller: "PageSelectionCtrl", init: "whitelistPages(#{shop_tab_names.to_json})", cloak: true } }
.tab-buttons
.row
- shop_tabs.each do |tab|
.tab{ id: "tab_#{tab[:name]}", name: tab[:name] }
%a{ href: 'javascript:void(0)' }=tab[:title]
.columns.small-12.large-8
- shop_tabs.each do |tab|
.page{ "ng-class" => "{ selected: selectedPage() == '#{tab[:name]}' }" }
%a{ href: "##{tab[:name]}" }=tab[:title]
.tab-view
.page-view{ ng: {include: "'shop/' + selectedPage() + '.html'" } }

View File

@@ -6,7 +6,7 @@
%div.center
.header
= t :shopping_contact_address
%strong=current_distributor.name
%span= current_distributor.name
%p
= current_distributor.address.address1
- unless current_distributor.address.address2.blank?
@@ -44,22 +44,19 @@
- if current_distributor.twitter.present?
%span
%a{href: "http://twitter.com/#{current_distributor.twitter}", target: "_blank" }
%i.ofn-i_041-twitter
%i.twitter.ofn-i_041-twitter
- if current_distributor.facebook.present?
%span
%a{href: "http://#{current_distributor.facebook}", target: "_blank" }
%i.ofn-i_044-facebook
/ = current_distributor.facebook
%i.facebook.ofn-i_044-facebook
- if current_distributor.linkedin.present?
%span
%a{href: "http://#{current_distributor.linkedin}", target: "_blank" }
%i.ofn-i_042-linkedin
/ = current_distributor.linkedin
%i.linkedin.ofn-i_042-linkedin
- if current_distributor.instagram.present?
%span
%a{href: "http://instagram.com/#{current_distributor.instagram}", target: "_blank" }
%i.ofn-i_043-instagram
/ = current_distributor.instagram
%i.instagram.ofn-i_043-instagram

View File

@@ -1,12 +1,12 @@
%script{ type: "text/ng-template", id: "shop/groups.html" }
.content
.row
.small-12.large-4.columns
.small-12.columns
- if current_distributor.groups.length > 0
%h5
=current_distributor.name
= t :shopping_groups_part_of
%ul.bullet-list
%ul.bullet-list.small-block-grid-1.medium-block-grid-2.large-block-grid-3
- for group in current_distributor.groups
%li
%a{href: main_app.groups_path + "/#{group.permalink}"}

View File

@@ -1,3 +1,6 @@
%script{ type: "text/ng-template", id: "shop/home.html" }
.order-cycle-bar.hide-for-large-up
= render partial: "shopping_shared/order_cycles"
.content
= render partial: 'shop/messages'

View File

@@ -4,7 +4,7 @@
.small-12.columns
%h5
= t :shopping_producers_of_hub, hub: '{{ shopfront.name }}'
%ul.small-block-grid-2.large-block-grid-4
%ul.small-block-grid-1.medium-block-grid-2.large-block-grid-3
%li{"ng-repeat" => "enterprise in shopfront.producers"}
%enterprise-modal
%i.ofn-i_036-producers

View File

@@ -1,4 +1,7 @@
%script{ type: "text/ng-template", id: "shop/shop.html" }
.order-cycle-bar.hide-for-large-up
= render partial: "shopping_shared/order_cycles"
.row
.small-12.columns
- if no_open_order_cycles?
@@ -8,10 +11,8 @@
= t :shopping_oc_closed
%small
%em
(
= render partial: "shopping_shared/next_order_cycle"
= render partial: "shopping_shared/last_order_cycle"
)
%p
= t :shopping_oc_closed_description

View File

@@ -84,7 +84,7 @@
%i.error.icon-remove-sign.with-tip{ng: {show: 'rowStatus[order.id] == "error"'}, 'ofn-with-tip' => t('.order_not_updated')}
%a.icon_link.with-tip.icon-edit.no-text{'ng-href' => '{{order.edit_path}}', 'data-action' => 'edit', 'ofn-with-tip' => t('.edit')}
%div{'ng-if' => 'order.ready_to_ship'}
%button.icon-road.icon_link.with-tip.no-text{'ng-click' => 'shipOrder(order)', 'data-confirm' => t(:are_you_sure), rel: 'nofollow', 'ofn-with-tip' => t('.ship')}
%button.icon-road.icon_link.with-tip.no-text{'ng-click' => 'shipOrder(order)', rel: 'nofollow', 'ofn-with-tip' => t('.ship')}
%div{'ng-if' => 'order.ready_to_capture'}
%button.icon-capture.icon_link.no-text{'ng-click' => 'capturePayment(order)', rel: 'nofollow', 'ofn-with-tip' => t('.capture')}

View File

@@ -17,7 +17,7 @@
%td{ :align => "right" }
%h4= @order.order_cycle.andand.name
%tr{ valign: "top" }
%td{ :align => "left" }
%td{ align: "left", colspan: 3 }
%strong= "#{t('.from')}: #{@order.distributor.name}"
- if @order.distributor.abn.present?
%br
@@ -26,31 +26,43 @@
= @order.distributor.address.full_address
%br
= @order.distributor.contact.email
%td{width: "10%" }
%tr{ valign: "top" }
%td{ colspan: 3 }
&nbsp;
%td{ :align => "right" }
%strong= "#{t('.to')}: #{@order.ship_address.full_name}"
%tr{ valign: "top" }
%td{ align: "left" }
%strong= "#{t('.to')}:"
%br
= @order.bill_address.full_name
- if @order.andand.customer.andand.code.present?
%br
= "#{t('.code')}: #{@order.customer.code}"
%br
= @order.ship_address.full_address
= @order.bill_address.full_address
%br
- if @order.andand.customer.andand.email.present?
= "#{@order.customer.email},"
= "#{@order.bill_address.phone}"
%td
&nbsp;
%td{ align: "left", style: "border-left: .1em solid black; padding-left: 1em" }
%strong= "#{t('.shipping')}: #{@order.shipping_method&.name}"
- if @order.shipping_method&.require_ship_address
%br
= @order.ship_address.full_name
%br
= @order.ship_address.full_address
%br
= @order.ship_address.phone
- if @order.special_instructions.present?
%br
%br
%strong= t :customer_instructions
= @order.special_instructions
= render 'spree/admin/orders/invoice_table'
- if @order.special_instructions.present?
%p.callout
%strong
= t :customer_instructions
%p
%em= @order.special_instructions
%p
&nbsp;
- if @order.distributor.invoice_text.present?
%p
= @order.distributor.invoice_text

View File

@@ -1,6 +1,9 @@
= @payment_method
- case @payment_method
- when Spree::Gateway::StripeConnect
= render 'stripe_connect'
- when Spree::Gateway::StripeSCA
= render 'stripe_connect'
- else
- if @payment_method.preferences.present?
%fieldset.alpha.eleven.columns.no-border-bottom#gateway_fields

View File

@@ -0,0 +1,16 @@
.stripe
%script{:src => "https://js.stripe.com/v3/", :type => "text/javascript"}
- if Stripe.publishable_key
:javascript
angular.module('admin.payments').value("stripeObject", Stripe("#{Stripe.publishable_key}"))
.row
.three.columns
= label_tag :cardholder_name, t(:cardholder_name)
.six.columns
= text_field_tag :cardholder_name, nil, {size: 40, "ng-model" => 'form_data.name'}
.row
.three.columns
= label_tag :card_details, t(:card_details)
.six.columns
%stripe-elements

View File

@@ -6,28 +6,28 @@
%dt
= Spree.t(:card_number)
\:
%dd= payment.source.display_number
%dd= payment.source&.display_number
%dt
= Spree.t(:expiration)
\:
%dd
= payment.source.month
= payment.source&.month
\/
= payment.source.year
= payment.source&.year
%dt
= Spree.t(:card_code)
\:
%dd= payment.source.verification_value
%dd= payment.source&.verification_value
.omega.six.columns
%dl
%dt
= t(:maestro_or_solo_cards)
\:
%dd= payment.source.issue_number
%dd= payment.source&.issue_number
%dt
= Spree.t(:start_date)
\:
%dd
= payment.source.start_month
= payment.source&.start_month
\/
= payment.source.start_year
= payment.source&.start_year

View File

@@ -0,0 +1 @@
= render "spree/admin/payments/source_views/gateway", payment: payment

View File

@@ -49,6 +49,6 @@
- content_for :page_actions do
%ul.inline-menu
%li#new_var_link
= link_to_with_icon('icon-plus', t('.new_variant'), new_admin_product_variant_url(@product), remote: true, 'data-update' => 'new_variant', class: 'button')
= link_to_with_icon('icon-plus', t('.new_variant'), new_admin_product_variant_url(@product), class: 'button')
%li= link_to_with_icon('icon-filter', @deleted.blank? ? t('.show_deleted') : t('.show_active'), admin_product_variants_url(@product, deleted: @deleted.blank? ? "on" : "off"), class: 'button')

View File

@@ -1,3 +1,8 @@
- content_for :injection_data do
- if Stripe.publishable_key
:javascript
angular.module('Darkswarm').value("stripeObject", Stripe("#{Stripe.publishable_key}"))
.row{ "ng-show" => "savedCreditCards.length > 0" }
.small-12.columns
%h6= t('.used_saved_card')

View File

@@ -0,0 +1,22 @@
- content_for :injection_data do
- if Stripe.publishable_key
:javascript
angular.module('Darkswarm').value("stripeObject", Stripe("#{Stripe.publishable_key}"))
.row{ "ng-show" => "savedCreditCards.length > 0" }
.small-12.columns
%h6= t('.used_saved_card')
%select{ name: "selected_card", required: false, ng: { model: "secrets.selected_card", options: "card.id as card.formatted for card in savedCreditCards" } }
%option{ value: "" }= "{{ secrets.selected_card ? '#{t('.enter_new_card')}' : '#{t('.choose_one')}' }}"
%h6{ ng: { if: '!secrets.selected_card' } }
= t('.or_enter_new_card')
%div{ ng: { if: '!secrets.selected_card' } }
%stripe-elements
- if spree_current_user
.row
.small-12.columns.text-right
= check_box_tag 'secrets.save_requested_by_customer', '1', false, 'ng-model' => 'secrets.save_requested_by_customer'
= label_tag 'secrets.save_requested_by_customer', t('.remember_this_card')

View File

@@ -8,7 +8,7 @@
= t :email_payment_summary
%h4
= t :email_payment_method
%strong= @order.payments.first.andand.payment_method.andand.name.andand.html_safe
%strong= OrderPaymentFinder.last_payment_method(@order)&.name
%p
%em= @order.payments.first.andand.payment_method.andand.description.andand.html_safe
%em= OrderPaymentFinder.last_payment_method(@order)&.description
%p &nbsp;

View File

@@ -22,7 +22,7 @@
- if @order.line_items.empty?
%div.row{"data-hook" => "empty_cart"}
%p= t(:your_cart_is_empty)
%p= link_to t(:continue_shopping), main_app.shop_path, :class => 'button continue'
%p= link_to t(:continue_shopping), current_shop_products_path, :class => 'button continue'
- else
%div{"data-hook" => "outside_cart_form"}

View File

@@ -1,6 +1,6 @@
.row.links{'data-hook' => "cart_buttons"}
.columns.large-8{"data-hook" => ""}
%a.button.large.secondary{href: main_app.shop_path}
%a.button.large.secondary{href: current_shop_products_path}
%i.ofn-i_008-caret-left
= t :orders_edit_continue
.columns.large-4.text-right

View File

@@ -1,12 +1,12 @@
.row
.columns.small-12.medium-3
- if current_order.andand.distributor == @order.distributor
- if current_order.line_items.present?
- if current_order.nil? || current_order.distributor.nil? || current_order.distributor == @order.distributor
- if current_order&.line_items.present?
= link_to main_app.cart_path, :class => "button expand" do
%i.ofn-i_008-caret-left
= t(:order_back_to_cart)
- else
= link_to main_app.shop_path, :class => "button expand" do
= link_to "#{main_app.enterprise_shop_path(@order.distributor)}#/shop", class: "button expand" do
%i.ofn-i_008-caret-left
= t(:order_back_to_store)
- else

View File

@@ -13,9 +13,9 @@
.pad
.text-big
= t :order_payment
%strong= order.payments.first.andand.payment_method.andand.name.andand.html_safe
%strong= OrderPaymentFinder.last_payment_method(order)&.name
%p.text-small.text-skinny.pre-line
%em= order.payments.first.andand.payment_method.andand.description.andand.html_safe
%em= OrderPaymentFinder.last_payment_method(order)&.description
.order-summary.text-small
%strong

View File

@@ -92,6 +92,7 @@ module Openfoodnetwork
app.config.spree.payment_methods << Spree::Gateway::Migs
app.config.spree.payment_methods << Spree::Gateway::Pin
app.config.spree.payment_methods << Spree::Gateway::StripeConnect
app.config.spree.payment_methods << Spree::Gateway::StripeSCA
end
# Settings in config/environments/* take precedence over those specified here.

View File

@@ -33,11 +33,12 @@ Openfoodnetwork::Application.configure do
# Use https in email links
config.action_mailer.default_url_options = { protocol: 'https' }
# See everything in the log (default is :info)
# Note: This config no longer works with our new logging strategy
# config.log_level = :debug
# Configure logging for Rails 3.2:
config.logger = ActiveSupport::TaggedLogging.new(Logger.new(Rails.root.join("log", "#{Rails.env}.log")))
config.logger.level = Logger::INFO
config.logger.formatter = Logger::Formatter.new
config.logger.datetime_format = "%Y-%m-%d %H:%M:%S"
# Once we get to Rails 4.0, we can replace the above with:

View File

@@ -33,11 +33,12 @@ Openfoodnetwork::Application.configure do
# Use https in email links
config.action_mailer.default_url_options = { protocol: 'https' }
# See everything in the log (default is :info)
# Note: This config no longer works with our new logging strategy
# config.log_level = :debug
# Configure logging for Rails 3.2:
config.logger = ActiveSupport::TaggedLogging.new(Logger.new(Rails.root.join("log", "#{Rails.env}.log")))
config.logger.level = Logger::INFO
config.logger.formatter = Logger::Formatter.new
config.logger.datetime_format = "%Y-%m-%d %H:%M:%S"
# Once we get to Rails 4.0, we can replace the above with:

View File

@@ -1 +1,7 @@
PaperTrail.config.track_associations = false
module PaperTrail
class Version < ActiveRecord::Base
attr_accessible :custom_data
end
end

View File

@@ -245,7 +245,7 @@ ar:
allow_cookies: "السماح لملفات تعريف الارتباط"
notes: ملاحظات
error: خطأ
processing_payment: معالجة الدفع...
processing_payment: "معالجة الدفع..."
filter_results: تصفية النتائج
quantity: الكمية
pick_up: النقل
@@ -1864,7 +1864,6 @@ ar:
headline: "تم الانتهاء !"
thanks: "شكرًا لملء تفاصيل %{enterprise}."
login: "يمكنك تغيير أو تحديث شركتك في أي مرحلة من خلال تسجيل الدخول إلى شبكة الغذاء المفتوح والذهاب إلى المسؤول."
action: "بيت شبكة الغذاء المفتوح"
back: "عودة"
continue: "استمر"
action_or: "أو"
@@ -3155,6 +3154,12 @@ ar:
used_saved_card: "استخدم بطاقة المحفوظة:"
or_enter_new_card: "أو أدخل تفاصيل البطاقة الجديدة:"
remember_this_card: تذكر هذه البطاقة؟
stripe_sca:
choose_one: اختيار واحد
enter_new_card: أدخل تفاصيل البطاقة الجديدة
used_saved_card: "استخدم بطاقة المحفوظة:"
or_enter_new_card: "أو أدخل تفاصيل البطاقة الجديدة:"
remember_this_card: تذكر هذه البطاقة؟
date_picker:
format: '٪ س-٪ م-%d'
js_format: 'يوم-شهر-سنة'

View File

@@ -245,7 +245,7 @@ ca:
allow_cookies: "Permet les galetes"
notes: Notes
error: Error
processing_payment: S'està processant el pagament...
processing_payment: "S'està processant el pagament..."
filter_results: Aplicar filtre
quantity: Quantitat
pick_up: Recollida
@@ -1285,6 +1285,7 @@ ca:
saving_credit_card: Desant la targeta de crèdit...
card_has_been_removed: "S'ha eliminat la teva targeta (número: %{number})"
card_could_not_be_removed: Ho sentim, no s'ha pogut eliminar la targeta
invalid_credit_card: "Targeta de crèdit no vàlida"
ie_warning_headline: "El vostre navegador no està actualitzat :-("
ie_warning_text: "Per obtenir la millor experiència a Open Food Network et recomanem que actualitzis el teu navegador:"
ie_warning_chrome: Descarrega Chrome
@@ -1859,7 +1860,6 @@ ca:
headline: "Acabat!"
thanks: "Gràcies per omplir els detalls de%{enterprise}."
login: "Pots canviar o actualitzar la teva organització en qualsevol moment accedint a Katuma i anant a Admin."
action: "Inici"
back: "Enrere"
continue: "Continua"
action_or: "O"
@@ -2276,6 +2276,7 @@ ca:
enterprise_register_success_notice: "Enhorabona! El registre de %{enterprise} s'ha completat!"
enterprise_bulk_update_success_notice: "Les organitzacions s'han actualitzat correctament"
enterprise_bulk_update_error: 'No s''ha pogut actualitzar'
enterprise_shop_show_error: "La botiga que busqueu no existeix o està inactiva a OFN. Consulteu altres botigues."
order_cycles_create_notice: 'S''ha creat el cicle de comanda.'
order_cycles_update_notice: 'S''ha actualitzat el cicle de comanda.'
order_cycles_bulk_update_notice: 'S''han actualitzat els cicles de comanda.'
@@ -2430,6 +2431,12 @@ ca:
severity: Severitat
description: Descripció
resolve: Resoldre
exchange_products:
load_more_variants: "Carregueu més variants"
load_all_variants: "Carregueu totes les variants"
select_all_variants: "Seleccioneu totes les %{total_number_of_variants} variants"
variants_loaded: "%{num_of_variants_loaded} de %{total_number_of_variants} variants carregades"
loading_variants: "Carregant variants"
tag_rules:
shipping_method_tagged_top: "Els mètodes d'enviament etiquetats"
shipping_method_tagged_bottom: "son:"
@@ -2588,6 +2595,73 @@ ca:
signup_or_login: "Comenceu registrant-vos (o iniciant sessió)"
have_an_account: "Ja tens un compte?"
action_login: "Inicia la sessió ara."
inflections:
each:
one: "cadascun"
other: "cadascun"
bunch:
one: "munt"
other: "grapats"
pack:
one: "paquet"
other: "paquets"
box:
one: "Caixa"
other: "caixes"
bottle:
one: "ampolla"
other: "ampolles"
jar:
one: "gerro"
other: "pots"
head:
one: "cap"
other: "caps"
bag:
one: "bossa"
other: "bosses"
loaf:
one: "pa"
other: "barres"
single:
one: "solter"
other: "únics"
tub:
one: "tina"
other: "cubells"
item:
one: "article"
other: "articles"
dozen:
one: "dotzena"
other: "dotzenes"
unit:
one: "unitat"
other: "unitats"
serve:
one: "servir"
other: "porcions"
tray:
one: "safata"
other: "safates"
piece:
one: "peça"
other: "peces"
pot:
one: "pot"
other: "pots"
bundle:
one: "paquet"
other: "paquets"
flask:
one: "matràs"
other: "ampolleta"
basket:
one: "cistella"
other: "cistelles"
sack:
one: "sac"
other: "sacs"
producers:
signup:
start_free_profile: "Comença amb un perfil gratuït i amplia'l quan estiguis preparada."
@@ -3139,6 +3213,12 @@ ca:
used_saved_card: "Utilitza una targeta desada:"
or_enter_new_card: "O bé introdueix els detalls d'una nova targeta:"
remember_this_card: Recordar aquesta targeta?
stripe_sca:
choose_one: Escull-ne un
enter_new_card: Introdueix els detalls d'una targeta nova
used_saved_card: "Utilitza una targeta desada:"
or_enter_new_card: "O bé introdueix els detalls d'una nova targeta:"
remember_this_card: Recordar aquesta targeta?
date_picker:
format: '%d-% m-% Y'
js_format: 'dd-mm-yy'

View File

@@ -243,7 +243,7 @@ de_DE:
allow_cookies: "Cookies erlauben"
notes: Anmerkungen
error: Fehler
processing_payment: Bezahlung wird verarbeitet...
processing_payment: "Bezahlung wird verarbeitet..."
filter_results: Ergebnisse filtern
quantity: Menge
pick_up: Abholen
@@ -1848,7 +1848,6 @@ de_DE:
headline: "Fertig!"
thanks: "Vielen Dank, dass Sie die Details für %{enterprise} ausgefüllt haben."
login: "Sie können Ihr Unternehmen jederzeit ändern oder aktualisieren, indem Sie sich bei Open Food Network anmelden und zum Administrator wechseln."
action: "Open Food Network nach Hause"
back: "Zurück"
continue: "Fortsetzen"
action_or: "ODER"

Some files were not shown because too many files have changed in this diff Show More