diff --git a/.palantir/revapi.yml b/.palantir/revapi.yml index 21e876abc24..e943bd00577 100644 --- a/.palantir/revapi.yml +++ b/.palantir/revapi.yml @@ -423,6 +423,22 @@ acceptedBreaks: new: "method void com.palantir.atlasdb.keyvalue.api.InsufficientConsistencyException::(java.lang.String,\ \ java.lang.Throwable, com.palantir.logsafe.Arg[])" justification: "I have fixed all the implementations and it is not used externally" + "0.1169.0": + com.palantir.atlasdb:atlasdb-api: + - code: "java.method.parameterTypeChanged" + old: "parameter void com.palantir.atlasdb.keyvalue.api.InsufficientConsistencyException::(===java.lang.String===,\ + \ java.lang.Throwable)" + new: "parameter void com.palantir.atlasdb.keyvalue.api.InsufficientConsistencyException::(===java.lang.Throwable===,\ + \ com.palantir.logsafe.Arg[])" + justification: "Not a break as I have handle the implementation in the same\ + \ PR" + - code: "java.method.parameterTypeChanged" + old: "parameter void com.palantir.atlasdb.keyvalue.api.InsufficientConsistencyException::(java.lang.String,\ + \ ===java.lang.Throwable===)" + new: "parameter void com.palantir.atlasdb.keyvalue.api.InsufficientConsistencyException::(java.lang.Throwable,\ + \ ===com.palantir.logsafe.Arg[]===)" + justification: "Not a break as I have handle the implementation in the same\ + \ PR" "0.1168.0": com.palantir.atlasdb:atlasdb-api: - code: "java.method.numberOfParametersChanged" diff --git a/atlasdb-api/src/main/java/com/palantir/atlasdb/keyvalue/api/InsufficientConsistencyException.java b/atlasdb-api/src/main/java/com/palantir/atlasdb/keyvalue/api/InsufficientConsistencyException.java index f393a8af254..3d6139e3490 100644 --- a/atlasdb-api/src/main/java/com/palantir/atlasdb/keyvalue/api/InsufficientConsistencyException.java +++ b/atlasdb-api/src/main/java/com/palantir/atlasdb/keyvalue/api/InsufficientConsistencyException.java @@ -33,4 +33,8 @@ public InsufficientConsistencyException(@CompileTimeConstant String msg, Arg. public InsufficientConsistencyException(@CompileTimeConstant String msg, Throwable ex, Arg... args) { super(msg, ex, args); } + + public InsufficientConsistencyException(Throwable ex, Arg... args) { + super(ex, args); + } } diff --git a/atlasdb-cassandra-multinode-tests/src/test/java/com/palantir/cassandra/multinode/OneNodeDownDeleteTest.java b/atlasdb-cassandra-multinode-tests/src/test/java/com/palantir/cassandra/multinode/OneNodeDownDeleteTest.java index 8e0b16e946d..1eeb0c88cf6 100644 --- a/atlasdb-cassandra-multinode-tests/src/test/java/com/palantir/cassandra/multinode/OneNodeDownDeleteTest.java +++ b/atlasdb-cassandra-multinode-tests/src/test/java/com/palantir/cassandra/multinode/OneNodeDownDeleteTest.java @@ -36,13 +36,13 @@ void testSetup(CassandraKeyValueService kvs) { @Test public void deletingThrows() { - assertThrowsInsufficientConsistencyExceptionAndDoesNotChangeCassandraSchema( + assertThrowsAtlasDbDependencyExceptionAndDoesNotChangeCassandraSchema( () -> getTestKvs().delete(TEST_TABLE, ImmutableMultimap.of(CELL_1_1, TIMESTAMP))); } @Test public void deleteAllTimestampsThrows() { - assertThrowsInsufficientConsistencyExceptionAndDoesNotChangeCassandraSchema(() -> getTestKvs() + assertThrowsAtlasDbDependencyExceptionAndDoesNotChangeCassandraSchema(() -> getTestKvs() .deleteAllTimestamps( TEST_TABLE, ImmutableMap.of( diff --git a/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraClientFactory.java b/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraClientFactory.java index 1193d750f6d..8a4a1ef75fe 100644 --- a/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraClientFactory.java +++ b/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraClientFactory.java @@ -137,8 +137,14 @@ private CassandraClient instrumentClient(Client rawClient) { return client; } - private Cassandra.Client getRawClientWithKeyspaceSet() throws TException { - Client ret = getRawClientWithTimedCreation(); + private Cassandra.Client getRawClientWithKeyspaceSet() { + Client ret; + try { + ret = getRawClientWithTimedCreation(); + } catch (TException e) { + throw CassandraTExceptions.mapToUncheckedException(e); + } + try { ret.set_keyspace(clientConfig.keyspace()); if (log.isDebugEnabled()) { @@ -154,7 +160,10 @@ private Cassandra.Client getRawClientWithKeyspaceSet() throws TException { return ret; } catch (TException e) { ret.getOutputProtocol().getTransport().close(); - throw e; + throw CassandraTExceptions.mapToUncheckedException( + "Failed to create new client for: {}", + e, + SafeArg.of("address", CassandraLogHelper.host(cassandraServer.proxy()))); } } @@ -228,8 +237,8 @@ private static Cassandra.Client getRawClient( addr); } catch (TException e) { client.getOutputProtocol().getTransport().close(); - log.error("Exception thrown attempting to authenticate with config provided credentials", e); - throw e; + throw CassandraTExceptions.mapToUncheckedException( + "Exception thrown attempting to authenticate with config provided credentials", e); } return client; diff --git a/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraKeyValueServiceImpl.java b/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraKeyValueServiceImpl.java index d0c224c108e..42eb895106b 100644 --- a/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraKeyValueServiceImpl.java +++ b/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraKeyValueServiceImpl.java @@ -151,6 +151,7 @@ import org.apache.cassandra.thrift.KsDef; import org.apache.cassandra.thrift.Mutation; import org.apache.cassandra.thrift.SlicePredicate; +import org.apache.cassandra.thrift.TimedOutException; import org.apache.thrift.TException; /** @@ -717,14 +718,18 @@ public Map> apply(CassandraClient client) SafeArg.of("startTs", startTs), SafeArg.of("host", host)); } + Map>> results = Collections.emptyMap(); + try { + results = wrappingQueryRunner.multiget_multislice( + "getRows", + client, + tableRef, + query, + readConsistencyProvider.getConsistency(tableRef)); - Map>> results = - wrappingQueryRunner.multiget_multislice( - "getRows", - client, - tableRef, - query, - readConsistencyProvider.getConsistency(tableRef)); + } catch (TException e) { + throw CassandraTExceptions.mapToUncheckedException(e, SafeArg.of("tableRef", tableRef)); + } return Maps.transformValues(results, CellLoader::flattenReadOnlyLists); } @@ -966,14 +971,18 @@ public RowColumnRangeResult apply(CassandraClient client) throws Exception { startTs); Limit limit = Limit.of(batchColumnRangeSelection.getBatchHint()); SlicePredicate pred = SlicePredicates.create(range, limit); - - Map> results = wrappingQueryRunner.multiget( - "getRowsColumnRange", - client, - tableRef, - wrap(rows), - pred, - readConsistencyProvider.getConsistency(tableRef)); + Map> results = Collections.emptyMap(); + try { + results = wrappingQueryRunner.multiget( + "getRowsColumnRange", + client, + tableRef, + wrap(rows), + pred, + readConsistencyProvider.getConsistency(tableRef)); + } catch (TException e) { + throw new TimedOutException(); + } return RowColumnRangeExtractor.extract(rows, results, startTs, metricsManager); } @@ -985,6 +994,8 @@ public String toString() { + " max columns)"; } }); + } catch (TimedOutException e) { + throw CassandraTExceptions.mapToUncheckedException(e, SafeArg.of("tableRef", tableRef)); } catch (Exception e) { throw Throwables.unwrapAndThrowAtlasDbDependencyException(e); } @@ -1029,15 +1040,19 @@ public TokenBackedBasicResultsPage, byte[]> apply( ByteBuffer rowByteBuffer = ByteBuffer.wrap(row); - Map> results = - wrappingQueryRunner.multiget( - "getRowsColumnRange", - client, - tableRef, - ImmutableList.of(rowByteBuffer), - pred, - readConsistencyProvider.getConsistency(tableRef)); - + Map> results = Collections.emptyMap(); + try { + results = wrappingQueryRunner.multiget( + "getRowsColumnRange", + client, + tableRef, + ImmutableList.of(rowByteBuffer), + pred, + readConsistencyProvider.getConsistency(tableRef)); + } catch (TException e) { + throw CassandraTExceptions.mapToUncheckedException( + e, SafeArg.of("tableRef", tableRef)); + } if (results.isEmpty()) { return SimpleTokenBackedResultsPage.create( startCol, ImmutableList.of(), false); @@ -1715,7 +1730,7 @@ public void deleteRange(final TableReference tableRef, final RangeRequest range) } catch (RetryLimitReachedException e) { throw CassandraUtils.wrapInIceForDeleteOrRethrow(e); } catch (TException e) { - throw Throwables.unwrapAndThrowAtlasDbDependencyException(e); + throw CassandraTExceptions.mapToUncheckedException(e); } } else { super.deleteRange(tableRef, range); @@ -1753,7 +1768,7 @@ public void deleteRows(TableReference tableRef, Iterable rows) { } catch (RetryLimitReachedException e) { throw CassandraUtils.wrapInIceForDeleteOrRethrow(e); } catch (TException e) { - throw Throwables.unwrapAndThrowAtlasDbDependencyException(e); + throw CassandraTExceptions.mapToUncheckedException(e); } } @@ -1891,7 +1906,7 @@ public void deleteFromAtomicTable(TableReference tableRef, Set cells) { try { atomicTableCellDeleter.deleteFromAtomicTable(client, tableRef, cell); } catch (TException e) { - throw Throwables.unwrapAndThrowAtlasDbDependencyException(e); + throw CassandraTExceptions.mapToUncheckedException(e); } } return null; diff --git a/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraNamespaceDeleter.java b/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraNamespaceDeleter.java index 96a118810f8..0b4723b0171 100644 --- a/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraNamespaceDeleter.java +++ b/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraNamespaceDeleter.java @@ -59,7 +59,7 @@ public boolean isNamespaceDeletedSuccessfully() { } catch (NotFoundException e) { return true; } catch (TException e) { - throw Throwables.throwUncheckedException(e); + throw CassandraTExceptions.mapToUncheckedException(e); } } diff --git a/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraNamespaceDeleterFactory.java b/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraNamespaceDeleterFactory.java index 150d8adbacf..c88ebea3ecf 100644 --- a/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraNamespaceDeleterFactory.java +++ b/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraNamespaceDeleterFactory.java @@ -27,7 +27,6 @@ import com.palantir.atlasdb.namespacedeleter.NamespaceDeleterFactory; import com.palantir.atlasdb.spi.KeyValueServiceConfig; import com.palantir.atlasdb.spi.KeyValueServiceRuntimeConfig; -import com.palantir.common.base.Throwables; import com.palantir.refreshable.Refreshable; import java.net.InetSocketAddress; import java.util.Optional; @@ -66,7 +65,7 @@ private static CassandraClient createClient( .orElseThrow(); return CassandraClientFactory.getClientInternal(CassandraServer.of(host), CassandraClientConfig.of(config)); } catch (TException e) { - throw Throwables.rewrapAndThrowUncheckedException(e); + throw CassandraTExceptions.mapToUncheckedException(e); } } } diff --git a/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraTExceptions.java b/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraTExceptions.java new file mode 100644 index 00000000000..b3df3f7a5ec --- /dev/null +++ b/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraTExceptions.java @@ -0,0 +1,52 @@ +/* + * (c) Copyright 2024 Palantir Technologies Inc. All rights reserved. + * + * 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. + */ + +package com.palantir.atlasdb.keyvalue.cassandra; + +import com.google.errorprone.annotations.CompileTimeConstant; +import com.palantir.atlasdb.keyvalue.api.InsufficientConsistencyException; +import com.palantir.common.exception.AtlasDbDependencyException; +import com.palantir.logsafe.Arg; +import org.apache.cassandra.thrift.TimedOutException; +import org.apache.cassandra.thrift.UnavailableException; + +public final class CassandraTExceptions { + private CassandraTExceptions() {} + + public static AtlasDbDependencyException mapToUncheckedException( + @CompileTimeConstant final String logMessage, Throwable throwable, Arg... args) { + if (throwable instanceof TimedOutException) { + return new CassandraTimedOutException(throwable, args); + } + if (throwable instanceof UnavailableException) { + return new InsufficientConsistencyException(logMessage, throwable); + } + if (throwable instanceof InsufficientConsistencyException) { + return new InsufficientConsistencyException(logMessage, throwable); + } + return new AtlasDbDependencyException(throwable); + } + + public static AtlasDbDependencyException mapToUncheckedException(Throwable throwable, Arg... args) { + if (throwable instanceof TimedOutException) { + return new CassandraTimedOutException(throwable, args); + } + if (throwable instanceof UnavailableException) { + return new InsufficientConsistencyException(throwable, args); + } + return new AtlasDbDependencyException(throwable, args); + } +} diff --git a/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraTableTruncator.java b/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraTableTruncator.java index 2a724a261df..02f6aa3a986 100644 --- a/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraTableTruncator.java +++ b/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraTableTruncator.java @@ -18,7 +18,6 @@ import com.palantir.atlasdb.keyvalue.api.TableReference; import com.palantir.common.base.FunctionCheckedException; -import com.palantir.common.base.Throwables; import java.util.Collection; import org.apache.thrift.TException; @@ -36,7 +35,7 @@ void truncateTables(Collection tablesToTruncate) { try { runTruncateInternal(tablesToTruncate); } catch (TException e) { - throw Throwables.unwrapAndThrowAtlasDbDependencyException(e); + throw CassandraTExceptions.mapToUncheckedException(e); } } } diff --git a/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraTimedOutException.java b/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraTimedOutException.java new file mode 100644 index 00000000000..3fbb496d2cc --- /dev/null +++ b/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraTimedOutException.java @@ -0,0 +1,44 @@ +/* + * (c) Copyright 2024 Palantir Technologies Inc. All rights reserved. + * + * 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. + */ + +package com.palantir.atlasdb.keyvalue.cassandra; + +import com.palantir.common.exception.AtlasDbDependencyException; +import com.palantir.logsafe.Arg; +import com.palantir.logsafe.exceptions.SafeExceptions; + +// Added the below suppression because the Runtime class compileTime string check sees the + in the static final as +// non compile time safe. But no other way to achieve as we are using a java version that does not have text blocks. +@SuppressWarnings("CompileTimeConstant") +public class CassandraTimedOutException extends AtlasDbDependencyException { + private static final long serialVersionUID = 1L; + + private static final String LOG_MESSAGE = + "Cassandra query threw a TimedOut exception. Possible reasons and actions to resolve include:\n" + + "1. Reason: AtlasDB clients are requesting too much data from Cassandra.\n" + + " Resolution: Change the query to request less data.\n" + + "2. Reason: Data that has been deleted is being read in the query (e.g. A large amount of" + + " tombstones).\n" + + " Resolution: Check the status of sweep for your client, and if required run a compaction on your" + + " Cassandra server.\n" + + "3. Reason: Cassandra is struggling, possibly due to another large query, server health issues, or a" + + " network outage.\n" + + " Resolution: Ask your CassandraOps to check the state of the Cassandra server."; + + public CassandraTimedOutException(Throwable throwable, Arg... args) { + super(SafeExceptions.renderMessage(LOG_MESSAGE, args), throwable); + } +} diff --git a/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraTimestampBackupRunner.java b/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraTimestampBackupRunner.java index 85e0e82e94a..166f299ebe8 100644 --- a/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraTimestampBackupRunner.java +++ b/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraTimestampBackupRunner.java @@ -20,7 +20,6 @@ import com.palantir.atlasdb.AtlasDbConstants; import com.palantir.atlasdb.encoding.PtBytes; import com.palantir.common.annotation.Idempotent; -import com.palantir.common.base.Throwables; import com.palantir.logsafe.Preconditions; import com.palantir.logsafe.SafeArg; import com.palantir.logsafe.logger.SafeLogger; @@ -185,7 +184,7 @@ private CqlResult executeQueryUnchecked(CassandraClient client, CqlQuery query) AtlasDbConstants.TIMESTAMP_TABLE, () -> client.execute_cql3_query(query, Compression.NONE, ConsistencyLevel.QUORUM)); } catch (TException e) { - throw Throwables.rewrapAndThrowUncheckedException(e); + throw CassandraTExceptions.mapToUncheckedException(e); } } diff --git a/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraUtils.java b/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraUtils.java index 9d553ffc1ea..e2d0f125be1 100644 --- a/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraUtils.java +++ b/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraUtils.java @@ -42,7 +42,8 @@ public static FunctionCheckedException, Except public static AtlasDbDependencyException wrapInIceForDeleteOrRethrow(RetryLimitReachedException ex) { if (ex.suppressed(UnavailableException.class) || ex.suppressed(InsufficientConsistencyException.class)) { - throw new InsufficientConsistencyException("Deleting requires all Cassandra nodes to be available.", ex); + throw CassandraTExceptions.mapToUncheckedException( + "Deleting requires all Cassandra nodes to be available.", ex); } throw ex; } diff --git a/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraVerifier.java b/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraVerifier.java index 3c90ae8173f..7373351428d 100644 --- a/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraVerifier.java +++ b/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CassandraVerifier.java @@ -35,7 +35,6 @@ import com.palantir.atlasdb.keyvalue.cassandra.CassandraClientFactory.CassandraClientConfig; import com.palantir.atlasdb.keyvalue.cassandra.pool.CassandraServer; import com.palantir.common.base.FunctionCheckedException; -import com.palantir.common.base.Throwables; import com.palantir.logsafe.DoNotLog; import com.palantir.logsafe.Preconditions; import com.palantir.logsafe.SafeArg; @@ -90,7 +89,7 @@ static Set sanityCheckDatacenters(CassandraClient client, CassandraVerif return sanityCheckDatacentersInternal( client, verifierConfig.replicationFactor(), verifierConfig.ignoreNodeTopologyChecks()); } catch (TException e) { - throw Throwables.throwUncheckedException(e); + throw CassandraTExceptions.mapToUncheckedException(e); } }); } diff --git a/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CellRangeDeleter.java b/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CellRangeDeleter.java index 1788a56e922..676285f2bd7 100644 --- a/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CellRangeDeleter.java +++ b/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CellRangeDeleter.java @@ -97,6 +97,8 @@ public String toString() { }); } catch (RetryLimitReachedException e) { throw CassandraUtils.wrapInIceForDeleteOrRethrow(e); + } catch (TException e) { + throw CassandraTExceptions.mapToUncheckedException(e); } catch (Exception e) { throw Throwables.unwrapAndThrowAtlasDbDependencyException(e); } diff --git a/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CqlExecutorImpl.java b/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CqlExecutorImpl.java index da7162be76f..3438cfa3878 100644 --- a/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CqlExecutorImpl.java +++ b/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/CqlExecutorImpl.java @@ -270,7 +270,7 @@ public CqlPreparedResult prepare(ByteBuffer query, byte[] rowHintForHostSelectio hostsPerPreparedQuery.put(preparedResult.getItemId(), hostForRow); return preparedResult; } catch (TException e) { - throw Throwables.throwUncheckedException(e); + throw CassandraTExceptions.mapToUncheckedException(e); } } @@ -304,7 +304,7 @@ private CqlResult executeFunctionOnHost( } throw e; } catch (TException e) { - throw Throwables.throwUncheckedException(e); + throw CassandraTExceptions.mapToUncheckedException(e, SafeArg.of("server", cassandraServer)); } } diff --git a/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/TracingQueryRunner.java b/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/TracingQueryRunner.java index eccb9734f7b..a6db28b8783 100644 --- a/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/TracingQueryRunner.java +++ b/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/TracingQueryRunner.java @@ -53,7 +53,7 @@ public V run(CassandraClient client, Set tableRefs, Action V trace(Action action, CassandraClient client, Set } catch (TException e) { failed = true; logFailedCall(tableRefs); - throw e; + throw CassandraTExceptions.mapToUncheckedException(e); } finally { long duration = stopwatch.elapsed(TimeUnit.MILLISECONDS); logTraceResults(duration, tableRefs, traceId, failed); diff --git a/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/WrappingQueryRunner.java b/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/WrappingQueryRunner.java index bc380f28dc1..803dbf366ec 100644 --- a/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/WrappingQueryRunner.java +++ b/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/WrappingQueryRunner.java @@ -54,8 +54,9 @@ Void batchMutate( return null; }); } catch (UnavailableException e) { - throw new InsufficientConsistencyException( - "This batch mutate operation requires {} Cassandra nodes to be up and available.", + throw CassandraTExceptions.mapToUncheckedException( + "Batch mutate operation requires a sufficient number of nodes to be up. Check that the consistency" + + " level of {} is adequate.", e, SafeArg.of("consistency", consistency)); } @@ -75,8 +76,9 @@ Map> multiget( tableRef, () -> client.multiget_slice(kvsMethodName, tableRef, rowNames, pred, consistency)); } catch (UnavailableException e) { - throw new InsufficientConsistencyException( - "This get operation requires {} Cassandra nodes to be up and available.", + throw CassandraTExceptions.mapToUncheckedException( + "This get operation requires a sufficient number of nodes to be up. Check that the consistency" + + " level of {} is adequate.", e, SafeArg.of("consistency", consistency)); } @@ -93,8 +95,9 @@ Map>> multiget_multislice( return queryRunner.run( client, tableRef, () -> client.multiget_multislice(kvsMethodName, tableRef, request, consistency)); } catch (UnavailableException e) { - throw new InsufficientConsistencyException( - "This get operation requires {} Cassandra nodes to be up and available.", + throw CassandraTExceptions.mapToUncheckedException( + "This get operation requires a sufficient number of nodes to be up. Check that the consistency" + + " level of {} is adequate.", e, SafeArg.of("consistency", consistency)); } diff --git a/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/cas/CheckAndSetRunner.java b/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/cas/CheckAndSetRunner.java index a5f6b6e5979..8206503b3b7 100644 --- a/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/cas/CheckAndSetRunner.java +++ b/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/cas/CheckAndSetRunner.java @@ -17,9 +17,9 @@ import com.google.protobuf.ByteString; import com.palantir.atlasdb.keyvalue.api.CheckAndSetRequest; -import com.palantir.atlasdb.keyvalue.api.InsufficientConsistencyException; import com.palantir.atlasdb.keyvalue.api.TableReference; import com.palantir.atlasdb.keyvalue.cassandra.CassandraClient; +import com.palantir.atlasdb.keyvalue.cassandra.CassandraTExceptions; import com.palantir.atlasdb.keyvalue.cassandra.TracingQueryRunner; import com.palantir.atlasdb.keyvalue.impl.CheckAndSetResult; import com.palantir.logsafe.SafeArg; @@ -48,8 +48,8 @@ public CheckAndSetResult executeCheckAndSet(CassandraClient client, CheckAndSetQueries.getQueryForRequest(request), Compression.NONE, writeConsistency)); return CheckAndSetResponseDecoder.decodeCqlResult(result); } catch (UnavailableException e) { - throw new InsufficientConsistencyException( - "Check-and-set requires {} Cassandra nodes to be up and available.", + throw CassandraTExceptions.mapToUncheckedException( + "Check-and-set requires Cassandra nodes to be up and available. Check these nodes: ", e, SafeArg.of("writeConsistency", writeConsistency)); } diff --git a/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/paging/RowGetter.java b/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/paging/RowGetter.java index 40acdfd0ff6..8e1eb5f19ba 100644 --- a/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/paging/RowGetter.java +++ b/atlasdb-cassandra/src/main/java/com/palantir/atlasdb/keyvalue/cassandra/paging/RowGetter.java @@ -15,10 +15,10 @@ */ package com.palantir.atlasdb.keyvalue.cassandra.paging; -import com.palantir.atlasdb.keyvalue.api.InsufficientConsistencyException; import com.palantir.atlasdb.keyvalue.api.TableReference; import com.palantir.atlasdb.keyvalue.cassandra.CassandraClient; import com.palantir.atlasdb.keyvalue.cassandra.CassandraClientPool; +import com.palantir.atlasdb.keyvalue.cassandra.CassandraTExceptions; import com.palantir.atlasdb.keyvalue.cassandra.TracingQueryRunner; import com.palantir.atlasdb.keyvalue.cassandra.pool.CassandraServer; import com.palantir.atlasdb.keyvalue.cassandra.thrift.SlicePredicates; @@ -62,8 +62,8 @@ public List apply(CassandraClient client) { () -> client.get_range_slices( kvsMethodName, tableRef, slicePredicate, keyRange, consistency)); } catch (UnavailableException e) { - throw new InsufficientConsistencyException( - "get_range_slices requires {} Cassandra nodes to be up and available.", + throw CassandraTExceptions.mapToUncheckedException( + "get_range_slices requires Cassandra nodes to be up and available. Check Cassandra nodes: ", e, SafeArg.of("consistency", consistency)); } catch (Exception e) { diff --git a/changelog/@unreleased/pr-7353.v2.yml b/changelog/@unreleased/pr-7353.v2.yml new file mode 100644 index 00000000000..3e8570f9b0f --- /dev/null +++ b/changelog/@unreleased/pr-7353.v2.yml @@ -0,0 +1,10 @@ +type: improvement +improvement: + description: |- + New Exception classes: + - CassandraTExceptions() + - CassandraTimedOutException() + + Amended how UnavailableException Thrift Cassandra native Exceptions are caught, and they now get mapped to InsufficientConsistencyException() via CassandraTExceptions(). + links: + - https://github.com/palantir/atlasdb/pull/7353