diff --git a/src/openlmis-adjustments/adjustments-modal.controller.js b/src/openlmis-adjustments/adjustments-modal.controller.js index c37ef66c..5c18d550 100644 --- a/src/openlmis-adjustments/adjustments-modal.controller.js +++ b/src/openlmis-adjustments/adjustments-modal.controller.js @@ -29,15 +29,15 @@ .controller('AdjustmentsModalController', AdjustmentsModalController); AdjustmentsModalController.$inject = [ - '$filter', '$q', 'modalDeferred', 'title', 'message', 'isDisabled', 'adjustments', + '$filter', '$q', '$scope', 'modalDeferred', 'title', 'message', 'isDisabled', 'adjustments', 'reasons', 'summaries', 'preSave', 'preCancel', 'filterReasons', 'showInDoses', 'lineItem', - 'quantityUnitCalculateService', 'alertService' + 'quantityUnitCalculateService', 'alertService', 'messageService' ]; - function AdjustmentsModalController($filter, $q, modalDeferred, title, message, isDisabled, + function AdjustmentsModalController($filter, $q, $scope, modalDeferred, title, message, isDisabled, adjustments, reasons, summaries, preSave, preCancel, filterReasons, showInDoses, lineItem, quantityUnitCalculateService, - alertService) { + alertService, messageService) { var vm = this; @@ -47,6 +47,7 @@ vm.cancel = cancel; vm.save = save; vm.hasInvalidAdjustments = hasInvalidAdjustments; + vm.validateAdjustment = validateAdjustment; /** * @ngdoc property @@ -230,7 +231,10 @@ * back to the modal without applying any changes; */ function save() { + angular.forEach(vm.adjustments, validateAdjustment); + if (hasInvalidAdjustments()) { + $scope.$broadcast('openlmis-form-submit'); alertService.error('openlmisAdjustments.quantityGreaterThanZero'); return; } @@ -269,6 +273,25 @@ }); } + /** + * @ngdoc method + * @methodOf openlmis-adjustments.controller:AdjustmentsModalController + * @name validateAdjustment + * + * @description + * Validates a single adjustment and stores an error message on its quantityInvalid property + * when the quantity is not greater than zero. The message is consumed by the openlmis-invalid + * directive on the quantity cell, marking the reasons that block the adjustments update - the + * same mechanism used by the stock add products modal. + * + * @param {Object} adjustment the adjustment to validate + */ + function validateAdjustment(adjustment) { + adjustment.quantityInvalid = hasValidQuantity(adjustment) + ? undefined + : messageService.get('openlmisAdjustments.quantityGreaterThanZero'); + } + function hasValidQuantity(adjustment) { return adjustment !== undefined && adjustment !== null diff --git a/src/openlmis-adjustments/adjustments-modal.controller.spec.js b/src/openlmis-adjustments/adjustments-modal.controller.spec.js index 8a65ff56..32b17511 100644 --- a/src/openlmis-adjustments/adjustments-modal.controller.spec.js +++ b/src/openlmis-adjustments/adjustments-modal.controller.spec.js @@ -23,6 +23,13 @@ describe('AdjustmentsModalController', function() { this.$rootScope = $injector.get('$rootScope'); this.$controller = $injector.get('$controller'); this.alertService = $injector.get('alertService'); + this.messageService = $injector.get('messageService'); + }); + + this.$scope = this.$rootScope.$new(); + + spyOn(this.messageService, 'get').andCallFake(function(key) { + return key; }); this.modalDeferred = this.$q.defer(); @@ -427,8 +434,121 @@ describe('AdjustmentsModalController', function() { }); + describe('validateAdjustment', function() { + + beforeEach(function() { + this.initController(); + }); + + it('should clear quantityInvalid when quantity is greater than zero', function() { + var adjustment = { + quantity: 5, + quantityInvalid: 'openlmisAdjustments.quantityGreaterThanZero' + }; + + this.vm.validateAdjustment(adjustment); + + expect(adjustment.quantityInvalid).toBeUndefined(); + }); + + it('should set quantityInvalid message when quantity is zero', function() { + var adjustment = { + quantity: 0 + }; + + this.vm.validateAdjustment(adjustment); + + expect(adjustment.quantityInvalid).toBe('openlmisAdjustments.quantityGreaterThanZero'); + }); + + it('should set quantityInvalid message when quantity is negative', function() { + var adjustment = { + quantity: -5 + }; + + this.vm.validateAdjustment(adjustment); + + expect(adjustment.quantityInvalid).toBe('openlmisAdjustments.quantityGreaterThanZero'); + }); + + it('should set quantityInvalid message when quantity is empty', function() { + var adjustment = { + quantity: '' + }; + + this.vm.validateAdjustment(adjustment); + + expect(adjustment.quantityInvalid).toBe('openlmisAdjustments.quantityGreaterThanZero'); + }); + + it('should set quantityInvalid message when quantity is undefined', function() { + var adjustment = {}; + + this.vm.validateAdjustment(adjustment); + + expect(adjustment.quantityInvalid).toBe('openlmisAdjustments.quantityGreaterThanZero'); + }); + + it('should set quantityInvalid message when quantity is not a number', function() { + var adjustment = { + quantity: 'abc' + }; + + this.vm.validateAdjustment(adjustment); + + expect(adjustment.quantityInvalid).toBe('openlmisAdjustments.quantityGreaterThanZero'); + }); + + }); + + describe('save marking', function() { + + it('should mark every invalid adjustment when saving', function() { + var message = 'openlmisAdjustments.quantityGreaterThanZero'; + + this.adjustments = [{ + reason: this.reasons[0], + quantity: 0 + }, { + reason: this.reasons[1], + quantity: 5 + }, { + reason: this.reasons[2], + quantity: '' + }]; + + this.initController(); + this.vm.$onInit(); + + this.vm.save(); + + expect(this.vm.adjustments[0].quantityInvalid).toBe(message); + expect(this.vm.adjustments[1].quantityInvalid).toBeUndefined(); + expect(this.vm.adjustments[2].quantityInvalid).toBe(message); + }); + + it('should broadcast openlmis-form-submit when saving invalid adjustments', function() { + spyOn(this.$scope, '$broadcast').andCallThrough(); + + this.adjustments = [{ + reason: this.reasons[0], + quantity: 0 + }]; + + this.initController(); + this.vm.$onInit(); + + this.vm.save(); + + expect(this.$scope.$broadcast).toHaveBeenCalledWith('openlmis-form-submit'); + }); + + }); + function initController() { this.vm = this.$controller('AdjustmentsModalController', { + $scope: this.$scope, + messageService: this.messageService, modalDeferred: this.modalDeferred, adjustments: this.adjustments, reasons: this.reasons, diff --git a/src/openlmis-adjustments/adjustments-modal.html b/src/openlmis-adjustments/adjustments-modal.html index 9113f168..fd852122 100644 --- a/src/openlmis-adjustments/adjustments-modal.html +++ b/src/openlmis-adjustments/adjustments-modal.html @@ -48,12 +48,14 @@