2 * ============LICENSE_START=======================================================
3 * Copyright (C) 2024-2025 Nordix Foundation
4 * ================================================================================
5 * Licensed under the Apache License, Version 2.0 (the 'License');
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at
9 * http://www.apache.org/licenses/LICENSE-2.0
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an 'AS IS' BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
17 * SPDX-License-Identifier: Apache-2.0
18 * ============LICENSE_END=========================================================
21 package org.onap.cps.integration.functional.ncmp
23 import org.onap.cps.integration.base.CpsIntegrationSpecBase
24 import org.onap.cps.ncmp.api.inventory.models.CmHandleRegistrationResponse
25 import org.onap.cps.ncmp.api.inventory.models.CmHandleState
26 import org.onap.cps.ncmp.api.inventory.models.DmiPluginRegistration
27 import org.onap.cps.ncmp.api.inventory.models.LockReasonCategory
28 import org.onap.cps.ncmp.api.inventory.models.UpgradedCmHandles
29 import org.onap.cps.ncmp.impl.NetworkCmProxyInventoryFacadeImpl
31 class CmHandleUpgradeSpec extends CpsIntegrationSpecBase {
33 NetworkCmProxyInventoryFacadeImpl objectUnderTest
35 def cmHandleId = 'ch-1'
36 def cmHandleIdWithExistingModuleSetTag = 'ch-2'
39 objectUnderTest = networkCmProxyInventoryFacade
42 def 'Upgrade CM-handle with and without (new) module set tags.'() {
43 given: 'a CM-handle is created with expected initial modules: M1 and M2'
44 dmiDispatcher1.moduleNamesPerCmHandleId[cmHandleId] = ['M1', 'M2']
45 registerCmHandle(DMI1_URL, cmHandleId, initialModuleSetTag)
46 assert ['M1', 'M2'] == objectUnderTest.getYangResourcesModuleReferences(cmHandleId).moduleName.sort()
48 when: "the CM-handle is upgraded with given moduleSetTag '${updatedModuleSetTag}'"
49 def cmHandlesToUpgrade = new UpgradedCmHandles(cmHandles: [cmHandleId], moduleSetTag: updatedModuleSetTag)
50 def dmiPluginRegistrationResponse = objectUnderTest.updateDmiRegistration(
51 new DmiPluginRegistration(dmiPlugin: DMI1_URL, upgradedCmHandles: cmHandlesToUpgrade))
53 then: 'registration gives successful response'
54 assert dmiPluginRegistrationResponse.upgradedCmHandles == [CmHandleRegistrationResponse.createSuccessResponse(cmHandleId)]
56 and: 'CM-handle is in LOCKED state due to MODULE_UPGRADE'
57 def cmHandleCompositeState = objectUnderTest.getCmHandleCompositeState(cmHandleId)
58 assert cmHandleCompositeState.cmHandleState == CmHandleState.LOCKED
59 assert cmHandleCompositeState.lockReason.lockReasonCategory == LockReasonCategory.MODULE_UPGRADE
60 assert cmHandleCompositeState.lockReason.details == "Upgrade to ModuleSetTag: ${updatedModuleSetTag}"
62 when: 'DMI will return different modules for upgrade: M1 and M3'
63 dmiDispatcher1.moduleNamesPerCmHandleId[cmHandleId] = ['M1', 'M3']
65 and: 'the module sync watchdog is triggered twice'
66 2.times { moduleSyncWatchdog.moduleSyncAdvisedCmHandles() }
68 then: 'CM-handle goes to READY state'
69 assert CmHandleState.READY == objectUnderTest.getCmHandleCompositeState(cmHandleId).cmHandleState
71 and: 'the CM-handle has expected moduleSetTag'
72 assert objectUnderTest.getNcmpServiceCmHandle(cmHandleId).moduleSetTag == updatedModuleSetTag
74 and: 'CM-handle has expected updated modules: M1 and M3'
75 assert ['M1', 'M3'] == objectUnderTest.getYangResourcesModuleReferences(cmHandleId).moduleName.sort()
77 cleanup: 'deregister CM-handle and remove all associated module resources'
78 deregisterCmHandle(DMI1_URL, cmHandleId)
80 where: 'following module set tags are used'
81 initialModuleSetTag | updatedModuleSetTag
82 NO_MODULE_SET_TAG | NO_MODULE_SET_TAG
83 NO_MODULE_SET_TAG | 'new@set'
84 'initial set' | NO_MODULE_SET_TAG
85 'initial set' | 'new@set'
88 def 'Upgrade CM-handle with existing moduleSetTag.'() {
89 given: 'DMI will return modules for registration'
90 dmiDispatcher1.moduleNamesPerCmHandleId[cmHandleId] = ['M1', 'M2']
91 dmiDispatcher1.moduleNamesPerCmHandleId[cmHandleIdWithExistingModuleSetTag] = ['M1', 'M3']
92 and: "an existing CM-handle handle with moduleSetTag '${updatedModuleSetTag}'"
93 registerCmHandle(DMI1_URL, cmHandleIdWithExistingModuleSetTag, updatedModuleSetTag)
94 assert ['M1', 'M3'] == objectUnderTest.getYangResourcesModuleReferences(cmHandleIdWithExistingModuleSetTag).moduleName.sort()
95 and: "a CM-handle with moduleSetTag '${initialModuleSetTag}' which will be upgraded"
96 registerCmHandle(DMI1_URL, cmHandleId, initialModuleSetTag)
97 assert ['M1', 'M2'] == objectUnderTest.getYangResourcesModuleReferences(cmHandleId).moduleName.sort()
99 when: "CM-handle is upgraded to moduleSetTag '${updatedModuleSetTag}'"
100 def cmHandlesToUpgrade = new UpgradedCmHandles(cmHandles: [cmHandleId], moduleSetTag: updatedModuleSetTag)
101 def dmiPluginRegistrationResponse = objectUnderTest.updateDmiRegistration(
102 new DmiPluginRegistration(dmiPlugin: DMI1_URL, upgradedCmHandles: cmHandlesToUpgrade))
104 then: 'registration gives successful response'
105 assert dmiPluginRegistrationResponse.upgradedCmHandles == [CmHandleRegistrationResponse.createSuccessResponse(cmHandleId)]
107 and: 'the module sync watchdog is triggered twice'
108 2.times { moduleSyncWatchdog.moduleSyncAdvisedCmHandles() }
110 and: 'CM-handle goes to READY state'
111 assert CmHandleState.READY == objectUnderTest.getCmHandleCompositeState(cmHandleId).cmHandleState
113 and: 'the CM-handle has expected moduleSetTag'
114 assert objectUnderTest.getNcmpServiceCmHandle(cmHandleId).moduleSetTag == updatedModuleSetTag
116 and: 'CM-handle has expected updated modules: M1 and M3'
117 assert ['M1', 'M3'] == objectUnderTest.getYangResourcesModuleReferences(cmHandleId).moduleName.sort()
119 cleanup: 'deregister CM-handle'
120 deregisterCmHandles(DMI1_URL, [cmHandleId, cmHandleIdWithExistingModuleSetTag])
123 initialModuleSetTag | updatedModuleSetTag
124 NO_MODULE_SET_TAG | 'module@Set2'
125 'module@Set1' | 'module@Set2'
128 def 'Skip upgrade of CM-handle with same moduleSetTag as before.'() {
129 given: 'an existing CM-handle with expected initial modules: M1 and M2'
130 dmiDispatcher1.moduleNamesPerCmHandleId[cmHandleId] = ['M1', 'M2']
131 registerCmHandle(DMI1_URL, cmHandleId, 'same')
132 assert ['M1', 'M2'] == objectUnderTest.getYangResourcesModuleReferences(cmHandleId).moduleName.sort()
134 when: 'CM-handle is upgraded with the same moduleSetTag'
135 def cmHandlesToUpgrade = new UpgradedCmHandles(cmHandles: [cmHandleId], moduleSetTag: 'same')
136 objectUnderTest.updateDmiRegistration(
137 new DmiPluginRegistration(dmiPlugin: DMI1_URL, upgradedCmHandles: cmHandlesToUpgrade))
139 then: 'CM-handle remains in READY state'
140 assert CmHandleState.READY == objectUnderTest.getCmHandleCompositeState(cmHandleId).cmHandleState
142 and: 'the CM-handle has same moduleSetTag as before'
143 assert objectUnderTest.getNcmpServiceCmHandle(cmHandleId).moduleSetTag == 'same'
145 then: 'CM-handle has same modules as before: M1 and M2'
146 assert ['M1', 'M2'] == objectUnderTest.getYangResourcesModuleReferences(cmHandleId).moduleName.sort()
148 cleanup: 'deregister CM-handle'
149 deregisterCmHandle(DMI1_URL, cmHandleId)
152 def 'Upgrade of CM-handle fails due to DMI error.'() {
153 given: 'a CM-handle exists'
154 dmiDispatcher1.moduleNamesPerCmHandleId[cmHandleId] = ['M1', 'M2']
155 registerCmHandle(DMI1_URL, cmHandleId, 'oldTag')
156 and: 'DMI is not available for upgrade'
157 dmiDispatcher1.isAvailable = false
159 when: 'the CM-handle is upgraded'
160 def cmHandlesToUpgrade = new UpgradedCmHandles(cmHandles: [cmHandleId], moduleSetTag: 'newTag')
161 objectUnderTest.updateDmiRegistration(
162 new DmiPluginRegistration(dmiPlugin: DMI1_URL, upgradedCmHandles: cmHandlesToUpgrade))
164 and: 'the module sync watchdog is triggered twice'
165 2.times { moduleSyncWatchdog.moduleSyncAdvisedCmHandles() }
167 then: 'CM-handle goes to LOCKED state with reason MODULE_UPGRADE_FAILED'
168 def cmHandleCompositeState = objectUnderTest.getCmHandleCompositeState(cmHandleId)
169 assert cmHandleCompositeState.cmHandleState == CmHandleState.LOCKED
170 assert cmHandleCompositeState.lockReason.lockReasonCategory == LockReasonCategory.MODULE_UPGRADE_FAILED
172 and: 'the CM-handle has same moduleSetTag as before'
173 assert objectUnderTest.getNcmpServiceCmHandle(cmHandleId).moduleSetTag == 'oldTag'
175 cleanup: 'deregister CM-handle'
176 deregisterCmHandle(DMI1_URL, cmHandleId)