diff --git a/horizon/static/framework/conf/resource-type-registry.service.js b/horizon/static/framework/conf/resource-type-registry.service.js index ef8985be35..8074df411f 100644 --- a/horizon/static/framework/conf/resource-type-registry.service.js +++ b/horizon/static/framework/conf/resource-type-registry.service.js @@ -149,7 +149,7 @@ * * If an action does not have an initAction() function, it is ignored. */ - function initActions(scope) { + function initActions() { angular.forEach(self.itemActions, setActionScope); angular.forEach(self.batchActions, setActionScope); angular.forEach(self.globalActions, setActionScope); @@ -157,14 +157,6 @@ function setActionScope(action) { if (action.service.initAction) { action.service.initAction(); - } else if (action.service.initScope) { - // The use of scope in action services breaks the singleton nature - // of the services, and should be stopped. State should be held on - // controllers instead; scope is now passed into allow() and perform() - // methods. - $log.warn('The initScope() method is deprecated. ' + - 'Invocation of it will stop in Queens.'); - action.service.initScope(scope.$new()); } } } diff --git a/horizon/static/framework/conf/resource-type-registry.service.spec.js b/horizon/static/framework/conf/resource-type-registry.service.spec.js index f4ce124e88..8459322dec 100644 --- a/horizon/static/framework/conf/resource-type-registry.service.spec.js +++ b/horizon/static/framework/conf/resource-type-registry.service.spec.js @@ -170,9 +170,8 @@ }); it('initActions calls initAction on item and batch actions', function () { - var action = {service: {initAction: angular.noop, initScope: angular.noop}}; + var action = {service: {initAction: angular.noop}}; spyOn(action.service, 'initAction'); - spyOn(action.service, 'initScope'); type.batchActions.push(action); type.initActions({ '$new': function () { @@ -180,22 +179,9 @@ } }); expect(action.service.initAction).toHaveBeenCalled(); - expect(action.service.initScope).not.toHaveBeenCalled(); }); - it('initActions calls initScope if initAction is not defined', function () { - var action = {service: {initScope: angular.noop}}; - spyOn(action.service, 'initScope'); - type.batchActions.push(action); - type.initActions({ - '$new': function () { - return 4; - } - }); - expect(action.service.initScope).toHaveBeenCalledWith(4); - }); - - it('initActions ignores initAction and initScope when not present', function () { + it('initActions ignores initAction when not present', function () { var action = {service: {}}; type.batchActions.push(action); var returned = type.initActions({}); diff --git a/horizon/static/framework/widgets/action-list/actions.directive.js b/horizon/static/framework/widgets/action-list/actions.directive.js index e68e2f36cb..88ebaf2a52 100644 --- a/horizon/static/framework/widgets/action-list/actions.directive.js +++ b/horizon/static/framework/widgets/action-list/actions.directive.js @@ -115,7 +115,7 @@ * - When using 'delete-selected' for 'batch' type, all selected rows are passed as * an array. * - * There is a third optional function, initAction (which was previously called initScope) + * There is a third optional function, initAction. * Actions may perform post-config (in the angular sense) initialization by * providing an initAction method. This might be typically invoked by initActions() * on a ResourceType. Actions should not perform blocking operations in their diff --git a/horizon/static/framework/widgets/details/routed-details-view.controller.js b/horizon/static/framework/widgets/details/routed-details-view.controller.js index a5afbbb0e9..0479775f80 100644 --- a/horizon/static/framework/widgets/details/routed-details-view.controller.js +++ b/horizon/static/framework/widgets/details/routed-details-view.controller.js @@ -25,8 +25,7 @@ 'horizon.framework.util.actions.action-result.service', 'horizon.framework.widgets.modal-wait-spinner.service', '$q', - '$routeParams', - '$rootScope' + '$routeParams' ]; function controller( @@ -34,8 +33,7 @@ resultService, spinnerService, $q, - $routeParams, - $rootScope + $routeParams ) { var ctrl = this; @@ -54,7 +52,7 @@ function loadData(response) { spinnerService.hideModalSpinner(); ctrl.showDetails = true; - ctrl.resourceType.initActions($rootScope.$new()); + ctrl.resourceType.initActions(); ctrl.itemData = response.data; ctrl.itemName = ctrl.resourceType.itemName(response.data); } diff --git a/horizon/static/framework/widgets/modal/wizard-modal.service.js b/horizon/static/framework/widgets/modal/wizard-modal.service.js index 35ac8c9344..0d66995b2e 100644 --- a/horizon/static/framework/widgets/modal/wizard-modal.service.js +++ b/horizon/static/framework/widgets/modal/wizard-modal.service.js @@ -28,13 +28,11 @@ * .controller('modalExampleCtrl', ExampleCtrl); * * ExampleCtrl.$inject = [ - * '$scope', * 'horizon.framework.widgets.modal.wizard-modal.service' * ]; * * function ExampleCtrl($scope, wizardModalService) { * var options = { - * scope: scope, // the scope to use for the Wizard * workflow: workflow, // the workflow used in the wizard * submit: submit // callback to call on a wizard submit * }; @@ -81,13 +79,6 @@ } }; - // backwards compatibility - if (angular.isDefined(params.scope)) { - $log.warn('The "scope" param to modal() is deprecated.' + - 'Handling of it will stop in Queens.'); - options.scope = params.scope; - } - return $uibModal.open(options); } } diff --git a/horizon/static/framework/widgets/modal/wizard-modal.service.spec.js b/horizon/static/framework/widgets/modal/wizard-modal.service.spec.js index 920fe7e8e5..cfb4fd719c 100644 --- a/horizon/static/framework/widgets/modal/wizard-modal.service.spec.js +++ b/horizon/static/framework/widgets/modal/wizard-modal.service.spec.js @@ -16,7 +16,7 @@ "use strict"; describe('horizon.framework.widgets.wizard-modal.service', function() { - var service, modal, $scope; + var service, modal; beforeEach(module('horizon.framework')); beforeEach(module(function($provide) { @@ -26,8 +26,7 @@ $provide.value('$uibModal', modal); })); - beforeEach(inject(function($injector, _$rootScope_) { - $scope = _$rootScope_.$new(); + beforeEach(inject(function($injector) { service = $injector.get('horizon.framework.widgets.modal.wizard-modal.service'); })); @@ -43,7 +42,7 @@ it('should open the modal if called with required parameters', function() { spyOn(modal, 'open').and.callThrough(); - service.modal({scope: $scope, workflow: {}, submit: {}}); + service.modal({workflow: {}, submit: {}}); expect(modal.open).toHaveBeenCalled(); }); @@ -51,11 +50,10 @@ spyOn(modal, 'open').and.callThrough(); var workflow = {id: 'w'}; var submit = {id: 's'}; - service.modal({scope: $scope, workflow: workflow, submit: submit}); + service.modal({workflow: workflow, submit: submit}); expect(modal.open).toHaveBeenCalled(); var modalOpenArgs = modal.open.calls.argsFor(0)[0]; expect(modalOpenArgs.controller).toEqual('WizardModalController as modalCtrl'); - expect(modalOpenArgs.scope).toEqual($scope); expect(modalOpenArgs.resolve.workflow()).toEqual(workflow); expect(modalOpenArgs.resolve.submit()).toEqual(submit); }); diff --git a/openstack_dashboard/contrib/developer/static/dashboard/developer/resource-browser/resource-browser-item.controller.js b/openstack_dashboard/contrib/developer/static/dashboard/developer/resource-browser/resource-browser-item.controller.js index 680128cbe8..85c7a402ab 100644 --- a/openstack_dashboard/contrib/developer/static/dashboard/developer/resource-browser/resource-browser-item.controller.js +++ b/openstack_dashboard/contrib/developer/static/dashboard/developer/resource-browser/resource-browser-item.controller.js @@ -193,11 +193,11 @@ } function onGlobalActionSelected(action) { - if (action.service.initScope) { - action.service.initScope($scope.$new()); + if (action.service.initAction) { + action.service.initAction(); } - return action.service.perform(); + return action.service.perform(null, $scope.$new()); } function onActionSelected(action) { @@ -206,11 +206,11 @@ typeData.load(ctrl.resourceId).then(performAction, loadFailed); function performAction(resource) { - if (action.service.initScope) { - action.service.initScope($scope.$new()); + if (action.service.initAction) { + action.service.initAction(); } - return action.service.perform(resource.data); + return action.service.perform(resource.data, $scope.$new()); } function loadFailed(reason) { diff --git a/openstack_dashboard/static/app/core/images/actions/create.action.service.js b/openstack_dashboard/static/app/core/images/actions/create.action.service.js index b19d2e6ef3..7e872642bf 100644 --- a/openstack_dashboard/static/app/core/images/actions/create.action.service.js +++ b/openstack_dashboard/static/app/core/images/actions/create.action.service.js @@ -55,12 +55,9 @@ success: gettext('Image %s was successfully created.') }; - var model = {}; - var scope; var service = { - initScope: initScope, perform: perform, allowed: allowed }; @@ -68,48 +65,25 @@ return service; ////////////// - function initScope($scope) { - var watchImageChange = $scope.$on(events.IMAGE_CHANGED, onImageChange); - var watchMetadataChange = $scope.$on(events.IMAGE_METADATA_CHANGED, onMetadataChange); - - scope = $scope; - - $scope.$on('$destroy', destroy); - - function destroy() { - watchImageChange(); - watchMetadataChange(); - } - } - - function onImageChange(e, image) { - model.image = image; - e.stopPropagation(); - } - - function onMetadataChange(e, metadata) { - model.metadata = metadata; - e.stopPropagation(); - } function allowed() { return policy.ifAllowed({ rules: [['image', 'add_image']] }); } - function perform() { - model.image = {}; - model.metadata = {}; - scope.image = {}; + function perform(selected, $scope) { + scope = $scope; return wizardModalService.modal({ - scope: scope, workflow: createWorkflow, submit: submit }).result; } - function submit() { - var finalModel = angular.extend({}, model.image, model.metadata); + function submit(stepModels) { + var finalModel = angular.extend( + {}, + stepModels.imageForm, + stepModels.updateMetadataForm); if (finalModel.source_type === 'url') { delete finalModel.data; } else { diff --git a/openstack_dashboard/static/app/core/images/actions/create.action.service.spec.js b/openstack_dashboard/static/app/core/images/actions/create.action.service.spec.js index 188f6be661..87a48d46e4 100644 --- a/openstack_dashboard/static/app/core/images/actions/create.action.service.spec.js +++ b/openstack_dashboard/static/app/core/images/actions/create.action.service.spec.js @@ -29,10 +29,8 @@ }; var wizardModalService = { - modal: function (config) { - deferredModal = $q.defer(); - deferredModal.resolve(config.scope.image); - return {result: deferredModal.promise}; + modal: function () { + return { result: {catch: angular.noop} }; } }; @@ -54,7 +52,7 @@ } }; - var service, events, $scope, deferredModal, deferredCreate, $q; + var service, $scope, deferredCreate, $q; /////////////////////// @@ -71,7 +69,6 @@ beforeEach(inject(function($injector, _$rootScope_, _$q_) { $scope = _$rootScope_.$new(); service = $injector.get('horizon.app.core.images.actions.create.service'); - events = $injector.get('horizon.app.core.images.events'); $q = _$q_; })); @@ -85,14 +82,11 @@ it('open the modal with the correct parameters', function() { spyOn(wizardModalService, 'modal').and.callThrough(); - service.initScope($scope); - service.perform(); + service.perform(null, $scope); expect(wizardModalService.modal).toHaveBeenCalled(); - expect($scope.image).toEqual({}); var modalArgs = wizardModalService.modal.calls.argsFor(0)[0]; - expect(modalArgs.scope).toEqual($scope); expect(modalArgs.workflow).toBeDefined(); expect(modalArgs.submit).toBeDefined(); }); @@ -105,14 +99,10 @@ spyOn(glanceAPI, 'createImage').and.callThrough(); spyOn(wizardModalService, 'modal').and.callThrough(); - service.initScope($scope); - service.perform(); - - $scope.$emit(events.IMAGE_CHANGED, image); - $scope.$emit(events.IMAGE_METADATA_CHANGED, newMetadata); + service.perform(null, $scope); var modalArgs = wizardModalService.modal.calls.argsFor(0)[0]; - modalArgs.submit(); + modalArgs.submit({imageForm: image, updateMetadataForm: newMetadata}); $scope.$apply(); expect(glanceAPI.createImage.calls.argsFor(0)[0]).toEqual( @@ -128,12 +118,10 @@ spyOn(glanceAPI, 'createImage').and.callThrough(); spyOn(wizardModalService, 'modal').and.callThrough(); - service.initScope($scope); - service.perform(); - $scope.$emit(events.IMAGE_CHANGED, image); + service.perform(null, $scope); var modalArgs = wizardModalService.modal.calls.argsFor(0)[0]; - modalArgs.submit(); + modalArgs.submit({imageForm: image}); expect(glanceAPI.createImage.calls.argsFor(0)[0]).toEqual({ name: 'Test', source_type: 'file-direct', data: {name: 'test_file'}}); @@ -148,12 +136,10 @@ spyOn(glanceAPI, 'createImage').and.callThrough(); spyOn(wizardModalService, 'modal').and.callThrough(); - service.initScope($scope); - service.perform(); - $scope.$emit(events.IMAGE_CHANGED, image); + service.perform(null, $scope); var modalArgs = wizardModalService.modal.calls.argsFor(0)[0]; - modalArgs.submit(); + modalArgs.submit({imageForm: image}); expect(glanceAPI.createImage.calls.argsFor(0)[0]).toEqual({ name: 'Test', source_type: 'url', image_url: 'http://somewhere'}); @@ -168,12 +154,10 @@ spyOn(glanceAPI, 'createImage').and.callThrough(); spyOn(wizardModalService, 'modal').and.callThrough(); - service.initScope($scope); - service.perform(); - $scope.$emit(events.IMAGE_CHANGED, image); + service.perform(null, $scope); var modalArgs = wizardModalService.modal.calls.argsFor(0)[0]; - modalArgs.submit(); + modalArgs.submit({imageForm: image}); expect(glanceAPI.createImage.calls.argsFor(0)[0]).toEqual({ name: 'Test', source_type: 'file-direct', data: {name: 'test_file'}}); @@ -188,71 +172,15 @@ spyOn(glanceAPI, 'createImage').and.callThrough(); spyOn(wizardModalService, 'modal').and.callThrough(); - service.initScope($scope); - service.perform(); - $scope.$emit(events.IMAGE_CHANGED, image); + service.perform(null, $scope); var modalArgs = wizardModalService.modal.calls.argsFor(0)[0]; - modalArgs.submit(); + modalArgs.submit({imageForm: image}); expect(glanceAPI.createImage.calls.argsFor(0)[0]).toEqual({ name: 'Test', source_type: 'url', image_url: 'http://somewhere'}); }); - it('should raise event even if update metadata fails', function() { - var image = { name: 'Test', id: '2' }; - var failedPromise = function() { - return { - then: function(callback, errorCallback) { - errorCallback(); - } - }; - }; - - spyOn(wizardModalService, 'modal').and.callThrough(); - spyOn(glanceAPI, 'createImage').and.callThrough(); - spyOn(metadataService, 'editMetadata').and.callFake(failedPromise); - spyOn($scope, '$emit').and.callThrough(); - - service.initScope($scope); - service.perform(); - $scope.$apply(); - - $scope.$emit(events.IMAGE_CHANGED, image); - $scope.$emit(events.IMAGE_METADATA_CHANGED, newMetadata); - - var newMetadata = {prop1: '11', prop3: '3'}; - var modalArgs = wizardModalService.modal.calls.argsFor(0)[0]; - modalArgs.submit(); - $scope.$apply(); - - expect($scope.$emit).toHaveBeenCalledWith( - 'horizon.app.core.images.IMAGE_METADATA_CHANGED', undefined); - }); - - it('should destroy the event watchers', function() { - var newImage = { name: 'Test2', id: '2' }; - var newMetadata = {p1: '11', p3: '3'}; - - spyOn(wizardModalService, 'modal').and.callThrough(); - spyOn(glanceAPI, 'createImage').and.callThrough(); - spyOn(metadataService, 'editMetadata').and.callThrough(); - - service.initScope($scope); - service.perform(); - $scope.$apply(); - - $scope.$emit('$destroy'); - $scope.$emit(events.IMAGE_CHANGED, newImage); - $scope.$emit(events.IMAGE_METADATA_CHANGED, newMetadata); - - var modalArgs = wizardModalService.modal.calls.argsFor(0)[0]; - modalArgs.submit(); - $scope.$apply(); - - expect(glanceAPI.createImage.calls.argsFor(0)[0]).toEqual({}); - }); - }); })(); diff --git a/openstack_dashboard/static/app/core/images/actions/delete-image.service.js b/openstack_dashboard/static/app/core/images/actions/delete-image.service.js index 75b382b004..86aa928d32 100644 --- a/openstack_dashboard/static/app/core/images/actions/delete-image.service.js +++ b/openstack_dashboard/static/app/core/images/actions/delete-image.service.js @@ -52,11 +52,9 @@ toast, imagesResourceType ) { - var scope, context, deleteImagePromise; var notAllowedMessage = gettext("You are not allowed to delete images: %s"); var service = { - initScope: initScope, allowed: allowed, perform: perform }; @@ -65,17 +63,29 @@ ////////////// - function initScope(newScope) { - scope = newScope; - context = { }; - deleteImagePromise = policy.ifAllowed({rules: [['image', 'delete_image']]}); - } - - function perform(items) { + function perform(items, newScope) { + var scope = newScope; + var context = { }; var images = angular.isArray(items) ? items : [items]; context.labels = labelize(images.length); context.deleteEntity = deleteImage; return $qExtensions.allSettled(images.map(checkPermission)).then(afterCheck); + + function checkPermission(image) { + return {promise: allowed(image), context: image}; + } + + function afterCheck(result) { + var outcome = $q.reject(); // Reject the promise by default + if (result.fail.length > 0) { + toast.add('error', getMessage(notAllowedMessage, result.fail)); + outcome = $q.reject(result.fail); + } + if (result.pass.length > 0) { + outcome = deleteModal.open(scope, result.pass.map(getEntity), context).then(createResult); + } + return outcome; + } } function allowed(image) { @@ -84,7 +94,6 @@ if (image) { return $q.all([ notProtected(image), - deleteImagePromise, policy.ifAllowed({ rules: [['image', 'delete_image']] }), notDeleted(image) ]); @@ -93,22 +102,6 @@ } } - function checkPermission(image) { - return {promise: allowed(image), context: image}; - } - - function afterCheck(result) { - var outcome = $q.reject(); // Reject the promise by default - if (result.fail.length > 0) { - toast.add('error', getMessage(notAllowedMessage, result.fail)); - outcome = $q.reject(result.fail); - } - if (result.pass.length > 0) { - outcome = deleteModal.open(scope, result.pass.map(getEntity), context).then(createResult); - } - return outcome; - } - function createResult(deleteModalResult) { // To make the result of this action generically useful, reformat the return // from the deleteModal into a standard form diff --git a/openstack_dashboard/static/app/core/images/actions/delete-image.service.spec.js b/openstack_dashboard/static/app/core/images/actions/delete-image.service.spec.js index 25ce9478c3..38fc91d9cf 100644 --- a/openstack_dashboard/static/app/core/images/actions/delete-image.service.spec.js +++ b/openstack_dashboard/static/app/core/images/actions/delete-image.service.spec.js @@ -91,19 +91,8 @@ beforeEach(function() { spyOn(deleteModalService, 'open').and.callThrough(); - service.initScope($scope, labelize); }); - function labelize(count) { - return { - title: ngettext('title', 'titles', count), - message: ngettext('message', 'messages', count), - submit: ngettext('submit', 'submits', count), - success: ngettext('success', 'successs', count), - error: ngettext('error', 'errors', count) - }; - } - //////////// it('should open the delete modal and show correct labels', testSingleLabels); @@ -221,7 +210,6 @@ beforeEach(function() { spyOn(resolver, 'success'); spyOn(resolver, 'error'); - service.initScope($scope); }); //////////// diff --git a/openstack_dashboard/static/app/core/images/actions/edit.action.service.js b/openstack_dashboard/static/app/core/images/actions/edit.action.service.js index 3d35a44f5c..014bf3fd0d 100644 --- a/openstack_dashboard/static/app/core/images/actions/edit.action.service.js +++ b/openstack_dashboard/static/app/core/images/actions/edit.action.service.js @@ -56,15 +56,8 @@ var message = { success: gettext('Image %s was successfully updated.') }; - var modifyImagePolicyCheck, scope; - - var model = { - image: {}, - metadata: {} - }; var service = { - initScope: initScope, allowed: allowed, perform: perform }; @@ -73,15 +66,9 @@ ////////////// - function initScope($scope) { - scope = $scope; - $scope.$on(events.IMAGE_METADATA_CHANGED, onMetadataChange); - modifyImagePolicyCheck = policy.ifAllowed({rules: [['image', 'modify_image']]}); - } - function allowed(image) { return $q.all([ - modifyImagePolicyCheck, + policy.ifAllowed({rules: [['image', 'modify_image']]}), isActive(image) ]); } @@ -89,62 +76,59 @@ function perform(image) { var deferred = glance.getImage(image.id); deferred.then(onLoad); - scope.imagePromise = deferred; + var data = {}; + data.imagePromise = deferred; function onLoad(response) { var localImage = response.data; - model.image = localImage; + data.image = localImage; } return wizardModalService.modal({ - scope: scope, + data: data, workflow: editWorkflow, submit: submit }).result; } - function onMetadataChange(e, metadata) { - model.metadata = metadata; - e.stopPropagation(); - } - - function submit() { + function submit(stepModels) { + var image = stepModels.imageForm; + var metadata = stepModels.updateMetadataForm; return updateMetadata().then(updateImage, onUpdateImageFail); - } - function updateImage() { - var finalModel = model.image; - return glance.updateImage(finalModel).then(onUpdateImageSuccess, onUpdateImageFail); - } - - function onUpdateImageSuccess() { - toast.add('success', interpolate(message.success, [model.image.name])); - return actionResultService.getActionResult() - .updated(imageResourceType, model.image.id) - .result; - } - - function onUpdateImageFail() { - return actionResultService.getActionResult() - .failed(imageResourceType, model.image.id) - .result; - } - - function updateMetadata() { - - return metadataService - .getMetadata('image', model.image.id) - .then(onMetadataGet); - - function onMetadataGet(response) { - var updated = model.metadata; - var removed = angular.copy(response.data); - angular.forEach(updated, function(value, key) { - delete removed[key]; - }); + function updateMetadata() { return metadataService - .editMetadata('image', model.image.id, updated, Object.keys(removed)); + .getMetadata('image', image.id) + .then(onMetadataGet); + + function onMetadataGet(response) { + var updated = metadata; + var removed = angular.copy(response.data); + angular.forEach(updated, function(value, key) { + delete removed[key]; + }); + + return metadataService + .editMetadata('image', image.id, updated, Object.keys(removed)); + } + } + + function updateImage() { + return glance.updateImage(image).then(onUpdateImageSuccess, onUpdateImageFail); + } + + function onUpdateImageSuccess() { + toast.add('success', interpolate(message.success, [image.name])); + return actionResultService.getActionResult() + .updated(imageResourceType, image.id) + .result; + } + + function onUpdateImageFail() { + return actionResultService.getActionResult() + .failed(imageResourceType, image.id) + .result; } } diff --git a/openstack_dashboard/static/app/core/images/actions/edit.action.service.spec.js b/openstack_dashboard/static/app/core/images/actions/edit.action.service.spec.js index c565b0721d..34d20f43ef 100644 --- a/openstack_dashboard/static/app/core/images/actions/edit.action.service.spec.js +++ b/openstack_dashboard/static/app/core/images/actions/edit.action.service.spec.js @@ -18,7 +18,8 @@ 'use strict'; describe('horizon.app.core.images.actions.edit.service', function() { - var service, $scope, $q, deferred, testImage, $timeout, updateImageDeferred; + var service, $scope, $q, deferred, $timeout, updateImageDeferred; + var image = {id: 1, name: 'Original'}; var existingMetadata = {p1: '1', p2: '2'}; var metadataService = { @@ -52,7 +53,7 @@ }, getImage: function() { var imageLoad = $q.defer(); - imageLoad.resolve({data: {id: 1, name: 'Test'}}); + imageLoad.resolve({data: image}); return imageLoad.promise; } }; @@ -91,7 +92,6 @@ $scope = _$rootScope_.$new(); $q = _$q_; service = $injector.get('horizon.app.core.images.actions.edit.service'); - service.initScope($scope); deferred = $q.defer(); updateImageDeferred = $q.defer(); $timeout = _$timeout_; @@ -101,16 +101,12 @@ it('should open the modal with the correct parameters', function() { spyOn(wizardModalService, 'modal').and.callThrough(); - testImage = {id: '12'}; - service.initScope($scope); - service.perform(testImage); + service.perform(image, $scope); $timeout.flush(); expect(wizardModalService.modal).toHaveBeenCalled(); - expect($scope.imagePromise).toBeDefined(); var modalArgs = wizardModalService.modal.calls.argsFor(0)[0]; - expect(modalArgs.scope).toEqual($scope); expect(modalArgs.workflow).toBeDefined(); }); @@ -124,45 +120,32 @@ describe('submit', function() { beforeEach(function() { - var image = {id: 1, name: 'Original'}; - spyOn(glanceAPI, 'updateImage').and.callThrough(); spyOn(wizardModalService, 'modal').and.callThrough(); - service.initScope($scope); - service.perform(image); + service.perform(image, $scope); $timeout.flush(); }); it('passes the image from the model to updateImage', function() { var modalArgs = wizardModalService.modal.calls.argsFor(0)[0]; - modalArgs.submit(); + modalArgs.submit({imageForm: image}); + updateImageDeferred.resolve(); $timeout.flush(); - expect(glanceAPI.updateImage.calls.argsFor(0)[0]).toEqual({id: 1, name: 'Test'}); + expect(glanceAPI.updateImage.calls.argsFor(0)[0]).toEqual(image); }); it('returns a failed result if API call fails', function() { var modalArgs = wizardModalService.modal.calls.argsFor(0)[0]; - var result = modalArgs.submit(); + var result = modalArgs.submit({imageForm: image}); updateImageDeferred.reject(); result.then(function err(data) { expect(data.failed.length).toBe(1); }); $timeout.flush(); }); - - it('updates metadata on event', function() { - $scope.$emit('horizon.app.core.images.IMAGE_METADATA_CHANGED', {i_am: 'metadata'}); - $scope.$apply(); - spyOn(metadataService, 'editMetadata').and.callThrough(); - - var modalArgs = wizardModalService.modal.calls.argsFor(0)[0]; - modalArgs.submit(); - - expect(metadataService.editMetadata.calls.argsFor(0)[2]).toEqual({i_am: 'metadata'}); - }); }); function permissionShouldFail(permissions) { diff --git a/openstack_dashboard/static/app/core/images/images.module.js b/openstack_dashboard/static/app/core/images/images.module.js index 833092c905..a940059559 100644 --- a/openstack_dashboard/static/app/core/images/images.module.js +++ b/openstack_dashboard/static/app/core/images/images.module.js @@ -269,8 +269,6 @@ */ function events() { return { - IMAGE_CHANGED: 'horizon.app.core.images.IMAGE_CHANGED', - IMAGE_METADATA_CHANGED: 'horizon.app.core.images.IMAGE_METADATA_CHANGED', IMAGE_UPLOAD_PROGRESS: 'horizon.app.core.images.IMAGE_UPLOAD_PROGRESS' }; } diff --git a/openstack_dashboard/static/app/core/images/steps/create-image/create-image.controller.js b/openstack_dashboard/static/app/core/images/steps/create-image/create-image.controller.js index ec58a60a65..5d15b307a0 100644 --- a/openstack_dashboard/static/app/core/images/steps/create-image/create-image.controller.js +++ b/openstack_dashboard/static/app/core/images/steps/create-image/create-image.controller.js @@ -56,7 +56,7 @@ ctrl.apiVersion = 0; ctrl.allowPublicizeImage = true; - ctrl.image = { + $scope.stepModels.imageForm = ctrl.image = { source_type: '', image_url: '', data: {}, @@ -96,11 +96,9 @@ init(); - var imageChangedWatcher = $scope.$watchCollection('ctrl.image', watchImageCollection); var watchUploadProgress = $scope.$on(events.IMAGE_UPLOAD_PROGRESS, watchImageUpload); $scope.$on('$destroy', function() { - imageChangedWatcher(); watchUploadProgress(); }); @@ -148,13 +146,6 @@ return (type === 'file-legacy' || type === 'file-direct'); } - // emits new data to parent listeners - function watchImageCollection(newValue, oldValue) { - if (newValue !== oldValue) { - $scope.$emit(events.IMAGE_CHANGED, newValue); - } - } - function init() { glance.getImages({paginate: false}).success(onGetImages); policyAPI.ifAllowed({rules: [['image', 'publicize_image']]}).then( diff --git a/openstack_dashboard/static/app/core/images/steps/create-image/create-image.controller.spec.js b/openstack_dashboard/static/app/core/images/steps/create-image/create-image.controller.spec.js index b45e330561..d0301d48f3 100644 --- a/openstack_dashboard/static/app/core/images/steps/create-image/create-image.controller.spec.js +++ b/openstack_dashboard/static/app/core/images/steps/create-image/create-image.controller.spec.js @@ -49,6 +49,7 @@ beforeEach(inject(function ($injector, _$rootScope_, _$q_, _$timeout_) { $scope = _$rootScope_.$new(); + $scope.stepModels = {imageForm: {}, updateMetadataForm: {}}; $q = _$q_; $timeout = _$timeout_; @@ -93,19 +94,6 @@ expect(ctrl.ramdiskImages).toEqual([{disk_format: 'ari'}]); }); - it('should emit events on image change', function() { - spyOn($scope, '$emit').and.callThrough(); - - var ctrl = createController(); - ctrl.image = 1; - $scope.$apply(); - - ctrl.image = 2; - $scope.$apply(); - - expect($scope.$emit).toHaveBeenCalledWith('horizon.app.core.images.IMAGE_CHANGED', 2); - }); - it('should have options for visibility, protected and copying', function() { var ctrl = createController(); diff --git a/openstack_dashboard/static/app/core/images/steps/edit-image/edit-image.controller.js b/openstack_dashboard/static/app/core/images/steps/edit-image/edit-image.controller.js index adbecb2307..745209a872 100644 --- a/openstack_dashboard/static/app/core/images/steps/edit-image/edit-image.controller.js +++ b/openstack_dashboard/static/app/core/images/steps/edit-image/edit-image.controller.js @@ -52,12 +52,12 @@ ]; ctrl.imageVisibilityOptions = [ - { label: gettext('Public'), value: 'public'}, + { label: gettext('Public'), value: 'public' }, { label: gettext('Private'), value: 'private' } ]; ctrl.setFormats = setFormats; - ctrl.allowPublicizeImage = { rules: [['image', 'image:publicize_image']]}; + ctrl.allowPublicizeImage = { rules: [['image', 'image:publicize_image']] }; $scope.imagePromise.then(init); @@ -76,7 +76,7 @@ } function init(response) { - ctrl.image = response.data; + $scope.stepModels.imageForm = ctrl.image = response.data; ctrl.image.kernel = ctrl.image.properties.kernel_id; ctrl.image.ramdisk = ctrl.image.properties.ramdisk_id; ctrl.image.architecture = ctrl.image.properties.architecture; diff --git a/openstack_dashboard/static/app/core/images/steps/edit-image/edit-image.controller.spec.js b/openstack_dashboard/static/app/core/images/steps/edit-image/edit-image.controller.spec.js index eedf7d0bbe..6080583ad8 100644 --- a/openstack_dashboard/static/app/core/images/steps/edit-image/edit-image.controller.spec.js +++ b/openstack_dashboard/static/app/core/images/steps/edit-image/edit-image.controller.spec.js @@ -30,6 +30,7 @@ beforeEach(inject(function ($injector, _$rootScope_, _$q_, _$timeout_) { $scope = _$rootScope_.$new(); + $scope.stepModels = {imageForm: {}, updateMetadataForm: {}}; $q = _$q_; $timeout = _$timeout_; @@ -132,22 +133,5 @@ expect(ctrl.image.container_format).toEqual('ari'); }); - it("should destroy the image changed watcher when the controller is destroyed", function() { - setImagePromise({id: '1', container_format: 'bare', properties: []}); - spyOn($scope, '$emit').and.callThrough(); - - var ctrl = createController(); - ctrl.image = 1; - $scope.$apply(); - - $scope.$emit("$destroy"); - $scope.$emit.calls.reset(); - - ctrl.image = 2; - $scope.$apply(); - - expect($scope.$emit).not.toHaveBeenCalled(); - }); - }); })(); diff --git a/openstack_dashboard/static/app/core/images/steps/update-metadata/update-metadata.controller.js b/openstack_dashboard/static/app/core/images/steps/update-metadata/update-metadata.controller.js index 253b4dbb28..15df30b832 100644 --- a/openstack_dashboard/static/app/core/images/steps/update-metadata/update-metadata.controller.js +++ b/openstack_dashboard/static/app/core/images/steps/update-metadata/update-metadata.controller.js @@ -92,7 +92,7 @@ function onMetadataChanged(newValue, oldValue) { if (newValue !== oldValue) { - $scope.$emit(events.IMAGE_METADATA_CHANGED, newValue); + $scope.stepModels.updateMetadataForm = newValue; } } diff --git a/openstack_dashboard/static/app/core/images/steps/update-metadata/update-metadata.controller.spec.js b/openstack_dashboard/static/app/core/images/steps/update-metadata/update-metadata.controller.spec.js index 59d63f2541..027f4e1aee 100644 --- a/openstack_dashboard/static/app/core/images/steps/update-metadata/update-metadata.controller.spec.js +++ b/openstack_dashboard/static/app/core/images/steps/update-metadata/update-metadata.controller.spec.js @@ -68,6 +68,7 @@ beforeEach(inject(function($injector, _$rootScope_, _$q_) { $controller = $injector.get('$controller'); $scope = _$rootScope_.$new(); + $scope.stepModels = {imageForm: {}, updateMetadataForm: {}}; $q = _$q_; })); @@ -118,7 +119,7 @@ expect(metadataTreeService.Tree).toHaveBeenCalledWith(availableMetadata, []); }); - it('should emit imageMetadataChanged event when metadata changes', function() { + it('should update stepModels.updateMetadataForm when metadata changes', function() { var deferred = $q.defer(); deferred.resolve({data: {id: '1'}}); $scope.imagePromise = deferred.promise; @@ -135,10 +136,7 @@ mockGetExisting.and.returnValue('2'); $scope.$apply(); - expect($scope.$emit).toHaveBeenCalledWith( - 'horizon.app.core.images.IMAGE_METADATA_CHANGED', - '2' - ); + expect($scope.stepModels.updateMetadataForm).toEqual('2'); }); function createController() { diff --git a/releasenotes/notes/remove-deprecated-init-scope-342153755181f0a4.yaml b/releasenotes/notes/remove-deprecated-init-scope-342153755181f0a4.yaml new file mode 100644 index 0000000000..fe3580608a --- /dev/null +++ b/releasenotes/notes/remove-deprecated-init-scope-342153755181f0a4.yaml @@ -0,0 +1,5 @@ +--- +deprecations: + - Remove formerly deprecated initScope() function for + Angularized actions. Instead use initAction() and get + scope from second parameter of perform() function.