diff options
author | Renu Kumari <renu.kumari@bell.ca> | 2022-02-10 09:31:17 -0500 |
---|---|---|
committer | Renu Kumari <renu.kumari@bell.ca> | 2022-02-15 12:56:08 -0500 |
commit | 21fa4f207e7d36befc49a3f4926dc4f52678a45e (patch) | |
tree | 98d2edc01d29622c6c34256529c866c17d5a4b7e /cps-service/src/test/groovy | |
parent | f7cb11a5d53d4964c236a6ecb2e2f4264f2437fd (diff) |
Fix to keep yang resource cache in sync
- Removed schemaset from cache when schemaset is deleted
- Added separate test cases for yang resource cache
Issue-ID: CPS-864
Signed-off-by: Renu Kumari <renu.kumari@bell.ca>
Change-Id: Ie1f9978406de1c92b513549216873cba4a98cdd7
Diffstat (limited to 'cps-service/src/test/groovy')
-rw-r--r-- | cps-service/src/test/groovy/org/onap/cps/api/impl/CpsModuleServiceImplSpec.groovy | 43 | ||||
-rw-r--r-- | cps-service/src/test/groovy/org/onap/cps/api/impl/YangTextSchemaSourceSetCacheSpec.groovy | 133 |
2 files changed, 144 insertions, 32 deletions
diff --git a/cps-service/src/test/groovy/org/onap/cps/api/impl/CpsModuleServiceImplSpec.groovy b/cps-service/src/test/groovy/org/onap/cps/api/impl/CpsModuleServiceImplSpec.groovy index b0205705a7..67dce1daf6 100644 --- a/cps-service/src/test/groovy/org/onap/cps/api/impl/CpsModuleServiceImplSpec.groovy +++ b/cps-service/src/test/groovy/org/onap/cps/api/impl/CpsModuleServiceImplSpec.groovy @@ -30,33 +30,18 @@ import org.onap.cps.spi.exceptions.SchemaSetInUseException import org.onap.cps.spi.model.Anchor import org.onap.cps.spi.model.ExtendedModuleReference import org.onap.cps.spi.model.ModuleReference -import org.spockframework.spring.SpringBean -import org.springframework.beans.factory.annotation.Autowired -import org.springframework.boot.test.context.SpringBootTest -import org.springframework.cache.CacheManager -import org.springframework.cache.annotation.EnableCaching -import org.springframework.cache.caffeine.CaffeineCacheManager -import org.springframework.test.context.ContextConfiguration +import org.onap.cps.yang.YangTextSchemaSourceSetBuilder import spock.lang.Specification import static org.onap.cps.spi.CascadeDeleteAllowed.CASCADE_DELETE_ALLOWED import static org.onap.cps.spi.CascadeDeleteAllowed.CASCADE_DELETE_PROHIBITED -@SpringBootTest -@EnableCaching -@ContextConfiguration(classes = [YangTextSchemaSourceSetCache, CpsModuleServiceImpl]) class CpsModuleServiceImplSpec extends Specification { - @SpringBean - CpsModulePersistenceService mockModuleStoreService = Mock() + def mockModuleStoreService = Mock(CpsModulePersistenceService) + def mockCpsAdminService = Mock(CpsAdminService) + def mockYangTextSchemaSourceSetCache = Mock(YangTextSchemaSourceSetCache) - @SpringBean - CpsAdminService mockCpsAdminService = Mock() - - @SpringBean - CacheManager cacheManager = new CaffeineCacheManager("yangSchema") - - @Autowired - CpsModuleServiceImpl objectUnderTest + def objectUnderTest = new CpsModuleServiceImpl(mockModuleStoreService, mockYangTextSchemaSourceSetCache, mockCpsAdminService) def 'Create schema set.'() { given: 'Valid yang resource as name-to-content map' @@ -90,7 +75,8 @@ class CpsModuleServiceImplSpec extends Specification { def 'Get schema set by name and dataspace.'() { given: 'an already present schema set' def yangResourcesNameToContentMap = TestUtils.getYangResourcesAsMap('bookstore.yang') - mockModuleStoreService.getYangSchemaResources('someDataspace', 'someSchemaSet') >> yangResourcesNameToContentMap + and: 'yang resource cache returns the expected schema set' + mockYangTextSchemaSourceSetCache.get('someDataspace', 'someSchemaSet') >> YangTextSchemaSourceSetBuilder.of(yangResourcesNameToContentMap) when: 'get schema set method is invoked' def result = objectUnderTest.getSchemaSet('someDataspace', 'someSchemaSet') then: 'the correct schema set is returned' @@ -99,17 +85,6 @@ class CpsModuleServiceImplSpec extends Specification { result.getExtendedModuleReferences().contains(new ExtendedModuleReference('stores', 'org:onap:ccsdk:sample', '2020-09-15')) } - def 'Schema set caching.'() { - given: 'an schema set' - def yangResourcesNameToContentMap = TestUtils.getYangResourcesAsMap('bookstore.yang') - when: 'get schema set method is invoked twice' - 2.times { - objectUnderTest.getSchemaSet('someDataspace', 'someSchemaSet') - } - then: 'the persistency service called only once' - 1 * mockModuleStoreService.getYangSchemaResources('someDataspace', 'someSchemaSet') >> yangResourcesNameToContentMap - } - def 'Delete schema-set when cascade is allowed.'() { given: '#numberOfAnchors anchors are associated with schemaset' def associatedAnchors = createAnchors(numberOfAnchors) @@ -120,6 +95,8 @@ class CpsModuleServiceImplSpec extends Specification { numberOfAnchors * mockCpsAdminService.deleteAnchor('my-dataspace', _) and: 'persistence service method is invoked with same parameters' 1 * mockModuleStoreService.deleteSchemaSet('my-dataspace', 'my-schemaset') + and: 'schema set will be removed from the cache' + 1 * mockYangTextSchemaSourceSetCache.removeFromCache('my-dataspace', 'my-schemaset') and: 'orphan yang resources are deleted' 1 * mockModuleStoreService.deleteUnusedYangResourceModules() where: 'following parameters are used' @@ -135,6 +112,8 @@ class CpsModuleServiceImplSpec extends Specification { 0 * mockCpsAdminService.deleteAnchor(_, _) and: 'persistence service method is invoked with same parameters' 1 * mockModuleStoreService.deleteSchemaSet('my-dataspace', 'my-schemaset') + and: 'schema set will be removed from the cache' + 1 * mockYangTextSchemaSourceSetCache.removeFromCache('my-dataspace', 'my-schemaset') and: 'orphan yang resources are deleted' 1 * mockModuleStoreService.deleteUnusedYangResourceModules() } diff --git a/cps-service/src/test/groovy/org/onap/cps/api/impl/YangTextSchemaSourceSetCacheSpec.groovy b/cps-service/src/test/groovy/org/onap/cps/api/impl/YangTextSchemaSourceSetCacheSpec.groovy new file mode 100644 index 0000000000..860b7399d2 --- /dev/null +++ b/cps-service/src/test/groovy/org/onap/cps/api/impl/YangTextSchemaSourceSetCacheSpec.groovy @@ -0,0 +1,133 @@ +/* + * ============LICENSE_START======================================================= + * Copyright (C) 2022 Bell Canada + * ================================================================================ + * 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. + * + * SPDX-License-Identifier: Apache-2.0 + * ============LICENSE_END========================================================= + */ + +package org.onap.cps.api.impl + +import org.onap.cps.TestUtils +import org.onap.cps.spi.CpsModulePersistenceService +import org.onap.cps.yang.YangTextSchemaSourceSet +import org.onap.cps.yang.YangTextSchemaSourceSetBuilder +import org.spockframework.spring.SpringBean +import org.springframework.beans.factory.annotation.Autowired +import org.springframework.boot.test.context.SpringBootTest +import org.springframework.cache.Cache +import org.springframework.cache.CacheManager +import org.springframework.cache.annotation.EnableCaching +import org.springframework.cache.caffeine.CaffeineCacheManager +import org.springframework.test.context.ContextConfiguration +import spock.lang.Specification + +@SpringBootTest +@EnableCaching +@ContextConfiguration(classes = [YangTextSchemaSourceSetCache, CaffeineCacheManager]) +class YangTextSchemaSourceSetCacheSpec extends Specification { + + @SpringBean + CpsModulePersistenceService mockModuleStoreService = Mock() + + @Autowired + YangTextSchemaSourceSetCache objectUnderTest + + @Autowired + CacheManager cacheManager + + Cache yangResourceCacheImpl; + + def setup() { + yangResourceCacheImpl = cacheManager.getCache('yangSchema') + yangResourceCacheImpl.clear() + } + + + def 'Cache Miss: Fetch data from Module persistence'() { + given: 'cache is empty' + yangResourceCacheImpl.clear() + and: 'a schema set exists' + def yangResourcesNameToContentMap = TestUtils.getYangResourcesAsMap('bookstore.yang') + def expectedYangTextSchemaSourceSet = YangTextSchemaSourceSetBuilder.of(yangResourcesNameToContentMap) + when: 'schema-set information is asked' + def result = objectUnderTest.get('my-dataspace', 'my-schemaset') + then: 'information fetched from cps module persistence' + 1 * mockModuleStoreService.getYangSchemaResources('my-dataspace', 'my-schemaset') + >> yangResourcesNameToContentMap + and: 'stored in the cache' + def cachedValue = getCachedValue('my-dataspace', 'my-schemaset') + assert cachedValue.getModuleReferences() == expectedYangTextSchemaSourceSet.getModuleReferences() + and: 'the response is as expected' + assert result.getModuleReferences() == expectedYangTextSchemaSourceSet.getModuleReferences() + } + + def 'Cache Hit: Respond from cache'() { + given: 'a schema set exists' + def yangResourcesNameToContentMap = TestUtils.getYangResourcesAsMap('bookstore.yang') + def expectedYangTextSchemaSourceSet = YangTextSchemaSourceSetBuilder.of(yangResourcesNameToContentMap) + and: 'stored in cache' + yangResourceCacheImpl.put(getCacheKey('my-dataspace', 'my-schemaset'), expectedYangTextSchemaSourceSet) + when: 'schema-set information is asked' + def result = objectUnderTest.get('my-dataspace', 'my-schemaset') + then: 'expected value is returned' + result.getModuleReferences() == expectedYangTextSchemaSourceSet.getModuleReferences() + and: 'module persistence is not invoked' + 0 * mockModuleStoreService.getYangSchemaResources(_, _) + } + + def 'Cache Update: when no data exist in the cache'() { + given: 'a schema set exists' + def yangResourcesNameToContentMap = TestUtils.getYangResourcesAsMap('bookstore.yang') + def yangTextSchemaSourceSet = YangTextSchemaSourceSetBuilder.of(yangResourcesNameToContentMap) + when: 'cache is updated' + objectUnderTest.updateCache('my-dataspace', 'my-schemaset', yangTextSchemaSourceSet) + then: 'cached value is same as expected' + def cachedValue = getCachedValue('my-dataspace', 'my-schemaset') + cachedValue.getModuleReferences() == yangTextSchemaSourceSet.getModuleReferences() + } + + def 'Cache Evict: remove when exist'() { + given: 'a schema set exists in cache' + def yangResourcesNameToContentMap = TestUtils.getYangResourcesAsMap('bookstore.yang') + def yangTextSchemaSourceSet = YangTextSchemaSourceSetBuilder.of(yangResourcesNameToContentMap) + yangResourceCacheImpl.put(getCacheKey('my-dataspace', 'my-schemaset'), yangTextSchemaSourceSet) + def cachedValue = getCachedValue('my-dataspace', 'my-schemaset') + assert cachedValue.getModuleReferences() == yangTextSchemaSourceSet.getModuleReferences() + when: 'cache is evicted for schemaset' + objectUnderTest.removeFromCache('my-dataspace', 'my-schemaset') + then: 'cached does not have value' + assert getCachedValue('my-dataspace', 'my-schemaset') == null + } + + def 'Cache Evict: remove when does not exist'() { + given: 'cache is empty' + yangResourceCacheImpl.clear() + when: 'cache is evicted for schemaset' + objectUnderTest.removeFromCache('my-dataspace', 'my-schemaset') + then: 'cached does not have value' + assert getCachedValue('my-dataspace', 'my-schemaset') == null + } + + def getCachedValue(dataSpace, schemaSet) { + yangResourceCacheImpl.get(getCacheKey(dataSpace, schemaSet), YangTextSchemaSourceSet) + } + + def getCacheKey(dataSpace, schemaSet) { + return new String("${dataSpace}-${schemaSet}") + } + + +} |