Skip to content
Merged
Show file tree
Hide file tree
Changes from 2 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -59,7 +59,7 @@ private <R> R runTransaction(final AsyncWork<R> work) {
try {
return work.doWorkAsync(transaction).get();
} catch (ExecutionException e) {
throw SpannerExceptionFactory.newSpannerException(e.getCause());
throw SpannerExceptionFactory.asSpannerException(e.getCause());
} catch (InterruptedException e) {
throw SpannerExceptionFactory.propagateInterrupt(e);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -123,7 +123,7 @@ private ApiFuture<TransactionContext> internalBeginAsync(
@Override
public void onFailure(Throwable t) {
onError(t);
res.setException(SpannerExceptionFactory.newSpannerException(t));
res.setException(SpannerExceptionFactory.asSpannerException(t));
}

@Override
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@

package com.google.cloud.spanner;

import static com.google.cloud.spanner.SpannerExceptionFactory.newSpannerException;
import static com.google.cloud.spanner.SpannerExceptionFactory.asSpannerException;
import static com.google.common.base.Preconditions.checkState;

import com.google.api.core.InternalApi;
Expand Down Expand Up @@ -76,7 +76,7 @@ protected GrpcStruct currRow() {
@Override
public boolean next() throws SpannerException {
if (error != null) {
throw newSpannerException(error);
throw asSpannerException(error);
}
try {
if (currRow == null) {
Expand Down Expand Up @@ -108,7 +108,7 @@ public boolean next() throws SpannerException {
return hasNext;
} catch (Throwable t) {
throw yieldError(
SpannerExceptionFactory.asSpannerException(t),
asSpannerException(t),
iterator.isWithBeginTransaction() && currRow == null,
iterator.isLastStatement());
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -155,7 +155,7 @@ protected final PartialResultSet computeNext() {
call = null;

if (error != null) {
throw SpannerExceptionFactory.newSpannerException(error);
throw SpannerExceptionFactory.asSpannerException(error);
}

endOfData();
Expand Down Expand Up @@ -192,25 +192,17 @@ public void onCompleted() {
}

@Override
public void onError(SpannerException e) {
public void onError(SpannerException exception) {
if (statement != null) {
if (logger.isLoggable(Level.FINEST)) {
// Include parameter values if logging level is set to FINEST or higher.
e =
SpannerExceptionFactory.newSpannerExceptionPreformatted(
e.getErrorCode(),
String.format("%s - Statement: '%s'", e.getMessage(), statement.toString()),
e);
logger.log(Level.FINEST, "Error executing statement", e);
exception.setStatement(statement.toString());
logger.log(Level.FINEST, "Error executing statement", exception);
} else {
e =
SpannerExceptionFactory.newSpannerExceptionPreformatted(
e.getErrorCode(),
String.format("%s - Statement: '%s'", e.getMessage(), statement.getSql()),
e);
exception.setStatement(statement.getSql());
}
}
error = e;
error = exception;
addToStream(END_OF_STREAM);
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -498,7 +498,7 @@ private void verifyBeginTransactionWithRWOnMultiplexedSessionAsync(String sessio
}
readWriteBeginTransactionReferenceFuture.set(txn);
} catch (Exception e) {
SpannerException spannerException = SpannerExceptionFactory.newSpannerException(e);
SpannerException spannerException = SpannerExceptionFactory.asSpannerException(e);
// Mark multiplexed sessions for RW as unimplemented and fall back to regular sessions
// if UNIMPLEMENTED is returned.
maybeMarkUnimplementedForRW(spannerException);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@ public static <T> T getOrNull(ApiFuture<T> future) throws SpannerException {
if (e.getCause() instanceof SpannerException) {
throw (SpannerException) e.getCause();
}
throw SpannerExceptionFactory.newSpannerException(e.getCause());
throw SpannerExceptionFactory.asSpannerException(e.getCause());
} catch (InterruptedException e) {
throw SpannerExceptionFactory.propagateInterrupt(e, null /*TODO: requestId*/);
} catch (CancellationException e) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -55,10 +55,12 @@ public String getResourceName() {
private static final long serialVersionUID = 20150916L;
private static final Metadata.Key<RetryInfo> KEY_RETRY_INFO =
ProtoUtils.keyForProto(RetryInfo.getDefaultInstance());
private static final String PG_ERR_CODE_KEY = "pg_sqlerrcode";

private final ErrorCode code;
private final ApiException apiException;
private XGoogSpannerRequestId requestId;
private String statement;

/** Private constructor. Use {@link SpannerExceptionFactory} to create instances. */
SpannerException(
Expand Down Expand Up @@ -99,11 +101,31 @@ public String getResourceName() {
this.requestId = requestId;
}

@Override
public String getMessage() {
if (this.statement == null) {
return super.getMessage();
}
return String.format("%s - Statement: '%s'", super.getMessage(), this.statement);
}

/** Returns the error code associated with this exception. */
public ErrorCode getErrorCode() {
return code;
}

/**
* Returns the PostgreSQL SQLState error code that is encoded in this exception, or null if this
* {@link SpannerException} does not include a PostgreSQL error code.
*/
public String getPostgreSQLErrorCode() {
ErrorDetails details = getErrorDetails();
if (details == null || details.getErrorInfo() == null) {
return null;
}
return details.getErrorInfo().getMetadataOrDefault(PG_ERR_CODE_KEY, null);
}

public String getRequestId() {
if (requestId == null) {
return "";
Expand Down Expand Up @@ -199,6 +221,10 @@ public ErrorDetails getErrorDetails() {
return null;
}

void setStatement(String statement) {
this.statement = statement;
}

/** Sets the requestId. */
@InternalApi
public void setRequestId(XGoogSpannerRequestId reqId) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -281,7 +281,7 @@ void ensureTxn() {
try {
ensureTxnAsync().get();
} catch (ExecutionException e) {
throw SpannerExceptionFactory.newSpannerException(e.getCause() == null ? e : e.getCause());
throw SpannerExceptionFactory.asSpannerException(e.getCause() == null ? e : e.getCause());
} catch (InterruptedException e) {
throw SpannerExceptionFactory.propagateInterrupt(e);
}
Expand Down Expand Up @@ -370,7 +370,7 @@ void commit() {
throw SpannerExceptionFactory.propagateTimeout((TimeoutException) e);
}
} catch (ExecutionException e) {
throw SpannerExceptionFactory.newSpannerException(e.getCause() == null ? e : e.getCause());
throw SpannerExceptionFactory.asSpannerException(e.getCause() == null ? e : e.getCause());
}
}

Expand Down Expand Up @@ -679,7 +679,7 @@ options, getPreviousTransactionId())))
aborted = true;
}
}
throw SpannerExceptionFactory.newSpannerException(e.getCause());
throw SpannerExceptionFactory.asSpannerException(e.getCause());
} catch (TimeoutException e) {
// Throw an ABORTED exception to force a retry of the transaction if no transaction
// has been returned by the first statement.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -74,7 +74,7 @@ protected Class<?> resolveClass(ObjectStreamClass desc)
throw SpannerExceptionFactory.newSpannerException(
ErrorCode.INVALID_ARGUMENT, invalidClassException.getMessage(), invalidClassException);
} catch (Exception exception) {
throw SpannerExceptionFactory.newSpannerException(exception);
throw SpannerExceptionFactory.asSpannerException(exception);
}
}

Expand All @@ -90,7 +90,7 @@ public static String encodeToString(BatchTransactionId transactionId, Partition
new ObjectOutputStream(new GZIPOutputStream(byteArrayOutputStream))) {
objectOutputStream.writeObject(id);
} catch (Exception exception) {
throw SpannerExceptionFactory.newSpannerException(exception);
throw SpannerExceptionFactory.asSpannerException(exception);
}
return Base64.getUrlEncoder().encodeToString(byteArrayOutputStream.toByteArray());
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@

package com.google.cloud.spanner.spi.v1;

import static com.google.cloud.spanner.SpannerExceptionFactory.asSpannerException;
import static com.google.cloud.spanner.SpannerExceptionFactory.newSpannerException;
import static com.google.cloud.spanner.ThreadFactoryUtil.tryCreateVirtualThreadPerTaskExecutor;

Expand Down Expand Up @@ -538,7 +539,7 @@ public <RequestT, ResponseT> UnaryCallable<RequestT, ResponseT> createUnaryCalla
// is actually running.
checkEmulatorConnection(options, channelProvider, credentialsProvider, emulatorHost);
} catch (Exception e) {
throw newSpannerException(e);
throw asSpannerException(e);
}
} else {
this.databaseAdminStub = null;
Expand Down Expand Up @@ -726,7 +727,7 @@ private <T> T runWithRetryOnAdministrativeRequestsExceeded(Callable<T> callable)
new AdminRequestsLimitExceededRetryAlgorithm<>(),
NanoClock.getDefaultClock());
} catch (RetryHelperException e) {
throw SpannerExceptionFactory.asSpannerException(e.getCause());
throw asSpannerException(e.getCause());
}
}

Expand Down Expand Up @@ -1317,7 +1318,7 @@ public OperationFuture<Empty, UpdateDatabaseDdlMetadata> updateDatabaseDdl(
throw newSpannerException(e);
} catch (ExecutionException e) {
Throwable t = e.getCause();
SpannerException se = SpannerExceptionFactory.asSpannerException(t);
SpannerException se = asSpannerException(t);
if (se instanceof AdminRequestsPerMinuteExceededException) {
// Propagate this to trigger a retry.
throw se;
Expand Down Expand Up @@ -1983,8 +1984,12 @@ private static <T> T get(final Future<T> future) throws SpannerException {
// We are the sole consumer of the future, so cancel it.
future.cancel(true);
throw SpannerExceptionFactory.propagateInterrupt(e);
} catch (Exception e) {
} catch (ExecutionException e) {
throw asSpannerException(e.getCause());
} catch (CancellationException e) {
throw newSpannerException(context, e, null);
} catch (Exception exception) {
throw asSpannerException(exception);
}
}

Expand Down Expand Up @@ -2222,7 +2227,7 @@ public void onError(Throwable t) {
if (this.consumer.cancelQueryWhenClientIsClosed()) {
unregisterResponseObserver(this);
}
consumer.onError(newSpannerException(t));
consumer.onError(asSpannerException(t));
}

@Override
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@
import static java.util.Arrays.asList;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertThrows;
import static org.junit.Assert.assertTrue;
import static org.junit.Assert.fail;
import static org.junit.Assume.assumeFalse;
Expand Down Expand Up @@ -131,16 +132,21 @@ public void simple() {

@Test
public void badQuery() {
try {
execute(Statement.of("SELECT Apples AND Oranges"), Type.int64());
fail("Expected exception");
} catch (SpannerException ex) {
assertThat(ex.getErrorCode()).isEqualTo(ErrorCode.INVALID_ARGUMENT);
if (dialect.dialect == Dialect.POSTGRESQL) {
assertThat(ex.getMessage()).contains("column \"apples\" does not exist");
} else {
assertThat(ex.getMessage()).contains("Unrecognized name: Apples");
}
SpannerException exception =
assertThrows(
SpannerException.class,
() -> execute(Statement.of("SELECT Apples AND Oranges"), Type.int64()));
assertEquals(ErrorCode.INVALID_ARGUMENT, exception.getErrorCode());
if (dialect.dialect == Dialect.POSTGRESQL) {
assertTrue(
exception.getMessage(),
exception.getMessage().contains("column \"apples\" does not exist"));
// See https://www.postgresql.org/docs/current/errcodes-appendix.html
// '42703' == undefined_column
assertEquals("42703", exception.getPostgreSQLErrorCode());
} else {
assertTrue(
exception.getMessage(), exception.getMessage().contains("Unrecognized name: Apples"));
}
}

Expand Down
Loading