use of com.scalar.db.api.Mutation in project scalardb by scalar-labs.
the class BatchHandler method execute.
private ResultSet execute(List<? extends Mutation> mutations) {
BatchStatement batch = new BatchStatement();
BatchComposer composer = new BatchComposer(batch, handlers);
boolean conditional = false;
for (Mutation mutation : mutations) {
if (mutation.getCondition().isPresent()) {
conditional = true;
}
// appropriate statement handler is selected here
mutation.accept(composer);
}
if (conditional) {
setConsistencyForConditionalMutation(batch);
}
return session.execute(batch);
}
use of com.scalar.db.api.Mutation in project scalardb by scalar-labs.
the class DynamoMutation method getCondition.
@Nonnull
public String getCondition() {
ConditionExpressionBuilder builder = new ConditionExpressionBuilder(CONDITION_COLUMN_NAME_ALIAS, CONDITION_VALUE_ALIAS);
Mutation mutation = (Mutation) getOperation();
mutation.getCondition().ifPresent(c -> c.accept(builder));
return builder.build();
}
use of com.scalar.db.api.Mutation in project scalardb by scalar-labs.
the class CosmosMutation method getMutationType.
@Nonnull
public MutationType getMutationType() {
Mutation mutation = (Mutation) getOperation();
if (!mutation.getCondition().isPresent()) {
if (mutation instanceof Put) {
return MutationType.PUT;
} else {
return MutationType.DELETE_IF;
}
}
MutationCondition condition = mutation.getCondition().get();
if (condition instanceof PutIfNotExists) {
return MutationType.PUT_IF_NOT_EXISTS;
} else if (condition instanceof PutIfExists || condition instanceof PutIf) {
return MutationType.PUT_IF;
} else {
return MutationType.DELETE_IF;
}
}
use of com.scalar.db.api.Mutation in project scalardb by scalar-labs.
the class CosmosMutation method makeConditionalQuery.
@Nonnull
public String makeConditionalQuery() {
Mutation mutation = (Mutation) getOperation();
SelectConditionStep<org.jooq.Record> select;
if (isPrimaryKeySpecified()) {
String id = getId();
select = DSL.using(SQLDialect.DEFAULT).selectFrom("Record r").where(DSL.field("r.id").eq(id));
} else {
String concatenatedPartitionKey = getConcatenatedPartitionKey();
select = DSL.using(SQLDialect.DEFAULT).selectFrom("Record r").where(DSL.field("r.concatenatedPartitionKey").eq(concatenatedPartitionKey));
mutation.getClusteringKey().ifPresent(k -> {
ValueBinder binder = new ValueBinder();
k.getColumns().forEach(c -> {
Field<Object> field = DSL.field("r.clusteringKey" + quoteKeyword(c.getName()));
binder.set(s -> select.and(field.equal(s)));
c.accept(binder);
});
});
}
ConditionalQueryBuilder builder = new ConditionalQueryBuilder(select);
mutation.getCondition().ifPresent(c -> c.accept(builder));
return builder.getQuery();
}
use of com.scalar.db.api.Mutation in project scalardb by scalar-labs.
the class MutateStatementHandler method handle.
/**
* Executes the specified {@link Mutation} {@link Operation}
*
* @param operation {@link Mutation} operation
* @return a {@code ResultSet}
* @throws RetriableExecutionException if the execution failed, but it can be retriable
* @throws ReadRepairableExecutionException if the execution partially failed, which can be
* repaired by a following read
*/
@Override
@Nonnull
public ResultSet handle(Operation operation) throws ExecutionException {
try {
ResultSet results = handleInternal(operation);
Mutation mutation = (Mutation) operation;
if (mutation.getCondition().isPresent() && !results.one().getBool(0)) {
throw new NoMutationException("no mutation was applied.");
}
return results;
} catch (WriteTimeoutException e) {
LOGGER.warn("write timeout happened during mutate operation.", e);
if (e.getWriteType() == WriteType.CAS) {
// retry needs to be done if applications need to do the operation exactly
throw new RetriableExecutionException("paxos phase in CAS operation failed.", e);
} else if (e.getWriteType() == WriteType.SIMPLE) {
Mutation mutation = (Mutation) operation;
if (mutation.getCondition().isPresent()) {
// learn phase needs to be repaired (by re-reading)
throw new ReadRepairableExecutionException("learn phase in CAS operation failed.", e);
} else {
// retry needs to be done if applications need to do the operation exactly
throw new RetriableExecutionException("simple write operation failed.", e);
}
} else {
throw new ExecutionException("something wrong because it is neither CAS nor SIMPLE", e);
}
} catch (RuntimeException e) {
LOGGER.warn(e.getMessage(), e);
throw new RetriableExecutionException(e.getMessage(), e);
}
}
Aggregations