diff --git a/ironic_ui/static/dashboard/admin/ironic/ironic.backend-mock.service.js b/ironic_ui/static/dashboard/admin/ironic/ironic.backend-mock.service.js index 8d7dc976..e69f2eae 100644 --- a/ironic_ui/static/dashboard/admin/ironic/ironic.backend-mock.service.js +++ b/ironic_ui/static/dashboard/admin/ironic/ironic.backend-mock.service.js @@ -598,6 +598,24 @@ return [status, null]; }); + // Set RAID config + $httpBackend.whenPUT(/\/api\/ironic\/nodes\/(.+)\/states\/raid/, + undefined, + undefined, + ['nodeId']) + .respond(function(method, url, data, headers, params) { + data = JSON.parse(data); + var status = responseCode.RESOURCE_NOT_FOUND; + if (angular.isDefined(nodes[params.nodeId])) { + var node = nodes[params.nodeId]; + if (angular.isDefined(data.target_raid_config)) { + node.base.target_raid_config = data.target_raid_config; + status = responseCode.SUCCESS; + } + } + return [status, null]; + }); + // Validate the interfaces associated with a specified node $httpBackend.whenGET(/\/api\/ironic\/nodes\/([^\/]+)\/validate$/, undefined, diff --git a/ironic_ui/static/dashboard/admin/ironic/ironic.service.spec.js b/ironic_ui/static/dashboard/admin/ironic/ironic.service.spec.js index e9a936cf..1880109b 100644 --- a/ironic_ui/static/dashboard/admin/ironic/ironic.service.spec.js +++ b/ironic_ui/static/dashboard/admin/ironic/ironic.service.spec.js @@ -389,6 +389,48 @@ ironicBackendMockService.flush(); }); + it('nodeSetRaidConfig', function() { + var raid = { + logical_disks: [{size_gb: 10, raid_level: '1', is_root_volume: false}] + }; + createNode({driver: defaultDriver}) + .then(function(node) { + return ironicAPI.nodeSetRaidConfig(node.uuid, raid) + .then(function() { + return node; + }); + }) + .then(function(node) { + ironicAPI.getNode(node.uuid).then(function(node) { + expect(node.target_raid_config).toEqual(raid); + }); + }) + .catch(failTest); + + ironicBackendMockService.flush(); + }); + + it('nodeSetRaidConfig - bad config', function() { + var badConfig = { + logical_disks: [{size_gb: 10, is_root_volume: false}] + }; + + createNode({driver: defaultDriver}) + .then(function(node) { + ironicAPI.nodeSetRaidConfig(node.uuid, badConfig) + .then(function() { + // Ensure the target raid config is unchanged + ironicAPI.getNode(node.uuid) + .then(function() { + expect(node.target_raid_config).toEqual({}); + }); + }); + }) + .catch(failTest); + + ironicBackendMockService.flush(); + }); + it('createPort', function() { var macAddr = '00:00:00:00:00:00'; var node; diff --git a/ironic_ui/static/dashboard/admin/ironic/raidconfig/raidconfig.controller.spec.js b/ironic_ui/static/dashboard/admin/ironic/raidconfig/raidconfig.controller.spec.js new file mode 100644 index 00000000..7277fc64 --- /dev/null +++ b/ironic_ui/static/dashboard/admin/ironic/raidconfig/raidconfig.controller.spec.js @@ -0,0 +1,99 @@ +/* + * Copyright 2017 Intel Corporation + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +(function () { + 'use strict'; + + describe('horizon.dashboard.admin.ironic.RaidConfigController', function () { + var RAID_CONFIG_CONTROLLER_PROPERTIES = [ + 'addLogicalDisk', + 'cancel', + 'deleteLogicalDisk', + 'logicalDisks', + 'logicalDisksSrc', + 'modalTitle', + 'raid_level', + 'root_volume', + 'setTargetRaidConfig', + 'size_gb', + 'target_raid_config' + ]; + var uibModalInstance, ironicBackendMockService, node; + var ctrl = {}; + + beforeEach(module('horizon.dashboard.admin.ironic')); + + beforeEach(module('horizon.framework.util')); + + beforeEach(module(function($provide) { + $provide.value('$uibModal', {}); + })); + + beforeEach(module(function($provide) { + uibModalInstance = { + close: jasmine.createSpy(), + dismiss: jasmine.createSpy() + }; + $provide.value('$uibModalInstance', uibModalInstance); + })); + + beforeEach(module(function($provide) { + $provide.value('horizon.framework.widgets.toast.service', {}); + })); + + beforeEach(module('horizon.app.core.openstack-service-api')); + + beforeEach(inject(function($injector) { + ironicBackendMockService = + $injector.get('horizon.dashboard.admin.ironic.backend-mock.service'); + ironicBackendMockService.init(); + + var ironicAPI = + $injector.get('horizon.app.core.openstack-service-api.ironic'); + + ironicAPI.createNode( + {driver: ironicBackendMockService.params.defaultDriver}) + .then(function(response) { + node = response.data; + var controller = $injector.get('$controller'); + ctrl = controller('RaidConfigController', {node: node}); + }); + ironicBackendMockService.flush(); + })); + + it('controller should be defined', function () { + expect(ctrl).toBeDefined(); + expect(Object.getOwnPropertyNames(ctrl).sort()).toEqual( + RAID_CONFIG_CONTROLLER_PROPERTIES.sort()); + }); + + it('cancel', function () { + ctrl.cancel(); + expect(uibModalInstance.dismiss).toHaveBeenCalled(); + }); + + it('setTargetRaidConfig', function () { + var testConfig = + {logical_disks: [{size_gb: 5, raid_level: '5', is_root_volume: true}]}; + ctrl.logicalDisks = angular.copy(testConfig.logical_disks); + ctrl.setTargetRaidConfig(); + expect(ctrl.logicalDisks.length).toBeGreaterThan(0); + expect(uibModalInstance.close).toHaveBeenCalledWith( + {target_raid_config: testConfig}); + }); + + }); +})(); + diff --git a/ironic_ui/static/dashboard/admin/ironic/raidconfig/raidconfig.service.spec.js b/ironic_ui/static/dashboard/admin/ironic/raidconfig/raidconfig.service.spec.js new file mode 100644 index 00000000..97bd3c54 --- /dev/null +++ b/ironic_ui/static/dashboard/admin/ironic/raidconfig/raidconfig.service.spec.js @@ -0,0 +1,133 @@ +/* + * Copyright 2017 Intel Corporation + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +(function() { + "use strict"; + + /** + * @description Unit tests for the Ironic-UI raid config service + */ + + describe('horizon.dashboard.admin.ironic.raidconfig.service', + function() { + var $q, + $uibModal, + raidConfigService, + ironicAPI, + ironicBackendMockService, + defaultDriver; + + beforeEach(module('horizon.dashboard.admin.ironic')); + + beforeEach(module('horizon.framework.util')); + + beforeEach(module(function($provide) { + $provide.value('$uibModal', { + open: function() { + var targetRaid = + {logical_disks: [{size_gb: 1, raid_level: '1', is_root_volume: false}]}; + return $q.when({target_raid_config: targetRaid}); + } + }); + })); + + beforeEach(module(function($provide) { + $provide.value('horizon.framework.widgets.toast.service', { + add: function() {} + }); + })); + + beforeEach(module('horizon.app.core.openstack-service-api')); + + beforeEach(inject(function($injector) { + ironicBackendMockService = + $injector.get('horizon.dashboard.admin.ironic.backend-mock.service'); + ironicBackendMockService.init(); + defaultDriver = ironicBackendMockService.params.defaultDriver; + })); + + beforeEach(inject(function($injector) { + $q = $injector.get('$q'); + + $uibModal = $injector.get('$uibModal'); + + ironicAPI = + $injector.get('horizon.app.core.openstack-service-api.ironic'); + + raidConfigService = + $injector.get('horizon.dashboard.admin.ironic.raidconfig.service'); + })); + + it('defines the raidConfigService', function() { + expect(raidConfigService).toBeDefined(); + expect(raidConfigService.setRaidConfig).toBeDefined(); + }); + + afterEach(function() { + ironicBackendMockService.postTest(); + }); + + /** + * @description Utility function that creates a node and returns + * the node + * + * @return {promise} Containing node + */ + function createNode() { + return ironicAPI.createNode({driver: defaultDriver}) + .then(function(response) { + return response.data; + }) + .then(function(node) { + return {node: node}; + }); + } + + it('setRaidConfig', function() { + var targetRaidConfig = + [{size_gb: 1, raid_level: '1', is_root_volume: false}]; + + spyOn($uibModal, 'open').and.returnValue( + {result: $q.when({target_raid_config: targetRaidConfig})}); + + createNode().then(function(data) { + raidConfigService.setRaidConfig(data.node) + .then(function() { + ironicAPI.getNode(data.node.uuid) + .then(function(node) { + expect(node.target_raid_config).toEqual(targetRaidConfig); + }); + }) + .catch(fail); + }); + ironicBackendMockService.flush(); + }); + + it('setRaidConfig - cancel', function() { + spyOn($uibModal, 'open').and.returnValue( + {result: $q.reject('cancel')}); + + createNode().then(function(data) { + raidConfigService.setRaidConfig(data.node) + .then(fail) + .catch(function() {}); + }); + + ironicBackendMockService.flush(); + }); + }); +})(); +