From 693cfdd2467d01bf9a90f588ba827454a7b20f33 Mon Sep 17 00:00:00 2001 From: ToineSiebelink Date: Tue, 9 Apr 2024 18:39:51 +0100 Subject: Introduce and handle Operation Too Large Exception for batch operations Issue-ID: CPS-2164 Signed-off-by: ToineSiebelink Change-Id: Iec05d2013be4f971309f0e75d84dc5d0936eb8ef --- .../NcmpDatastoreRequestHandlerSpec.groovy | 23 +++++++++++++------ .../NetworkCmProxyRestExceptionHandlerSpec.groovy | 26 ++++++++++++---------- 2 files changed, 30 insertions(+), 19 deletions(-) (limited to 'cps-ncmp-rest/src/test/groovy') diff --git a/cps-ncmp-rest/src/test/groovy/org/onap/cps/ncmp/rest/controller/handlers/NcmpDatastoreRequestHandlerSpec.groovy b/cps-ncmp-rest/src/test/groovy/org/onap/cps/ncmp/rest/controller/handlers/NcmpDatastoreRequestHandlerSpec.groovy index bdd0e716d..aef37c91e 100644 --- a/cps-ncmp-rest/src/test/groovy/org/onap/cps/ncmp/rest/controller/handlers/NcmpDatastoreRequestHandlerSpec.groovy +++ b/cps-ncmp-rest/src/test/groovy/org/onap/cps/ncmp/rest/controller/handlers/NcmpDatastoreRequestHandlerSpec.groovy @@ -27,6 +27,7 @@ import org.onap.cps.ncmp.api.models.DataOperationDefinition import org.onap.cps.ncmp.api.models.DataOperationRequest import org.onap.cps.ncmp.api.models.CmResourceAddress import org.onap.cps.ncmp.rest.exceptions.OperationNotSupportedException +import org.onap.cps.ncmp.rest.exceptions.PayloadTooLargeException import org.onap.cps.ncmp.rest.executor.CpsNcmpTaskExecutor import spock.lang.Specification import spock.util.concurrent.PollingConditions @@ -110,9 +111,7 @@ class NcmpDatastoreRequestHandlerSpec extends Specification { } def 'Attempt to execute async data operation request with error #scenario'() { - given: 'notification feature is turned on' - objectUnderTest.notificationFeatureEnabled = true - and: 'a data operation definition with datastore: #datastore' + given: 'a data operation definition with datastore: #datastore' def dataOperationDefinition = new DataOperationDefinition(operation: 'read', datastore: datastore) when: 'data operation request is executed' def dataOperationRequest = new DataOperationRequest(dataOperationDefinitions: [dataOperationDefinition]) @@ -127,11 +126,9 @@ class NcmpDatastoreRequestHandlerSpec extends Specification { } def 'Attempt to execute async data operation request with #scenario operation: #operation.'() { - given: 'notification feature is turned on' - objectUnderTest.notificationFeatureEnabled = true - and: 'a data operation definition with operation: #operation' + given: 'a data operation definition with operation: #operation' def dataOperationDefinition = new DataOperationDefinition(operation: operation, datastore: 'ncmp-datastore:passthrough-running') - when: 'bulk request is executed' + when: 'data operation request is executed' objectUnderTest.executeRequest('someTopic', new DataOperationRequest(dataOperationDefinitions:[dataOperationDefinition]), NO_AUTH_HEADER) then: 'the expected type of exception is thrown' thrown(expectedException) @@ -144,4 +141,16 @@ class NcmpDatastoreRequestHandlerSpec extends Specification { 'unsupported' | 'delete' || OperationNotSupportedException } + def 'Attempt to execute async data operation request with too many cm handles.'() { + given: 'a data operation definition with too many cm handles' + def cmHandleIds = new String[51] + def dataOperationDefinition = new DataOperationDefinition(operationId: 'abc', operation: 'read', datastore: 'ncmp-datastore:passthrough-running', cmHandleIds: cmHandleIds) + when: 'data operation request is executed' + objectUnderTest.executeRequest('someTopic', new DataOperationRequest(dataOperationDefinitions:[dataOperationDefinition]), NO_AUTH_HEADER) + then: 'a payload too large exception is thrown' + def exceptionThrown = thrown(PayloadTooLargeException) + and: 'the error message contains the offending number of cm handles' + assert exceptionThrown.message == "Operation 'abc' affects too many (51) cm handles" + } + } diff --git a/cps-ncmp-rest/src/test/groovy/org/onap/cps/ncmp/rest/exceptions/NetworkCmProxyRestExceptionHandlerSpec.groovy b/cps-ncmp-rest/src/test/groovy/org/onap/cps/ncmp/rest/exceptions/NetworkCmProxyRestExceptionHandlerSpec.groovy index dd02b312a..a79ea25ab 100644 --- a/cps-ncmp-rest/src/test/groovy/org/onap/cps/ncmp/rest/exceptions/NetworkCmProxyRestExceptionHandlerSpec.groovy +++ b/cps-ncmp-rest/src/test/groovy/org/onap/cps/ncmp/rest/exceptions/NetworkCmProxyRestExceptionHandlerSpec.groovy @@ -1,7 +1,7 @@ /* * ============LICENSE_START======================================================= * Copyright (C) 2021 highstreet technologies GmbH - * Modifications Copyright (C) 2021-2023 Nordix Foundation + * Modifications Copyright (C) 2021-2024 Nordix Foundation * ================================================================================ * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -23,9 +23,10 @@ package org.onap.cps.ncmp.rest.exceptions import static org.springframework.http.HttpStatus.BAD_GATEWAY import static org.springframework.http.HttpStatus.BAD_REQUEST +import static org.springframework.http.HttpStatus.CONFLICT import static org.springframework.http.HttpStatus.INTERNAL_SERVER_ERROR import static org.springframework.http.HttpStatus.NOT_FOUND -import static org.springframework.http.HttpStatus.CONFLICT +import static org.springframework.http.HttpStatus.PAYLOAD_TOO_LARGE import static org.onap.cps.ncmp.rest.exceptions.NetworkCmProxyRestExceptionHandlerSpec.ApiType.NCMP import static org.onap.cps.ncmp.rest.exceptions.NetworkCmProxyRestExceptionHandlerSpec.ApiType.NCMPINVENTORY import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.get @@ -111,22 +112,23 @@ class NetworkCmProxyRestExceptionHandlerSpec extends Specification { dataNodeBaseEndpointNcmpInventory = "$basePathNcmpInventory/v1" } - def 'Get request with generic #scenario exception returns correct HTTP Status with #scenario'() { + def 'Get request with #scenario exception returns correct HTTP Status with #scenario'() { when: 'an exception is thrown by the service' setupTestException(exception, NCMP) def response = performTestRequest(NCMP) then: 'an HTTP response is returned with correct message and details' assertTestResponse(response, expectedErrorCode, expectedErrorMessage, expectedErrorDetails) where: - scenario | exception || expectedErrorDetails | expectedErrorMessage | expectedErrorCode - 'CPS' | new CpsException(sampleErrorMessage, sampleErrorDetails) || sampleErrorDetails | sampleErrorMessage | INTERNAL_SERVER_ERROR - 'NCMP-server' | new ServerNcmpException(sampleErrorMessage, sampleErrorDetails) || null | sampleErrorMessage | INTERNAL_SERVER_ERROR - 'NCMP-client' | new DmiRequestException(sampleErrorMessage, sampleErrorDetails) || null | sampleErrorMessage | BAD_REQUEST - 'DataNode Validation' | new DataNodeNotFoundException('myDataspaceName', 'myAnchorName') || null | 'DataNode not found' | NOT_FOUND - 'other' | new IllegalStateException(sampleErrorMessage) || null | sampleErrorMessage | INTERNAL_SERVER_ERROR - 'Data Node Not Found' | new DataNodeNotFoundException('myDataspaceName', 'myAnchorName') || 'DataNode not found' | 'DataNode not found' | NOT_FOUND - 'Existing entry' | new AlreadyDefinedException('name',null) || 'name already exists' | 'Already defined exception' | CONFLICT - 'Existing entries' | AlreadyDefinedException.forDataNodes(['A', 'B'], 'myAnchorName') || '2 data node(s) already exist' | 'Already defined exception' | CONFLICT + scenario | exception || expectedErrorCode | expectedErrorMessage | expectedErrorDetails + 'CPS' | new CpsException(sampleErrorMessage, sampleErrorDetails) || INTERNAL_SERVER_ERROR | sampleErrorMessage | sampleErrorDetails + 'NCMP-server' | new ServerNcmpException(sampleErrorMessage, sampleErrorDetails) || INTERNAL_SERVER_ERROR | sampleErrorMessage | null + 'NCMP-client' | new DmiRequestException(sampleErrorMessage, sampleErrorDetails) || BAD_REQUEST | sampleErrorMessage | null + 'DataNode Validation' | new DataNodeNotFoundException('myDataspaceName', 'myAnchorName') || NOT_FOUND | 'DataNode not found' | null + 'other' | new IllegalStateException(sampleErrorMessage) || INTERNAL_SERVER_ERROR | sampleErrorMessage | null + 'Data Node Not Found' | new DataNodeNotFoundException('myDataspaceName', 'myAnchorName') || NOT_FOUND | 'DataNode not found' | 'DataNode not found' + 'Existing entry' | new AlreadyDefinedException('name',null) || CONFLICT | 'Already defined exception' | 'name already exists' + 'Existing entries' | AlreadyDefinedException.forDataNodes(['A', 'B'], 'myAnchorName') || CONFLICT | 'Already defined exception' | '2 data node(s) already exist' + 'Operation too large' | new PayloadTooLargeException(sampleErrorMessage) || PAYLOAD_TOO_LARGE | sampleErrorMessage | 'Check logs' } def 'Post request with exception returns correct HTTP Status.'() { -- cgit 1.2.3-korg