You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@accumulo.apache.org by kt...@apache.org on 2013/07/17 14:58:18 UTC
[04/10] git commit: ACCUMULO-1000 initial checkin of conditional
mutations that does locking on tablet server. The implementation is pretty
far along, but still a good bit to do.
ACCUMULO-1000 initial checkin of conditional mutations that does locking on tablet server. The implementation is pretty far along, but still a good bit to do.
Project: http://git-wip-us.apache.org/repos/asf/accumulo/repo
Commit: http://git-wip-us.apache.org/repos/asf/accumulo/commit/49a7626c
Tree: http://git-wip-us.apache.org/repos/asf/accumulo/tree/49a7626c
Diff: http://git-wip-us.apache.org/repos/asf/accumulo/diff/49a7626c
Branch: refs/heads/ACCUMULO-1000
Commit: 49a7626c359a5f25a2f8c103f4909d83c40ab4f0
Parents: 8d49260
Author: Keith Turner <kt...@apache.org>
Authored: Mon Jul 15 13:36:28 2013 -0400
Committer: Keith Turner <kt...@apache.org>
Committed: Mon Jul 15 13:36:28 2013 -0400
----------------------------------------------------------------------
.../accumulo/core/client/ConditionalWriter.java | 97 ++
.../apache/accumulo/core/client/Connector.java | 16 +
.../core/client/impl/ConditionalWriterImpl.java | 380 +++++
.../core/client/impl/ConnectorImpl.java | 9 +-
.../client/impl/TabletServerBatchWriter.java | 2 +
.../core/client/mock/MockConnector.java | 7 +
.../apache/accumulo/core/data/Condition.java | 148 ++
.../accumulo/core/data/ConditionalMutation.java | 77 +
.../accumulo/core/data/thrift/TCMResult.java | 516 ++++++
.../accumulo/core/data/thrift/TCMStatus.java | 67 +
.../accumulo/core/data/thrift/TCondition.java | 1306 ++++++++++++++
.../core/data/thrift/TConditionalMutation.java | 659 +++++++
.../thrift/TabletClientService.java | 1603 ++++++++++++++++--
.../accumulo/core/util/ByteBufferUtil.java | 13 +
core/src/main/thrift/data.thrift | 31 +
core/src/main/thrift/tabletserver.thrift | 4 +-
.../server/data/ServerConditionalMutation.java | 58 +
.../tabletserver/ConditionalMutationSet.java | 91 +
.../accumulo/server/tabletserver/RowLocks.java | 162 ++
.../server/tabletserver/TabletServer.java | 202 +++
.../accumulo/test/FaultyConditionalWriter.java | 85 +
.../test/performance/thrift/NullTserver.java | 8 +
.../accumulo/test/ConditionalWriterTest.java | 740 ++++++++
23 files changed, 6129 insertions(+), 152 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/accumulo/blob/49a7626c/core/src/main/java/org/apache/accumulo/core/client/ConditionalWriter.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/accumulo/core/client/ConditionalWriter.java b/core/src/main/java/org/apache/accumulo/core/client/ConditionalWriter.java
new file mode 100644
index 0000000..a23abcf
--- /dev/null
+++ b/core/src/main/java/org/apache/accumulo/core/client/ConditionalWriter.java
@@ -0,0 +1,97 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You 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 org.apache.accumulo.core.client;
+
+import java.util.Iterator;
+import java.util.concurrent.TimeUnit;
+
+import org.apache.accumulo.core.data.ConditionalMutation;
+
+/**
+ * @since 1.6.0
+ */
+public interface ConditionalWriter {
+ public static class Result {
+
+ private Status status;
+ private ConditionalMutation mutation;
+
+ public Result(Status s, ConditionalMutation m) {
+ this.status = s;
+ this.mutation = m;
+ }
+
+ public Status getStatus() {
+ return status;
+ }
+
+ public ConditionalMutation getMutation() {
+ return mutation;
+ }
+ }
+
+ public static enum Status {
+ /**
+ * conditions were met and mutation was written
+ */
+ ACCEPTED,
+ /**
+ * conditions were not met and mutation was not written
+ */
+ REJECTED,
+ /**
+ * mutation violated a constraint and was not written
+ */
+ VIOLATED,
+ /**
+ * error occurred after mutation was sent to server, its unknown if the mutation was written
+ */
+ UNKNOWN,
+ /**
+ * A condition contained a column visibility that could never be seen
+ */
+ INVISIBLE_VISIBILITY,
+ /**
+ * nothing was done with this mutation, this is caused by previous mutations failing in some way like timing out
+ */
+ IGNORED
+ }
+
+ public abstract Iterator<Result> write(Iterator<ConditionalMutation> mutations);
+
+ public abstract Result write(ConditionalMutation mutation);
+
+ /**
+ * This setting determines how long a scanner will automatically retry when a failure occurs. By default a scanner will retry forever.
+ *
+ * Setting to zero or Long.MAX_VALUE and TimeUnit.MILLISECONDS means to retry forever.
+ *
+ * @param timeOut
+ * @param timeUnit
+ * determines how timeout is interpreted
+ */
+ public void setTimeout(long timeOut, TimeUnit timeUnit);
+
+ /**
+ * Returns the setting for how long a scanner will automatically retry when a failure occurs.
+ *
+ * @return the timeout configured for this scanner
+ */
+ public long getTimeout(TimeUnit timeUnit);
+
+}
http://git-wip-us.apache.org/repos/asf/accumulo/blob/49a7626c/core/src/main/java/org/apache/accumulo/core/client/Connector.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/accumulo/core/client/Connector.java b/core/src/main/java/org/apache/accumulo/core/client/Connector.java
index d2e7321..45a8162 100644
--- a/core/src/main/java/org/apache/accumulo/core/client/Connector.java
+++ b/core/src/main/java/org/apache/accumulo/core/client/Connector.java
@@ -174,6 +174,22 @@ public abstract class Connector {
public abstract Scanner createScanner(String tableName, Authorizations authorizations) throws TableNotFoundException;
/**
+ * Factory method to create a ConditionalWriter connected to Accumulo.
+ *
+ * @param tableName
+ * the name of the table to query data from
+ * @param authorizations
+ * A set of authorization labels that will be checked against the column visibility of each key in order to filter data. The authorizations passed in
+ * must be a subset of the accumulo user's set of authorizations. If the accumulo user has authorizations (A1, A2) and authorizations (A2, A3) are
+ * passed, then an exception will be thrown.
+ *
+ * @return ConditionalWriter object for writing ConditionalMutations
+ * @throws TableNotFoundException
+ * when the specified table doesn't exist
+ */
+ public abstract ConditionalWriter createConditionalWriter(String tableName, Authorizations authorizations) throws TableNotFoundException;
+
+ /**
* Accessor method for internal instance object.
*
* @return the internal instance object
http://git-wip-us.apache.org/repos/asf/accumulo/blob/49a7626c/core/src/main/java/org/apache/accumulo/core/client/impl/ConditionalWriterImpl.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/accumulo/core/client/impl/ConditionalWriterImpl.java b/core/src/main/java/org/apache/accumulo/core/client/impl/ConditionalWriterImpl.java
new file mode 100644
index 0000000..73aa480
--- /dev/null
+++ b/core/src/main/java/org/apache/accumulo/core/client/impl/ConditionalWriterImpl.java
@@ -0,0 +1,380 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You 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 org.apache.accumulo.core.client.impl;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Map;
+import java.util.Map.Entry;
+import java.util.Set;
+import java.util.concurrent.TimeUnit;
+
+import org.apache.accumulo.core.client.AccumuloException;
+import org.apache.accumulo.core.client.AccumuloSecurityException;
+import org.apache.accumulo.core.client.ConditionalWriter;
+import org.apache.accumulo.core.client.Instance;
+import org.apache.accumulo.core.client.IteratorSetting;
+import org.apache.accumulo.core.client.TableNotFoundException;
+import org.apache.accumulo.core.client.impl.TabletLocator.TabletServerMutations;
+import org.apache.accumulo.core.data.ByteSequence;
+import org.apache.accumulo.core.data.Condition;
+import org.apache.accumulo.core.data.ConditionalMutation;
+import org.apache.accumulo.core.data.KeyExtent;
+import org.apache.accumulo.core.data.Mutation;
+import org.apache.accumulo.core.data.thrift.IterInfo;
+import org.apache.accumulo.core.data.thrift.TCMResult;
+import org.apache.accumulo.core.data.thrift.TCMStatus;
+import org.apache.accumulo.core.data.thrift.TCondition;
+import org.apache.accumulo.core.data.thrift.TConditionalMutation;
+import org.apache.accumulo.core.data.thrift.TKeyExtent;
+import org.apache.accumulo.core.data.thrift.TMutation;
+import org.apache.accumulo.core.security.Authorizations;
+import org.apache.accumulo.core.security.ColumnVisibility;
+import org.apache.accumulo.core.security.VisibilityEvaluator;
+import org.apache.accumulo.core.security.VisibilityParseException;
+import org.apache.accumulo.core.security.thrift.TCredentials;
+import org.apache.accumulo.core.tabletserver.thrift.TabletClientService;
+import org.apache.accumulo.core.util.BadArgumentException;
+import org.apache.accumulo.core.util.ByteBufferUtil;
+import org.apache.accumulo.core.util.ThriftUtil;
+import org.apache.accumulo.core.util.UtilWaitThread;
+import org.apache.accumulo.trace.instrument.Tracer;
+import org.apache.accumulo.trace.thrift.TInfo;
+import org.apache.commons.collections.map.LRUMap;
+import org.apache.commons.lang.mutable.MutableLong;
+import org.apache.hadoop.io.Text;
+import org.apache.thrift.TApplicationException;
+import org.apache.thrift.TException;
+import org.apache.thrift.TServiceClient;
+import org.apache.thrift.transport.TTransportException;
+
+
+class ConditionalWriterImpl implements ConditionalWriter {
+
+ private Text tableId;
+ private Authorizations auths;
+ private VisibilityEvaluator ve;
+ private Map cache;
+ private Instance instance;
+ private TCredentials credentials;
+
+ ConditionalWriterImpl(Instance instance, TCredentials credentials, String tableId, Authorizations authorizations) {
+ cache = Collections.synchronizedMap(new LRUMap(1000));
+ this.instance = instance;
+ this.credentials = credentials;
+ this.tableId = new Text(tableId);
+ this.auths = authorizations;
+ this.ve = new VisibilityEvaluator(authorizations);
+ }
+
+ public Iterator<Result> write(Iterator<ConditionalMutation> mutations) {
+
+
+ TabletLocator locator = TabletLocator.getLocator(instance, tableId);
+
+ List<Mutation> mutationList = new ArrayList<Mutation>();
+
+ ArrayList<Result> results = new ArrayList<Result>();
+
+ mloop: while (mutations.hasNext()) {
+ ConditionalMutation mut = mutations.next();
+
+ for (Condition cond : mut.getConditions()) {
+ if (!isVisible(cond.getVisibility())) {
+ results.add(new Result(Status.INVISIBLE_VISIBILITY, mut));
+ continue mloop;
+ }
+ }
+
+ mutationList.add(mut);
+ }
+
+ try {
+ List<Mutation> ignored = (List<Mutation>) (ArrayList<? extends Mutation>) sendToServers(locator, mutationList, results);
+
+ while (ignored.size() > 0) {
+ // TODO requeue ignored and return whats done for iteration
+ ignored = (List<Mutation>) (ArrayList<? extends Mutation>) sendToServers(locator, ignored, results);
+ }
+
+ return results.iterator();
+ } catch (AccumuloException e) {
+ // TODO Auto-generated catch block
+ e.printStackTrace();
+ } catch (AccumuloSecurityException e) {
+ // TODO Auto-generated catch block
+ e.printStackTrace();
+ } catch (TableNotFoundException e) {
+ // TODO Auto-generated catch block
+ e.printStackTrace();
+ }
+
+ return null;
+ }
+
+ private class SendTask implements Runnable {
+
+ private TabletServerMutations mutations;
+ private String location;
+ private ArrayList<Result> results;
+ private List<ConditionalMutation> ignored;
+ private TabletLocator locator;
+
+ public SendTask(String location, TabletServerMutations mutations, ArrayList<Result> results, ArrayList<ConditionalMutation> ignored, TabletLocator locator) {
+ this.location = location;
+ this.mutations = mutations;
+ this.results = results;
+ this.ignored = ignored;
+ this.locator = locator;
+ }
+
+ @Override
+ public void run() {
+ ArrayList<Result> tmpResults = new ArrayList<ConditionalWriter.Result>();
+ List<ConditionalMutation> tmpIgnored = new ArrayList<ConditionalMutation>();
+
+ sendToServer(location, mutations, tmpResults, tmpIgnored, locator);
+
+ synchronized (results) {
+ results.addAll(tmpResults);
+ ignored.addAll(tmpIgnored);
+ }
+ }
+ }
+ protected ArrayList<ConditionalMutation> sendToServers(TabletLocator locator, List<Mutation> mutationList, ArrayList<Result> results) throws AccumuloException,
+ AccumuloSecurityException, TableNotFoundException {
+
+ List<Mutation> failures = new ArrayList<Mutation>();
+ Map<String,TabletServerMutations> binnedMutations = new HashMap<String,TabletLocator.TabletServerMutations>();
+
+ do {
+ binnedMutations.clear();
+ failures.clear();
+
+ locator.binMutations(mutationList, binnedMutations, failures, credentials);
+
+ // TODO queue failed mutations to be retried in a bit and write what can be written
+ if (failures.size() > 0)
+ UtilWaitThread.sleep(100);
+
+ } while (failures.size() > 0);
+
+ ArrayList<ConditionalMutation> ignored = new ArrayList<ConditionalMutation>();
+
+ ArrayList<Thread> threads = new ArrayList<Thread>();
+
+ for (Entry<String,TabletServerMutations> entry : binnedMutations.entrySet()) {
+ Thread t = new Thread(new SendTask(entry.getKey(), entry.getValue(), results, ignored, locator));
+ threads.add(t);
+ t.start();
+ }
+
+ for (Thread thread : threads) {
+ try {
+ thread.join();
+ } catch (InterruptedException e) {
+ // TODO Auto-generated catch block
+ e.printStackTrace();
+ }
+ }
+
+ return ignored;
+ }
+
+ private static class CMK {
+
+ ConditionalMutation cm;
+ KeyExtent ke;
+
+ public CMK(KeyExtent ke, ConditionalMutation cm) {
+ this.ke = ke;
+ this.cm = cm;
+ }
+ }
+
+ private void sendToServer(String location, TabletServerMutations mutations, ArrayList<Result> results, List<ConditionalMutation> ignored,
+ TabletLocator locator) {
+ TabletClientService.Iface client = null;
+
+ TInfo tinfo = Tracer.traceInfo();
+
+ Map<Long,CMK> cmidToCm = new HashMap<Long,CMK>();
+ MutableLong cmid = new MutableLong(0);
+
+ try {
+ client = ThriftUtil.getTServerClient(location, instance.getConfiguration());
+
+ Map<TKeyExtent,List<TConditionalMutation>> tmutations = new HashMap<TKeyExtent,List<TConditionalMutation>>();
+
+ convertMutations(mutations, cmidToCm, cmid, tmutations);
+
+ List<TCMResult> tresults = client.conditionalUpdate(tinfo, credentials, ByteBufferUtil.toByteBuffers(auths.getAuthorizations()), tmutations);
+
+ HashSet<KeyExtent> extentsToInvalidate = new HashSet<KeyExtent>();
+
+ for (TCMResult tcmResult : tresults) {
+ if (tcmResult.status == TCMStatus.IGNORED) {
+ CMK cmk = cmidToCm.get(tcmResult.cmid);
+ ignored.add(cmk.cm);
+ extentsToInvalidate.add(cmk.ke);
+ } else {
+ results.add(new Result(fromThrift(tcmResult.status), cmidToCm.get(tcmResult.cmid).cm));
+ }
+ }
+
+ // TODO maybe have thrift call return bad extents
+
+ for (KeyExtent ke : extentsToInvalidate) {
+ locator.invalidateCache(ke);
+ }
+
+ } catch (TTransportException e) {
+ locator.invalidateCache(location);
+ for (CMK cmk : cmidToCm.values())
+ results.add(new Result(Status.UNKNOWN, cmk.cm));
+ } catch (TApplicationException tae) {
+ for (CMK cmk : cmidToCm.values())
+ results.add(new Result(Status.UNKNOWN, cmk.cm));
+ // TODO should another status be used?
+ // TODO need to get server where error occurred back to client
+ } catch (TException e) {
+ locator.invalidateCache(location);
+ for (CMK cmk : cmidToCm.values())
+ results.add(new Result(Status.UNKNOWN, cmk.cm));
+ } finally {
+ ThriftUtil.returnClient((TServiceClient) client);
+ }
+ }
+
+ private Status fromThrift(TCMStatus status) {
+ switch (status) {
+ case ACCEPTED:
+ return Status.ACCEPTED;
+ case REJECTED:
+ return Status.REJECTED;
+ case VIOLATED:
+ return Status.VIOLATED;
+ default:
+ throw new IllegalArgumentException(status.toString());
+ }
+ }
+
+ private void convertMutations(TabletServerMutations mutations, Map<Long,CMK> cmidToCm, MutableLong cmid,
+ Map<TKeyExtent,List<TConditionalMutation>> tmutations) {
+
+ // TODO compress repeated iterator configurations
+
+ Set<Entry<KeyExtent,List<Mutation>>> es = mutations.getMutations().entrySet();
+ for (Entry<KeyExtent,List<Mutation>> entry : es) {
+ TKeyExtent tke = entry.getKey().toThrift();
+ ArrayList<TConditionalMutation> tcondMutaions = new ArrayList<TConditionalMutation>();
+
+ List<ConditionalMutation> condMutations = (List<ConditionalMutation>) (List<? extends Mutation>) entry.getValue();
+
+ for (ConditionalMutation cm : condMutations) {
+ TMutation tm = cm.toThrift();
+
+
+ List<TCondition> conditions = convertConditions(cm);
+
+ cmidToCm.put(cmid.longValue(), new CMK(entry.getKey(), cm));
+ TConditionalMutation tcm = new TConditionalMutation(conditions, tm, cmid.longValue());
+ cmid.increment();
+ tcondMutaions.add(tcm);
+ }
+
+ tmutations.put(tke, tcondMutaions);
+ }
+ }
+
+ private List<TCondition> convertConditions(ConditionalMutation cm) {
+ List<TCondition> conditions = new ArrayList<TCondition>(cm.getConditions().size());
+
+ for (Condition cond : cm.getConditions()) {
+ long ts = 0;
+ boolean hasTs = false;
+
+ if (cond.getTimestamp() != null) {
+ ts = cond.getTimestamp();
+ hasTs = true;
+ }
+
+ IteratorSetting[] iters = cond.getIterators();
+
+ List<IterInfo> ssiList = new ArrayList<IterInfo>(iters.length);
+ Map<String,Map<String,String>> sso = new HashMap<String,Map<String,String>>();
+
+ if (iters.length == 0) {
+ ssiList = Collections.emptyList();
+ sso = Collections.emptyMap();
+ } else {
+ ssiList = new ArrayList<IterInfo>(iters.length);
+ sso = new HashMap<String,Map<String,String>>();
+
+ for (IteratorSetting is : iters) {
+ ssiList.add(new IterInfo(is.getPriority(), is.getIteratorClass(), is.getName()));
+ sso.put(is.getName(), is.getOptions());
+ }
+ }
+
+ TCondition tc = new TCondition(ByteBufferUtil.toByteBuffers(cond.getFamily()), ByteBufferUtil.toByteBuffers(cond.getQualifier()),
+ ByteBufferUtil.toByteBuffers(cond.getVisibility()), ts, hasTs, ByteBufferUtil.toByteBuffers(cond.getValue()), ssiList, sso);
+
+ conditions.add(tc);
+ }
+
+ return conditions;
+ }
+
+ private boolean isVisible(ByteSequence cv) {
+ Text testVis = new Text(cv.toArray());
+ if (testVis.getLength() == 0)
+ return true;
+
+ Boolean b = (Boolean) cache.get(testVis);
+ if (b != null)
+ return b;
+
+ try {
+ Boolean bb = ve.evaluate(new ColumnVisibility(testVis));
+ cache.put(new Text(testVis), bb);
+ return bb;
+ } catch (VisibilityParseException e) {
+ return false;
+ } catch (BadArgumentException e) {
+ return false;
+ }
+ }
+
+ public Result write(ConditionalMutation mutation) {
+ return write(Collections.singleton(mutation).iterator()).next();
+ }
+
+ public void setTimeout(long timeOut, TimeUnit timeUnit) {
+ throw new UnsupportedOperationException();
+ }
+
+ public long getTimeout(TimeUnit timeUnit) {
+ throw new UnsupportedOperationException();
+ }
+
+}
http://git-wip-us.apache.org/repos/asf/accumulo/blob/49a7626c/core/src/main/java/org/apache/accumulo/core/client/impl/ConnectorImpl.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/accumulo/core/client/impl/ConnectorImpl.java b/core/src/main/java/org/apache/accumulo/core/client/impl/ConnectorImpl.java
index 1702082..9851ea0 100644
--- a/core/src/main/java/org/apache/accumulo/core/client/impl/ConnectorImpl.java
+++ b/core/src/main/java/org/apache/accumulo/core/client/impl/ConnectorImpl.java
@@ -24,6 +24,7 @@ import org.apache.accumulo.core.client.BatchDeleter;
import org.apache.accumulo.core.client.BatchScanner;
import org.apache.accumulo.core.client.BatchWriter;
import org.apache.accumulo.core.client.BatchWriterConfig;
+import org.apache.accumulo.core.client.ConditionalWriter;
import org.apache.accumulo.core.client.Connector;
import org.apache.accumulo.core.client.Instance;
import org.apache.accumulo.core.client.MultiTableBatchWriter;
@@ -132,6 +133,13 @@ public class ConnectorImpl extends Connector {
}
@Override
+ public ConditionalWriter createConditionalWriter(String tableName, Authorizations authorizations) throws TableNotFoundException {
+ ArgumentChecker.notNull(tableName, authorizations);
+ // TODO resolve table name to table id here and pass that
+ return new ConditionalWriterImpl(instance, credentials, getTableId(tableName), authorizations);
+ }
+
+ @Override
public Scanner createScanner(String tableName, Authorizations authorizations) throws TableNotFoundException {
ArgumentChecker.notNull(tableName, authorizations);
return new ScannerImpl(instance, credentials, getTableId(tableName), authorizations);
@@ -164,5 +172,4 @@ public class ConnectorImpl extends Connector {
return instanceops;
}
-
}
http://git-wip-us.apache.org/repos/asf/accumulo/blob/49a7626c/core/src/main/java/org/apache/accumulo/core/client/impl/TabletServerBatchWriter.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/accumulo/core/client/impl/TabletServerBatchWriter.java b/core/src/main/java/org/apache/accumulo/core/client/impl/TabletServerBatchWriter.java
index 766cea9..40a9da4 100644
--- a/core/src/main/java/org/apache/accumulo/core/client/impl/TabletServerBatchWriter.java
+++ b/core/src/main/java/org/apache/accumulo/core/client/impl/TabletServerBatchWriter.java
@@ -846,6 +846,8 @@ public class TabletServerBatchWriter {
return new MutationSet();
}
TInfo tinfo = Tracer.traceInfo();
+
+ // TODO remove this
TTransport transport = null;
timeoutTracker.startingWrite();
http://git-wip-us.apache.org/repos/asf/accumulo/blob/49a7626c/core/src/main/java/org/apache/accumulo/core/client/mock/MockConnector.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/accumulo/core/client/mock/MockConnector.java b/core/src/main/java/org/apache/accumulo/core/client/mock/MockConnector.java
index 1179559..4a405aa 100644
--- a/core/src/main/java/org/apache/accumulo/core/client/mock/MockConnector.java
+++ b/core/src/main/java/org/apache/accumulo/core/client/mock/MockConnector.java
@@ -22,6 +22,7 @@ import org.apache.accumulo.core.client.BatchDeleter;
import org.apache.accumulo.core.client.BatchScanner;
import org.apache.accumulo.core.client.BatchWriter;
import org.apache.accumulo.core.client.BatchWriterConfig;
+import org.apache.accumulo.core.client.ConditionalWriter;
import org.apache.accumulo.core.client.Connector;
import org.apache.accumulo.core.client.Instance;
import org.apache.accumulo.core.client.MultiTableBatchWriter;
@@ -128,4 +129,10 @@ public class MockConnector extends Connector {
return new MockInstanceOperations(acu);
}
+ @Override
+ public ConditionalWriter createConditionalWriter(String tableName, Authorizations authorizations) throws TableNotFoundException {
+ // TODO add implementation
+ throw new UnsupportedOperationException();
+ }
+
}
http://git-wip-us.apache.org/repos/asf/accumulo/blob/49a7626c/core/src/main/java/org/apache/accumulo/core/data/Condition.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/accumulo/core/data/Condition.java b/core/src/main/java/org/apache/accumulo/core/data/Condition.java
new file mode 100644
index 0000000..97df7e0
--- /dev/null
+++ b/core/src/main/java/org/apache/accumulo/core/data/Condition.java
@@ -0,0 +1,148 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You 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 org.apache.accumulo.core.data;
+
+import java.util.HashSet;
+
+import org.apache.accumulo.core.Constants;
+import org.apache.accumulo.core.client.IteratorSetting;
+import org.apache.accumulo.core.security.ColumnVisibility;
+import org.apache.accumulo.core.util.ArgumentChecker;
+import org.apache.hadoop.io.Text;
+
+/**
+ *
+ * @since 1.6.0
+ */
+public class Condition {
+
+ private ByteSequence cf;
+ private ByteSequence cq;
+ private ByteSequence cv;
+ private ByteSequence val;
+ private Long ts;
+ private IteratorSetting iterators[] = new IteratorSetting[0];
+ private static final ByteSequence EMPTY = new ArrayByteSequence(new byte[0]);
+
+
+ public Condition(CharSequence cf, CharSequence cq) {
+ ArgumentChecker.notNull(cf, cq);
+ this.cf = new ArrayByteSequence(cf.toString().getBytes(Constants.UTF8));
+ this.cq = new ArrayByteSequence(cq.toString().getBytes(Constants.UTF8));
+ this.cv = EMPTY;
+ }
+
+ public Condition(byte[] cf, byte[] cq) {
+ ArgumentChecker.notNull(cf, cq);
+ this.cf = new ArrayByteSequence(cf);
+ this.cq = new ArrayByteSequence(cq);
+ this.cv = EMPTY;
+ }
+
+ public Condition(Text cf, Text cq) {
+ ArgumentChecker.notNull(cf, cq);
+ this.cf = new ArrayByteSequence(cf.getBytes(), 0, cf.getLength());
+ this.cq = new ArrayByteSequence(cq.getBytes(), 0, cq.getLength());
+ this.cv = EMPTY;
+ }
+
+ public Condition(ByteSequence cf, ByteSequence cq) {
+ ArgumentChecker.notNull(cf, cq);
+ this.cf = cf;
+ this.cq = cq;
+ this.cv = EMPTY;
+ }
+
+ public ByteSequence getFamily() {
+ return cf;
+ }
+
+ public ByteSequence getQualifier() {
+ return cq;
+ }
+
+ public Condition setTimestamp(long ts) {
+ this.ts = ts;
+ return this;
+ }
+
+ public Long getTimestamp() {
+ return ts;
+ }
+
+ public Condition setValue(CharSequence value) {
+ ArgumentChecker.notNull(value);
+ this.val = new ArrayByteSequence(value.toString().getBytes(Constants.UTF8));
+ return this;
+ }
+
+ public Condition setValue(byte[] value) {
+ ArgumentChecker.notNull(value);
+ this.val = new ArrayByteSequence(value);
+ return this;
+ }
+
+ public Condition setValue(Text value) {
+ ArgumentChecker.notNull(value);
+ this.val = new ArrayByteSequence(value.getBytes(), 0, value.getLength());
+ return this;
+ }
+
+ public Condition setValue(ByteSequence value) {
+ ArgumentChecker.notNull(value);
+ this.val = value;
+ return this;
+ }
+
+ public ByteSequence getValue() {
+ return val;
+ }
+
+ public Condition setVisibility(ColumnVisibility cv) {
+ ArgumentChecker.notNull(cv);
+ this.cv = new ArrayByteSequence(cv.getExpression());
+ return this;
+ }
+
+ public ByteSequence getVisibility() {
+ return cv;
+ }
+
+ public Condition setIterators(IteratorSetting... iterators) {
+ ArgumentChecker.notNull(iterators);
+
+ if (iterators.length > 1) {
+ HashSet<String> names = new HashSet<String>();
+ HashSet<Integer> prios = new HashSet<Integer>();
+
+ for (IteratorSetting iteratorSetting : iterators) {
+ if (!names.add(iteratorSetting.getName()))
+ throw new IllegalArgumentException("iterator name used more than once " + iteratorSetting.getName());
+ if (!prios.add(iteratorSetting.getPriority()))
+ throw new IllegalArgumentException("iterator priority used more than once " + iteratorSetting.getPriority());
+ }
+ }
+
+ this.iterators = iterators;
+ return this;
+ }
+
+ public IteratorSetting[] getIterators() {
+ return iterators;
+ }
+
+}
http://git-wip-us.apache.org/repos/asf/accumulo/blob/49a7626c/core/src/main/java/org/apache/accumulo/core/data/ConditionalMutation.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/accumulo/core/data/ConditionalMutation.java b/core/src/main/java/org/apache/accumulo/core/data/ConditionalMutation.java
new file mode 100644
index 0000000..5b38559
--- /dev/null
+++ b/core/src/main/java/org/apache/accumulo/core/data/ConditionalMutation.java
@@ -0,0 +1,77 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You 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 org.apache.accumulo.core.data;
+
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
+
+import org.apache.accumulo.core.util.ArgumentChecker;
+import org.apache.hadoop.io.Text;
+
+/**
+ * @since 1.6.0
+ */
+public class ConditionalMutation extends Mutation {
+
+ private List<Condition> conditions = new ArrayList<Condition>();
+
+ public ConditionalMutation(byte[] row, Condition condition, Condition... conditions) {
+ super(row);
+ init(condition, conditions);
+ }
+
+ public ConditionalMutation(byte[] row, int start, int length, Condition condition, Condition... conditions) {
+ super(row, start, length);
+ init(condition, conditions);
+ }
+
+ public ConditionalMutation(Text row, Condition condition, Condition... conditions) {
+ super(row);
+ init(condition, conditions);
+ }
+
+ public ConditionalMutation(CharSequence row, Condition condition, Condition... conditions) {
+ super(row);
+ init(condition, conditions);
+ }
+
+ public ConditionalMutation(ByteSequence row, Condition condition, Condition... conditions) {
+ // TODO add ByteSequence methods to mutations
+ super(row.toArray());
+ init(condition, conditions);
+ }
+
+ private void init(Condition condition, Condition... conditions) {
+ ArgumentChecker.notNull(condition);
+ this.conditions.add(condition);
+ if (conditions.length > 0) {
+ this.conditions.addAll(Arrays.asList(conditions));
+ }
+ }
+
+ public void addCondition(Condition condition) {
+ ArgumentChecker.notNull(condition);
+ this.conditions.add(condition);
+ }
+
+ public List<Condition> getConditions() {
+ return conditions;
+ }
+
+}
http://git-wip-us.apache.org/repos/asf/accumulo/blob/49a7626c/core/src/main/java/org/apache/accumulo/core/data/thrift/TCMResult.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/accumulo/core/data/thrift/TCMResult.java b/core/src/main/java/org/apache/accumulo/core/data/thrift/TCMResult.java
new file mode 100644
index 0000000..fe72fd6
--- /dev/null
+++ b/core/src/main/java/org/apache/accumulo/core/data/thrift/TCMResult.java
@@ -0,0 +1,516 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You 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.
+ */
+/**
+ * Autogenerated by Thrift Compiler (0.9.0)
+ *
+ * DO NOT EDIT UNLESS YOU ARE SURE THAT YOU KNOW WHAT YOU ARE DOING
+ * @generated
+ */
+package org.apache.accumulo.core.data.thrift;
+
+import org.apache.thrift.scheme.IScheme;
+import org.apache.thrift.scheme.SchemeFactory;
+import org.apache.thrift.scheme.StandardScheme;
+
+import org.apache.thrift.scheme.TupleScheme;
+import org.apache.thrift.protocol.TTupleProtocol;
+import org.apache.thrift.protocol.TProtocolException;
+import org.apache.thrift.EncodingUtils;
+import org.apache.thrift.TException;
+import java.util.List;
+import java.util.ArrayList;
+import java.util.Map;
+import java.util.HashMap;
+import java.util.EnumMap;
+import java.util.Set;
+import java.util.HashSet;
+import java.util.EnumSet;
+import java.util.Collections;
+import java.util.BitSet;
+import java.nio.ByteBuffer;
+import java.util.Arrays;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+@SuppressWarnings("all") public class TCMResult implements org.apache.thrift.TBase<TCMResult, TCMResult._Fields>, java.io.Serializable, Cloneable {
+ private static final org.apache.thrift.protocol.TStruct STRUCT_DESC = new org.apache.thrift.protocol.TStruct("TCMResult");
+
+ private static final org.apache.thrift.protocol.TField CMID_FIELD_DESC = new org.apache.thrift.protocol.TField("cmid", org.apache.thrift.protocol.TType.I64, (short)1);
+ private static final org.apache.thrift.protocol.TField STATUS_FIELD_DESC = new org.apache.thrift.protocol.TField("status", org.apache.thrift.protocol.TType.I32, (short)2);
+
+ private static final Map<Class<? extends IScheme>, SchemeFactory> schemes = new HashMap<Class<? extends IScheme>, SchemeFactory>();
+ static {
+ schemes.put(StandardScheme.class, new TCMResultStandardSchemeFactory());
+ schemes.put(TupleScheme.class, new TCMResultTupleSchemeFactory());
+ }
+
+ public long cmid; // required
+ /**
+ *
+ * @see TCMStatus
+ */
+ public TCMStatus status; // required
+
+ /** The set of fields this struct contains, along with convenience methods for finding and manipulating them. */
+ @SuppressWarnings("all") public enum _Fields implements org.apache.thrift.TFieldIdEnum {
+ CMID((short)1, "cmid"),
+ /**
+ *
+ * @see TCMStatus
+ */
+ STATUS((short)2, "status");
+
+ private static final Map<String, _Fields> byName = new HashMap<String, _Fields>();
+
+ static {
+ for (_Fields field : EnumSet.allOf(_Fields.class)) {
+ byName.put(field.getFieldName(), field);
+ }
+ }
+
+ /**
+ * Find the _Fields constant that matches fieldId, or null if its not found.
+ */
+ public static _Fields findByThriftId(int fieldId) {
+ switch(fieldId) {
+ case 1: // CMID
+ return CMID;
+ case 2: // STATUS
+ return STATUS;
+ default:
+ return null;
+ }
+ }
+
+ /**
+ * Find the _Fields constant that matches fieldId, throwing an exception
+ * if it is not found.
+ */
+ public static _Fields findByThriftIdOrThrow(int fieldId) {
+ _Fields fields = findByThriftId(fieldId);
+ if (fields == null) throw new IllegalArgumentException("Field " + fieldId + " doesn't exist!");
+ return fields;
+ }
+
+ /**
+ * Find the _Fields constant that matches name, or null if its not found.
+ */
+ public static _Fields findByName(String name) {
+ return byName.get(name);
+ }
+
+ private final short _thriftId;
+ private final String _fieldName;
+
+ _Fields(short thriftId, String fieldName) {
+ _thriftId = thriftId;
+ _fieldName = fieldName;
+ }
+
+ public short getThriftFieldId() {
+ return _thriftId;
+ }
+
+ public String getFieldName() {
+ return _fieldName;
+ }
+ }
+
+ // isset id assignments
+ private static final int __CMID_ISSET_ID = 0;
+ private byte __isset_bitfield = 0;
+ public static final Map<_Fields, org.apache.thrift.meta_data.FieldMetaData> metaDataMap;
+ static {
+ Map<_Fields, org.apache.thrift.meta_data.FieldMetaData> tmpMap = new EnumMap<_Fields, org.apache.thrift.meta_data.FieldMetaData>(_Fields.class);
+ tmpMap.put(_Fields.CMID, new org.apache.thrift.meta_data.FieldMetaData("cmid", org.apache.thrift.TFieldRequirementType.DEFAULT,
+ new org.apache.thrift.meta_data.FieldValueMetaData(org.apache.thrift.protocol.TType.I64)));
+ tmpMap.put(_Fields.STATUS, new org.apache.thrift.meta_data.FieldMetaData("status", org.apache.thrift.TFieldRequirementType.DEFAULT,
+ new org.apache.thrift.meta_data.EnumMetaData(org.apache.thrift.protocol.TType.ENUM, TCMStatus.class)));
+ metaDataMap = Collections.unmodifiableMap(tmpMap);
+ org.apache.thrift.meta_data.FieldMetaData.addStructMetaDataMap(TCMResult.class, metaDataMap);
+ }
+
+ public TCMResult() {
+ }
+
+ public TCMResult(
+ long cmid,
+ TCMStatus status)
+ {
+ this();
+ this.cmid = cmid;
+ setCmidIsSet(true);
+ this.status = status;
+ }
+
+ /**
+ * Performs a deep copy on <i>other</i>.
+ */
+ public TCMResult(TCMResult other) {
+ __isset_bitfield = other.__isset_bitfield;
+ this.cmid = other.cmid;
+ if (other.isSetStatus()) {
+ this.status = other.status;
+ }
+ }
+
+ public TCMResult deepCopy() {
+ return new TCMResult(this);
+ }
+
+ @Override
+ public void clear() {
+ setCmidIsSet(false);
+ this.cmid = 0;
+ this.status = null;
+ }
+
+ public long getCmid() {
+ return this.cmid;
+ }
+
+ public TCMResult setCmid(long cmid) {
+ this.cmid = cmid;
+ setCmidIsSet(true);
+ return this;
+ }
+
+ public void unsetCmid() {
+ __isset_bitfield = EncodingUtils.clearBit(__isset_bitfield, __CMID_ISSET_ID);
+ }
+
+ /** Returns true if field cmid is set (has been assigned a value) and false otherwise */
+ public boolean isSetCmid() {
+ return EncodingUtils.testBit(__isset_bitfield, __CMID_ISSET_ID);
+ }
+
+ public void setCmidIsSet(boolean value) {
+ __isset_bitfield = EncodingUtils.setBit(__isset_bitfield, __CMID_ISSET_ID, value);
+ }
+
+ /**
+ *
+ * @see TCMStatus
+ */
+ public TCMStatus getStatus() {
+ return this.status;
+ }
+
+ /**
+ *
+ * @see TCMStatus
+ */
+ public TCMResult setStatus(TCMStatus status) {
+ this.status = status;
+ return this;
+ }
+
+ public void unsetStatus() {
+ this.status = null;
+ }
+
+ /** Returns true if field status is set (has been assigned a value) and false otherwise */
+ public boolean isSetStatus() {
+ return this.status != null;
+ }
+
+ public void setStatusIsSet(boolean value) {
+ if (!value) {
+ this.status = null;
+ }
+ }
+
+ public void setFieldValue(_Fields field, Object value) {
+ switch (field) {
+ case CMID:
+ if (value == null) {
+ unsetCmid();
+ } else {
+ setCmid((Long)value);
+ }
+ break;
+
+ case STATUS:
+ if (value == null) {
+ unsetStatus();
+ } else {
+ setStatus((TCMStatus)value);
+ }
+ break;
+
+ }
+ }
+
+ public Object getFieldValue(_Fields field) {
+ switch (field) {
+ case CMID:
+ return Long.valueOf(getCmid());
+
+ case STATUS:
+ return getStatus();
+
+ }
+ throw new IllegalStateException();
+ }
+
+ /** Returns true if field corresponding to fieldID is set (has been assigned a value) and false otherwise */
+ public boolean isSet(_Fields field) {
+ if (field == null) {
+ throw new IllegalArgumentException();
+ }
+
+ switch (field) {
+ case CMID:
+ return isSetCmid();
+ case STATUS:
+ return isSetStatus();
+ }
+ throw new IllegalStateException();
+ }
+
+ @Override
+ public boolean equals(Object that) {
+ if (that == null)
+ return false;
+ if (that instanceof TCMResult)
+ return this.equals((TCMResult)that);
+ return false;
+ }
+
+ public boolean equals(TCMResult that) {
+ if (that == null)
+ return false;
+
+ boolean this_present_cmid = true;
+ boolean that_present_cmid = true;
+ if (this_present_cmid || that_present_cmid) {
+ if (!(this_present_cmid && that_present_cmid))
+ return false;
+ if (this.cmid != that.cmid)
+ return false;
+ }
+
+ boolean this_present_status = true && this.isSetStatus();
+ boolean that_present_status = true && that.isSetStatus();
+ if (this_present_status || that_present_status) {
+ if (!(this_present_status && that_present_status))
+ return false;
+ if (!this.status.equals(that.status))
+ return false;
+ }
+
+ return true;
+ }
+
+ @Override
+ public int hashCode() {
+ return 0;
+ }
+
+ public int compareTo(TCMResult other) {
+ if (!getClass().equals(other.getClass())) {
+ return getClass().getName().compareTo(other.getClass().getName());
+ }
+
+ int lastComparison = 0;
+ TCMResult typedOther = (TCMResult)other;
+
+ lastComparison = Boolean.valueOf(isSetCmid()).compareTo(typedOther.isSetCmid());
+ if (lastComparison != 0) {
+ return lastComparison;
+ }
+ if (isSetCmid()) {
+ lastComparison = org.apache.thrift.TBaseHelper.compareTo(this.cmid, typedOther.cmid);
+ if (lastComparison != 0) {
+ return lastComparison;
+ }
+ }
+ lastComparison = Boolean.valueOf(isSetStatus()).compareTo(typedOther.isSetStatus());
+ if (lastComparison != 0) {
+ return lastComparison;
+ }
+ if (isSetStatus()) {
+ lastComparison = org.apache.thrift.TBaseHelper.compareTo(this.status, typedOther.status);
+ if (lastComparison != 0) {
+ return lastComparison;
+ }
+ }
+ return 0;
+ }
+
+ public _Fields fieldForId(int fieldId) {
+ return _Fields.findByThriftId(fieldId);
+ }
+
+ public void read(org.apache.thrift.protocol.TProtocol iprot) throws org.apache.thrift.TException {
+ schemes.get(iprot.getScheme()).getScheme().read(iprot, this);
+ }
+
+ public void write(org.apache.thrift.protocol.TProtocol oprot) throws org.apache.thrift.TException {
+ schemes.get(oprot.getScheme()).getScheme().write(oprot, this);
+ }
+
+ @Override
+ public String toString() {
+ StringBuilder sb = new StringBuilder("TCMResult(");
+ boolean first = true;
+
+ sb.append("cmid:");
+ sb.append(this.cmid);
+ first = false;
+ if (!first) sb.append(", ");
+ sb.append("status:");
+ if (this.status == null) {
+ sb.append("null");
+ } else {
+ sb.append(this.status);
+ }
+ first = false;
+ sb.append(")");
+ return sb.toString();
+ }
+
+ public void validate() throws org.apache.thrift.TException {
+ // check for required fields
+ // check for sub-struct validity
+ }
+
+ private void writeObject(java.io.ObjectOutputStream out) throws java.io.IOException {
+ try {
+ write(new org.apache.thrift.protocol.TCompactProtocol(new org.apache.thrift.transport.TIOStreamTransport(out)));
+ } catch (org.apache.thrift.TException te) {
+ throw new java.io.IOException(te);
+ }
+ }
+
+ private void readObject(java.io.ObjectInputStream in) throws java.io.IOException, ClassNotFoundException {
+ try {
+ // it doesn't seem like you should have to do this, but java serialization is wacky, and doesn't call the default constructor.
+ __isset_bitfield = 0;
+ read(new org.apache.thrift.protocol.TCompactProtocol(new org.apache.thrift.transport.TIOStreamTransport(in)));
+ } catch (org.apache.thrift.TException te) {
+ throw new java.io.IOException(te);
+ }
+ }
+
+ private static class TCMResultStandardSchemeFactory implements SchemeFactory {
+ public TCMResultStandardScheme getScheme() {
+ return new TCMResultStandardScheme();
+ }
+ }
+
+ private static class TCMResultStandardScheme extends StandardScheme<TCMResult> {
+
+ public void read(org.apache.thrift.protocol.TProtocol iprot, TCMResult struct) throws org.apache.thrift.TException {
+ org.apache.thrift.protocol.TField schemeField;
+ iprot.readStructBegin();
+ while (true)
+ {
+ schemeField = iprot.readFieldBegin();
+ if (schemeField.type == org.apache.thrift.protocol.TType.STOP) {
+ break;
+ }
+ switch (schemeField.id) {
+ case 1: // CMID
+ if (schemeField.type == org.apache.thrift.protocol.TType.I64) {
+ struct.cmid = iprot.readI64();
+ struct.setCmidIsSet(true);
+ } else {
+ org.apache.thrift.protocol.TProtocolUtil.skip(iprot, schemeField.type);
+ }
+ break;
+ case 2: // STATUS
+ if (schemeField.type == org.apache.thrift.protocol.TType.I32) {
+ struct.status = TCMStatus.findByValue(iprot.readI32());
+ struct.setStatusIsSet(true);
+ } else {
+ org.apache.thrift.protocol.TProtocolUtil.skip(iprot, schemeField.type);
+ }
+ break;
+ default:
+ org.apache.thrift.protocol.TProtocolUtil.skip(iprot, schemeField.type);
+ }
+ iprot.readFieldEnd();
+ }
+ iprot.readStructEnd();
+
+ // check for required fields of primitive type, which can't be checked in the validate method
+ struct.validate();
+ }
+
+ public void write(org.apache.thrift.protocol.TProtocol oprot, TCMResult struct) throws org.apache.thrift.TException {
+ struct.validate();
+
+ oprot.writeStructBegin(STRUCT_DESC);
+ oprot.writeFieldBegin(CMID_FIELD_DESC);
+ oprot.writeI64(struct.cmid);
+ oprot.writeFieldEnd();
+ if (struct.status != null) {
+ oprot.writeFieldBegin(STATUS_FIELD_DESC);
+ oprot.writeI32(struct.status.getValue());
+ oprot.writeFieldEnd();
+ }
+ oprot.writeFieldStop();
+ oprot.writeStructEnd();
+ }
+
+ }
+
+ private static class TCMResultTupleSchemeFactory implements SchemeFactory {
+ public TCMResultTupleScheme getScheme() {
+ return new TCMResultTupleScheme();
+ }
+ }
+
+ private static class TCMResultTupleScheme extends TupleScheme<TCMResult> {
+
+ @Override
+ public void write(org.apache.thrift.protocol.TProtocol prot, TCMResult struct) throws org.apache.thrift.TException {
+ TTupleProtocol oprot = (TTupleProtocol) prot;
+ BitSet optionals = new BitSet();
+ if (struct.isSetCmid()) {
+ optionals.set(0);
+ }
+ if (struct.isSetStatus()) {
+ optionals.set(1);
+ }
+ oprot.writeBitSet(optionals, 2);
+ if (struct.isSetCmid()) {
+ oprot.writeI64(struct.cmid);
+ }
+ if (struct.isSetStatus()) {
+ oprot.writeI32(struct.status.getValue());
+ }
+ }
+
+ @Override
+ public void read(org.apache.thrift.protocol.TProtocol prot, TCMResult struct) throws org.apache.thrift.TException {
+ TTupleProtocol iprot = (TTupleProtocol) prot;
+ BitSet incoming = iprot.readBitSet(2);
+ if (incoming.get(0)) {
+ struct.cmid = iprot.readI64();
+ struct.setCmidIsSet(true);
+ }
+ if (incoming.get(1)) {
+ struct.status = TCMStatus.findByValue(iprot.readI32());
+ struct.setStatusIsSet(true);
+ }
+ }
+ }
+
+}
+
http://git-wip-us.apache.org/repos/asf/accumulo/blob/49a7626c/core/src/main/java/org/apache/accumulo/core/data/thrift/TCMStatus.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/org/apache/accumulo/core/data/thrift/TCMStatus.java b/core/src/main/java/org/apache/accumulo/core/data/thrift/TCMStatus.java
new file mode 100644
index 0000000..6ef94d5
--- /dev/null
+++ b/core/src/main/java/org/apache/accumulo/core/data/thrift/TCMStatus.java
@@ -0,0 +1,67 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You 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.
+ */
+/**
+ * Autogenerated by Thrift Compiler (0.9.0)
+ *
+ * DO NOT EDIT UNLESS YOU ARE SURE THAT YOU KNOW WHAT YOU ARE DOING
+ * @generated
+ */
+package org.apache.accumulo.core.data.thrift;
+
+
+import java.util.Map;
+import java.util.HashMap;
+import org.apache.thrift.TEnum;
+
+@SuppressWarnings("all") public enum TCMStatus implements org.apache.thrift.TEnum {
+ ACCEPTED(0),
+ REJECTED(1),
+ VIOLATED(2),
+ IGNORED(3);
+
+ private final int value;
+
+ private TCMStatus(int value) {
+ this.value = value;
+ }
+
+ /**
+ * Get the integer value of this enum value, as defined in the Thrift IDL.
+ */
+ public int getValue() {
+ return value;
+ }
+
+ /**
+ * Find a the enum type by its integer value, as defined in the Thrift IDL.
+ * @return null if the value is not found.
+ */
+ public static TCMStatus findByValue(int value) {
+ switch (value) {
+ case 0:
+ return ACCEPTED;
+ case 1:
+ return REJECTED;
+ case 2:
+ return VIOLATED;
+ case 3:
+ return IGNORED;
+ default:
+ return null;
+ }
+ }
+}