Search in sources :

Example 41 with ServerErrorCode

use of com.github.ambry.server.ServerErrorCode in project ambry by linkedin.

the class StoredBlob method updateBlobMap.

/**
 * Updates the blob map based on the {@code undeleteRequest}.
 * @param undeleteRequest the {@link TtlUpdateRequest} that needs to be processed
 */
private ServerErrorCode updateBlobMap(UndeleteRequest undeleteRequest) {
    ServerErrorCode errorCode = ServerErrorCode.No_Error;
    StoredBlob blob = blobs.get(undeleteRequest.getBlobId().getID());
    if (blob == null) {
        errorCode = ServerErrorCode.Blob_Not_Found;
    } else if (blob.isUndeleted()) {
        errorCode = ServerErrorCode.Blob_Already_Undeleted;
    } else if (!blob.isDeleted()) {
        errorCode = ServerErrorCode.Blob_Not_Deleted;
    } else if (blob.hasExpired()) {
        errorCode = ServerErrorCode.Blob_Expired;
    } else {
        blob.updateLifeVersion();
    }
    return errorCode;
}
Also used : ServerErrorCode(com.github.ambry.server.ServerErrorCode)

Example 42 with ServerErrorCode

use of com.github.ambry.server.ServerErrorCode in project ambry by linkedin.

the class DeleteManagerTest method testSelectorError.

/**
 * Test the case when the {@link com.github.ambry.network.Selector} of {@link SocketNetworkClient}
 * experiences various exceptions. The order of received responses is the same as defined in {@code serverErrorCodes}.
 */
@Test
public void testSelectorError() throws Exception {
    ServerErrorCode[] serverErrorCodes = new ServerErrorCode[9];
    Arrays.fill(serverErrorCodes, ServerErrorCode.No_Error);
    HashMap<MockSelectorState, RouterErrorCode> errorCodeHashMap = new HashMap<>();
    errorCodeHashMap.put(MockSelectorState.DisconnectOnSend, RouterErrorCode.OperationTimedOut);
    errorCodeHashMap.put(MockSelectorState.ThrowExceptionOnAllPoll, RouterErrorCode.OperationTimedOut);
    errorCodeHashMap.put(MockSelectorState.ThrowExceptionOnConnect, RouterErrorCode.OperationTimedOut);
    errorCodeHashMap.put(MockSelectorState.ThrowExceptionOnSend, RouterErrorCode.OperationTimedOut);
    errorCodeHashMap.put(MockSelectorState.ThrowThrowableOnSend, RouterErrorCode.RouterClosed);
    for (MockSelectorState state : MockSelectorState.values()) {
        if (state == MockSelectorState.Good || state == MockSelectorState.FailConnectionInitiationOnPoll) {
            // FailConnectionInitiationOnPoll is temporarily used for warm up failure test, skip it here
            continue;
        }
        mockSelectorState.set(state);
        setServerErrorCodes(serverErrorCodes, partition, serverLayout);
        CountDownLatch operationCompleteLatch = new CountDownLatch(1);
        future = router.deleteBlob(blobIdString, null, new ClientCallback(operationCompleteLatch), quotaChargeCallback);
        do {
            // increment mock time
            mockTime.sleep(1000);
        } while (!operationCompleteLatch.await(10, TimeUnit.MILLISECONDS));
        assertFailureAndCheckErrorCode(future, errorCodeHashMap.get(state));
    }
}
Also used : HashMap(java.util.HashMap) LinkedHashMap(java.util.LinkedHashMap) CountDownLatch(java.util.concurrent.CountDownLatch) ServerErrorCode(com.github.ambry.server.ServerErrorCode) Test(org.junit.Test)

Example 43 with ServerErrorCode

use of com.github.ambry.server.ServerErrorCode in project ambry by linkedin.

the class MockRouterCallback method testFailureOnServerErrors.

/**
 * Tests the case where all servers return the same server level error code
 * @throws Exception
 */
@Test
public void testFailureOnServerErrors() throws Exception {
    // set the status to various server level errors (remove all partition level errors or non errors)
    EnumSet<ServerErrorCode> serverErrors = EnumSet.complementOf(EnumSet.of(ServerErrorCode.Blob_Deleted, ServerErrorCode.Blob_Expired, ServerErrorCode.No_Error, ServerErrorCode.Blob_Authorization_Failure, ServerErrorCode.Blob_Not_Found));
    for (ServerErrorCode serverErrorCode : serverErrors) {
        mockServerLayout.getMockServers().forEach(server -> server.setServerErrorForAllRequests(serverErrorCode));
        RouterErrorCode expectedRouterError;
        switch(serverErrorCode) {
            case Replica_Unavailable:
                expectedRouterError = RouterErrorCode.AmbryUnavailable;
                break;
            case Disk_Unavailable:
                // if all the disks are unavailable (which should be extremely rare), after replacing these disks, the blob is
                // definitely not present.
                expectedRouterError = RouterErrorCode.BlobDoesNotExist;
                break;
            default:
                expectedRouterError = RouterErrorCode.UnexpectedInternalError;
        }
        assertOperationFailure(expectedRouterError);
    }
}
Also used : ServerErrorCode(com.github.ambry.server.ServerErrorCode) PutManagerTest(com.github.ambry.router.PutManagerTest) Test(org.junit.Test)

Example 44 with ServerErrorCode

use of com.github.ambry.server.ServerErrorCode in project ambry by linkedin.

the class MockRouterCallback method testBlobAuthorizationFailureOverrideAll.

/**
 * Test the case where servers return different {@link ServerErrorCode} or success, and the {@link GetBlobInfoOperation}
 * is able to resolve and conclude the correct {@link RouterErrorCode}. The get blob operation should be able
 * to resolve the router error code as {@code Blob_Authorization_Failure}.
 * @throws Exception
 */
@Test
public void testBlobAuthorizationFailureOverrideAll() throws Exception {
    // set it to 2 for more coverage
    successTarget = 2;
    Properties props = getNonBlockingRouterProperties(true);
    routerConfig = new RouterConfig(new VerifiableProperties(props));
    ServerErrorCode[] serverErrorCodes = new ServerErrorCode[9];
    serverErrorCodes[0] = ServerErrorCode.Blob_Not_Found;
    serverErrorCodes[1] = ServerErrorCode.Data_Corrupt;
    serverErrorCodes[2] = ServerErrorCode.IO_Error;
    serverErrorCodes[3] = ServerErrorCode.Partition_Unknown;
    serverErrorCodes[4] = ServerErrorCode.Disk_Unavailable;
    serverErrorCodes[5] = ServerErrorCode.Blob_Authorization_Failure;
    serverErrorCodes[6] = ServerErrorCode.Unknown_Error;
    serverErrorCodes[7] = ServerErrorCode.Unknown_Error;
    serverErrorCodes[8] = ServerErrorCode.No_Error;
    testErrorPrecedence(serverErrorCodes, RouterErrorCode.BlobAuthorizationFailure);
}
Also used : VerifiableProperties(com.github.ambry.config.VerifiableProperties) BlobProperties(com.github.ambry.messageformat.BlobProperties) Properties(java.util.Properties) VerifiableProperties(com.github.ambry.config.VerifiableProperties) RouterConfig(com.github.ambry.config.RouterConfig) ServerErrorCode(com.github.ambry.server.ServerErrorCode) PutManagerTest(com.github.ambry.router.PutManagerTest) Test(org.junit.Test)

Example 45 with ServerErrorCode

use of com.github.ambry.server.ServerErrorCode in project ambry by linkedin.

the class TtlUpdateOperation method handleResponse.

/**
 * Handles a response for a TTL update operation. It determines whether the request was successful and updates
 * operation tracker. For the same operation, it is possible that different {@link ServerErrorCode} are received from
 * different replicas. These error codes are eventually resolved to a single {@link RouterErrorCode}.
 * @param responseInfo The {@link ResponseInfo} to be handled.
 * @param ttlUpdateResponse The {@link TtlUpdateResponse} associated with this response.
 */
void handleResponse(ResponseInfo responseInfo, TtlUpdateResponse ttlUpdateResponse) {
    TtlUpdateRequest ttlUpdateRequest = (TtlUpdateRequest) responseInfo.getRequestInfo().getRequest();
    TtlUpdateRequestInfo ttlUpdateRequestInfo = ttlUpdateRequestInfos.remove(ttlUpdateRequest.getCorrelationId());
    // metric is updated here, as corresponding metrics have been updated when the request was timed out.
    if (ttlUpdateRequestInfo == null) {
        return;
    }
    ReplicaId replica = ttlUpdateRequestInfo.replica;
    long requestLatencyMs = time.milliseconds() - ttlUpdateRequestInfo.startTimeMs;
    routerMetrics.routerRequestLatencyMs.update(requestLatencyMs);
    routerMetrics.getDataNodeBasedMetrics(replica.getDataNodeId()).ttlUpdateRequestLatencyMs.update(requestLatencyMs);
    // Check the error code from NetworkClient.
    if (responseInfo.getError() != null) {
        LOGGER.debug("TtlUpdateRequest with response correlationId {} timed out for replica {} ", ttlUpdateRequest.getCorrelationId(), replica.getDataNodeId());
        onErrorResponse(replica, new RouterException("Operation timed out because of " + responseInfo.getError() + " at DataNode " + responseInfo.getDataNode(), RouterErrorCode.OperationTimedOut));
    } else {
        if (ttlUpdateResponse == null) {
            LOGGER.debug("TtlUpdateRequest with response correlationId {} received UnexpectedInternalError on response deserialization for replica {} ", ttlUpdateRequest.getCorrelationId(), replica.getDataNodeId());
            onErrorResponse(replica, new RouterException("Response deserialization received an unexpected error", RouterErrorCode.UnexpectedInternalError));
        } else {
            // not for its original request. We will immediately fail this operation.
            if (ttlUpdateResponse.getCorrelationId() != ttlUpdateRequest.getCorrelationId()) {
                LOGGER.error("The correlation id in the TtlUpdateResponse {} is not the same as the correlation id in the associated TtlUpdateRequest: {}", ttlUpdateResponse.getCorrelationId(), ttlUpdateRequest.getCorrelationId());
                routerMetrics.unknownReplicaResponseError.inc();
                onErrorResponse(replica, new RouterException("Received wrong response that is not for the corresponding request.", RouterErrorCode.UnexpectedInternalError));
            } else {
                ServerErrorCode serverError = ttlUpdateResponse.getError();
                if (serverError == ServerErrorCode.No_Error || serverError == ServerErrorCode.Blob_Already_Updated) {
                    operationTracker.onResponse(replica, TrackedRequestFinalState.SUCCESS);
                    if (RouterUtils.isRemoteReplica(routerConfig, replica)) {
                        LOGGER.trace("Cross colo request successful for remote replica {} in {} ", replica.getDataNodeId(), replica.getDataNodeId().getDatacenterName());
                        routerMetrics.crossColoSuccessCount.inc();
                    }
                } else if (serverError == ServerErrorCode.Disk_Unavailable) {
                    LOGGER.debug("Replica {} returned Disk_Unavailable for a Ttl update request with response correlationId : {} ", replica.getDataNodeId(), ttlUpdateResponse.getCorrelationId());
                    operationTracker.onResponse(replica, TrackedRequestFinalState.DISK_DOWN);
                    setOperationException(new RouterException("Server returned: " + serverError, RouterErrorCode.AmbryUnavailable));
                    routerMetrics.getDataNodeBasedMetrics(replica.getDataNodeId()).ttlUpdateRequestErrorCount.inc();
                } else {
                    LOGGER.debug("Replica {} returned an error {} for a Ttl update request with response correlationId : {} ", replica.getDataNodeId(), serverError, ttlUpdateResponse.getCorrelationId());
                    RouterErrorCode routerErrorCode = processServerError(serverError);
                    if (ttlUpdateResponse.getError() == ServerErrorCode.Blob_Authorization_Failure) {
                        // this is a successful response and one that completes the operation regardless of whether the
                        // success target has been reached or not.
                        operationCompleted = true;
                    }
                    // any server error code that is not equal to ServerErrorCode.No_Error, the onErrorResponse should be invoked
                    // because the operation itself doesn't succeed although the response in some cases is successful (i.e. Blob_Deleted)
                    onErrorResponse(replica, new RouterException("Server returned: " + serverError, routerErrorCode));
                }
            }
        }
    }
    checkAndMaybeComplete();
}
Also used : TtlUpdateRequest(com.github.ambry.protocol.TtlUpdateRequest) ReplicaId(com.github.ambry.clustermap.ReplicaId) ServerErrorCode(com.github.ambry.server.ServerErrorCode)

Aggregations

ServerErrorCode (com.github.ambry.server.ServerErrorCode)56 ArrayList (java.util.ArrayList)21 Test (org.junit.Test)20 DataInputStream (java.io.DataInputStream)16 BlobProperties (com.github.ambry.messageformat.BlobProperties)12 IOException (java.io.IOException)11 HashMap (java.util.HashMap)11 BlobId (com.github.ambry.commons.BlobId)10 VerifiableProperties (com.github.ambry.config.VerifiableProperties)10 MessageFormatException (com.github.ambry.messageformat.MessageFormatException)9 NettyByteBufDataInputStream (com.github.ambry.utils.NettyByteBufDataInputStream)9 MockClusterMap (com.github.ambry.clustermap.MockClusterMap)8 LoggingNotificationSystem (com.github.ambry.commons.LoggingNotificationSystem)8 RouterConfig (com.github.ambry.config.RouterConfig)8 Map (java.util.Map)8 Properties (java.util.Properties)8 DataNodeId (com.github.ambry.clustermap.DataNodeId)7 PartitionId (com.github.ambry.clustermap.PartitionId)7 MessageInfo (com.github.ambry.store.MessageInfo)7 IdUndeletedStoreException (com.github.ambry.store.IdUndeletedStoreException)6