diff --git a/app/assets/javascripts/admin/standing_orders/controllers/details_controller.js.coffee b/app/assets/javascripts/admin/standing_orders/controllers/details_controller.js.coffee new file mode 100644 index 0000000000..7ac5e11946 --- /dev/null +++ b/app/assets/javascripts/admin/standing_orders/controllers/details_controller.js.coffee @@ -0,0 +1,10 @@ +angular.module("admin.standingOrders").controller "DetailsController", ($scope, StatusMessage) -> + $scope.submitted = false + + $scope.next = -> + $scope.submitted = true + if $scope.standing_order_details_form.$valid + StatusMessage.clear() + $scope.setView('products') + else + StatusMessage.display 'failure', 'Oops! There seems to be a problem...' diff --git a/app/assets/javascripts/admin/standing_orders/controllers/products_controller.js.coffee b/app/assets/javascripts/admin/standing_orders/controllers/products_controller.js.coffee new file mode 100644 index 0000000000..05287a01c8 --- /dev/null +++ b/app/assets/javascripts/admin/standing_orders/controllers/products_controller.js.coffee @@ -0,0 +1,9 @@ +angular.module("admin.standingOrders").controller "ProductsController", ($scope, StatusMessage) -> + $scope.next = -> + if $scope.standingOrder.standing_line_items.length > 0 + StatusMessage.clear() + $scope.setView('review') + else + StatusMessage.display 'failure', 'Please add at least one product' + + $scope.back = -> $scope.setView('details') diff --git a/app/assets/javascripts/admin/standing_orders/controllers/standing_order_controller.js.coffee b/app/assets/javascripts/admin/standing_orders/controllers/standing_order_controller.js.coffee index 0e2670ebd0..adbc576076 100644 --- a/app/assets/javascripts/admin/standing_orders/controllers/standing_order_controller.js.coffee +++ b/app/assets/javascripts/admin/standing_orders/controllers/standing_order_controller.js.coffee @@ -7,20 +7,13 @@ angular.module("admin.standingOrders").controller "StandingOrderController", ($s $scope.errors = StandingOrder.errors $scope.newItem = { variant_id: 0, quantity: 1 } $scope.distributor_id = $scope.standingOrder.shop_id # variant selector requires distributor_id - $scope.views = ['details','products','review'] - $scope.view = if $scope.standingOrder.id? then $scope.views[$scope.views.length-1] else $scope.views[0] + $scope.view = if $scope.standingOrder.id? then 'review' else 'details' $scope.save = -> $scope.standing_order_form.$setPristine() StandingOrder.save() - $scope.next = -> - viewIndex = $scope.views.indexOf($scope.view) - $scope.view = $scope.views[viewIndex+1] - - $scope.back = -> - viewIndex = $scope.views.indexOf($scope.view) - $scope.view = $scope.views[viewIndex-1] + $scope.setView = (view) -> $scope.view = view $scope.addStandingLineItem = -> StandingOrder.buildItem($scope.newItem) diff --git a/app/assets/stylesheets/admin/disabled.css.scss b/app/assets/stylesheets/admin/disabled.css.scss index a393c5d80b..defa38d33f 100644 --- a/app/assets/stylesheets/admin/disabled.css.scss +++ b/app/assets/stylesheets/admin/disabled.css.scss @@ -3,9 +3,11 @@ label.disabled { pointer-events: none; } -input[type='button']:disabled { - background-color: #c3c3c3; - color: #ffffff; +input[type='button'], input[type='submit'] { + &:disabled { + background-color: #c3c3c3; + color: #ffffff; + } } .select2-container-disabled { diff --git a/app/assets/stylesheets/admin/openfoodnetwork.css.scss b/app/assets/stylesheets/admin/openfoodnetwork.css.scss index 2f575af1bb..c6a55a655e 100644 --- a/app/assets/stylesheets/admin/openfoodnetwork.css.scss +++ b/app/assets/stylesheets/admin/openfoodnetwork.css.scss @@ -62,10 +62,6 @@ input.search { float: right; } -.ng .ng-invalid.ng-dirty { - background-color: #fa787e; -} - a { cursor:pointer; } diff --git a/app/assets/stylesheets/admin/validation.css.scss b/app/assets/stylesheets/admin/validation.css.scss index f8fa261fdb..9664a1fc7a 100644 --- a/app/assets/stylesheets/admin/validation.css.scss +++ b/app/assets/stylesheets/admin/validation.css.scss @@ -1,4 +1,4 @@ -input.ng-invalid { +input.ng-invalid.ng-dirty { border: solid 1px red; &.update-pending { @@ -9,4 +9,3 @@ input.ng-invalid { select.ng-invalid { border: solid 1px red; } - diff --git a/app/views/admin/standing_orders/_details.html.haml b/app/views/admin/standing_orders/_details.html.haml index 885da71a02..655a98ccac 100644 --- a/app/views/admin/standing_orders/_details.html.haml +++ b/app/views/admin/standing_orders/_details.html.haml @@ -1,37 +1,43 @@ -%fieldset +%fieldset.no-border-bottom %legend{ align: 'center'}= t("admin.standing_orders.form.details") .row .four.columns.alpha.field Customer .four.columns.field - %input.ofn-select2.fullwidth#customer_id{ name: 'customer_id', type: 'number', data: 'customers', text: 'email', ng: { model: 'standingOrder.customer_id' } } - .error{ ng: { repeat: 'error in errors.customer', show: 'standing_order_form.customer_id.$pristine' } } {{ error }} + %input.ofn-select2.fullwidth#customer_id{ name: 'customer_id', type: 'number', data: 'customers', text: 'email', required: true, ng: { model: 'standingOrder.customer_id' } } + .error{ ng: { show: 'submitted && standing_order_details_form.customer_id.$error.required' } }= t(:error_required) + .error{ ng: { repeat: 'error in errors.customer', show: 'standing_order_details_form.customer_id.$pristine' } } {{ error }} .four.columns.field Schedule .four.columns.omega.field - %input.ofn-select2.fullwidth#schedule_id{ name: 'schedule_id', type: 'number', data: 'schedules', ng: { model: 'standingOrder.schedule_id' } } - .error{ ng: { repeat: 'error in errors.schedule', show: 'standing_order_form.schedule_id.$pristine'} } {{ error }} + %input.ofn-select2.fullwidth#schedule_id{ name: 'schedule_id', type: 'number', data: 'schedules', required: true, ng: { model: 'standingOrder.schedule_id' } } + .error{ ng: { show: 'submitted && standing_order_details_form.schedule_id.$error.required' } }= t(:error_required) + .error{ ng: { repeat: 'error in errors.schedule', show: 'standing_order_details_form.schedule_id.$pristine'} } {{ error }} .row .four.columns.alpha.field Payment Method .four.columns.field - %input.ofn-select2.fullwidth#payment_method_id{ name: 'payment_method_id',type: 'number', data: 'paymentMethods', ng: { model: 'standingOrder.payment_method_id' } } - .error{ ng: { repeat: 'error in errors.payment_method', show: 'standing_order_form.payment_method_id.$pristine' } } {{ error }} + %input.ofn-select2.fullwidth#payment_method_id{ name: 'payment_method_id', type: 'number', data: 'paymentMethods', required: true, ng: { model: 'standingOrder.payment_method_id' } } + %div + .error{ ng: { show: 'submitted && standing_order_details_form.payment_method_id.$error.required' } }= t(:error_required) + .error{ ng: { repeat: 'error in errors.payment_method', show: 'standing_order_details_form.payment_method_id.$pristine' } } {{ error }} .four.columns.field Shipping Method .four.columns.omega.field - %input.ofn-select2.fullwidth#shipping_method_id{ name: 'shipping_method_id', type: 'number', data: 'shippingMethods', ng: { model: 'standingOrder.shipping_method_id' } } - .error{ ng: { repeat: 'error in errors.shipping_method', show: 'standing_order_form.shipping_method_id.$pristine' } } {{ error }} + %input.ofn-select2.fullwidth#shipping_method_id{ name: 'shipping_method_id', type: 'number', data: 'shippingMethods', required: true, ng: { model: 'standingOrder.shipping_method_id' } } + .error{ ng: { show: 'submitted && standing_order_details_form.shipping_method_id.$error.required' } }= t(:error_required) + .error{ ng: { repeat: 'error in errors.shipping_method', show: 'standing_order_details_form.shipping_method_id.$pristine' } } {{ error }} .row .four.columns.alpha.field Begins At .four.columns.field - %input.fullwidth#begins_at{ name: 'begins_at', type: 'text', placeholder: 'Select A Date', datepicker: 'standingOrder.begins_at', ng: { model: 'standingOrder.begins_at' } } - .error{ ng: { repeat: 'error in errors.begins_at', show: 'standing_order_form.begins_at.$pristine' } } {{ error }} + %input.fullwidth#begins_at{ name: 'begins_at', type: 'text', placeholder: 'Select A Date', datepicker: 'standingOrder.begins_at', required: true, ng: { model: 'standingOrder.begins_at' } } + .error{ ng: { show: 'submitted && standing_order_details_form.begins_at.$error.required' } }= t(:error_required) + .error{ ng: { repeat: 'error in errors.begins_at', show: 'standing_order_details_form.begins_at.$pristine' } } {{ error }} .four.columns.field Ends at .four.columns.omega.field %input.fullwidth#ends_at{ name: 'ends_at', type: 'text', placeholder: 'Optional', datepicker: 'standingOrder.begins_at', ng: { model: 'standingOrder.ends_at' } } - .error{ ng: { repeat: 'error in errors.ends_at', show: 'standing_order_form.ends_at.$pristine' } } {{ error }} + .error{ ng: { repeat: 'error in errors.ends_at', show: 'standing_order_details_form.ends_at.$pristine' } } {{ error }} diff --git a/app/views/admin/standing_orders/_form.html.haml b/app/views/admin/standing_orders/_form.html.haml index acea2103d1..e0c37dd7d7 100644 --- a/app/views/admin/standing_orders/_form.html.haml +++ b/app/views/admin/standing_orders/_form.html.haml @@ -1,13 +1,18 @@ -%form.margin-bottom-50{ name: 'standing_order_form', ng: { app: 'admin.standingOrders', controller: 'StandingOrderController' } } - %save-bar{ dirty: "standing_order_form.$dirty" } - %input{ type: "submit", ng: { click: "back()", hide: "view == 'details' || view == 'review'", disabled: "!standing_order_form.$dirty", value: "'Back'" } } - %input.red{ type: "submit", ng: { click: "next()", hide: "view == 'review'", disabled: "!standing_order_form.$dirty", value: "'Next'" } } - %input.red{ type: "submit", ng: { click: "save()", show: "view == 'review'", disabled: "!standing_order_form.$dirty", value: "'Save'" } } - -# %input{ type: "button", ng: { value: "order_cycle_form.$dirty ? 'Cancel' : 'Close'", click: "cancel('#{main_app.admin_order_cycles_path}')" } } +%form.margin-bottom-50{ name: 'standing_order_form', novalidate: true, ng: { app: 'admin.standingOrders', controller: 'StandingOrderController', submit: 'save()' } } + %save-bar{ dirty: "standing_order_form.$dirty", persist: 'true', ng: { show: "view == 'review'" } } + %input.red{ type: "submit", value: "Save" } .details{ ng: { show: "['details','review'].indexOf(view) >= 0" } } - = render 'details' + %ng-form{ name: 'standing_order_details_form', ng: { controller: 'DetailsController' } } + %save-bar{ dirty: "standing_order_details_form.$dirty", persist: 'true', ng: { hide: "view == 'review'" } } + %input{ type: "button", value: 'Back', ng: { click: "back()" } } + %input.red{ type: "button", value: 'Next', ng: { click: 'next()' } } + = render 'details' .products{ ng: { show: "['products','review'].indexOf(view) >= 0" } } + %ng-form{ name: 'standing_order_products_form', ng: { controller: 'ProductsController' } } + %save-bar{ dirty: "standing_order_products_form.$dirty", persist: 'true', ng: { hide: "view == 'review'" } } + %input{ type: "button", value: 'Back', ng: { click: "back()" } } + %input.red{ type: "button", value: 'Next', ng: { click: 'next()' } } = render 'autocomplete' = render 'products' diff --git a/spec/features/admin/standing_orders_spec.rb b/spec/features/admin/standing_orders_spec.rb index 4c705c5186..029c2e09cb 100644 --- a/spec/features/admin/standing_orders_spec.rb +++ b/spec/features/admin/standing_orders_spec.rb @@ -27,7 +27,16 @@ feature 'Standing Orders' do select2_select payment_method.name, from: 'payment_method_id' select2_select shipping_method.name, from: 'shipping_method_id' + # No date filled out, so error returned click_button('Next') + expect(page).to have_content 'can\'t be blank' + expect(page).to have_content 'Oops! There seems to be a problem...' + fill_in 'begins_at', with: Date.today.strftime('%F') + + click_button('Next') + expect(page).to have_content 'NAME OR SKU' + click_button('Next') + expect(page).to have_content 'Please add at least one product' # Adding a product and getting a price estimate targetted_select2_search product.name, from: '#add_variant_id', dropdown_css: '.select2-drop' @@ -42,16 +51,6 @@ feature 'Standing Orders' do click_button('Next') - # No date filled out, so error returned - expect{ - click_button('Save') - expect(page).to have_content 'Oh no! I was unable to save your changes.' - }.to_not change(StandingOrder, :count) - - expect(page).to have_content 'Begins at can\'t be blank' - fill_in 'begins_at', with: Date.today.strftime('%F') - - # Date filled out, so submit should be successful expect{ click_button('Save') expect(page).to have_content 'Saved'