# 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.1)
#
# DO NOT EDIT UNLESS YOU ARE SURE THAT YOU KNOW WHAT YOU ARE DOING
#
#  options string: py
#

from thrift.Thrift import TType, TMessageType, TException, TApplicationException
from ttypes import *
from thrift.Thrift import TProcessor
from thrift.transport import TTransport
from thrift.protocol import TBinaryProtocol, TProtocol
try:
  from thrift.protocol import fastbinary
except:
  fastbinary = None


class Iface:
  def login(self, principal, loginProperties):
    """
    Parameters:
     - principal
     - loginProperties
    """
    pass

  def addConstraint(self, login, tableName, constraintClassName):
    """
    Parameters:
     - login
     - tableName
     - constraintClassName
    """
    pass

  def addSplits(self, login, tableName, splits):
    """
    Parameters:
     - login
     - tableName
     - splits
    """
    pass

  def attachIterator(self, login, tableName, setting, scopes):
    """
    Parameters:
     - login
     - tableName
     - setting
     - scopes
    """
    pass

  def checkIteratorConflicts(self, login, tableName, setting, scopes):
    """
    Parameters:
     - login
     - tableName
     - setting
     - scopes
    """
    pass

  def clearLocatorCache(self, login, tableName):
    """
    Parameters:
     - login
     - tableName
    """
    pass

  def cloneTable(self, login, tableName, newTableName, flush, propertiesToSet, propertiesToExclude):
    """
    Parameters:
     - login
     - tableName
     - newTableName
     - flush
     - propertiesToSet
     - propertiesToExclude
    """
    pass

  def compactTable(self, login, tableName, startRow, endRow, iterators, flush, wait, compactionStrategy):
    """
    Parameters:
     - login
     - tableName
     - startRow
     - endRow
     - iterators
     - flush
     - wait
     - compactionStrategy
    """
    pass

  def cancelCompaction(self, login, tableName):
    """
    Parameters:
     - login
     - tableName
    """
    pass

  def createTable(self, login, tableName, versioningIter, type):
    """
    Parameters:
     - login
     - tableName
     - versioningIter
     - type
    """
    pass

  def deleteTable(self, login, tableName):
    """
    Parameters:
     - login
     - tableName
    """
    pass

  def deleteRows(self, login, tableName, startRow, endRow):
    """
    Parameters:
     - login
     - tableName
     - startRow
     - endRow
    """
    pass

  def exportTable(self, login, tableName, exportDir):
    """
    Parameters:
     - login
     - tableName
     - exportDir
    """
    pass

  def flushTable(self, login, tableName, startRow, endRow, wait):
    """
    Parameters:
     - login
     - tableName
     - startRow
     - endRow
     - wait
    """
    pass

  def getDiskUsage(self, login, tables):
    """
    Parameters:
     - login
     - tables
    """
    pass

  def getLocalityGroups(self, login, tableName):
    """
    Parameters:
     - login
     - tableName
    """
    pass

  def getIteratorSetting(self, login, tableName, iteratorName, scope):
    """
    Parameters:
     - login
     - tableName
     - iteratorName
     - scope
    """
    pass

  def getMaxRow(self, login, tableName, auths, startRow, startInclusive, endRow, endInclusive):
    """
    Parameters:
     - login
     - tableName
     - auths
     - startRow
     - startInclusive
     - endRow
     - endInclusive
    """
    pass

  def getTableProperties(self, login, tableName):
    """
    Parameters:
     - login
     - tableName
    """
    pass

  def importDirectory(self, login, tableName, importDir, failureDir, setTime):
    """
    Parameters:
     - login
     - tableName
     - importDir
     - failureDir
     - setTime
    """
    pass

  def importTable(self, login, tableName, importDir):
    """
    Parameters:
     - login
     - tableName
     - importDir
    """
    pass

  def listSplits(self, login, tableName, maxSplits):
    """
    Parameters:
     - login
     - tableName
     - maxSplits
    """
    pass

  def listTables(self, login):
    """
    Parameters:
     - login
    """
    pass

  def listIterators(self, login, tableName):
    """
    Parameters:
     - login
     - tableName
    """
    pass

  def listConstraints(self, login, tableName):
    """
    Parameters:
     - login
     - tableName
    """
    pass

  def mergeTablets(self, login, tableName, startRow, endRow):
    """
    Parameters:
     - login
     - tableName
     - startRow
     - endRow
    """
    pass

  def offlineTable(self, login, tableName, wait):
    """
    Parameters:
     - login
     - tableName
     - wait
    """
    pass

  def onlineTable(self, login, tableName, wait):
    """
    Parameters:
     - login
     - tableName
     - wait
    """
    pass

  def removeConstraint(self, login, tableName, constraint):
    """
    Parameters:
     - login
     - tableName
     - constraint
    """
    pass

  def removeIterator(self, login, tableName, iterName, scopes):
    """
    Parameters:
     - login
     - tableName
     - iterName
     - scopes
    """
    pass

  def removeTableProperty(self, login, tableName, property):
    """
    Parameters:
     - login
     - tableName
     - property
    """
    pass

  def renameTable(self, login, oldTableName, newTableName):
    """
    Parameters:
     - login
     - oldTableName
     - newTableName
    """
    pass

  def setLocalityGroups(self, login, tableName, groups):
    """
    Parameters:
     - login
     - tableName
     - groups
    """
    pass

  def setTableProperty(self, login, tableName, property, value):
    """
    Parameters:
     - login
     - tableName
     - property
     - value
    """
    pass

  def splitRangeByTablets(self, login, tableName, range, maxSplits):
    """
    Parameters:
     - login
     - tableName
     - range
     - maxSplits
    """
    pass

  def tableExists(self, login, tableName):
    """
    Parameters:
     - login
     - tableName
    """
    pass

  def tableIdMap(self, login):
    """
    Parameters:
     - login
    """
    pass

  def testTableClassLoad(self, login, tableName, className, asTypeName):
    """
    Parameters:
     - login
     - tableName
     - className
     - asTypeName
    """
    pass

  def pingTabletServer(self, login, tserver):
    """
    Parameters:
     - login
     - tserver
    """
    pass

  def getActiveScans(self, login, tserver):
    """
    Parameters:
     - login
     - tserver
    """
    pass

  def getActiveCompactions(self, login, tserver):
    """
    Parameters:
     - login
     - tserver
    """
    pass

  def getSiteConfiguration(self, login):
    """
    Parameters:
     - login
    """
    pass

  def getSystemConfiguration(self, login):
    """
    Parameters:
     - login
    """
    pass

  def getTabletServers(self, login):
    """
    Parameters:
     - login
    """
    pass

  def removeProperty(self, login, property):
    """
    Parameters:
     - login
     - property
    """
    pass

  def setProperty(self, login, property, value):
    """
    Parameters:
     - login
     - property
     - value
    """
    pass

  def testClassLoad(self, login, className, asTypeName):
    """
    Parameters:
     - login
     - className
     - asTypeName
    """
    pass

  def authenticateUser(self, login, user, properties):
    """
    Parameters:
     - login
     - user
     - properties
    """
    pass

  def changeUserAuthorizations(self, login, user, authorizations):
    """
    Parameters:
     - login
     - user
     - authorizations
    """
    pass

  def changeLocalUserPassword(self, login, user, password):
    """
    Parameters:
     - login
     - user
     - password
    """
    pass

  def createLocalUser(self, login, user, password):
    """
    Parameters:
     - login
     - user
     - password
    """
    pass

  def dropLocalUser(self, login, user):
    """
    Parameters:
     - login
     - user
    """
    pass

  def getUserAuthorizations(self, login, user):
    """
    Parameters:
     - login
     - user
    """
    pass

  def grantSystemPermission(self, login, user, perm):
    """
    Parameters:
     - login
     - user
     - perm
    """
    pass

  def grantTablePermission(self, login, user, table, perm):
    """
    Parameters:
     - login
     - user
     - table
     - perm
    """
    pass

  def hasSystemPermission(self, login, user, perm):
    """
    Parameters:
     - login
     - user
     - perm
    """
    pass

  def hasTablePermission(self, login, user, table, perm):
    """
    Parameters:
     - login
     - user
     - table
     - perm
    """
    pass

  def listLocalUsers(self, login):
    """
    Parameters:
     - login
    """
    pass

  def revokeSystemPermission(self, login, user, perm):
    """
    Parameters:
     - login
     - user
     - perm
    """
    pass

  def revokeTablePermission(self, login, user, table, perm):
    """
    Parameters:
     - login
     - user
     - table
     - perm
    """
    pass

  def createBatchScanner(self, login, tableName, options):
    """
    Parameters:
     - login
     - tableName
     - options
    """
    pass

  def createScanner(self, login, tableName, options):
    """
    Parameters:
     - login
     - tableName
     - options
    """
    pass

  def hasNext(self, scanner):
    """
    Parameters:
     - scanner
    """
    pass

  def nextEntry(self, scanner):
    """
    Parameters:
     - scanner
    """
    pass

  def nextK(self, scanner, k):
    """
    Parameters:
     - scanner
     - k
    """
    pass

  def closeScanner(self, scanner):
    """
    Parameters:
     - scanner
    """
    pass

  def updateAndFlush(self, login, tableName, cells):
    """
    Parameters:
     - login
     - tableName
     - cells
    """
    pass

  def createWriter(self, login, tableName, opts):
    """
    Parameters:
     - login
     - tableName
     - opts
    """
    pass

  def update(self, writer, cells):
    """
    Parameters:
     - writer
     - cells
    """
    pass

  def flush(self, writer):
    """
    Parameters:
     - writer
    """
    pass

  def closeWriter(self, writer):
    """
    Parameters:
     - writer
    """
    pass

  def updateRowConditionally(self, login, tableName, row, updates):
    """
    Parameters:
     - login
     - tableName
     - row
     - updates
    """
    pass

  def createConditionalWriter(self, login, tableName, options):
    """
    Parameters:
     - login
     - tableName
     - options
    """
    pass

  def updateRowsConditionally(self, conditionalWriter, updates):
    """
    Parameters:
     - conditionalWriter
     - updates
    """
    pass

  def closeConditionalWriter(self, conditionalWriter):
    """
    Parameters:
     - conditionalWriter
    """
    pass

  def getRowRange(self, row):
    """
    Parameters:
     - row
    """
    pass

  def getFollowing(self, key, part):
    """
    Parameters:
     - key
     - part
    """
    pass


class Client(Iface):
  def __init__(self, iprot, oprot=None):
    self._iprot = self._oprot = iprot
    if oprot is not None:
      self._oprot = oprot
    self._seqid = 0

  def login(self, principal, loginProperties):
    """
    Parameters:
     - principal
     - loginProperties
    """
    self.send_login(principal, loginProperties)
    return self.recv_login()

  def send_login(self, principal, loginProperties):
    self._oprot.writeMessageBegin('login', TMessageType.CALL, self._seqid)
    args = login_args()
    args.principal = principal
    args.loginProperties = loginProperties
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_login(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = login_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    if result.ouch2 is not None:
      raise result.ouch2
    raise TApplicationException(TApplicationException.MISSING_RESULT, "login failed: unknown result");

  def addConstraint(self, login, tableName, constraintClassName):
    """
    Parameters:
     - login
     - tableName
     - constraintClassName
    """
    self.send_addConstraint(login, tableName, constraintClassName)
    return self.recv_addConstraint()

  def send_addConstraint(self, login, tableName, constraintClassName):
    self._oprot.writeMessageBegin('addConstraint', TMessageType.CALL, self._seqid)
    args = addConstraint_args()
    args.login = login
    args.tableName = tableName
    args.constraintClassName = constraintClassName
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_addConstraint(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = addConstraint_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    raise TApplicationException(TApplicationException.MISSING_RESULT, "addConstraint failed: unknown result");

  def addSplits(self, login, tableName, splits):
    """
    Parameters:
     - login
     - tableName
     - splits
    """
    self.send_addSplits(login, tableName, splits)
    self.recv_addSplits()

  def send_addSplits(self, login, tableName, splits):
    self._oprot.writeMessageBegin('addSplits', TMessageType.CALL, self._seqid)
    args = addSplits_args()
    args.login = login
    args.tableName = tableName
    args.splits = splits
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_addSplits(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = addSplits_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    return

  def attachIterator(self, login, tableName, setting, scopes):
    """
    Parameters:
     - login
     - tableName
     - setting
     - scopes
    """
    self.send_attachIterator(login, tableName, setting, scopes)
    self.recv_attachIterator()

  def send_attachIterator(self, login, tableName, setting, scopes):
    self._oprot.writeMessageBegin('attachIterator', TMessageType.CALL, self._seqid)
    args = attachIterator_args()
    args.login = login
    args.tableName = tableName
    args.setting = setting
    args.scopes = scopes
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_attachIterator(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = attachIterator_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    return

  def checkIteratorConflicts(self, login, tableName, setting, scopes):
    """
    Parameters:
     - login
     - tableName
     - setting
     - scopes
    """
    self.send_checkIteratorConflicts(login, tableName, setting, scopes)
    self.recv_checkIteratorConflicts()

  def send_checkIteratorConflicts(self, login, tableName, setting, scopes):
    self._oprot.writeMessageBegin('checkIteratorConflicts', TMessageType.CALL, self._seqid)
    args = checkIteratorConflicts_args()
    args.login = login
    args.tableName = tableName
    args.setting = setting
    args.scopes = scopes
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_checkIteratorConflicts(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = checkIteratorConflicts_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    return

  def clearLocatorCache(self, login, tableName):
    """
    Parameters:
     - login
     - tableName
    """
    self.send_clearLocatorCache(login, tableName)
    self.recv_clearLocatorCache()

  def send_clearLocatorCache(self, login, tableName):
    self._oprot.writeMessageBegin('clearLocatorCache', TMessageType.CALL, self._seqid)
    args = clearLocatorCache_args()
    args.login = login
    args.tableName = tableName
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_clearLocatorCache(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = clearLocatorCache_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    return

  def cloneTable(self, login, tableName, newTableName, flush, propertiesToSet, propertiesToExclude):
    """
    Parameters:
     - login
     - tableName
     - newTableName
     - flush
     - propertiesToSet
     - propertiesToExclude
    """
    self.send_cloneTable(login, tableName, newTableName, flush, propertiesToSet, propertiesToExclude)
    self.recv_cloneTable()

  def send_cloneTable(self, login, tableName, newTableName, flush, propertiesToSet, propertiesToExclude):
    self._oprot.writeMessageBegin('cloneTable', TMessageType.CALL, self._seqid)
    args = cloneTable_args()
    args.login = login
    args.tableName = tableName
    args.newTableName = newTableName
    args.flush = flush
    args.propertiesToSet = propertiesToSet
    args.propertiesToExclude = propertiesToExclude
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_cloneTable(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = cloneTable_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    if result.ouch4 is not None:
      raise result.ouch4
    return

  def compactTable(self, login, tableName, startRow, endRow, iterators, flush, wait, compactionStrategy):
    """
    Parameters:
     - login
     - tableName
     - startRow
     - endRow
     - iterators
     - flush
     - wait
     - compactionStrategy
    """
    self.send_compactTable(login, tableName, startRow, endRow, iterators, flush, wait, compactionStrategy)
    self.recv_compactTable()

  def send_compactTable(self, login, tableName, startRow, endRow, iterators, flush, wait, compactionStrategy):
    self._oprot.writeMessageBegin('compactTable', TMessageType.CALL, self._seqid)
    args = compactTable_args()
    args.login = login
    args.tableName = tableName
    args.startRow = startRow
    args.endRow = endRow
    args.iterators = iterators
    args.flush = flush
    args.wait = wait
    args.compactionStrategy = compactionStrategy
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_compactTable(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = compactTable_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    return

  def cancelCompaction(self, login, tableName):
    """
    Parameters:
     - login
     - tableName
    """
    self.send_cancelCompaction(login, tableName)
    self.recv_cancelCompaction()

  def send_cancelCompaction(self, login, tableName):
    self._oprot.writeMessageBegin('cancelCompaction', TMessageType.CALL, self._seqid)
    args = cancelCompaction_args()
    args.login = login
    args.tableName = tableName
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_cancelCompaction(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = cancelCompaction_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    return

  def createTable(self, login, tableName, versioningIter, type):
    """
    Parameters:
     - login
     - tableName
     - versioningIter
     - type
    """
    self.send_createTable(login, tableName, versioningIter, type)
    self.recv_createTable()

  def send_createTable(self, login, tableName, versioningIter, type):
    self._oprot.writeMessageBegin('createTable', TMessageType.CALL, self._seqid)
    args = createTable_args()
    args.login = login
    args.tableName = tableName
    args.versioningIter = versioningIter
    args.type = type
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_createTable(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = createTable_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    return

  def deleteTable(self, login, tableName):
    """
    Parameters:
     - login
     - tableName
    """
    self.send_deleteTable(login, tableName)
    self.recv_deleteTable()

  def send_deleteTable(self, login, tableName):
    self._oprot.writeMessageBegin('deleteTable', TMessageType.CALL, self._seqid)
    args = deleteTable_args()
    args.login = login
    args.tableName = tableName
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_deleteTable(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = deleteTable_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    return

  def deleteRows(self, login, tableName, startRow, endRow):
    """
    Parameters:
     - login
     - tableName
     - startRow
     - endRow
    """
    self.send_deleteRows(login, tableName, startRow, endRow)
    self.recv_deleteRows()

  def send_deleteRows(self, login, tableName, startRow, endRow):
    self._oprot.writeMessageBegin('deleteRows', TMessageType.CALL, self._seqid)
    args = deleteRows_args()
    args.login = login
    args.tableName = tableName
    args.startRow = startRow
    args.endRow = endRow
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_deleteRows(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = deleteRows_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    return

  def exportTable(self, login, tableName, exportDir):
    """
    Parameters:
     - login
     - tableName
     - exportDir
    """
    self.send_exportTable(login, tableName, exportDir)
    self.recv_exportTable()

  def send_exportTable(self, login, tableName, exportDir):
    self._oprot.writeMessageBegin('exportTable', TMessageType.CALL, self._seqid)
    args = exportTable_args()
    args.login = login
    args.tableName = tableName
    args.exportDir = exportDir
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_exportTable(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = exportTable_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    return

  def flushTable(self, login, tableName, startRow, endRow, wait):
    """
    Parameters:
     - login
     - tableName
     - startRow
     - endRow
     - wait
    """
    self.send_flushTable(login, tableName, startRow, endRow, wait)
    self.recv_flushTable()

  def send_flushTable(self, login, tableName, startRow, endRow, wait):
    self._oprot.writeMessageBegin('flushTable', TMessageType.CALL, self._seqid)
    args = flushTable_args()
    args.login = login
    args.tableName = tableName
    args.startRow = startRow
    args.endRow = endRow
    args.wait = wait
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_flushTable(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = flushTable_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    return

  def getDiskUsage(self, login, tables):
    """
    Parameters:
     - login
     - tables
    """
    self.send_getDiskUsage(login, tables)
    return self.recv_getDiskUsage()

  def send_getDiskUsage(self, login, tables):
    self._oprot.writeMessageBegin('getDiskUsage', TMessageType.CALL, self._seqid)
    args = getDiskUsage_args()
    args.login = login
    args.tables = tables
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_getDiskUsage(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = getDiskUsage_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    raise TApplicationException(TApplicationException.MISSING_RESULT, "getDiskUsage failed: unknown result");

  def getLocalityGroups(self, login, tableName):
    """
    Parameters:
     - login
     - tableName
    """
    self.send_getLocalityGroups(login, tableName)
    return self.recv_getLocalityGroups()

  def send_getLocalityGroups(self, login, tableName):
    self._oprot.writeMessageBegin('getLocalityGroups', TMessageType.CALL, self._seqid)
    args = getLocalityGroups_args()
    args.login = login
    args.tableName = tableName
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_getLocalityGroups(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = getLocalityGroups_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    raise TApplicationException(TApplicationException.MISSING_RESULT, "getLocalityGroups failed: unknown result");

  def getIteratorSetting(self, login, tableName, iteratorName, scope):
    """
    Parameters:
     - login
     - tableName
     - iteratorName
     - scope
    """
    self.send_getIteratorSetting(login, tableName, iteratorName, scope)
    return self.recv_getIteratorSetting()

  def send_getIteratorSetting(self, login, tableName, iteratorName, scope):
    self._oprot.writeMessageBegin('getIteratorSetting', TMessageType.CALL, self._seqid)
    args = getIteratorSetting_args()
    args.login = login
    args.tableName = tableName
    args.iteratorName = iteratorName
    args.scope = scope
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_getIteratorSetting(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = getIteratorSetting_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    raise TApplicationException(TApplicationException.MISSING_RESULT, "getIteratorSetting failed: unknown result");

  def getMaxRow(self, login, tableName, auths, startRow, startInclusive, endRow, endInclusive):
    """
    Parameters:
     - login
     - tableName
     - auths
     - startRow
     - startInclusive
     - endRow
     - endInclusive
    """
    self.send_getMaxRow(login, tableName, auths, startRow, startInclusive, endRow, endInclusive)
    return self.recv_getMaxRow()

  def send_getMaxRow(self, login, tableName, auths, startRow, startInclusive, endRow, endInclusive):
    self._oprot.writeMessageBegin('getMaxRow', TMessageType.CALL, self._seqid)
    args = getMaxRow_args()
    args.login = login
    args.tableName = tableName
    args.auths = auths
    args.startRow = startRow
    args.startInclusive = startInclusive
    args.endRow = endRow
    args.endInclusive = endInclusive
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_getMaxRow(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = getMaxRow_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    raise TApplicationException(TApplicationException.MISSING_RESULT, "getMaxRow failed: unknown result");

  def getTableProperties(self, login, tableName):
    """
    Parameters:
     - login
     - tableName
    """
    self.send_getTableProperties(login, tableName)
    return self.recv_getTableProperties()

  def send_getTableProperties(self, login, tableName):
    self._oprot.writeMessageBegin('getTableProperties', TMessageType.CALL, self._seqid)
    args = getTableProperties_args()
    args.login = login
    args.tableName = tableName
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_getTableProperties(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = getTableProperties_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    raise TApplicationException(TApplicationException.MISSING_RESULT, "getTableProperties failed: unknown result");

  def importDirectory(self, login, tableName, importDir, failureDir, setTime):
    """
    Parameters:
     - login
     - tableName
     - importDir
     - failureDir
     - setTime
    """
    self.send_importDirectory(login, tableName, importDir, failureDir, setTime)
    self.recv_importDirectory()

  def send_importDirectory(self, login, tableName, importDir, failureDir, setTime):
    self._oprot.writeMessageBegin('importDirectory', TMessageType.CALL, self._seqid)
    args = importDirectory_args()
    args.login = login
    args.tableName = tableName
    args.importDir = importDir
    args.failureDir = failureDir
    args.setTime = setTime
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_importDirectory(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = importDirectory_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch3 is not None:
      raise result.ouch3
    if result.ouch4 is not None:
      raise result.ouch4
    return

  def importTable(self, login, tableName, importDir):
    """
    Parameters:
     - login
     - tableName
     - importDir
    """
    self.send_importTable(login, tableName, importDir)
    self.recv_importTable()

  def send_importTable(self, login, tableName, importDir):
    self._oprot.writeMessageBegin('importTable', TMessageType.CALL, self._seqid)
    args = importTable_args()
    args.login = login
    args.tableName = tableName
    args.importDir = importDir
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_importTable(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = importTable_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    return

  def listSplits(self, login, tableName, maxSplits):
    """
    Parameters:
     - login
     - tableName
     - maxSplits
    """
    self.send_listSplits(login, tableName, maxSplits)
    return self.recv_listSplits()

  def send_listSplits(self, login, tableName, maxSplits):
    self._oprot.writeMessageBegin('listSplits', TMessageType.CALL, self._seqid)
    args = listSplits_args()
    args.login = login
    args.tableName = tableName
    args.maxSplits = maxSplits
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_listSplits(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = listSplits_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    raise TApplicationException(TApplicationException.MISSING_RESULT, "listSplits failed: unknown result");

  def listTables(self, login):
    """
    Parameters:
     - login
    """
    self.send_listTables(login)
    return self.recv_listTables()

  def send_listTables(self, login):
    self._oprot.writeMessageBegin('listTables', TMessageType.CALL, self._seqid)
    args = listTables_args()
    args.login = login
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_listTables(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = listTables_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    raise TApplicationException(TApplicationException.MISSING_RESULT, "listTables failed: unknown result");

  def listIterators(self, login, tableName):
    """
    Parameters:
     - login
     - tableName
    """
    self.send_listIterators(login, tableName)
    return self.recv_listIterators()

  def send_listIterators(self, login, tableName):
    self._oprot.writeMessageBegin('listIterators', TMessageType.CALL, self._seqid)
    args = listIterators_args()
    args.login = login
    args.tableName = tableName
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_listIterators(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = listIterators_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    raise TApplicationException(TApplicationException.MISSING_RESULT, "listIterators failed: unknown result");

  def listConstraints(self, login, tableName):
    """
    Parameters:
     - login
     - tableName
    """
    self.send_listConstraints(login, tableName)
    return self.recv_listConstraints()

  def send_listConstraints(self, login, tableName):
    self._oprot.writeMessageBegin('listConstraints', TMessageType.CALL, self._seqid)
    args = listConstraints_args()
    args.login = login
    args.tableName = tableName
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_listConstraints(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = listConstraints_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    raise TApplicationException(TApplicationException.MISSING_RESULT, "listConstraints failed: unknown result");

  def mergeTablets(self, login, tableName, startRow, endRow):
    """
    Parameters:
     - login
     - tableName
     - startRow
     - endRow
    """
    self.send_mergeTablets(login, tableName, startRow, endRow)
    self.recv_mergeTablets()

  def send_mergeTablets(self, login, tableName, startRow, endRow):
    self._oprot.writeMessageBegin('mergeTablets', TMessageType.CALL, self._seqid)
    args = mergeTablets_args()
    args.login = login
    args.tableName = tableName
    args.startRow = startRow
    args.endRow = endRow
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_mergeTablets(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = mergeTablets_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    return

  def offlineTable(self, login, tableName, wait):
    """
    Parameters:
     - login
     - tableName
     - wait
    """
    self.send_offlineTable(login, tableName, wait)
    self.recv_offlineTable()

  def send_offlineTable(self, login, tableName, wait):
    self._oprot.writeMessageBegin('offlineTable', TMessageType.CALL, self._seqid)
    args = offlineTable_args()
    args.login = login
    args.tableName = tableName
    args.wait = wait
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_offlineTable(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = offlineTable_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    return

  def onlineTable(self, login, tableName, wait):
    """
    Parameters:
     - login
     - tableName
     - wait
    """
    self.send_onlineTable(login, tableName, wait)
    self.recv_onlineTable()

  def send_onlineTable(self, login, tableName, wait):
    self._oprot.writeMessageBegin('onlineTable', TMessageType.CALL, self._seqid)
    args = onlineTable_args()
    args.login = login
    args.tableName = tableName
    args.wait = wait
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_onlineTable(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = onlineTable_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    return

  def removeConstraint(self, login, tableName, constraint):
    """
    Parameters:
     - login
     - tableName
     - constraint
    """
    self.send_removeConstraint(login, tableName, constraint)
    self.recv_removeConstraint()

  def send_removeConstraint(self, login, tableName, constraint):
    self._oprot.writeMessageBegin('removeConstraint', TMessageType.CALL, self._seqid)
    args = removeConstraint_args()
    args.login = login
    args.tableName = tableName
    args.constraint = constraint
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_removeConstraint(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = removeConstraint_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    return

  def removeIterator(self, login, tableName, iterName, scopes):
    """
    Parameters:
     - login
     - tableName
     - iterName
     - scopes
    """
    self.send_removeIterator(login, tableName, iterName, scopes)
    self.recv_removeIterator()

  def send_removeIterator(self, login, tableName, iterName, scopes):
    self._oprot.writeMessageBegin('removeIterator', TMessageType.CALL, self._seqid)
    args = removeIterator_args()
    args.login = login
    args.tableName = tableName
    args.iterName = iterName
    args.scopes = scopes
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_removeIterator(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = removeIterator_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    return

  def removeTableProperty(self, login, tableName, property):
    """
    Parameters:
     - login
     - tableName
     - property
    """
    self.send_removeTableProperty(login, tableName, property)
    self.recv_removeTableProperty()

  def send_removeTableProperty(self, login, tableName, property):
    self._oprot.writeMessageBegin('removeTableProperty', TMessageType.CALL, self._seqid)
    args = removeTableProperty_args()
    args.login = login
    args.tableName = tableName
    args.property = property
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_removeTableProperty(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = removeTableProperty_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    return

  def renameTable(self, login, oldTableName, newTableName):
    """
    Parameters:
     - login
     - oldTableName
     - newTableName
    """
    self.send_renameTable(login, oldTableName, newTableName)
    self.recv_renameTable()

  def send_renameTable(self, login, oldTableName, newTableName):
    self._oprot.writeMessageBegin('renameTable', TMessageType.CALL, self._seqid)
    args = renameTable_args()
    args.login = login
    args.oldTableName = oldTableName
    args.newTableName = newTableName
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_renameTable(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = renameTable_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    if result.ouch4 is not None:
      raise result.ouch4
    return

  def setLocalityGroups(self, login, tableName, groups):
    """
    Parameters:
     - login
     - tableName
     - groups
    """
    self.send_setLocalityGroups(login, tableName, groups)
    self.recv_setLocalityGroups()

  def send_setLocalityGroups(self, login, tableName, groups):
    self._oprot.writeMessageBegin('setLocalityGroups', TMessageType.CALL, self._seqid)
    args = setLocalityGroups_args()
    args.login = login
    args.tableName = tableName
    args.groups = groups
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_setLocalityGroups(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = setLocalityGroups_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    return

  def setTableProperty(self, login, tableName, property, value):
    """
    Parameters:
     - login
     - tableName
     - property
     - value
    """
    self.send_setTableProperty(login, tableName, property, value)
    self.recv_setTableProperty()

  def send_setTableProperty(self, login, tableName, property, value):
    self._oprot.writeMessageBegin('setTableProperty', TMessageType.CALL, self._seqid)
    args = setTableProperty_args()
    args.login = login
    args.tableName = tableName
    args.property = property
    args.value = value
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_setTableProperty(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = setTableProperty_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    return

  def splitRangeByTablets(self, login, tableName, range, maxSplits):
    """
    Parameters:
     - login
     - tableName
     - range
     - maxSplits
    """
    self.send_splitRangeByTablets(login, tableName, range, maxSplits)
    return self.recv_splitRangeByTablets()

  def send_splitRangeByTablets(self, login, tableName, range, maxSplits):
    self._oprot.writeMessageBegin('splitRangeByTablets', TMessageType.CALL, self._seqid)
    args = splitRangeByTablets_args()
    args.login = login
    args.tableName = tableName
    args.range = range
    args.maxSplits = maxSplits
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_splitRangeByTablets(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = splitRangeByTablets_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    raise TApplicationException(TApplicationException.MISSING_RESULT, "splitRangeByTablets failed: unknown result");

  def tableExists(self, login, tableName):
    """
    Parameters:
     - login
     - tableName
    """
    self.send_tableExists(login, tableName)
    return self.recv_tableExists()

  def send_tableExists(self, login, tableName):
    self._oprot.writeMessageBegin('tableExists', TMessageType.CALL, self._seqid)
    args = tableExists_args()
    args.login = login
    args.tableName = tableName
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_tableExists(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = tableExists_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    raise TApplicationException(TApplicationException.MISSING_RESULT, "tableExists failed: unknown result");

  def tableIdMap(self, login):
    """
    Parameters:
     - login
    """
    self.send_tableIdMap(login)
    return self.recv_tableIdMap()

  def send_tableIdMap(self, login):
    self._oprot.writeMessageBegin('tableIdMap', TMessageType.CALL, self._seqid)
    args = tableIdMap_args()
    args.login = login
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_tableIdMap(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = tableIdMap_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    raise TApplicationException(TApplicationException.MISSING_RESULT, "tableIdMap failed: unknown result");

  def testTableClassLoad(self, login, tableName, className, asTypeName):
    """
    Parameters:
     - login
     - tableName
     - className
     - asTypeName
    """
    self.send_testTableClassLoad(login, tableName, className, asTypeName)
    return self.recv_testTableClassLoad()

  def send_testTableClassLoad(self, login, tableName, className, asTypeName):
    self._oprot.writeMessageBegin('testTableClassLoad', TMessageType.CALL, self._seqid)
    args = testTableClassLoad_args()
    args.login = login
    args.tableName = tableName
    args.className = className
    args.asTypeName = asTypeName
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_testTableClassLoad(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = testTableClassLoad_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    raise TApplicationException(TApplicationException.MISSING_RESULT, "testTableClassLoad failed: unknown result");

  def pingTabletServer(self, login, tserver):
    """
    Parameters:
     - login
     - tserver
    """
    self.send_pingTabletServer(login, tserver)
    self.recv_pingTabletServer()

  def send_pingTabletServer(self, login, tserver):
    self._oprot.writeMessageBegin('pingTabletServer', TMessageType.CALL, self._seqid)
    args = pingTabletServer_args()
    args.login = login
    args.tserver = tserver
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_pingTabletServer(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = pingTabletServer_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    return

  def getActiveScans(self, login, tserver):
    """
    Parameters:
     - login
     - tserver
    """
    self.send_getActiveScans(login, tserver)
    return self.recv_getActiveScans()

  def send_getActiveScans(self, login, tserver):
    self._oprot.writeMessageBegin('getActiveScans', TMessageType.CALL, self._seqid)
    args = getActiveScans_args()
    args.login = login
    args.tserver = tserver
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_getActiveScans(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = getActiveScans_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    raise TApplicationException(TApplicationException.MISSING_RESULT, "getActiveScans failed: unknown result");

  def getActiveCompactions(self, login, tserver):
    """
    Parameters:
     - login
     - tserver
    """
    self.send_getActiveCompactions(login, tserver)
    return self.recv_getActiveCompactions()

  def send_getActiveCompactions(self, login, tserver):
    self._oprot.writeMessageBegin('getActiveCompactions', TMessageType.CALL, self._seqid)
    args = getActiveCompactions_args()
    args.login = login
    args.tserver = tserver
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_getActiveCompactions(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = getActiveCompactions_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    raise TApplicationException(TApplicationException.MISSING_RESULT, "getActiveCompactions failed: unknown result");

  def getSiteConfiguration(self, login):
    """
    Parameters:
     - login
    """
    self.send_getSiteConfiguration(login)
    return self.recv_getSiteConfiguration()

  def send_getSiteConfiguration(self, login):
    self._oprot.writeMessageBegin('getSiteConfiguration', TMessageType.CALL, self._seqid)
    args = getSiteConfiguration_args()
    args.login = login
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_getSiteConfiguration(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = getSiteConfiguration_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    raise TApplicationException(TApplicationException.MISSING_RESULT, "getSiteConfiguration failed: unknown result");

  def getSystemConfiguration(self, login):
    """
    Parameters:
     - login
    """
    self.send_getSystemConfiguration(login)
    return self.recv_getSystemConfiguration()

  def send_getSystemConfiguration(self, login):
    self._oprot.writeMessageBegin('getSystemConfiguration', TMessageType.CALL, self._seqid)
    args = getSystemConfiguration_args()
    args.login = login
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_getSystemConfiguration(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = getSystemConfiguration_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    raise TApplicationException(TApplicationException.MISSING_RESULT, "getSystemConfiguration failed: unknown result");

  def getTabletServers(self, login):
    """
    Parameters:
     - login
    """
    self.send_getTabletServers(login)
    return self.recv_getTabletServers()

  def send_getTabletServers(self, login):
    self._oprot.writeMessageBegin('getTabletServers', TMessageType.CALL, self._seqid)
    args = getTabletServers_args()
    args.login = login
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_getTabletServers(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = getTabletServers_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    raise TApplicationException(TApplicationException.MISSING_RESULT, "getTabletServers failed: unknown result");

  def removeProperty(self, login, property):
    """
    Parameters:
     - login
     - property
    """
    self.send_removeProperty(login, property)
    self.recv_removeProperty()

  def send_removeProperty(self, login, property):
    self._oprot.writeMessageBegin('removeProperty', TMessageType.CALL, self._seqid)
    args = removeProperty_args()
    args.login = login
    args.property = property
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_removeProperty(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = removeProperty_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    return

  def setProperty(self, login, property, value):
    """
    Parameters:
     - login
     - property
     - value
    """
    self.send_setProperty(login, property, value)
    self.recv_setProperty()

  def send_setProperty(self, login, property, value):
    self._oprot.writeMessageBegin('setProperty', TMessageType.CALL, self._seqid)
    args = setProperty_args()
    args.login = login
    args.property = property
    args.value = value
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_setProperty(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = setProperty_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    return

  def testClassLoad(self, login, className, asTypeName):
    """
    Parameters:
     - login
     - className
     - asTypeName
    """
    self.send_testClassLoad(login, className, asTypeName)
    return self.recv_testClassLoad()

  def send_testClassLoad(self, login, className, asTypeName):
    self._oprot.writeMessageBegin('testClassLoad', TMessageType.CALL, self._seqid)
    args = testClassLoad_args()
    args.login = login
    args.className = className
    args.asTypeName = asTypeName
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_testClassLoad(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = testClassLoad_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    raise TApplicationException(TApplicationException.MISSING_RESULT, "testClassLoad failed: unknown result");

  def authenticateUser(self, login, user, properties):
    """
    Parameters:
     - login
     - user
     - properties
    """
    self.send_authenticateUser(login, user, properties)
    return self.recv_authenticateUser()

  def send_authenticateUser(self, login, user, properties):
    self._oprot.writeMessageBegin('authenticateUser', TMessageType.CALL, self._seqid)
    args = authenticateUser_args()
    args.login = login
    args.user = user
    args.properties = properties
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_authenticateUser(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = authenticateUser_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    raise TApplicationException(TApplicationException.MISSING_RESULT, "authenticateUser failed: unknown result");

  def changeUserAuthorizations(self, login, user, authorizations):
    """
    Parameters:
     - login
     - user
     - authorizations
    """
    self.send_changeUserAuthorizations(login, user, authorizations)
    self.recv_changeUserAuthorizations()

  def send_changeUserAuthorizations(self, login, user, authorizations):
    self._oprot.writeMessageBegin('changeUserAuthorizations', TMessageType.CALL, self._seqid)
    args = changeUserAuthorizations_args()
    args.login = login
    args.user = user
    args.authorizations = authorizations
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_changeUserAuthorizations(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = changeUserAuthorizations_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    return

  def changeLocalUserPassword(self, login, user, password):
    """
    Parameters:
     - login
     - user
     - password
    """
    self.send_changeLocalUserPassword(login, user, password)
    self.recv_changeLocalUserPassword()

  def send_changeLocalUserPassword(self, login, user, password):
    self._oprot.writeMessageBegin('changeLocalUserPassword', TMessageType.CALL, self._seqid)
    args = changeLocalUserPassword_args()
    args.login = login
    args.user = user
    args.password = password
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_changeLocalUserPassword(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = changeLocalUserPassword_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    return

  def createLocalUser(self, login, user, password):
    """
    Parameters:
     - login
     - user
     - password
    """
    self.send_createLocalUser(login, user, password)
    self.recv_createLocalUser()

  def send_createLocalUser(self, login, user, password):
    self._oprot.writeMessageBegin('createLocalUser', TMessageType.CALL, self._seqid)
    args = createLocalUser_args()
    args.login = login
    args.user = user
    args.password = password
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_createLocalUser(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = createLocalUser_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    return

  def dropLocalUser(self, login, user):
    """
    Parameters:
     - login
     - user
    """
    self.send_dropLocalUser(login, user)
    self.recv_dropLocalUser()

  def send_dropLocalUser(self, login, user):
    self._oprot.writeMessageBegin('dropLocalUser', TMessageType.CALL, self._seqid)
    args = dropLocalUser_args()
    args.login = login
    args.user = user
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_dropLocalUser(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = dropLocalUser_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    return

  def getUserAuthorizations(self, login, user):
    """
    Parameters:
     - login
     - user
    """
    self.send_getUserAuthorizations(login, user)
    return self.recv_getUserAuthorizations()

  def send_getUserAuthorizations(self, login, user):
    self._oprot.writeMessageBegin('getUserAuthorizations', TMessageType.CALL, self._seqid)
    args = getUserAuthorizations_args()
    args.login = login
    args.user = user
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_getUserAuthorizations(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = getUserAuthorizations_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    raise TApplicationException(TApplicationException.MISSING_RESULT, "getUserAuthorizations failed: unknown result");

  def grantSystemPermission(self, login, user, perm):
    """
    Parameters:
     - login
     - user
     - perm
    """
    self.send_grantSystemPermission(login, user, perm)
    self.recv_grantSystemPermission()

  def send_grantSystemPermission(self, login, user, perm):
    self._oprot.writeMessageBegin('grantSystemPermission', TMessageType.CALL, self._seqid)
    args = grantSystemPermission_args()
    args.login = login
    args.user = user
    args.perm = perm
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_grantSystemPermission(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = grantSystemPermission_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    return

  def grantTablePermission(self, login, user, table, perm):
    """
    Parameters:
     - login
     - user
     - table
     - perm
    """
    self.send_grantTablePermission(login, user, table, perm)
    self.recv_grantTablePermission()

  def send_grantTablePermission(self, login, user, table, perm):
    self._oprot.writeMessageBegin('grantTablePermission', TMessageType.CALL, self._seqid)
    args = grantTablePermission_args()
    args.login = login
    args.user = user
    args.table = table
    args.perm = perm
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_grantTablePermission(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = grantTablePermission_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    return

  def hasSystemPermission(self, login, user, perm):
    """
    Parameters:
     - login
     - user
     - perm
    """
    self.send_hasSystemPermission(login, user, perm)
    return self.recv_hasSystemPermission()

  def send_hasSystemPermission(self, login, user, perm):
    self._oprot.writeMessageBegin('hasSystemPermission', TMessageType.CALL, self._seqid)
    args = hasSystemPermission_args()
    args.login = login
    args.user = user
    args.perm = perm
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_hasSystemPermission(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = hasSystemPermission_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    raise TApplicationException(TApplicationException.MISSING_RESULT, "hasSystemPermission failed: unknown result");

  def hasTablePermission(self, login, user, table, perm):
    """
    Parameters:
     - login
     - user
     - table
     - perm
    """
    self.send_hasTablePermission(login, user, table, perm)
    return self.recv_hasTablePermission()

  def send_hasTablePermission(self, login, user, table, perm):
    self._oprot.writeMessageBegin('hasTablePermission', TMessageType.CALL, self._seqid)
    args = hasTablePermission_args()
    args.login = login
    args.user = user
    args.table = table
    args.perm = perm
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_hasTablePermission(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = hasTablePermission_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    raise TApplicationException(TApplicationException.MISSING_RESULT, "hasTablePermission failed: unknown result");

  def listLocalUsers(self, login):
    """
    Parameters:
     - login
    """
    self.send_listLocalUsers(login)
    return self.recv_listLocalUsers()

  def send_listLocalUsers(self, login):
    self._oprot.writeMessageBegin('listLocalUsers', TMessageType.CALL, self._seqid)
    args = listLocalUsers_args()
    args.login = login
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_listLocalUsers(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = listLocalUsers_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    raise TApplicationException(TApplicationException.MISSING_RESULT, "listLocalUsers failed: unknown result");

  def revokeSystemPermission(self, login, user, perm):
    """
    Parameters:
     - login
     - user
     - perm
    """
    self.send_revokeSystemPermission(login, user, perm)
    self.recv_revokeSystemPermission()

  def send_revokeSystemPermission(self, login, user, perm):
    self._oprot.writeMessageBegin('revokeSystemPermission', TMessageType.CALL, self._seqid)
    args = revokeSystemPermission_args()
    args.login = login
    args.user = user
    args.perm = perm
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_revokeSystemPermission(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = revokeSystemPermission_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    return

  def revokeTablePermission(self, login, user, table, perm):
    """
    Parameters:
     - login
     - user
     - table
     - perm
    """
    self.send_revokeTablePermission(login, user, table, perm)
    self.recv_revokeTablePermission()

  def send_revokeTablePermission(self, login, user, table, perm):
    self._oprot.writeMessageBegin('revokeTablePermission', TMessageType.CALL, self._seqid)
    args = revokeTablePermission_args()
    args.login = login
    args.user = user
    args.table = table
    args.perm = perm
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_revokeTablePermission(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = revokeTablePermission_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    return

  def createBatchScanner(self, login, tableName, options):
    """
    Parameters:
     - login
     - tableName
     - options
    """
    self.send_createBatchScanner(login, tableName, options)
    return self.recv_createBatchScanner()

  def send_createBatchScanner(self, login, tableName, options):
    self._oprot.writeMessageBegin('createBatchScanner', TMessageType.CALL, self._seqid)
    args = createBatchScanner_args()
    args.login = login
    args.tableName = tableName
    args.options = options
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_createBatchScanner(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = createBatchScanner_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    raise TApplicationException(TApplicationException.MISSING_RESULT, "createBatchScanner failed: unknown result");

  def createScanner(self, login, tableName, options):
    """
    Parameters:
     - login
     - tableName
     - options
    """
    self.send_createScanner(login, tableName, options)
    return self.recv_createScanner()

  def send_createScanner(self, login, tableName, options):
    self._oprot.writeMessageBegin('createScanner', TMessageType.CALL, self._seqid)
    args = createScanner_args()
    args.login = login
    args.tableName = tableName
    args.options = options
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_createScanner(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = createScanner_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    raise TApplicationException(TApplicationException.MISSING_RESULT, "createScanner failed: unknown result");

  def hasNext(self, scanner):
    """
    Parameters:
     - scanner
    """
    self.send_hasNext(scanner)
    return self.recv_hasNext()

  def send_hasNext(self, scanner):
    self._oprot.writeMessageBegin('hasNext', TMessageType.CALL, self._seqid)
    args = hasNext_args()
    args.scanner = scanner
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_hasNext(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = hasNext_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    if result.ouch1 is not None:
      raise result.ouch1
    raise TApplicationException(TApplicationException.MISSING_RESULT, "hasNext failed: unknown result");

  def nextEntry(self, scanner):
    """
    Parameters:
     - scanner
    """
    self.send_nextEntry(scanner)
    return self.recv_nextEntry()

  def send_nextEntry(self, scanner):
    self._oprot.writeMessageBegin('nextEntry', TMessageType.CALL, self._seqid)
    args = nextEntry_args()
    args.scanner = scanner
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_nextEntry(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = nextEntry_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    raise TApplicationException(TApplicationException.MISSING_RESULT, "nextEntry failed: unknown result");

  def nextK(self, scanner, k):
    """
    Parameters:
     - scanner
     - k
    """
    self.send_nextK(scanner, k)
    return self.recv_nextK()

  def send_nextK(self, scanner, k):
    self._oprot.writeMessageBegin('nextK', TMessageType.CALL, self._seqid)
    args = nextK_args()
    args.scanner = scanner
    args.k = k
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_nextK(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = nextK_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    raise TApplicationException(TApplicationException.MISSING_RESULT, "nextK failed: unknown result");

  def closeScanner(self, scanner):
    """
    Parameters:
     - scanner
    """
    self.send_closeScanner(scanner)
    self.recv_closeScanner()

  def send_closeScanner(self, scanner):
    self._oprot.writeMessageBegin('closeScanner', TMessageType.CALL, self._seqid)
    args = closeScanner_args()
    args.scanner = scanner
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_closeScanner(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = closeScanner_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    return

  def updateAndFlush(self, login, tableName, cells):
    """
    Parameters:
     - login
     - tableName
     - cells
    """
    self.send_updateAndFlush(login, tableName, cells)
    self.recv_updateAndFlush()

  def send_updateAndFlush(self, login, tableName, cells):
    self._oprot.writeMessageBegin('updateAndFlush', TMessageType.CALL, self._seqid)
    args = updateAndFlush_args()
    args.login = login
    args.tableName = tableName
    args.cells = cells
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_updateAndFlush(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = updateAndFlush_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.outch1 is not None:
      raise result.outch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    if result.ouch4 is not None:
      raise result.ouch4
    return

  def createWriter(self, login, tableName, opts):
    """
    Parameters:
     - login
     - tableName
     - opts
    """
    self.send_createWriter(login, tableName, opts)
    return self.recv_createWriter()

  def send_createWriter(self, login, tableName, opts):
    self._oprot.writeMessageBegin('createWriter', TMessageType.CALL, self._seqid)
    args = createWriter_args()
    args.login = login
    args.tableName = tableName
    args.opts = opts
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_createWriter(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = createWriter_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    if result.outch1 is not None:
      raise result.outch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    raise TApplicationException(TApplicationException.MISSING_RESULT, "createWriter failed: unknown result");

  def update(self, writer, cells):
    """
    Parameters:
     - writer
     - cells
    """
    self.send_update(writer, cells)

  def send_update(self, writer, cells):
    self._oprot.writeMessageBegin('update', TMessageType.CALL, self._seqid)
    args = update_args()
    args.writer = writer
    args.cells = cells
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()
  def flush(self, writer):
    """
    Parameters:
     - writer
    """
    self.send_flush(writer)
    self.recv_flush()

  def send_flush(self, writer):
    self._oprot.writeMessageBegin('flush', TMessageType.CALL, self._seqid)
    args = flush_args()
    args.writer = writer
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_flush(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = flush_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    return

  def closeWriter(self, writer):
    """
    Parameters:
     - writer
    """
    self.send_closeWriter(writer)
    self.recv_closeWriter()

  def send_closeWriter(self, writer):
    self._oprot.writeMessageBegin('closeWriter', TMessageType.CALL, self._seqid)
    args = closeWriter_args()
    args.writer = writer
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_closeWriter(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = closeWriter_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    return

  def updateRowConditionally(self, login, tableName, row, updates):
    """
    Parameters:
     - login
     - tableName
     - row
     - updates
    """
    self.send_updateRowConditionally(login, tableName, row, updates)
    return self.recv_updateRowConditionally()

  def send_updateRowConditionally(self, login, tableName, row, updates):
    self._oprot.writeMessageBegin('updateRowConditionally', TMessageType.CALL, self._seqid)
    args = updateRowConditionally_args()
    args.login = login
    args.tableName = tableName
    args.row = row
    args.updates = updates
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_updateRowConditionally(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = updateRowConditionally_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    raise TApplicationException(TApplicationException.MISSING_RESULT, "updateRowConditionally failed: unknown result");

  def createConditionalWriter(self, login, tableName, options):
    """
    Parameters:
     - login
     - tableName
     - options
    """
    self.send_createConditionalWriter(login, tableName, options)
    return self.recv_createConditionalWriter()

  def send_createConditionalWriter(self, login, tableName, options):
    self._oprot.writeMessageBegin('createConditionalWriter', TMessageType.CALL, self._seqid)
    args = createConditionalWriter_args()
    args.login = login
    args.tableName = tableName
    args.options = options
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_createConditionalWriter(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = createConditionalWriter_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    raise TApplicationException(TApplicationException.MISSING_RESULT, "createConditionalWriter failed: unknown result");

  def updateRowsConditionally(self, conditionalWriter, updates):
    """
    Parameters:
     - conditionalWriter
     - updates
    """
    self.send_updateRowsConditionally(conditionalWriter, updates)
    return self.recv_updateRowsConditionally()

  def send_updateRowsConditionally(self, conditionalWriter, updates):
    self._oprot.writeMessageBegin('updateRowsConditionally', TMessageType.CALL, self._seqid)
    args = updateRowsConditionally_args()
    args.conditionalWriter = conditionalWriter
    args.updates = updates
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_updateRowsConditionally(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = updateRowsConditionally_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    if result.ouch1 is not None:
      raise result.ouch1
    if result.ouch2 is not None:
      raise result.ouch2
    if result.ouch3 is not None:
      raise result.ouch3
    raise TApplicationException(TApplicationException.MISSING_RESULT, "updateRowsConditionally failed: unknown result");

  def closeConditionalWriter(self, conditionalWriter):
    """
    Parameters:
     - conditionalWriter
    """
    self.send_closeConditionalWriter(conditionalWriter)
    self.recv_closeConditionalWriter()

  def send_closeConditionalWriter(self, conditionalWriter):
    self._oprot.writeMessageBegin('closeConditionalWriter', TMessageType.CALL, self._seqid)
    args = closeConditionalWriter_args()
    args.conditionalWriter = conditionalWriter
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_closeConditionalWriter(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = closeConditionalWriter_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    return

  def getRowRange(self, row):
    """
    Parameters:
     - row
    """
    self.send_getRowRange(row)
    return self.recv_getRowRange()

  def send_getRowRange(self, row):
    self._oprot.writeMessageBegin('getRowRange', TMessageType.CALL, self._seqid)
    args = getRowRange_args()
    args.row = row
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_getRowRange(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = getRowRange_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    raise TApplicationException(TApplicationException.MISSING_RESULT, "getRowRange failed: unknown result");

  def getFollowing(self, key, part):
    """
    Parameters:
     - key
     - part
    """
    self.send_getFollowing(key, part)
    return self.recv_getFollowing()

  def send_getFollowing(self, key, part):
    self._oprot.writeMessageBegin('getFollowing', TMessageType.CALL, self._seqid)
    args = getFollowing_args()
    args.key = key
    args.part = part
    args.write(self._oprot)
    self._oprot.writeMessageEnd()
    self._oprot.trans.flush()

  def recv_getFollowing(self):
    (fname, mtype, rseqid) = self._iprot.readMessageBegin()
    if mtype == TMessageType.EXCEPTION:
      x = TApplicationException()
      x.read(self._iprot)
      self._iprot.readMessageEnd()
      raise x
    result = getFollowing_result()
    result.read(self._iprot)
    self._iprot.readMessageEnd()
    if result.success is not None:
      return result.success
    raise TApplicationException(TApplicationException.MISSING_RESULT, "getFollowing failed: unknown result");


class Processor(Iface, TProcessor):
  def __init__(self, handler):
    self._handler = handler
    self._processMap = {}
    self._processMap["login"] = Processor.process_login
    self._processMap["addConstraint"] = Processor.process_addConstraint
    self._processMap["addSplits"] = Processor.process_addSplits
    self._processMap["attachIterator"] = Processor.process_attachIterator
    self._processMap["checkIteratorConflicts"] = Processor.process_checkIteratorConflicts
    self._processMap["clearLocatorCache"] = Processor.process_clearLocatorCache
    self._processMap["cloneTable"] = Processor.process_cloneTable
    self._processMap["compactTable"] = Processor.process_compactTable
    self._processMap["cancelCompaction"] = Processor.process_cancelCompaction
    self._processMap["createTable"] = Processor.process_createTable
    self._processMap["deleteTable"] = Processor.process_deleteTable
    self._processMap["deleteRows"] = Processor.process_deleteRows
    self._processMap["exportTable"] = Processor.process_exportTable
    self._processMap["flushTable"] = Processor.process_flushTable
    self._processMap["getDiskUsage"] = Processor.process_getDiskUsage
    self._processMap["getLocalityGroups"] = Processor.process_getLocalityGroups
    self._processMap["getIteratorSetting"] = Processor.process_getIteratorSetting
    self._processMap["getMaxRow"] = Processor.process_getMaxRow
    self._processMap["getTableProperties"] = Processor.process_getTableProperties
    self._processMap["importDirectory"] = Processor.process_importDirectory
    self._processMap["importTable"] = Processor.process_importTable
    self._processMap["listSplits"] = Processor.process_listSplits
    self._processMap["listTables"] = Processor.process_listTables
    self._processMap["listIterators"] = Processor.process_listIterators
    self._processMap["listConstraints"] = Processor.process_listConstraints
    self._processMap["mergeTablets"] = Processor.process_mergeTablets
    self._processMap["offlineTable"] = Processor.process_offlineTable
    self._processMap["onlineTable"] = Processor.process_onlineTable
    self._processMap["removeConstraint"] = Processor.process_removeConstraint
    self._processMap["removeIterator"] = Processor.process_removeIterator
    self._processMap["removeTableProperty"] = Processor.process_removeTableProperty
    self._processMap["renameTable"] = Processor.process_renameTable
    self._processMap["setLocalityGroups"] = Processor.process_setLocalityGroups
    self._processMap["setTableProperty"] = Processor.process_setTableProperty
    self._processMap["splitRangeByTablets"] = Processor.process_splitRangeByTablets
    self._processMap["tableExists"] = Processor.process_tableExists
    self._processMap["tableIdMap"] = Processor.process_tableIdMap
    self._processMap["testTableClassLoad"] = Processor.process_testTableClassLoad
    self._processMap["pingTabletServer"] = Processor.process_pingTabletServer
    self._processMap["getActiveScans"] = Processor.process_getActiveScans
    self._processMap["getActiveCompactions"] = Processor.process_getActiveCompactions
    self._processMap["getSiteConfiguration"] = Processor.process_getSiteConfiguration
    self._processMap["getSystemConfiguration"] = Processor.process_getSystemConfiguration
    self._processMap["getTabletServers"] = Processor.process_getTabletServers
    self._processMap["removeProperty"] = Processor.process_removeProperty
    self._processMap["setProperty"] = Processor.process_setProperty
    self._processMap["testClassLoad"] = Processor.process_testClassLoad
    self._processMap["authenticateUser"] = Processor.process_authenticateUser
    self._processMap["changeUserAuthorizations"] = Processor.process_changeUserAuthorizations
    self._processMap["changeLocalUserPassword"] = Processor.process_changeLocalUserPassword
    self._processMap["createLocalUser"] = Processor.process_createLocalUser
    self._processMap["dropLocalUser"] = Processor.process_dropLocalUser
    self._processMap["getUserAuthorizations"] = Processor.process_getUserAuthorizations
    self._processMap["grantSystemPermission"] = Processor.process_grantSystemPermission
    self._processMap["grantTablePermission"] = Processor.process_grantTablePermission
    self._processMap["hasSystemPermission"] = Processor.process_hasSystemPermission
    self._processMap["hasTablePermission"] = Processor.process_hasTablePermission
    self._processMap["listLocalUsers"] = Processor.process_listLocalUsers
    self._processMap["revokeSystemPermission"] = Processor.process_revokeSystemPermission
    self._processMap["revokeTablePermission"] = Processor.process_revokeTablePermission
    self._processMap["createBatchScanner"] = Processor.process_createBatchScanner
    self._processMap["createScanner"] = Processor.process_createScanner
    self._processMap["hasNext"] = Processor.process_hasNext
    self._processMap["nextEntry"] = Processor.process_nextEntry
    self._processMap["nextK"] = Processor.process_nextK
    self._processMap["closeScanner"] = Processor.process_closeScanner
    self._processMap["updateAndFlush"] = Processor.process_updateAndFlush
    self._processMap["createWriter"] = Processor.process_createWriter
    self._processMap["update"] = Processor.process_update
    self._processMap["flush"] = Processor.process_flush
    self._processMap["closeWriter"] = Processor.process_closeWriter
    self._processMap["updateRowConditionally"] = Processor.process_updateRowConditionally
    self._processMap["createConditionalWriter"] = Processor.process_createConditionalWriter
    self._processMap["updateRowsConditionally"] = Processor.process_updateRowsConditionally
    self._processMap["closeConditionalWriter"] = Processor.process_closeConditionalWriter
    self._processMap["getRowRange"] = Processor.process_getRowRange
    self._processMap["getFollowing"] = Processor.process_getFollowing

  def process(self, iprot, oprot):
    (name, type, seqid) = iprot.readMessageBegin()
    if name not in self._processMap:
      iprot.skip(TType.STRUCT)
      iprot.readMessageEnd()
      x = TApplicationException(TApplicationException.UNKNOWN_METHOD, 'Unknown function %s' % (name))
      oprot.writeMessageBegin(name, TMessageType.EXCEPTION, seqid)
      x.write(oprot)
      oprot.writeMessageEnd()
      oprot.trans.flush()
      return
    else:
      self._processMap[name](self, seqid, iprot, oprot)
    return True

  def process_login(self, seqid, iprot, oprot):
    args = login_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = login_result()
    try:
      result.success = self._handler.login(args.principal, args.loginProperties)
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    oprot.writeMessageBegin("login", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_addConstraint(self, seqid, iprot, oprot):
    args = addConstraint_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = addConstraint_result()
    try:
      result.success = self._handler.addConstraint(args.login, args.tableName, args.constraintClassName)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("addConstraint", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_addSplits(self, seqid, iprot, oprot):
    args = addSplits_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = addSplits_result()
    try:
      self._handler.addSplits(args.login, args.tableName, args.splits)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("addSplits", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_attachIterator(self, seqid, iprot, oprot):
    args = attachIterator_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = attachIterator_result()
    try:
      self._handler.attachIterator(args.login, args.tableName, args.setting, args.scopes)
    except AccumuloSecurityException, ouch1:
      result.ouch1 = ouch1
    except AccumuloException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("attachIterator", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_checkIteratorConflicts(self, seqid, iprot, oprot):
    args = checkIteratorConflicts_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = checkIteratorConflicts_result()
    try:
      self._handler.checkIteratorConflicts(args.login, args.tableName, args.setting, args.scopes)
    except AccumuloSecurityException, ouch1:
      result.ouch1 = ouch1
    except AccumuloException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("checkIteratorConflicts", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_clearLocatorCache(self, seqid, iprot, oprot):
    args = clearLocatorCache_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = clearLocatorCache_result()
    try:
      self._handler.clearLocatorCache(args.login, args.tableName)
    except TableNotFoundException, ouch1:
      result.ouch1 = ouch1
    oprot.writeMessageBegin("clearLocatorCache", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_cloneTable(self, seqid, iprot, oprot):
    args = cloneTable_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = cloneTable_result()
    try:
      self._handler.cloneTable(args.login, args.tableName, args.newTableName, args.flush, args.propertiesToSet, args.propertiesToExclude)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    except TableExistsException, ouch4:
      result.ouch4 = ouch4
    oprot.writeMessageBegin("cloneTable", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_compactTable(self, seqid, iprot, oprot):
    args = compactTable_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = compactTable_result()
    try:
      self._handler.compactTable(args.login, args.tableName, args.startRow, args.endRow, args.iterators, args.flush, args.wait, args.compactionStrategy)
    except AccumuloSecurityException, ouch1:
      result.ouch1 = ouch1
    except TableNotFoundException, ouch2:
      result.ouch2 = ouch2
    except AccumuloException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("compactTable", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_cancelCompaction(self, seqid, iprot, oprot):
    args = cancelCompaction_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = cancelCompaction_result()
    try:
      self._handler.cancelCompaction(args.login, args.tableName)
    except AccumuloSecurityException, ouch1:
      result.ouch1 = ouch1
    except TableNotFoundException, ouch2:
      result.ouch2 = ouch2
    except AccumuloException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("cancelCompaction", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_createTable(self, seqid, iprot, oprot):
    args = createTable_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = createTable_result()
    try:
      self._handler.createTable(args.login, args.tableName, args.versioningIter, args.type)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableExistsException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("createTable", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_deleteTable(self, seqid, iprot, oprot):
    args = deleteTable_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = deleteTable_result()
    try:
      self._handler.deleteTable(args.login, args.tableName)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("deleteTable", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_deleteRows(self, seqid, iprot, oprot):
    args = deleteRows_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = deleteRows_result()
    try:
      self._handler.deleteRows(args.login, args.tableName, args.startRow, args.endRow)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("deleteRows", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_exportTable(self, seqid, iprot, oprot):
    args = exportTable_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = exportTable_result()
    try:
      self._handler.exportTable(args.login, args.tableName, args.exportDir)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("exportTable", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_flushTable(self, seqid, iprot, oprot):
    args = flushTable_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = flushTable_result()
    try:
      self._handler.flushTable(args.login, args.tableName, args.startRow, args.endRow, args.wait)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("flushTable", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_getDiskUsage(self, seqid, iprot, oprot):
    args = getDiskUsage_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = getDiskUsage_result()
    try:
      result.success = self._handler.getDiskUsage(args.login, args.tables)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("getDiskUsage", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_getLocalityGroups(self, seqid, iprot, oprot):
    args = getLocalityGroups_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = getLocalityGroups_result()
    try:
      result.success = self._handler.getLocalityGroups(args.login, args.tableName)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("getLocalityGroups", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_getIteratorSetting(self, seqid, iprot, oprot):
    args = getIteratorSetting_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = getIteratorSetting_result()
    try:
      result.success = self._handler.getIteratorSetting(args.login, args.tableName, args.iteratorName, args.scope)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("getIteratorSetting", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_getMaxRow(self, seqid, iprot, oprot):
    args = getMaxRow_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = getMaxRow_result()
    try:
      result.success = self._handler.getMaxRow(args.login, args.tableName, args.auths, args.startRow, args.startInclusive, args.endRow, args.endInclusive)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("getMaxRow", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_getTableProperties(self, seqid, iprot, oprot):
    args = getTableProperties_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = getTableProperties_result()
    try:
      result.success = self._handler.getTableProperties(args.login, args.tableName)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("getTableProperties", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_importDirectory(self, seqid, iprot, oprot):
    args = importDirectory_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = importDirectory_result()
    try:
      self._handler.importDirectory(args.login, args.tableName, args.importDir, args.failureDir, args.setTime)
    except TableNotFoundException, ouch1:
      result.ouch1 = ouch1
    except AccumuloException, ouch3:
      result.ouch3 = ouch3
    except AccumuloSecurityException, ouch4:
      result.ouch4 = ouch4
    oprot.writeMessageBegin("importDirectory", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_importTable(self, seqid, iprot, oprot):
    args = importTable_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = importTable_result()
    try:
      self._handler.importTable(args.login, args.tableName, args.importDir)
    except TableExistsException, ouch1:
      result.ouch1 = ouch1
    except AccumuloException, ouch2:
      result.ouch2 = ouch2
    except AccumuloSecurityException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("importTable", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_listSplits(self, seqid, iprot, oprot):
    args = listSplits_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = listSplits_result()
    try:
      result.success = self._handler.listSplits(args.login, args.tableName, args.maxSplits)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("listSplits", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_listTables(self, seqid, iprot, oprot):
    args = listTables_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = listTables_result()
    result.success = self._handler.listTables(args.login)
    oprot.writeMessageBegin("listTables", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_listIterators(self, seqid, iprot, oprot):
    args = listIterators_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = listIterators_result()
    try:
      result.success = self._handler.listIterators(args.login, args.tableName)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("listIterators", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_listConstraints(self, seqid, iprot, oprot):
    args = listConstraints_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = listConstraints_result()
    try:
      result.success = self._handler.listConstraints(args.login, args.tableName)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("listConstraints", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_mergeTablets(self, seqid, iprot, oprot):
    args = mergeTablets_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = mergeTablets_result()
    try:
      self._handler.mergeTablets(args.login, args.tableName, args.startRow, args.endRow)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("mergeTablets", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_offlineTable(self, seqid, iprot, oprot):
    args = offlineTable_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = offlineTable_result()
    try:
      self._handler.offlineTable(args.login, args.tableName, args.wait)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("offlineTable", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_onlineTable(self, seqid, iprot, oprot):
    args = onlineTable_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = onlineTable_result()
    try:
      self._handler.onlineTable(args.login, args.tableName, args.wait)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("onlineTable", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_removeConstraint(self, seqid, iprot, oprot):
    args = removeConstraint_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = removeConstraint_result()
    try:
      self._handler.removeConstraint(args.login, args.tableName, args.constraint)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("removeConstraint", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_removeIterator(self, seqid, iprot, oprot):
    args = removeIterator_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = removeIterator_result()
    try:
      self._handler.removeIterator(args.login, args.tableName, args.iterName, args.scopes)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("removeIterator", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_removeTableProperty(self, seqid, iprot, oprot):
    args = removeTableProperty_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = removeTableProperty_result()
    try:
      self._handler.removeTableProperty(args.login, args.tableName, args.property)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("removeTableProperty", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_renameTable(self, seqid, iprot, oprot):
    args = renameTable_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = renameTable_result()
    try:
      self._handler.renameTable(args.login, args.oldTableName, args.newTableName)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    except TableExistsException, ouch4:
      result.ouch4 = ouch4
    oprot.writeMessageBegin("renameTable", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_setLocalityGroups(self, seqid, iprot, oprot):
    args = setLocalityGroups_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = setLocalityGroups_result()
    try:
      self._handler.setLocalityGroups(args.login, args.tableName, args.groups)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("setLocalityGroups", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_setTableProperty(self, seqid, iprot, oprot):
    args = setTableProperty_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = setTableProperty_result()
    try:
      self._handler.setTableProperty(args.login, args.tableName, args.property, args.value)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("setTableProperty", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_splitRangeByTablets(self, seqid, iprot, oprot):
    args = splitRangeByTablets_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = splitRangeByTablets_result()
    try:
      result.success = self._handler.splitRangeByTablets(args.login, args.tableName, args.range, args.maxSplits)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("splitRangeByTablets", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_tableExists(self, seqid, iprot, oprot):
    args = tableExists_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = tableExists_result()
    result.success = self._handler.tableExists(args.login, args.tableName)
    oprot.writeMessageBegin("tableExists", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_tableIdMap(self, seqid, iprot, oprot):
    args = tableIdMap_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = tableIdMap_result()
    result.success = self._handler.tableIdMap(args.login)
    oprot.writeMessageBegin("tableIdMap", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_testTableClassLoad(self, seqid, iprot, oprot):
    args = testTableClassLoad_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = testTableClassLoad_result()
    try:
      result.success = self._handler.testTableClassLoad(args.login, args.tableName, args.className, args.asTypeName)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("testTableClassLoad", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_pingTabletServer(self, seqid, iprot, oprot):
    args = pingTabletServer_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = pingTabletServer_result()
    try:
      self._handler.pingTabletServer(args.login, args.tserver)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    oprot.writeMessageBegin("pingTabletServer", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_getActiveScans(self, seqid, iprot, oprot):
    args = getActiveScans_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = getActiveScans_result()
    try:
      result.success = self._handler.getActiveScans(args.login, args.tserver)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    oprot.writeMessageBegin("getActiveScans", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_getActiveCompactions(self, seqid, iprot, oprot):
    args = getActiveCompactions_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = getActiveCompactions_result()
    try:
      result.success = self._handler.getActiveCompactions(args.login, args.tserver)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    oprot.writeMessageBegin("getActiveCompactions", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_getSiteConfiguration(self, seqid, iprot, oprot):
    args = getSiteConfiguration_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = getSiteConfiguration_result()
    try:
      result.success = self._handler.getSiteConfiguration(args.login)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    oprot.writeMessageBegin("getSiteConfiguration", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_getSystemConfiguration(self, seqid, iprot, oprot):
    args = getSystemConfiguration_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = getSystemConfiguration_result()
    try:
      result.success = self._handler.getSystemConfiguration(args.login)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    oprot.writeMessageBegin("getSystemConfiguration", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_getTabletServers(self, seqid, iprot, oprot):
    args = getTabletServers_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = getTabletServers_result()
    result.success = self._handler.getTabletServers(args.login)
    oprot.writeMessageBegin("getTabletServers", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_removeProperty(self, seqid, iprot, oprot):
    args = removeProperty_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = removeProperty_result()
    try:
      self._handler.removeProperty(args.login, args.property)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    oprot.writeMessageBegin("removeProperty", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_setProperty(self, seqid, iprot, oprot):
    args = setProperty_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = setProperty_result()
    try:
      self._handler.setProperty(args.login, args.property, args.value)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    oprot.writeMessageBegin("setProperty", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_testClassLoad(self, seqid, iprot, oprot):
    args = testClassLoad_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = testClassLoad_result()
    try:
      result.success = self._handler.testClassLoad(args.login, args.className, args.asTypeName)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    oprot.writeMessageBegin("testClassLoad", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_authenticateUser(self, seqid, iprot, oprot):
    args = authenticateUser_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = authenticateUser_result()
    try:
      result.success = self._handler.authenticateUser(args.login, args.user, args.properties)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    oprot.writeMessageBegin("authenticateUser", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_changeUserAuthorizations(self, seqid, iprot, oprot):
    args = changeUserAuthorizations_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = changeUserAuthorizations_result()
    try:
      self._handler.changeUserAuthorizations(args.login, args.user, args.authorizations)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    oprot.writeMessageBegin("changeUserAuthorizations", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_changeLocalUserPassword(self, seqid, iprot, oprot):
    args = changeLocalUserPassword_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = changeLocalUserPassword_result()
    try:
      self._handler.changeLocalUserPassword(args.login, args.user, args.password)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    oprot.writeMessageBegin("changeLocalUserPassword", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_createLocalUser(self, seqid, iprot, oprot):
    args = createLocalUser_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = createLocalUser_result()
    try:
      self._handler.createLocalUser(args.login, args.user, args.password)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    oprot.writeMessageBegin("createLocalUser", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_dropLocalUser(self, seqid, iprot, oprot):
    args = dropLocalUser_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = dropLocalUser_result()
    try:
      self._handler.dropLocalUser(args.login, args.user)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    oprot.writeMessageBegin("dropLocalUser", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_getUserAuthorizations(self, seqid, iprot, oprot):
    args = getUserAuthorizations_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = getUserAuthorizations_result()
    try:
      result.success = self._handler.getUserAuthorizations(args.login, args.user)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    oprot.writeMessageBegin("getUserAuthorizations", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_grantSystemPermission(self, seqid, iprot, oprot):
    args = grantSystemPermission_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = grantSystemPermission_result()
    try:
      self._handler.grantSystemPermission(args.login, args.user, args.perm)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    oprot.writeMessageBegin("grantSystemPermission", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_grantTablePermission(self, seqid, iprot, oprot):
    args = grantTablePermission_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = grantTablePermission_result()
    try:
      self._handler.grantTablePermission(args.login, args.user, args.table, args.perm)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("grantTablePermission", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_hasSystemPermission(self, seqid, iprot, oprot):
    args = hasSystemPermission_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = hasSystemPermission_result()
    try:
      result.success = self._handler.hasSystemPermission(args.login, args.user, args.perm)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    oprot.writeMessageBegin("hasSystemPermission", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_hasTablePermission(self, seqid, iprot, oprot):
    args = hasTablePermission_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = hasTablePermission_result()
    try:
      result.success = self._handler.hasTablePermission(args.login, args.user, args.table, args.perm)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("hasTablePermission", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_listLocalUsers(self, seqid, iprot, oprot):
    args = listLocalUsers_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = listLocalUsers_result()
    try:
      result.success = self._handler.listLocalUsers(args.login)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("listLocalUsers", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_revokeSystemPermission(self, seqid, iprot, oprot):
    args = revokeSystemPermission_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = revokeSystemPermission_result()
    try:
      self._handler.revokeSystemPermission(args.login, args.user, args.perm)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    oprot.writeMessageBegin("revokeSystemPermission", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_revokeTablePermission(self, seqid, iprot, oprot):
    args = revokeTablePermission_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = revokeTablePermission_result()
    try:
      self._handler.revokeTablePermission(args.login, args.user, args.table, args.perm)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("revokeTablePermission", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_createBatchScanner(self, seqid, iprot, oprot):
    args = createBatchScanner_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = createBatchScanner_result()
    try:
      result.success = self._handler.createBatchScanner(args.login, args.tableName, args.options)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("createBatchScanner", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_createScanner(self, seqid, iprot, oprot):
    args = createScanner_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = createScanner_result()
    try:
      result.success = self._handler.createScanner(args.login, args.tableName, args.options)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("createScanner", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_hasNext(self, seqid, iprot, oprot):
    args = hasNext_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = hasNext_result()
    try:
      result.success = self._handler.hasNext(args.scanner)
    except UnknownScanner, ouch1:
      result.ouch1 = ouch1
    oprot.writeMessageBegin("hasNext", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_nextEntry(self, seqid, iprot, oprot):
    args = nextEntry_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = nextEntry_result()
    try:
      result.success = self._handler.nextEntry(args.scanner)
    except NoMoreEntriesException, ouch1:
      result.ouch1 = ouch1
    except UnknownScanner, ouch2:
      result.ouch2 = ouch2
    except AccumuloSecurityException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("nextEntry", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_nextK(self, seqid, iprot, oprot):
    args = nextK_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = nextK_result()
    try:
      result.success = self._handler.nextK(args.scanner, args.k)
    except NoMoreEntriesException, ouch1:
      result.ouch1 = ouch1
    except UnknownScanner, ouch2:
      result.ouch2 = ouch2
    except AccumuloSecurityException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("nextK", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_closeScanner(self, seqid, iprot, oprot):
    args = closeScanner_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = closeScanner_result()
    try:
      self._handler.closeScanner(args.scanner)
    except UnknownScanner, ouch1:
      result.ouch1 = ouch1
    oprot.writeMessageBegin("closeScanner", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_updateAndFlush(self, seqid, iprot, oprot):
    args = updateAndFlush_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = updateAndFlush_result()
    try:
      self._handler.updateAndFlush(args.login, args.tableName, args.cells)
    except AccumuloException, outch1:
      result.outch1 = outch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    except MutationsRejectedException, ouch4:
      result.ouch4 = ouch4
    oprot.writeMessageBegin("updateAndFlush", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_createWriter(self, seqid, iprot, oprot):
    args = createWriter_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = createWriter_result()
    try:
      result.success = self._handler.createWriter(args.login, args.tableName, args.opts)
    except AccumuloException, outch1:
      result.outch1 = outch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("createWriter", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_update(self, seqid, iprot, oprot):
    args = update_args()
    args.read(iprot)
    iprot.readMessageEnd()
    self._handler.update(args.writer, args.cells)
    return

  def process_flush(self, seqid, iprot, oprot):
    args = flush_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = flush_result()
    try:
      self._handler.flush(args.writer)
    except UnknownWriter, ouch1:
      result.ouch1 = ouch1
    except MutationsRejectedException, ouch2:
      result.ouch2 = ouch2
    oprot.writeMessageBegin("flush", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_closeWriter(self, seqid, iprot, oprot):
    args = closeWriter_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = closeWriter_result()
    try:
      self._handler.closeWriter(args.writer)
    except UnknownWriter, ouch1:
      result.ouch1 = ouch1
    except MutationsRejectedException, ouch2:
      result.ouch2 = ouch2
    oprot.writeMessageBegin("closeWriter", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_updateRowConditionally(self, seqid, iprot, oprot):
    args = updateRowConditionally_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = updateRowConditionally_result()
    try:
      result.success = self._handler.updateRowConditionally(args.login, args.tableName, args.row, args.updates)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("updateRowConditionally", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_createConditionalWriter(self, seqid, iprot, oprot):
    args = createConditionalWriter_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = createConditionalWriter_result()
    try:
      result.success = self._handler.createConditionalWriter(args.login, args.tableName, args.options)
    except AccumuloException, ouch1:
      result.ouch1 = ouch1
    except AccumuloSecurityException, ouch2:
      result.ouch2 = ouch2
    except TableNotFoundException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("createConditionalWriter", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_updateRowsConditionally(self, seqid, iprot, oprot):
    args = updateRowsConditionally_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = updateRowsConditionally_result()
    try:
      result.success = self._handler.updateRowsConditionally(args.conditionalWriter, args.updates)
    except UnknownWriter, ouch1:
      result.ouch1 = ouch1
    except AccumuloException, ouch2:
      result.ouch2 = ouch2
    except AccumuloSecurityException, ouch3:
      result.ouch3 = ouch3
    oprot.writeMessageBegin("updateRowsConditionally", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_closeConditionalWriter(self, seqid, iprot, oprot):
    args = closeConditionalWriter_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = closeConditionalWriter_result()
    self._handler.closeConditionalWriter(args.conditionalWriter)
    oprot.writeMessageBegin("closeConditionalWriter", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_getRowRange(self, seqid, iprot, oprot):
    args = getRowRange_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = getRowRange_result()
    result.success = self._handler.getRowRange(args.row)
    oprot.writeMessageBegin("getRowRange", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()

  def process_getFollowing(self, seqid, iprot, oprot):
    args = getFollowing_args()
    args.read(iprot)
    iprot.readMessageEnd()
    result = getFollowing_result()
    result.success = self._handler.getFollowing(args.key, args.part)
    oprot.writeMessageBegin("getFollowing", TMessageType.REPLY, seqid)
    result.write(oprot)
    oprot.writeMessageEnd()
    oprot.trans.flush()


# HELPER FUNCTIONS AND STRUCTURES

class login_args:
  """
  Attributes:
   - principal
   - loginProperties
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'principal', None, None, ), # 1
    (2, TType.MAP, 'loginProperties', (TType.STRING,None,TType.STRING,None), None, ), # 2
  )

  def __init__(self, principal=None, loginProperties=None,):
    self.principal = principal
    self.loginProperties = loginProperties

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.principal = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.MAP:
          self.loginProperties = {}
          (_ktype145, _vtype146, _size144 ) = iprot.readMapBegin()
          for _i148 in xrange(_size144):
            _key149 = iprot.readString();
            _val150 = iprot.readString();
            self.loginProperties[_key149] = _val150
          iprot.readMapEnd()
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('login_args')
    if self.principal is not None:
      oprot.writeFieldBegin('principal', TType.STRING, 1)
      oprot.writeString(self.principal)
      oprot.writeFieldEnd()
    if self.loginProperties is not None:
      oprot.writeFieldBegin('loginProperties', TType.MAP, 2)
      oprot.writeMapBegin(TType.STRING, TType.STRING, len(self.loginProperties))
      for kiter151,viter152 in self.loginProperties.items():
        oprot.writeString(kiter151)
        oprot.writeString(viter152)
      oprot.writeMapEnd()
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class login_result:
  """
  Attributes:
   - success
   - ouch2
  """

  thrift_spec = (
    (0, TType.STRING, 'success', None, None, ), # 0
    (1, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 1
  )

  def __init__(self, success=None, ouch2=None,):
    self.success = success
    self.ouch2 = ouch2

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.STRING:
          self.success = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 1:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('login_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.STRING, 0)
      oprot.writeString(self.success)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 1)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class addConstraint_args:
  """
  Attributes:
   - login
   - tableName
   - constraintClassName
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
    (3, TType.STRING, 'constraintClassName', None, None, ), # 3
  )

  def __init__(self, login=None, tableName=None, constraintClassName=None,):
    self.login = login
    self.tableName = tableName
    self.constraintClassName = constraintClassName

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRING:
          self.constraintClassName = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('addConstraint_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    if self.constraintClassName is not None:
      oprot.writeFieldBegin('constraintClassName', TType.STRING, 3)
      oprot.writeString(self.constraintClassName)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class addConstraint_result:
  """
  Attributes:
   - success
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    (0, TType.I32, 'success', None, None, ), # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, success=None, ouch1=None, ouch2=None, ouch3=None,):
    self.success = success
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.I32:
          self.success = iprot.readI32();
        else:
          iprot.skip(ftype)
      elif fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('addConstraint_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.I32, 0)
      oprot.writeI32(self.success)
      oprot.writeFieldEnd()
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class addSplits_args:
  """
  Attributes:
   - login
   - tableName
   - splits
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
    (3, TType.SET, 'splits', (TType.STRING,None), None, ), # 3
  )

  def __init__(self, login=None, tableName=None, splits=None,):
    self.login = login
    self.tableName = tableName
    self.splits = splits

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.SET:
          self.splits = set()
          (_etype156, _size153) = iprot.readSetBegin()
          for _i157 in xrange(_size153):
            _elem158 = iprot.readString();
            self.splits.add(_elem158)
          iprot.readSetEnd()
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('addSplits_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    if self.splits is not None:
      oprot.writeFieldBegin('splits', TType.SET, 3)
      oprot.writeSetBegin(TType.STRING, len(self.splits))
      for iter159 in self.splits:
        oprot.writeString(iter159)
      oprot.writeSetEnd()
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class addSplits_result:
  """
  Attributes:
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, ouch1=None, ouch2=None, ouch3=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('addSplits_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class attachIterator_args:
  """
  Attributes:
   - login
   - tableName
   - setting
   - scopes
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
    (3, TType.STRUCT, 'setting', (IteratorSetting, IteratorSetting.thrift_spec), None, ), # 3
    (4, TType.SET, 'scopes', (TType.I32,None), None, ), # 4
  )

  def __init__(self, login=None, tableName=None, setting=None, scopes=None,):
    self.login = login
    self.tableName = tableName
    self.setting = setting
    self.scopes = scopes

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.setting = IteratorSetting()
          self.setting.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 4:
        if ftype == TType.SET:
          self.scopes = set()
          (_etype163, _size160) = iprot.readSetBegin()
          for _i164 in xrange(_size160):
            _elem165 = iprot.readI32();
            self.scopes.add(_elem165)
          iprot.readSetEnd()
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('attachIterator_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    if self.setting is not None:
      oprot.writeFieldBegin('setting', TType.STRUCT, 3)
      self.setting.write(oprot)
      oprot.writeFieldEnd()
    if self.scopes is not None:
      oprot.writeFieldBegin('scopes', TType.SET, 4)
      oprot.writeSetBegin(TType.I32, len(self.scopes))
      for iter166 in self.scopes:
        oprot.writeI32(iter166)
      oprot.writeSetEnd()
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class attachIterator_result:
  """
  Attributes:
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloException, AccumuloException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, ouch1=None, ouch2=None, ouch3=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloSecurityException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('attachIterator_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class checkIteratorConflicts_args:
  """
  Attributes:
   - login
   - tableName
   - setting
   - scopes
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
    (3, TType.STRUCT, 'setting', (IteratorSetting, IteratorSetting.thrift_spec), None, ), # 3
    (4, TType.SET, 'scopes', (TType.I32,None), None, ), # 4
  )

  def __init__(self, login=None, tableName=None, setting=None, scopes=None,):
    self.login = login
    self.tableName = tableName
    self.setting = setting
    self.scopes = scopes

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.setting = IteratorSetting()
          self.setting.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 4:
        if ftype == TType.SET:
          self.scopes = set()
          (_etype170, _size167) = iprot.readSetBegin()
          for _i171 in xrange(_size167):
            _elem172 = iprot.readI32();
            self.scopes.add(_elem172)
          iprot.readSetEnd()
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('checkIteratorConflicts_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    if self.setting is not None:
      oprot.writeFieldBegin('setting', TType.STRUCT, 3)
      self.setting.write(oprot)
      oprot.writeFieldEnd()
    if self.scopes is not None:
      oprot.writeFieldBegin('scopes', TType.SET, 4)
      oprot.writeSetBegin(TType.I32, len(self.scopes))
      for iter173 in self.scopes:
        oprot.writeI32(iter173)
      oprot.writeSetEnd()
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class checkIteratorConflicts_result:
  """
  Attributes:
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloException, AccumuloException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, ouch1=None, ouch2=None, ouch3=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloSecurityException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('checkIteratorConflicts_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class clearLocatorCache_args:
  """
  Attributes:
   - login
   - tableName
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
  )

  def __init__(self, login=None, tableName=None,):
    self.login = login
    self.tableName = tableName

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('clearLocatorCache_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class clearLocatorCache_result:
  """
  Attributes:
   - ouch1
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 1
  )

  def __init__(self, ouch1=None,):
    self.ouch1 = ouch1

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = TableNotFoundException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('clearLocatorCache_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class cloneTable_args:
  """
  Attributes:
   - login
   - tableName
   - newTableName
   - flush
   - propertiesToSet
   - propertiesToExclude
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
    (3, TType.STRING, 'newTableName', None, None, ), # 3
    (4, TType.BOOL, 'flush', None, None, ), # 4
    (5, TType.MAP, 'propertiesToSet', (TType.STRING,None,TType.STRING,None), None, ), # 5
    (6, TType.SET, 'propertiesToExclude', (TType.STRING,None), None, ), # 6
  )

  def __init__(self, login=None, tableName=None, newTableName=None, flush=None, propertiesToSet=None, propertiesToExclude=None,):
    self.login = login
    self.tableName = tableName
    self.newTableName = newTableName
    self.flush = flush
    self.propertiesToSet = propertiesToSet
    self.propertiesToExclude = propertiesToExclude

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRING:
          self.newTableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 4:
        if ftype == TType.BOOL:
          self.flush = iprot.readBool();
        else:
          iprot.skip(ftype)
      elif fid == 5:
        if ftype == TType.MAP:
          self.propertiesToSet = {}
          (_ktype175, _vtype176, _size174 ) = iprot.readMapBegin()
          for _i178 in xrange(_size174):
            _key179 = iprot.readString();
            _val180 = iprot.readString();
            self.propertiesToSet[_key179] = _val180
          iprot.readMapEnd()
        else:
          iprot.skip(ftype)
      elif fid == 6:
        if ftype == TType.SET:
          self.propertiesToExclude = set()
          (_etype184, _size181) = iprot.readSetBegin()
          for _i185 in xrange(_size181):
            _elem186 = iprot.readString();
            self.propertiesToExclude.add(_elem186)
          iprot.readSetEnd()
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('cloneTable_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    if self.newTableName is not None:
      oprot.writeFieldBegin('newTableName', TType.STRING, 3)
      oprot.writeString(self.newTableName)
      oprot.writeFieldEnd()
    if self.flush is not None:
      oprot.writeFieldBegin('flush', TType.BOOL, 4)
      oprot.writeBool(self.flush)
      oprot.writeFieldEnd()
    if self.propertiesToSet is not None:
      oprot.writeFieldBegin('propertiesToSet', TType.MAP, 5)
      oprot.writeMapBegin(TType.STRING, TType.STRING, len(self.propertiesToSet))
      for kiter187,viter188 in self.propertiesToSet.items():
        oprot.writeString(kiter187)
        oprot.writeString(viter188)
      oprot.writeMapEnd()
      oprot.writeFieldEnd()
    if self.propertiesToExclude is not None:
      oprot.writeFieldBegin('propertiesToExclude', TType.SET, 6)
      oprot.writeSetBegin(TType.STRING, len(self.propertiesToExclude))
      for iter189 in self.propertiesToExclude:
        oprot.writeString(iter189)
      oprot.writeSetEnd()
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class cloneTable_result:
  """
  Attributes:
   - ouch1
   - ouch2
   - ouch3
   - ouch4
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
    (4, TType.STRUCT, 'ouch4', (TableExistsException, TableExistsException.thrift_spec), None, ), # 4
  )

  def __init__(self, ouch1=None, ouch2=None, ouch3=None, ouch4=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3
    self.ouch4 = ouch4

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 4:
        if ftype == TType.STRUCT:
          self.ouch4 = TableExistsException()
          self.ouch4.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('cloneTable_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch4 is not None:
      oprot.writeFieldBegin('ouch4', TType.STRUCT, 4)
      self.ouch4.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class compactTable_args:
  """
  Attributes:
   - login
   - tableName
   - startRow
   - endRow
   - iterators
   - flush
   - wait
   - compactionStrategy
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
    (3, TType.STRING, 'startRow', None, None, ), # 3
    (4, TType.STRING, 'endRow', None, None, ), # 4
    (5, TType.LIST, 'iterators', (TType.STRUCT,(IteratorSetting, IteratorSetting.thrift_spec)), None, ), # 5
    (6, TType.BOOL, 'flush', None, None, ), # 6
    (7, TType.BOOL, 'wait', None, None, ), # 7
    (8, TType.STRUCT, 'compactionStrategy', (CompactionStrategyConfig, CompactionStrategyConfig.thrift_spec), None, ), # 8
  )

  def __init__(self, login=None, tableName=None, startRow=None, endRow=None, iterators=None, flush=None, wait=None, compactionStrategy=None,):
    self.login = login
    self.tableName = tableName
    self.startRow = startRow
    self.endRow = endRow
    self.iterators = iterators
    self.flush = flush
    self.wait = wait
    self.compactionStrategy = compactionStrategy

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRING:
          self.startRow = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 4:
        if ftype == TType.STRING:
          self.endRow = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 5:
        if ftype == TType.LIST:
          self.iterators = []
          (_etype193, _size190) = iprot.readListBegin()
          for _i194 in xrange(_size190):
            _elem195 = IteratorSetting()
            _elem195.read(iprot)
            self.iterators.append(_elem195)
          iprot.readListEnd()
        else:
          iprot.skip(ftype)
      elif fid == 6:
        if ftype == TType.BOOL:
          self.flush = iprot.readBool();
        else:
          iprot.skip(ftype)
      elif fid == 7:
        if ftype == TType.BOOL:
          self.wait = iprot.readBool();
        else:
          iprot.skip(ftype)
      elif fid == 8:
        if ftype == TType.STRUCT:
          self.compactionStrategy = CompactionStrategyConfig()
          self.compactionStrategy.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('compactTable_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    if self.startRow is not None:
      oprot.writeFieldBegin('startRow', TType.STRING, 3)
      oprot.writeString(self.startRow)
      oprot.writeFieldEnd()
    if self.endRow is not None:
      oprot.writeFieldBegin('endRow', TType.STRING, 4)
      oprot.writeString(self.endRow)
      oprot.writeFieldEnd()
    if self.iterators is not None:
      oprot.writeFieldBegin('iterators', TType.LIST, 5)
      oprot.writeListBegin(TType.STRUCT, len(self.iterators))
      for iter196 in self.iterators:
        iter196.write(oprot)
      oprot.writeListEnd()
      oprot.writeFieldEnd()
    if self.flush is not None:
      oprot.writeFieldBegin('flush', TType.BOOL, 6)
      oprot.writeBool(self.flush)
      oprot.writeFieldEnd()
    if self.wait is not None:
      oprot.writeFieldBegin('wait', TType.BOOL, 7)
      oprot.writeBool(self.wait)
      oprot.writeFieldEnd()
    if self.compactionStrategy is not None:
      oprot.writeFieldBegin('compactionStrategy', TType.STRUCT, 8)
      self.compactionStrategy.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class compactTable_result:
  """
  Attributes:
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (AccumuloException, AccumuloException.thrift_spec), None, ), # 3
  )

  def __init__(self, ouch1=None, ouch2=None, ouch3=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloSecurityException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = TableNotFoundException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = AccumuloException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('compactTable_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class cancelCompaction_args:
  """
  Attributes:
   - login
   - tableName
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
  )

  def __init__(self, login=None, tableName=None,):
    self.login = login
    self.tableName = tableName

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('cancelCompaction_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class cancelCompaction_result:
  """
  Attributes:
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (AccumuloException, AccumuloException.thrift_spec), None, ), # 3
  )

  def __init__(self, ouch1=None, ouch2=None, ouch3=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloSecurityException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = TableNotFoundException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = AccumuloException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('cancelCompaction_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class createTable_args:
  """
  Attributes:
   - login
   - tableName
   - versioningIter
   - type
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
    (3, TType.BOOL, 'versioningIter', None, None, ), # 3
    (4, TType.I32, 'type', None, None, ), # 4
  )

  def __init__(self, login=None, tableName=None, versioningIter=None, type=None,):
    self.login = login
    self.tableName = tableName
    self.versioningIter = versioningIter
    self.type = type

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.BOOL:
          self.versioningIter = iprot.readBool();
        else:
          iprot.skip(ftype)
      elif fid == 4:
        if ftype == TType.I32:
          self.type = iprot.readI32();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('createTable_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    if self.versioningIter is not None:
      oprot.writeFieldBegin('versioningIter', TType.BOOL, 3)
      oprot.writeBool(self.versioningIter)
      oprot.writeFieldEnd()
    if self.type is not None:
      oprot.writeFieldBegin('type', TType.I32, 4)
      oprot.writeI32(self.type)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class createTable_result:
  """
  Attributes:
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableExistsException, TableExistsException.thrift_spec), None, ), # 3
  )

  def __init__(self, ouch1=None, ouch2=None, ouch3=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableExistsException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('createTable_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class deleteTable_args:
  """
  Attributes:
   - login
   - tableName
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
  )

  def __init__(self, login=None, tableName=None,):
    self.login = login
    self.tableName = tableName

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('deleteTable_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class deleteTable_result:
  """
  Attributes:
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, ouch1=None, ouch2=None, ouch3=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('deleteTable_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class deleteRows_args:
  """
  Attributes:
   - login
   - tableName
   - startRow
   - endRow
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
    (3, TType.STRING, 'startRow', None, None, ), # 3
    (4, TType.STRING, 'endRow', None, None, ), # 4
  )

  def __init__(self, login=None, tableName=None, startRow=None, endRow=None,):
    self.login = login
    self.tableName = tableName
    self.startRow = startRow
    self.endRow = endRow

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRING:
          self.startRow = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 4:
        if ftype == TType.STRING:
          self.endRow = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('deleteRows_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    if self.startRow is not None:
      oprot.writeFieldBegin('startRow', TType.STRING, 3)
      oprot.writeString(self.startRow)
      oprot.writeFieldEnd()
    if self.endRow is not None:
      oprot.writeFieldBegin('endRow', TType.STRING, 4)
      oprot.writeString(self.endRow)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class deleteRows_result:
  """
  Attributes:
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, ouch1=None, ouch2=None, ouch3=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('deleteRows_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class exportTable_args:
  """
  Attributes:
   - login
   - tableName
   - exportDir
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
    (3, TType.STRING, 'exportDir', None, None, ), # 3
  )

  def __init__(self, login=None, tableName=None, exportDir=None,):
    self.login = login
    self.tableName = tableName
    self.exportDir = exportDir

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRING:
          self.exportDir = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('exportTable_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    if self.exportDir is not None:
      oprot.writeFieldBegin('exportDir', TType.STRING, 3)
      oprot.writeString(self.exportDir)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class exportTable_result:
  """
  Attributes:
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, ouch1=None, ouch2=None, ouch3=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('exportTable_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class flushTable_args:
  """
  Attributes:
   - login
   - tableName
   - startRow
   - endRow
   - wait
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
    (3, TType.STRING, 'startRow', None, None, ), # 3
    (4, TType.STRING, 'endRow', None, None, ), # 4
    (5, TType.BOOL, 'wait', None, None, ), # 5
  )

  def __init__(self, login=None, tableName=None, startRow=None, endRow=None, wait=None,):
    self.login = login
    self.tableName = tableName
    self.startRow = startRow
    self.endRow = endRow
    self.wait = wait

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRING:
          self.startRow = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 4:
        if ftype == TType.STRING:
          self.endRow = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 5:
        if ftype == TType.BOOL:
          self.wait = iprot.readBool();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('flushTable_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    if self.startRow is not None:
      oprot.writeFieldBegin('startRow', TType.STRING, 3)
      oprot.writeString(self.startRow)
      oprot.writeFieldEnd()
    if self.endRow is not None:
      oprot.writeFieldBegin('endRow', TType.STRING, 4)
      oprot.writeString(self.endRow)
      oprot.writeFieldEnd()
    if self.wait is not None:
      oprot.writeFieldBegin('wait', TType.BOOL, 5)
      oprot.writeBool(self.wait)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class flushTable_result:
  """
  Attributes:
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, ouch1=None, ouch2=None, ouch3=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('flushTable_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class getDiskUsage_args:
  """
  Attributes:
   - login
   - tables
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.SET, 'tables', (TType.STRING,None), None, ), # 2
  )

  def __init__(self, login=None, tables=None,):
    self.login = login
    self.tables = tables

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.SET:
          self.tables = set()
          (_etype200, _size197) = iprot.readSetBegin()
          for _i201 in xrange(_size197):
            _elem202 = iprot.readString();
            self.tables.add(_elem202)
          iprot.readSetEnd()
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('getDiskUsage_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tables is not None:
      oprot.writeFieldBegin('tables', TType.SET, 2)
      oprot.writeSetBegin(TType.STRING, len(self.tables))
      for iter203 in self.tables:
        oprot.writeString(iter203)
      oprot.writeSetEnd()
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class getDiskUsage_result:
  """
  Attributes:
   - success
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    (0, TType.LIST, 'success', (TType.STRUCT,(DiskUsage, DiskUsage.thrift_spec)), None, ), # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, success=None, ouch1=None, ouch2=None, ouch3=None,):
    self.success = success
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.LIST:
          self.success = []
          (_etype207, _size204) = iprot.readListBegin()
          for _i208 in xrange(_size204):
            _elem209 = DiskUsage()
            _elem209.read(iprot)
            self.success.append(_elem209)
          iprot.readListEnd()
        else:
          iprot.skip(ftype)
      elif fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('getDiskUsage_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.LIST, 0)
      oprot.writeListBegin(TType.STRUCT, len(self.success))
      for iter210 in self.success:
        iter210.write(oprot)
      oprot.writeListEnd()
      oprot.writeFieldEnd()
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class getLocalityGroups_args:
  """
  Attributes:
   - login
   - tableName
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
  )

  def __init__(self, login=None, tableName=None,):
    self.login = login
    self.tableName = tableName

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('getLocalityGroups_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class getLocalityGroups_result:
  """
  Attributes:
   - success
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    (0, TType.MAP, 'success', (TType.STRING,None,TType.SET,(TType.STRING,None)), None, ), # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, success=None, ouch1=None, ouch2=None, ouch3=None,):
    self.success = success
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.MAP:
          self.success = {}
          (_ktype212, _vtype213, _size211 ) = iprot.readMapBegin()
          for _i215 in xrange(_size211):
            _key216 = iprot.readString();
            _val217 = set()
            (_etype221, _size218) = iprot.readSetBegin()
            for _i222 in xrange(_size218):
              _elem223 = iprot.readString();
              _val217.add(_elem223)
            iprot.readSetEnd()
            self.success[_key216] = _val217
          iprot.readMapEnd()
        else:
          iprot.skip(ftype)
      elif fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('getLocalityGroups_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.MAP, 0)
      oprot.writeMapBegin(TType.STRING, TType.SET, len(self.success))
      for kiter224,viter225 in self.success.items():
        oprot.writeString(kiter224)
        oprot.writeSetBegin(TType.STRING, len(viter225))
        for iter226 in viter225:
          oprot.writeString(iter226)
        oprot.writeSetEnd()
      oprot.writeMapEnd()
      oprot.writeFieldEnd()
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class getIteratorSetting_args:
  """
  Attributes:
   - login
   - tableName
   - iteratorName
   - scope
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
    (3, TType.STRING, 'iteratorName', None, None, ), # 3
    (4, TType.I32, 'scope', None, None, ), # 4
  )

  def __init__(self, login=None, tableName=None, iteratorName=None, scope=None,):
    self.login = login
    self.tableName = tableName
    self.iteratorName = iteratorName
    self.scope = scope

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRING:
          self.iteratorName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 4:
        if ftype == TType.I32:
          self.scope = iprot.readI32();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('getIteratorSetting_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    if self.iteratorName is not None:
      oprot.writeFieldBegin('iteratorName', TType.STRING, 3)
      oprot.writeString(self.iteratorName)
      oprot.writeFieldEnd()
    if self.scope is not None:
      oprot.writeFieldBegin('scope', TType.I32, 4)
      oprot.writeI32(self.scope)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class getIteratorSetting_result:
  """
  Attributes:
   - success
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    (0, TType.STRUCT, 'success', (IteratorSetting, IteratorSetting.thrift_spec), None, ), # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, success=None, ouch1=None, ouch2=None, ouch3=None,):
    self.success = success
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.STRUCT:
          self.success = IteratorSetting()
          self.success.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('getIteratorSetting_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.STRUCT, 0)
      self.success.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class getMaxRow_args:
  """
  Attributes:
   - login
   - tableName
   - auths
   - startRow
   - startInclusive
   - endRow
   - endInclusive
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
    (3, TType.SET, 'auths', (TType.STRING,None), None, ), # 3
    (4, TType.STRING, 'startRow', None, None, ), # 4
    (5, TType.BOOL, 'startInclusive', None, None, ), # 5
    (6, TType.STRING, 'endRow', None, None, ), # 6
    (7, TType.BOOL, 'endInclusive', None, None, ), # 7
  )

  def __init__(self, login=None, tableName=None, auths=None, startRow=None, startInclusive=None, endRow=None, endInclusive=None,):
    self.login = login
    self.tableName = tableName
    self.auths = auths
    self.startRow = startRow
    self.startInclusive = startInclusive
    self.endRow = endRow
    self.endInclusive = endInclusive

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.SET:
          self.auths = set()
          (_etype230, _size227) = iprot.readSetBegin()
          for _i231 in xrange(_size227):
            _elem232 = iprot.readString();
            self.auths.add(_elem232)
          iprot.readSetEnd()
        else:
          iprot.skip(ftype)
      elif fid == 4:
        if ftype == TType.STRING:
          self.startRow = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 5:
        if ftype == TType.BOOL:
          self.startInclusive = iprot.readBool();
        else:
          iprot.skip(ftype)
      elif fid == 6:
        if ftype == TType.STRING:
          self.endRow = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 7:
        if ftype == TType.BOOL:
          self.endInclusive = iprot.readBool();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('getMaxRow_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    if self.auths is not None:
      oprot.writeFieldBegin('auths', TType.SET, 3)
      oprot.writeSetBegin(TType.STRING, len(self.auths))
      for iter233 in self.auths:
        oprot.writeString(iter233)
      oprot.writeSetEnd()
      oprot.writeFieldEnd()
    if self.startRow is not None:
      oprot.writeFieldBegin('startRow', TType.STRING, 4)
      oprot.writeString(self.startRow)
      oprot.writeFieldEnd()
    if self.startInclusive is not None:
      oprot.writeFieldBegin('startInclusive', TType.BOOL, 5)
      oprot.writeBool(self.startInclusive)
      oprot.writeFieldEnd()
    if self.endRow is not None:
      oprot.writeFieldBegin('endRow', TType.STRING, 6)
      oprot.writeString(self.endRow)
      oprot.writeFieldEnd()
    if self.endInclusive is not None:
      oprot.writeFieldBegin('endInclusive', TType.BOOL, 7)
      oprot.writeBool(self.endInclusive)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class getMaxRow_result:
  """
  Attributes:
   - success
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    (0, TType.STRING, 'success', None, None, ), # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, success=None, ouch1=None, ouch2=None, ouch3=None,):
    self.success = success
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.STRING:
          self.success = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('getMaxRow_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.STRING, 0)
      oprot.writeString(self.success)
      oprot.writeFieldEnd()
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class getTableProperties_args:
  """
  Attributes:
   - login
   - tableName
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
  )

  def __init__(self, login=None, tableName=None,):
    self.login = login
    self.tableName = tableName

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('getTableProperties_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class getTableProperties_result:
  """
  Attributes:
   - success
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    (0, TType.MAP, 'success', (TType.STRING,None,TType.STRING,None), None, ), # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, success=None, ouch1=None, ouch2=None, ouch3=None,):
    self.success = success
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.MAP:
          self.success = {}
          (_ktype235, _vtype236, _size234 ) = iprot.readMapBegin()
          for _i238 in xrange(_size234):
            _key239 = iprot.readString();
            _val240 = iprot.readString();
            self.success[_key239] = _val240
          iprot.readMapEnd()
        else:
          iprot.skip(ftype)
      elif fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('getTableProperties_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.MAP, 0)
      oprot.writeMapBegin(TType.STRING, TType.STRING, len(self.success))
      for kiter241,viter242 in self.success.items():
        oprot.writeString(kiter241)
        oprot.writeString(viter242)
      oprot.writeMapEnd()
      oprot.writeFieldEnd()
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class importDirectory_args:
  """
  Attributes:
   - login
   - tableName
   - importDir
   - failureDir
   - setTime
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
    (3, TType.STRING, 'importDir', None, None, ), # 3
    (4, TType.STRING, 'failureDir', None, None, ), # 4
    (5, TType.BOOL, 'setTime', None, None, ), # 5
  )

  def __init__(self, login=None, tableName=None, importDir=None, failureDir=None, setTime=None,):
    self.login = login
    self.tableName = tableName
    self.importDir = importDir
    self.failureDir = failureDir
    self.setTime = setTime

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRING:
          self.importDir = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 4:
        if ftype == TType.STRING:
          self.failureDir = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 5:
        if ftype == TType.BOOL:
          self.setTime = iprot.readBool();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('importDirectory_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    if self.importDir is not None:
      oprot.writeFieldBegin('importDir', TType.STRING, 3)
      oprot.writeString(self.importDir)
      oprot.writeFieldEnd()
    if self.failureDir is not None:
      oprot.writeFieldBegin('failureDir', TType.STRING, 4)
      oprot.writeString(self.failureDir)
      oprot.writeFieldEnd()
    if self.setTime is not None:
      oprot.writeFieldBegin('setTime', TType.BOOL, 5)
      oprot.writeBool(self.setTime)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class importDirectory_result:
  """
  Attributes:
   - ouch1
   - ouch3
   - ouch4
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch3', (AccumuloException, AccumuloException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch4', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 3
  )

  def __init__(self, ouch1=None, ouch3=None, ouch4=None,):
    self.ouch1 = ouch1
    self.ouch3 = ouch3
    self.ouch4 = ouch4

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = TableNotFoundException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch3 = AccumuloException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch4 = AccumuloSecurityException()
          self.ouch4.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('importDirectory_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 2)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch4 is not None:
      oprot.writeFieldBegin('ouch4', TType.STRUCT, 3)
      self.ouch4.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class importTable_args:
  """
  Attributes:
   - login
   - tableName
   - importDir
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
    (3, TType.STRING, 'importDir', None, None, ), # 3
  )

  def __init__(self, login=None, tableName=None, importDir=None,):
    self.login = login
    self.tableName = tableName
    self.importDir = importDir

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRING:
          self.importDir = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('importTable_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    if self.importDir is not None:
      oprot.writeFieldBegin('importDir', TType.STRING, 3)
      oprot.writeString(self.importDir)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class importTable_result:
  """
  Attributes:
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (TableExistsException, TableExistsException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloException, AccumuloException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 3
  )

  def __init__(self, ouch1=None, ouch2=None, ouch3=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = TableExistsException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = AccumuloSecurityException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('importTable_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class listSplits_args:
  """
  Attributes:
   - login
   - tableName
   - maxSplits
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
    (3, TType.I32, 'maxSplits', None, None, ), # 3
  )

  def __init__(self, login=None, tableName=None, maxSplits=None,):
    self.login = login
    self.tableName = tableName
    self.maxSplits = maxSplits

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.I32:
          self.maxSplits = iprot.readI32();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('listSplits_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    if self.maxSplits is not None:
      oprot.writeFieldBegin('maxSplits', TType.I32, 3)
      oprot.writeI32(self.maxSplits)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class listSplits_result:
  """
  Attributes:
   - success
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    (0, TType.LIST, 'success', (TType.STRING,None), None, ), # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, success=None, ouch1=None, ouch2=None, ouch3=None,):
    self.success = success
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.LIST:
          self.success = []
          (_etype246, _size243) = iprot.readListBegin()
          for _i247 in xrange(_size243):
            _elem248 = iprot.readString();
            self.success.append(_elem248)
          iprot.readListEnd()
        else:
          iprot.skip(ftype)
      elif fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('listSplits_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.LIST, 0)
      oprot.writeListBegin(TType.STRING, len(self.success))
      for iter249 in self.success:
        oprot.writeString(iter249)
      oprot.writeListEnd()
      oprot.writeFieldEnd()
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class listTables_args:
  """
  Attributes:
   - login
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
  )

  def __init__(self, login=None,):
    self.login = login

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('listTables_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class listTables_result:
  """
  Attributes:
   - success
  """

  thrift_spec = (
    (0, TType.SET, 'success', (TType.STRING,None), None, ), # 0
  )

  def __init__(self, success=None,):
    self.success = success

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.SET:
          self.success = set()
          (_etype253, _size250) = iprot.readSetBegin()
          for _i254 in xrange(_size250):
            _elem255 = iprot.readString();
            self.success.add(_elem255)
          iprot.readSetEnd()
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('listTables_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.SET, 0)
      oprot.writeSetBegin(TType.STRING, len(self.success))
      for iter256 in self.success:
        oprot.writeString(iter256)
      oprot.writeSetEnd()
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class listIterators_args:
  """
  Attributes:
   - login
   - tableName
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
  )

  def __init__(self, login=None, tableName=None,):
    self.login = login
    self.tableName = tableName

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('listIterators_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class listIterators_result:
  """
  Attributes:
   - success
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    (0, TType.MAP, 'success', (TType.STRING,None,TType.SET,(TType.I32,None)), None, ), # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, success=None, ouch1=None, ouch2=None, ouch3=None,):
    self.success = success
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.MAP:
          self.success = {}
          (_ktype258, _vtype259, _size257 ) = iprot.readMapBegin()
          for _i261 in xrange(_size257):
            _key262 = iprot.readString();
            _val263 = set()
            (_etype267, _size264) = iprot.readSetBegin()
            for _i268 in xrange(_size264):
              _elem269 = iprot.readI32();
              _val263.add(_elem269)
            iprot.readSetEnd()
            self.success[_key262] = _val263
          iprot.readMapEnd()
        else:
          iprot.skip(ftype)
      elif fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('listIterators_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.MAP, 0)
      oprot.writeMapBegin(TType.STRING, TType.SET, len(self.success))
      for kiter270,viter271 in self.success.items():
        oprot.writeString(kiter270)
        oprot.writeSetBegin(TType.I32, len(viter271))
        for iter272 in viter271:
          oprot.writeI32(iter272)
        oprot.writeSetEnd()
      oprot.writeMapEnd()
      oprot.writeFieldEnd()
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class listConstraints_args:
  """
  Attributes:
   - login
   - tableName
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
  )

  def __init__(self, login=None, tableName=None,):
    self.login = login
    self.tableName = tableName

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('listConstraints_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class listConstraints_result:
  """
  Attributes:
   - success
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    (0, TType.MAP, 'success', (TType.STRING,None,TType.I32,None), None, ), # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, success=None, ouch1=None, ouch2=None, ouch3=None,):
    self.success = success
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.MAP:
          self.success = {}
          (_ktype274, _vtype275, _size273 ) = iprot.readMapBegin()
          for _i277 in xrange(_size273):
            _key278 = iprot.readString();
            _val279 = iprot.readI32();
            self.success[_key278] = _val279
          iprot.readMapEnd()
        else:
          iprot.skip(ftype)
      elif fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('listConstraints_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.MAP, 0)
      oprot.writeMapBegin(TType.STRING, TType.I32, len(self.success))
      for kiter280,viter281 in self.success.items():
        oprot.writeString(kiter280)
        oprot.writeI32(viter281)
      oprot.writeMapEnd()
      oprot.writeFieldEnd()
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class mergeTablets_args:
  """
  Attributes:
   - login
   - tableName
   - startRow
   - endRow
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
    (3, TType.STRING, 'startRow', None, None, ), # 3
    (4, TType.STRING, 'endRow', None, None, ), # 4
  )

  def __init__(self, login=None, tableName=None, startRow=None, endRow=None,):
    self.login = login
    self.tableName = tableName
    self.startRow = startRow
    self.endRow = endRow

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRING:
          self.startRow = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 4:
        if ftype == TType.STRING:
          self.endRow = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('mergeTablets_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    if self.startRow is not None:
      oprot.writeFieldBegin('startRow', TType.STRING, 3)
      oprot.writeString(self.startRow)
      oprot.writeFieldEnd()
    if self.endRow is not None:
      oprot.writeFieldBegin('endRow', TType.STRING, 4)
      oprot.writeString(self.endRow)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class mergeTablets_result:
  """
  Attributes:
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, ouch1=None, ouch2=None, ouch3=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('mergeTablets_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class offlineTable_args:
  """
  Attributes:
   - login
   - tableName
   - wait
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
    (3, TType.BOOL, 'wait', None, False, ), # 3
  )

  def __init__(self, login=None, tableName=None, wait=thrift_spec[3][4],):
    self.login = login
    self.tableName = tableName
    self.wait = wait

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.BOOL:
          self.wait = iprot.readBool();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('offlineTable_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    if self.wait is not None:
      oprot.writeFieldBegin('wait', TType.BOOL, 3)
      oprot.writeBool(self.wait)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class offlineTable_result:
  """
  Attributes:
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, ouch1=None, ouch2=None, ouch3=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('offlineTable_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class onlineTable_args:
  """
  Attributes:
   - login
   - tableName
   - wait
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
    (3, TType.BOOL, 'wait', None, False, ), # 3
  )

  def __init__(self, login=None, tableName=None, wait=thrift_spec[3][4],):
    self.login = login
    self.tableName = tableName
    self.wait = wait

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.BOOL:
          self.wait = iprot.readBool();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('onlineTable_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    if self.wait is not None:
      oprot.writeFieldBegin('wait', TType.BOOL, 3)
      oprot.writeBool(self.wait)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class onlineTable_result:
  """
  Attributes:
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, ouch1=None, ouch2=None, ouch3=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('onlineTable_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class removeConstraint_args:
  """
  Attributes:
   - login
   - tableName
   - constraint
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
    (3, TType.I32, 'constraint', None, None, ), # 3
  )

  def __init__(self, login=None, tableName=None, constraint=None,):
    self.login = login
    self.tableName = tableName
    self.constraint = constraint

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.I32:
          self.constraint = iprot.readI32();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('removeConstraint_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    if self.constraint is not None:
      oprot.writeFieldBegin('constraint', TType.I32, 3)
      oprot.writeI32(self.constraint)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class removeConstraint_result:
  """
  Attributes:
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, ouch1=None, ouch2=None, ouch3=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('removeConstraint_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class removeIterator_args:
  """
  Attributes:
   - login
   - tableName
   - iterName
   - scopes
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
    (3, TType.STRING, 'iterName', None, None, ), # 3
    (4, TType.SET, 'scopes', (TType.I32,None), None, ), # 4
  )

  def __init__(self, login=None, tableName=None, iterName=None, scopes=None,):
    self.login = login
    self.tableName = tableName
    self.iterName = iterName
    self.scopes = scopes

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRING:
          self.iterName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 4:
        if ftype == TType.SET:
          self.scopes = set()
          (_etype285, _size282) = iprot.readSetBegin()
          for _i286 in xrange(_size282):
            _elem287 = iprot.readI32();
            self.scopes.add(_elem287)
          iprot.readSetEnd()
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('removeIterator_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    if self.iterName is not None:
      oprot.writeFieldBegin('iterName', TType.STRING, 3)
      oprot.writeString(self.iterName)
      oprot.writeFieldEnd()
    if self.scopes is not None:
      oprot.writeFieldBegin('scopes', TType.SET, 4)
      oprot.writeSetBegin(TType.I32, len(self.scopes))
      for iter288 in self.scopes:
        oprot.writeI32(iter288)
      oprot.writeSetEnd()
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class removeIterator_result:
  """
  Attributes:
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, ouch1=None, ouch2=None, ouch3=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('removeIterator_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class removeTableProperty_args:
  """
  Attributes:
   - login
   - tableName
   - property
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
    (3, TType.STRING, 'property', None, None, ), # 3
  )

  def __init__(self, login=None, tableName=None, property=None,):
    self.login = login
    self.tableName = tableName
    self.property = property

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRING:
          self.property = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('removeTableProperty_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    if self.property is not None:
      oprot.writeFieldBegin('property', TType.STRING, 3)
      oprot.writeString(self.property)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class removeTableProperty_result:
  """
  Attributes:
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, ouch1=None, ouch2=None, ouch3=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('removeTableProperty_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class renameTable_args:
  """
  Attributes:
   - login
   - oldTableName
   - newTableName
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'oldTableName', None, None, ), # 2
    (3, TType.STRING, 'newTableName', None, None, ), # 3
  )

  def __init__(self, login=None, oldTableName=None, newTableName=None,):
    self.login = login
    self.oldTableName = oldTableName
    self.newTableName = newTableName

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.oldTableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRING:
          self.newTableName = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('renameTable_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.oldTableName is not None:
      oprot.writeFieldBegin('oldTableName', TType.STRING, 2)
      oprot.writeString(self.oldTableName)
      oprot.writeFieldEnd()
    if self.newTableName is not None:
      oprot.writeFieldBegin('newTableName', TType.STRING, 3)
      oprot.writeString(self.newTableName)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class renameTable_result:
  """
  Attributes:
   - ouch1
   - ouch2
   - ouch3
   - ouch4
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
    (4, TType.STRUCT, 'ouch4', (TableExistsException, TableExistsException.thrift_spec), None, ), # 4
  )

  def __init__(self, ouch1=None, ouch2=None, ouch3=None, ouch4=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3
    self.ouch4 = ouch4

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 4:
        if ftype == TType.STRUCT:
          self.ouch4 = TableExistsException()
          self.ouch4.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('renameTable_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch4 is not None:
      oprot.writeFieldBegin('ouch4', TType.STRUCT, 4)
      self.ouch4.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class setLocalityGroups_args:
  """
  Attributes:
   - login
   - tableName
   - groups
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
    (3, TType.MAP, 'groups', (TType.STRING,None,TType.SET,(TType.STRING,None)), None, ), # 3
  )

  def __init__(self, login=None, tableName=None, groups=None,):
    self.login = login
    self.tableName = tableName
    self.groups = groups

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.MAP:
          self.groups = {}
          (_ktype290, _vtype291, _size289 ) = iprot.readMapBegin()
          for _i293 in xrange(_size289):
            _key294 = iprot.readString();
            _val295 = set()
            (_etype299, _size296) = iprot.readSetBegin()
            for _i300 in xrange(_size296):
              _elem301 = iprot.readString();
              _val295.add(_elem301)
            iprot.readSetEnd()
            self.groups[_key294] = _val295
          iprot.readMapEnd()
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('setLocalityGroups_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    if self.groups is not None:
      oprot.writeFieldBegin('groups', TType.MAP, 3)
      oprot.writeMapBegin(TType.STRING, TType.SET, len(self.groups))
      for kiter302,viter303 in self.groups.items():
        oprot.writeString(kiter302)
        oprot.writeSetBegin(TType.STRING, len(viter303))
        for iter304 in viter303:
          oprot.writeString(iter304)
        oprot.writeSetEnd()
      oprot.writeMapEnd()
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class setLocalityGroups_result:
  """
  Attributes:
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, ouch1=None, ouch2=None, ouch3=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('setLocalityGroups_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class setTableProperty_args:
  """
  Attributes:
   - login
   - tableName
   - property
   - value
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
    (3, TType.STRING, 'property', None, None, ), # 3
    (4, TType.STRING, 'value', None, None, ), # 4
  )

  def __init__(self, login=None, tableName=None, property=None, value=None,):
    self.login = login
    self.tableName = tableName
    self.property = property
    self.value = value

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRING:
          self.property = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 4:
        if ftype == TType.STRING:
          self.value = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('setTableProperty_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    if self.property is not None:
      oprot.writeFieldBegin('property', TType.STRING, 3)
      oprot.writeString(self.property)
      oprot.writeFieldEnd()
    if self.value is not None:
      oprot.writeFieldBegin('value', TType.STRING, 4)
      oprot.writeString(self.value)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class setTableProperty_result:
  """
  Attributes:
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, ouch1=None, ouch2=None, ouch3=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('setTableProperty_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class splitRangeByTablets_args:
  """
  Attributes:
   - login
   - tableName
   - range
   - maxSplits
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
    (3, TType.STRUCT, 'range', (Range, Range.thrift_spec), None, ), # 3
    (4, TType.I32, 'maxSplits', None, None, ), # 4
  )

  def __init__(self, login=None, tableName=None, range=None, maxSplits=None,):
    self.login = login
    self.tableName = tableName
    self.range = range
    self.maxSplits = maxSplits

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.range = Range()
          self.range.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 4:
        if ftype == TType.I32:
          self.maxSplits = iprot.readI32();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('splitRangeByTablets_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    if self.range is not None:
      oprot.writeFieldBegin('range', TType.STRUCT, 3)
      self.range.write(oprot)
      oprot.writeFieldEnd()
    if self.maxSplits is not None:
      oprot.writeFieldBegin('maxSplits', TType.I32, 4)
      oprot.writeI32(self.maxSplits)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class splitRangeByTablets_result:
  """
  Attributes:
   - success
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    (0, TType.SET, 'success', (TType.STRUCT,(Range, Range.thrift_spec)), None, ), # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, success=None, ouch1=None, ouch2=None, ouch3=None,):
    self.success = success
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.SET:
          self.success = set()
          (_etype308, _size305) = iprot.readSetBegin()
          for _i309 in xrange(_size305):
            _elem310 = Range()
            _elem310.read(iprot)
            self.success.add(_elem310)
          iprot.readSetEnd()
        else:
          iprot.skip(ftype)
      elif fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('splitRangeByTablets_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.SET, 0)
      oprot.writeSetBegin(TType.STRUCT, len(self.success))
      for iter311 in self.success:
        iter311.write(oprot)
      oprot.writeSetEnd()
      oprot.writeFieldEnd()
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class tableExists_args:
  """
  Attributes:
   - login
   - tableName
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
  )

  def __init__(self, login=None, tableName=None,):
    self.login = login
    self.tableName = tableName

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('tableExists_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class tableExists_result:
  """
  Attributes:
   - success
  """

  thrift_spec = (
    (0, TType.BOOL, 'success', None, None, ), # 0
  )

  def __init__(self, success=None,):
    self.success = success

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.BOOL:
          self.success = iprot.readBool();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('tableExists_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.BOOL, 0)
      oprot.writeBool(self.success)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class tableIdMap_args:
  """
  Attributes:
   - login
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
  )

  def __init__(self, login=None,):
    self.login = login

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('tableIdMap_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class tableIdMap_result:
  """
  Attributes:
   - success
  """

  thrift_spec = (
    (0, TType.MAP, 'success', (TType.STRING,None,TType.STRING,None), None, ), # 0
  )

  def __init__(self, success=None,):
    self.success = success

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.MAP:
          self.success = {}
          (_ktype313, _vtype314, _size312 ) = iprot.readMapBegin()
          for _i316 in xrange(_size312):
            _key317 = iprot.readString();
            _val318 = iprot.readString();
            self.success[_key317] = _val318
          iprot.readMapEnd()
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('tableIdMap_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.MAP, 0)
      oprot.writeMapBegin(TType.STRING, TType.STRING, len(self.success))
      for kiter319,viter320 in self.success.items():
        oprot.writeString(kiter319)
        oprot.writeString(viter320)
      oprot.writeMapEnd()
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class testTableClassLoad_args:
  """
  Attributes:
   - login
   - tableName
   - className
   - asTypeName
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
    (3, TType.STRING, 'className', None, None, ), # 3
    (4, TType.STRING, 'asTypeName', None, None, ), # 4
  )

  def __init__(self, login=None, tableName=None, className=None, asTypeName=None,):
    self.login = login
    self.tableName = tableName
    self.className = className
    self.asTypeName = asTypeName

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRING:
          self.className = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 4:
        if ftype == TType.STRING:
          self.asTypeName = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('testTableClassLoad_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    if self.className is not None:
      oprot.writeFieldBegin('className', TType.STRING, 3)
      oprot.writeString(self.className)
      oprot.writeFieldEnd()
    if self.asTypeName is not None:
      oprot.writeFieldBegin('asTypeName', TType.STRING, 4)
      oprot.writeString(self.asTypeName)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class testTableClassLoad_result:
  """
  Attributes:
   - success
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    (0, TType.BOOL, 'success', None, None, ), # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, success=None, ouch1=None, ouch2=None, ouch3=None,):
    self.success = success
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.BOOL:
          self.success = iprot.readBool();
        else:
          iprot.skip(ftype)
      elif fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('testTableClassLoad_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.BOOL, 0)
      oprot.writeBool(self.success)
      oprot.writeFieldEnd()
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class pingTabletServer_args:
  """
  Attributes:
   - login
   - tserver
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tserver', None, None, ), # 2
  )

  def __init__(self, login=None, tserver=None,):
    self.login = login
    self.tserver = tserver

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tserver = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('pingTabletServer_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tserver is not None:
      oprot.writeFieldBegin('tserver', TType.STRING, 2)
      oprot.writeString(self.tserver)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class pingTabletServer_result:
  """
  Attributes:
   - ouch1
   - ouch2
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
  )

  def __init__(self, ouch1=None, ouch2=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('pingTabletServer_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class getActiveScans_args:
  """
  Attributes:
   - login
   - tserver
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tserver', None, None, ), # 2
  )

  def __init__(self, login=None, tserver=None,):
    self.login = login
    self.tserver = tserver

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tserver = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('getActiveScans_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tserver is not None:
      oprot.writeFieldBegin('tserver', TType.STRING, 2)
      oprot.writeString(self.tserver)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class getActiveScans_result:
  """
  Attributes:
   - success
   - ouch1
   - ouch2
  """

  thrift_spec = (
    (0, TType.LIST, 'success', (TType.STRUCT,(ActiveScan, ActiveScan.thrift_spec)), None, ), # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
  )

  def __init__(self, success=None, ouch1=None, ouch2=None,):
    self.success = success
    self.ouch1 = ouch1
    self.ouch2 = ouch2

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.LIST:
          self.success = []
          (_etype324, _size321) = iprot.readListBegin()
          for _i325 in xrange(_size321):
            _elem326 = ActiveScan()
            _elem326.read(iprot)
            self.success.append(_elem326)
          iprot.readListEnd()
        else:
          iprot.skip(ftype)
      elif fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('getActiveScans_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.LIST, 0)
      oprot.writeListBegin(TType.STRUCT, len(self.success))
      for iter327 in self.success:
        iter327.write(oprot)
      oprot.writeListEnd()
      oprot.writeFieldEnd()
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class getActiveCompactions_args:
  """
  Attributes:
   - login
   - tserver
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tserver', None, None, ), # 2
  )

  def __init__(self, login=None, tserver=None,):
    self.login = login
    self.tserver = tserver

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tserver = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('getActiveCompactions_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tserver is not None:
      oprot.writeFieldBegin('tserver', TType.STRING, 2)
      oprot.writeString(self.tserver)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class getActiveCompactions_result:
  """
  Attributes:
   - success
   - ouch1
   - ouch2
  """

  thrift_spec = (
    (0, TType.LIST, 'success', (TType.STRUCT,(ActiveCompaction, ActiveCompaction.thrift_spec)), None, ), # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
  )

  def __init__(self, success=None, ouch1=None, ouch2=None,):
    self.success = success
    self.ouch1 = ouch1
    self.ouch2 = ouch2

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.LIST:
          self.success = []
          (_etype331, _size328) = iprot.readListBegin()
          for _i332 in xrange(_size328):
            _elem333 = ActiveCompaction()
            _elem333.read(iprot)
            self.success.append(_elem333)
          iprot.readListEnd()
        else:
          iprot.skip(ftype)
      elif fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('getActiveCompactions_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.LIST, 0)
      oprot.writeListBegin(TType.STRUCT, len(self.success))
      for iter334 in self.success:
        iter334.write(oprot)
      oprot.writeListEnd()
      oprot.writeFieldEnd()
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class getSiteConfiguration_args:
  """
  Attributes:
   - login
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
  )

  def __init__(self, login=None,):
    self.login = login

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('getSiteConfiguration_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class getSiteConfiguration_result:
  """
  Attributes:
   - success
   - ouch1
   - ouch2
  """

  thrift_spec = (
    (0, TType.MAP, 'success', (TType.STRING,None,TType.STRING,None), None, ), # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
  )

  def __init__(self, success=None, ouch1=None, ouch2=None,):
    self.success = success
    self.ouch1 = ouch1
    self.ouch2 = ouch2

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.MAP:
          self.success = {}
          (_ktype336, _vtype337, _size335 ) = iprot.readMapBegin()
          for _i339 in xrange(_size335):
            _key340 = iprot.readString();
            _val341 = iprot.readString();
            self.success[_key340] = _val341
          iprot.readMapEnd()
        else:
          iprot.skip(ftype)
      elif fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('getSiteConfiguration_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.MAP, 0)
      oprot.writeMapBegin(TType.STRING, TType.STRING, len(self.success))
      for kiter342,viter343 in self.success.items():
        oprot.writeString(kiter342)
        oprot.writeString(viter343)
      oprot.writeMapEnd()
      oprot.writeFieldEnd()
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class getSystemConfiguration_args:
  """
  Attributes:
   - login
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
  )

  def __init__(self, login=None,):
    self.login = login

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('getSystemConfiguration_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class getSystemConfiguration_result:
  """
  Attributes:
   - success
   - ouch1
   - ouch2
  """

  thrift_spec = (
    (0, TType.MAP, 'success', (TType.STRING,None,TType.STRING,None), None, ), # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
  )

  def __init__(self, success=None, ouch1=None, ouch2=None,):
    self.success = success
    self.ouch1 = ouch1
    self.ouch2 = ouch2

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.MAP:
          self.success = {}
          (_ktype345, _vtype346, _size344 ) = iprot.readMapBegin()
          for _i348 in xrange(_size344):
            _key349 = iprot.readString();
            _val350 = iprot.readString();
            self.success[_key349] = _val350
          iprot.readMapEnd()
        else:
          iprot.skip(ftype)
      elif fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('getSystemConfiguration_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.MAP, 0)
      oprot.writeMapBegin(TType.STRING, TType.STRING, len(self.success))
      for kiter351,viter352 in self.success.items():
        oprot.writeString(kiter351)
        oprot.writeString(viter352)
      oprot.writeMapEnd()
      oprot.writeFieldEnd()
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class getTabletServers_args:
  """
  Attributes:
   - login
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
  )

  def __init__(self, login=None,):
    self.login = login

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('getTabletServers_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class getTabletServers_result:
  """
  Attributes:
   - success
  """

  thrift_spec = (
    (0, TType.LIST, 'success', (TType.STRING,None), None, ), # 0
  )

  def __init__(self, success=None,):
    self.success = success

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.LIST:
          self.success = []
          (_etype356, _size353) = iprot.readListBegin()
          for _i357 in xrange(_size353):
            _elem358 = iprot.readString();
            self.success.append(_elem358)
          iprot.readListEnd()
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('getTabletServers_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.LIST, 0)
      oprot.writeListBegin(TType.STRING, len(self.success))
      for iter359 in self.success:
        oprot.writeString(iter359)
      oprot.writeListEnd()
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class removeProperty_args:
  """
  Attributes:
   - login
   - property
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'property', None, None, ), # 2
  )

  def __init__(self, login=None, property=None,):
    self.login = login
    self.property = property

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.property = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('removeProperty_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.property is not None:
      oprot.writeFieldBegin('property', TType.STRING, 2)
      oprot.writeString(self.property)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class removeProperty_result:
  """
  Attributes:
   - ouch1
   - ouch2
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
  )

  def __init__(self, ouch1=None, ouch2=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('removeProperty_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class setProperty_args:
  """
  Attributes:
   - login
   - property
   - value
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'property', None, None, ), # 2
    (3, TType.STRING, 'value', None, None, ), # 3
  )

  def __init__(self, login=None, property=None, value=None,):
    self.login = login
    self.property = property
    self.value = value

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.property = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRING:
          self.value = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('setProperty_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.property is not None:
      oprot.writeFieldBegin('property', TType.STRING, 2)
      oprot.writeString(self.property)
      oprot.writeFieldEnd()
    if self.value is not None:
      oprot.writeFieldBegin('value', TType.STRING, 3)
      oprot.writeString(self.value)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class setProperty_result:
  """
  Attributes:
   - ouch1
   - ouch2
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
  )

  def __init__(self, ouch1=None, ouch2=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('setProperty_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class testClassLoad_args:
  """
  Attributes:
   - login
   - className
   - asTypeName
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'className', None, None, ), # 2
    (3, TType.STRING, 'asTypeName', None, None, ), # 3
  )

  def __init__(self, login=None, className=None, asTypeName=None,):
    self.login = login
    self.className = className
    self.asTypeName = asTypeName

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.className = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRING:
          self.asTypeName = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('testClassLoad_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.className is not None:
      oprot.writeFieldBegin('className', TType.STRING, 2)
      oprot.writeString(self.className)
      oprot.writeFieldEnd()
    if self.asTypeName is not None:
      oprot.writeFieldBegin('asTypeName', TType.STRING, 3)
      oprot.writeString(self.asTypeName)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class testClassLoad_result:
  """
  Attributes:
   - success
   - ouch1
   - ouch2
  """

  thrift_spec = (
    (0, TType.BOOL, 'success', None, None, ), # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
  )

  def __init__(self, success=None, ouch1=None, ouch2=None,):
    self.success = success
    self.ouch1 = ouch1
    self.ouch2 = ouch2

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.BOOL:
          self.success = iprot.readBool();
        else:
          iprot.skip(ftype)
      elif fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('testClassLoad_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.BOOL, 0)
      oprot.writeBool(self.success)
      oprot.writeFieldEnd()
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class authenticateUser_args:
  """
  Attributes:
   - login
   - user
   - properties
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'user', None, None, ), # 2
    (3, TType.MAP, 'properties', (TType.STRING,None,TType.STRING,None), None, ), # 3
  )

  def __init__(self, login=None, user=None, properties=None,):
    self.login = login
    self.user = user
    self.properties = properties

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.user = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.MAP:
          self.properties = {}
          (_ktype361, _vtype362, _size360 ) = iprot.readMapBegin()
          for _i364 in xrange(_size360):
            _key365 = iprot.readString();
            _val366 = iprot.readString();
            self.properties[_key365] = _val366
          iprot.readMapEnd()
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('authenticateUser_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.user is not None:
      oprot.writeFieldBegin('user', TType.STRING, 2)
      oprot.writeString(self.user)
      oprot.writeFieldEnd()
    if self.properties is not None:
      oprot.writeFieldBegin('properties', TType.MAP, 3)
      oprot.writeMapBegin(TType.STRING, TType.STRING, len(self.properties))
      for kiter367,viter368 in self.properties.items():
        oprot.writeString(kiter367)
        oprot.writeString(viter368)
      oprot.writeMapEnd()
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class authenticateUser_result:
  """
  Attributes:
   - success
   - ouch1
   - ouch2
  """

  thrift_spec = (
    (0, TType.BOOL, 'success', None, None, ), # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
  )

  def __init__(self, success=None, ouch1=None, ouch2=None,):
    self.success = success
    self.ouch1 = ouch1
    self.ouch2 = ouch2

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.BOOL:
          self.success = iprot.readBool();
        else:
          iprot.skip(ftype)
      elif fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('authenticateUser_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.BOOL, 0)
      oprot.writeBool(self.success)
      oprot.writeFieldEnd()
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class changeUserAuthorizations_args:
  """
  Attributes:
   - login
   - user
   - authorizations
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'user', None, None, ), # 2
    (3, TType.SET, 'authorizations', (TType.STRING,None), None, ), # 3
  )

  def __init__(self, login=None, user=None, authorizations=None,):
    self.login = login
    self.user = user
    self.authorizations = authorizations

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.user = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.SET:
          self.authorizations = set()
          (_etype372, _size369) = iprot.readSetBegin()
          for _i373 in xrange(_size369):
            _elem374 = iprot.readString();
            self.authorizations.add(_elem374)
          iprot.readSetEnd()
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('changeUserAuthorizations_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.user is not None:
      oprot.writeFieldBegin('user', TType.STRING, 2)
      oprot.writeString(self.user)
      oprot.writeFieldEnd()
    if self.authorizations is not None:
      oprot.writeFieldBegin('authorizations', TType.SET, 3)
      oprot.writeSetBegin(TType.STRING, len(self.authorizations))
      for iter375 in self.authorizations:
        oprot.writeString(iter375)
      oprot.writeSetEnd()
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class changeUserAuthorizations_result:
  """
  Attributes:
   - ouch1
   - ouch2
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
  )

  def __init__(self, ouch1=None, ouch2=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('changeUserAuthorizations_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class changeLocalUserPassword_args:
  """
  Attributes:
   - login
   - user
   - password
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'user', None, None, ), # 2
    (3, TType.STRING, 'password', None, None, ), # 3
  )

  def __init__(self, login=None, user=None, password=None,):
    self.login = login
    self.user = user
    self.password = password

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.user = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRING:
          self.password = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('changeLocalUserPassword_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.user is not None:
      oprot.writeFieldBegin('user', TType.STRING, 2)
      oprot.writeString(self.user)
      oprot.writeFieldEnd()
    if self.password is not None:
      oprot.writeFieldBegin('password', TType.STRING, 3)
      oprot.writeString(self.password)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class changeLocalUserPassword_result:
  """
  Attributes:
   - ouch1
   - ouch2
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
  )

  def __init__(self, ouch1=None, ouch2=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('changeLocalUserPassword_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class createLocalUser_args:
  """
  Attributes:
   - login
   - user
   - password
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'user', None, None, ), # 2
    (3, TType.STRING, 'password', None, None, ), # 3
  )

  def __init__(self, login=None, user=None, password=None,):
    self.login = login
    self.user = user
    self.password = password

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.user = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRING:
          self.password = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('createLocalUser_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.user is not None:
      oprot.writeFieldBegin('user', TType.STRING, 2)
      oprot.writeString(self.user)
      oprot.writeFieldEnd()
    if self.password is not None:
      oprot.writeFieldBegin('password', TType.STRING, 3)
      oprot.writeString(self.password)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class createLocalUser_result:
  """
  Attributes:
   - ouch1
   - ouch2
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
  )

  def __init__(self, ouch1=None, ouch2=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('createLocalUser_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class dropLocalUser_args:
  """
  Attributes:
   - login
   - user
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'user', None, None, ), # 2
  )

  def __init__(self, login=None, user=None,):
    self.login = login
    self.user = user

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.user = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('dropLocalUser_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.user is not None:
      oprot.writeFieldBegin('user', TType.STRING, 2)
      oprot.writeString(self.user)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class dropLocalUser_result:
  """
  Attributes:
   - ouch1
   - ouch2
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
  )

  def __init__(self, ouch1=None, ouch2=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('dropLocalUser_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class getUserAuthorizations_args:
  """
  Attributes:
   - login
   - user
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'user', None, None, ), # 2
  )

  def __init__(self, login=None, user=None,):
    self.login = login
    self.user = user

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.user = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('getUserAuthorizations_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.user is not None:
      oprot.writeFieldBegin('user', TType.STRING, 2)
      oprot.writeString(self.user)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class getUserAuthorizations_result:
  """
  Attributes:
   - success
   - ouch1
   - ouch2
  """

  thrift_spec = (
    (0, TType.LIST, 'success', (TType.STRING,None), None, ), # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
  )

  def __init__(self, success=None, ouch1=None, ouch2=None,):
    self.success = success
    self.ouch1 = ouch1
    self.ouch2 = ouch2

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.LIST:
          self.success = []
          (_etype379, _size376) = iprot.readListBegin()
          for _i380 in xrange(_size376):
            _elem381 = iprot.readString();
            self.success.append(_elem381)
          iprot.readListEnd()
        else:
          iprot.skip(ftype)
      elif fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('getUserAuthorizations_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.LIST, 0)
      oprot.writeListBegin(TType.STRING, len(self.success))
      for iter382 in self.success:
        oprot.writeString(iter382)
      oprot.writeListEnd()
      oprot.writeFieldEnd()
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class grantSystemPermission_args:
  """
  Attributes:
   - login
   - user
   - perm
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'user', None, None, ), # 2
    (3, TType.I32, 'perm', None, None, ), # 3
  )

  def __init__(self, login=None, user=None, perm=None,):
    self.login = login
    self.user = user
    self.perm = perm

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.user = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.I32:
          self.perm = iprot.readI32();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('grantSystemPermission_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.user is not None:
      oprot.writeFieldBegin('user', TType.STRING, 2)
      oprot.writeString(self.user)
      oprot.writeFieldEnd()
    if self.perm is not None:
      oprot.writeFieldBegin('perm', TType.I32, 3)
      oprot.writeI32(self.perm)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class grantSystemPermission_result:
  """
  Attributes:
   - ouch1
   - ouch2
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
  )

  def __init__(self, ouch1=None, ouch2=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('grantSystemPermission_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class grantTablePermission_args:
  """
  Attributes:
   - login
   - user
   - table
   - perm
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'user', None, None, ), # 2
    (3, TType.STRING, 'table', None, None, ), # 3
    (4, TType.I32, 'perm', None, None, ), # 4
  )

  def __init__(self, login=None, user=None, table=None, perm=None,):
    self.login = login
    self.user = user
    self.table = table
    self.perm = perm

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.user = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRING:
          self.table = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 4:
        if ftype == TType.I32:
          self.perm = iprot.readI32();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('grantTablePermission_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.user is not None:
      oprot.writeFieldBegin('user', TType.STRING, 2)
      oprot.writeString(self.user)
      oprot.writeFieldEnd()
    if self.table is not None:
      oprot.writeFieldBegin('table', TType.STRING, 3)
      oprot.writeString(self.table)
      oprot.writeFieldEnd()
    if self.perm is not None:
      oprot.writeFieldBegin('perm', TType.I32, 4)
      oprot.writeI32(self.perm)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class grantTablePermission_result:
  """
  Attributes:
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, ouch1=None, ouch2=None, ouch3=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('grantTablePermission_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class hasSystemPermission_args:
  """
  Attributes:
   - login
   - user
   - perm
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'user', None, None, ), # 2
    (3, TType.I32, 'perm', None, None, ), # 3
  )

  def __init__(self, login=None, user=None, perm=None,):
    self.login = login
    self.user = user
    self.perm = perm

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.user = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.I32:
          self.perm = iprot.readI32();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('hasSystemPermission_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.user is not None:
      oprot.writeFieldBegin('user', TType.STRING, 2)
      oprot.writeString(self.user)
      oprot.writeFieldEnd()
    if self.perm is not None:
      oprot.writeFieldBegin('perm', TType.I32, 3)
      oprot.writeI32(self.perm)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class hasSystemPermission_result:
  """
  Attributes:
   - success
   - ouch1
   - ouch2
  """

  thrift_spec = (
    (0, TType.BOOL, 'success', None, None, ), # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
  )

  def __init__(self, success=None, ouch1=None, ouch2=None,):
    self.success = success
    self.ouch1 = ouch1
    self.ouch2 = ouch2

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.BOOL:
          self.success = iprot.readBool();
        else:
          iprot.skip(ftype)
      elif fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('hasSystemPermission_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.BOOL, 0)
      oprot.writeBool(self.success)
      oprot.writeFieldEnd()
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class hasTablePermission_args:
  """
  Attributes:
   - login
   - user
   - table
   - perm
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'user', None, None, ), # 2
    (3, TType.STRING, 'table', None, None, ), # 3
    (4, TType.I32, 'perm', None, None, ), # 4
  )

  def __init__(self, login=None, user=None, table=None, perm=None,):
    self.login = login
    self.user = user
    self.table = table
    self.perm = perm

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.user = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRING:
          self.table = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 4:
        if ftype == TType.I32:
          self.perm = iprot.readI32();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('hasTablePermission_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.user is not None:
      oprot.writeFieldBegin('user', TType.STRING, 2)
      oprot.writeString(self.user)
      oprot.writeFieldEnd()
    if self.table is not None:
      oprot.writeFieldBegin('table', TType.STRING, 3)
      oprot.writeString(self.table)
      oprot.writeFieldEnd()
    if self.perm is not None:
      oprot.writeFieldBegin('perm', TType.I32, 4)
      oprot.writeI32(self.perm)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class hasTablePermission_result:
  """
  Attributes:
   - success
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    (0, TType.BOOL, 'success', None, None, ), # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, success=None, ouch1=None, ouch2=None, ouch3=None,):
    self.success = success
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.BOOL:
          self.success = iprot.readBool();
        else:
          iprot.skip(ftype)
      elif fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('hasTablePermission_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.BOOL, 0)
      oprot.writeBool(self.success)
      oprot.writeFieldEnd()
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class listLocalUsers_args:
  """
  Attributes:
   - login
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
  )

  def __init__(self, login=None,):
    self.login = login

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('listLocalUsers_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class listLocalUsers_result:
  """
  Attributes:
   - success
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    (0, TType.SET, 'success', (TType.STRING,None), None, ), # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, success=None, ouch1=None, ouch2=None, ouch3=None,):
    self.success = success
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.SET:
          self.success = set()
          (_etype386, _size383) = iprot.readSetBegin()
          for _i387 in xrange(_size383):
            _elem388 = iprot.readString();
            self.success.add(_elem388)
          iprot.readSetEnd()
        else:
          iprot.skip(ftype)
      elif fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('listLocalUsers_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.SET, 0)
      oprot.writeSetBegin(TType.STRING, len(self.success))
      for iter389 in self.success:
        oprot.writeString(iter389)
      oprot.writeSetEnd()
      oprot.writeFieldEnd()
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class revokeSystemPermission_args:
  """
  Attributes:
   - login
   - user
   - perm
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'user', None, None, ), # 2
    (3, TType.I32, 'perm', None, None, ), # 3
  )

  def __init__(self, login=None, user=None, perm=None,):
    self.login = login
    self.user = user
    self.perm = perm

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.user = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.I32:
          self.perm = iprot.readI32();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('revokeSystemPermission_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.user is not None:
      oprot.writeFieldBegin('user', TType.STRING, 2)
      oprot.writeString(self.user)
      oprot.writeFieldEnd()
    if self.perm is not None:
      oprot.writeFieldBegin('perm', TType.I32, 3)
      oprot.writeI32(self.perm)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class revokeSystemPermission_result:
  """
  Attributes:
   - ouch1
   - ouch2
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
  )

  def __init__(self, ouch1=None, ouch2=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('revokeSystemPermission_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class revokeTablePermission_args:
  """
  Attributes:
   - login
   - user
   - table
   - perm
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'user', None, None, ), # 2
    (3, TType.STRING, 'table', None, None, ), # 3
    (4, TType.I32, 'perm', None, None, ), # 4
  )

  def __init__(self, login=None, user=None, table=None, perm=None,):
    self.login = login
    self.user = user
    self.table = table
    self.perm = perm

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.user = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRING:
          self.table = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 4:
        if ftype == TType.I32:
          self.perm = iprot.readI32();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('revokeTablePermission_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.user is not None:
      oprot.writeFieldBegin('user', TType.STRING, 2)
      oprot.writeString(self.user)
      oprot.writeFieldEnd()
    if self.table is not None:
      oprot.writeFieldBegin('table', TType.STRING, 3)
      oprot.writeString(self.table)
      oprot.writeFieldEnd()
    if self.perm is not None:
      oprot.writeFieldBegin('perm', TType.I32, 4)
      oprot.writeI32(self.perm)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class revokeTablePermission_result:
  """
  Attributes:
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, ouch1=None, ouch2=None, ouch3=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('revokeTablePermission_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class createBatchScanner_args:
  """
  Attributes:
   - login
   - tableName
   - options
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
    (3, TType.STRUCT, 'options', (BatchScanOptions, BatchScanOptions.thrift_spec), None, ), # 3
  )

  def __init__(self, login=None, tableName=None, options=None,):
    self.login = login
    self.tableName = tableName
    self.options = options

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.options = BatchScanOptions()
          self.options.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('createBatchScanner_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    if self.options is not None:
      oprot.writeFieldBegin('options', TType.STRUCT, 3)
      self.options.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class createBatchScanner_result:
  """
  Attributes:
   - success
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    (0, TType.STRING, 'success', None, None, ), # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, success=None, ouch1=None, ouch2=None, ouch3=None,):
    self.success = success
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.STRING:
          self.success = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('createBatchScanner_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.STRING, 0)
      oprot.writeString(self.success)
      oprot.writeFieldEnd()
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class createScanner_args:
  """
  Attributes:
   - login
   - tableName
   - options
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
    (3, TType.STRUCT, 'options', (ScanOptions, ScanOptions.thrift_spec), None, ), # 3
  )

  def __init__(self, login=None, tableName=None, options=None,):
    self.login = login
    self.tableName = tableName
    self.options = options

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.options = ScanOptions()
          self.options.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('createScanner_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    if self.options is not None:
      oprot.writeFieldBegin('options', TType.STRUCT, 3)
      self.options.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class createScanner_result:
  """
  Attributes:
   - success
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    (0, TType.STRING, 'success', None, None, ), # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, success=None, ouch1=None, ouch2=None, ouch3=None,):
    self.success = success
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.STRING:
          self.success = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('createScanner_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.STRING, 0)
      oprot.writeString(self.success)
      oprot.writeFieldEnd()
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class hasNext_args:
  """
  Attributes:
   - scanner
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'scanner', None, None, ), # 1
  )

  def __init__(self, scanner=None,):
    self.scanner = scanner

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.scanner = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('hasNext_args')
    if self.scanner is not None:
      oprot.writeFieldBegin('scanner', TType.STRING, 1)
      oprot.writeString(self.scanner)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class hasNext_result:
  """
  Attributes:
   - success
   - ouch1
  """

  thrift_spec = (
    (0, TType.BOOL, 'success', None, None, ), # 0
    (1, TType.STRUCT, 'ouch1', (UnknownScanner, UnknownScanner.thrift_spec), None, ), # 1
  )

  def __init__(self, success=None, ouch1=None,):
    self.success = success
    self.ouch1 = ouch1

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.BOOL:
          self.success = iprot.readBool();
        else:
          iprot.skip(ftype)
      elif fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = UnknownScanner()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('hasNext_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.BOOL, 0)
      oprot.writeBool(self.success)
      oprot.writeFieldEnd()
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class nextEntry_args:
  """
  Attributes:
   - scanner
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'scanner', None, None, ), # 1
  )

  def __init__(self, scanner=None,):
    self.scanner = scanner

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.scanner = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('nextEntry_args')
    if self.scanner is not None:
      oprot.writeFieldBegin('scanner', TType.STRING, 1)
      oprot.writeString(self.scanner)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class nextEntry_result:
  """
  Attributes:
   - success
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    (0, TType.STRUCT, 'success', (KeyValueAndPeek, KeyValueAndPeek.thrift_spec), None, ), # 0
    (1, TType.STRUCT, 'ouch1', (NoMoreEntriesException, NoMoreEntriesException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (UnknownScanner, UnknownScanner.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 3
  )

  def __init__(self, success=None, ouch1=None, ouch2=None, ouch3=None,):
    self.success = success
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.STRUCT:
          self.success = KeyValueAndPeek()
          self.success.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = NoMoreEntriesException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = UnknownScanner()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = AccumuloSecurityException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('nextEntry_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.STRUCT, 0)
      self.success.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class nextK_args:
  """
  Attributes:
   - scanner
   - k
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'scanner', None, None, ), # 1
    (2, TType.I32, 'k', None, None, ), # 2
  )

  def __init__(self, scanner=None, k=None,):
    self.scanner = scanner
    self.k = k

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.scanner = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.I32:
          self.k = iprot.readI32();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('nextK_args')
    if self.scanner is not None:
      oprot.writeFieldBegin('scanner', TType.STRING, 1)
      oprot.writeString(self.scanner)
      oprot.writeFieldEnd()
    if self.k is not None:
      oprot.writeFieldBegin('k', TType.I32, 2)
      oprot.writeI32(self.k)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class nextK_result:
  """
  Attributes:
   - success
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    (0, TType.STRUCT, 'success', (ScanResult, ScanResult.thrift_spec), None, ), # 0
    (1, TType.STRUCT, 'ouch1', (NoMoreEntriesException, NoMoreEntriesException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (UnknownScanner, UnknownScanner.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 3
  )

  def __init__(self, success=None, ouch1=None, ouch2=None, ouch3=None,):
    self.success = success
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.STRUCT:
          self.success = ScanResult()
          self.success.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = NoMoreEntriesException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = UnknownScanner()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = AccumuloSecurityException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('nextK_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.STRUCT, 0)
      self.success.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class closeScanner_args:
  """
  Attributes:
   - scanner
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'scanner', None, None, ), # 1
  )

  def __init__(self, scanner=None,):
    self.scanner = scanner

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.scanner = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('closeScanner_args')
    if self.scanner is not None:
      oprot.writeFieldBegin('scanner', TType.STRING, 1)
      oprot.writeString(self.scanner)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class closeScanner_result:
  """
  Attributes:
   - ouch1
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (UnknownScanner, UnknownScanner.thrift_spec), None, ), # 1
  )

  def __init__(self, ouch1=None,):
    self.ouch1 = ouch1

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = UnknownScanner()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('closeScanner_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class updateAndFlush_args:
  """
  Attributes:
   - login
   - tableName
   - cells
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
    (3, TType.MAP, 'cells', (TType.STRING,None,TType.LIST,(TType.STRUCT,(ColumnUpdate, ColumnUpdate.thrift_spec))), None, ), # 3
  )

  def __init__(self, login=None, tableName=None, cells=None,):
    self.login = login
    self.tableName = tableName
    self.cells = cells

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.MAP:
          self.cells = {}
          (_ktype391, _vtype392, _size390 ) = iprot.readMapBegin()
          for _i394 in xrange(_size390):
            _key395 = iprot.readString();
            _val396 = []
            (_etype400, _size397) = iprot.readListBegin()
            for _i401 in xrange(_size397):
              _elem402 = ColumnUpdate()
              _elem402.read(iprot)
              _val396.append(_elem402)
            iprot.readListEnd()
            self.cells[_key395] = _val396
          iprot.readMapEnd()
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('updateAndFlush_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    if self.cells is not None:
      oprot.writeFieldBegin('cells', TType.MAP, 3)
      oprot.writeMapBegin(TType.STRING, TType.LIST, len(self.cells))
      for kiter403,viter404 in self.cells.items():
        oprot.writeString(kiter403)
        oprot.writeListBegin(TType.STRUCT, len(viter404))
        for iter405 in viter404:
          iter405.write(oprot)
        oprot.writeListEnd()
      oprot.writeMapEnd()
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class updateAndFlush_result:
  """
  Attributes:
   - outch1
   - ouch2
   - ouch3
   - ouch4
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'outch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
    (4, TType.STRUCT, 'ouch4', (MutationsRejectedException, MutationsRejectedException.thrift_spec), None, ), # 4
  )

  def __init__(self, outch1=None, ouch2=None, ouch3=None, ouch4=None,):
    self.outch1 = outch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3
    self.ouch4 = ouch4

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.outch1 = AccumuloException()
          self.outch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 4:
        if ftype == TType.STRUCT:
          self.ouch4 = MutationsRejectedException()
          self.ouch4.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('updateAndFlush_result')
    if self.outch1 is not None:
      oprot.writeFieldBegin('outch1', TType.STRUCT, 1)
      self.outch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch4 is not None:
      oprot.writeFieldBegin('ouch4', TType.STRUCT, 4)
      self.ouch4.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class createWriter_args:
  """
  Attributes:
   - login
   - tableName
   - opts
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
    (3, TType.STRUCT, 'opts', (WriterOptions, WriterOptions.thrift_spec), None, ), # 3
  )

  def __init__(self, login=None, tableName=None, opts=None,):
    self.login = login
    self.tableName = tableName
    self.opts = opts

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.opts = WriterOptions()
          self.opts.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('createWriter_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    if self.opts is not None:
      oprot.writeFieldBegin('opts', TType.STRUCT, 3)
      self.opts.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class createWriter_result:
  """
  Attributes:
   - success
   - outch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    (0, TType.STRING, 'success', None, None, ), # 0
    (1, TType.STRUCT, 'outch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, success=None, outch1=None, ouch2=None, ouch3=None,):
    self.success = success
    self.outch1 = outch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.STRING:
          self.success = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 1:
        if ftype == TType.STRUCT:
          self.outch1 = AccumuloException()
          self.outch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('createWriter_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.STRING, 0)
      oprot.writeString(self.success)
      oprot.writeFieldEnd()
    if self.outch1 is not None:
      oprot.writeFieldBegin('outch1', TType.STRUCT, 1)
      self.outch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class update_args:
  """
  Attributes:
   - writer
   - cells
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'writer', None, None, ), # 1
    (2, TType.MAP, 'cells', (TType.STRING,None,TType.LIST,(TType.STRUCT,(ColumnUpdate, ColumnUpdate.thrift_spec))), None, ), # 2
  )

  def __init__(self, writer=None, cells=None,):
    self.writer = writer
    self.cells = cells

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.writer = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.MAP:
          self.cells = {}
          (_ktype407, _vtype408, _size406 ) = iprot.readMapBegin()
          for _i410 in xrange(_size406):
            _key411 = iprot.readString();
            _val412 = []
            (_etype416, _size413) = iprot.readListBegin()
            for _i417 in xrange(_size413):
              _elem418 = ColumnUpdate()
              _elem418.read(iprot)
              _val412.append(_elem418)
            iprot.readListEnd()
            self.cells[_key411] = _val412
          iprot.readMapEnd()
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('update_args')
    if self.writer is not None:
      oprot.writeFieldBegin('writer', TType.STRING, 1)
      oprot.writeString(self.writer)
      oprot.writeFieldEnd()
    if self.cells is not None:
      oprot.writeFieldBegin('cells', TType.MAP, 2)
      oprot.writeMapBegin(TType.STRING, TType.LIST, len(self.cells))
      for kiter419,viter420 in self.cells.items():
        oprot.writeString(kiter419)
        oprot.writeListBegin(TType.STRUCT, len(viter420))
        for iter421 in viter420:
          iter421.write(oprot)
        oprot.writeListEnd()
      oprot.writeMapEnd()
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class flush_args:
  """
  Attributes:
   - writer
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'writer', None, None, ), # 1
  )

  def __init__(self, writer=None,):
    self.writer = writer

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.writer = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('flush_args')
    if self.writer is not None:
      oprot.writeFieldBegin('writer', TType.STRING, 1)
      oprot.writeString(self.writer)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class flush_result:
  """
  Attributes:
   - ouch1
   - ouch2
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (UnknownWriter, UnknownWriter.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (MutationsRejectedException, MutationsRejectedException.thrift_spec), None, ), # 2
  )

  def __init__(self, ouch1=None, ouch2=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = UnknownWriter()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = MutationsRejectedException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('flush_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class closeWriter_args:
  """
  Attributes:
   - writer
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'writer', None, None, ), # 1
  )

  def __init__(self, writer=None,):
    self.writer = writer

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.writer = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('closeWriter_args')
    if self.writer is not None:
      oprot.writeFieldBegin('writer', TType.STRING, 1)
      oprot.writeString(self.writer)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class closeWriter_result:
  """
  Attributes:
   - ouch1
   - ouch2
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'ouch1', (UnknownWriter, UnknownWriter.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (MutationsRejectedException, MutationsRejectedException.thrift_spec), None, ), # 2
  )

  def __init__(self, ouch1=None, ouch2=None,):
    self.ouch1 = ouch1
    self.ouch2 = ouch2

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = UnknownWriter()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = MutationsRejectedException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('closeWriter_result')
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class updateRowConditionally_args:
  """
  Attributes:
   - login
   - tableName
   - row
   - updates
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
    (3, TType.STRING, 'row', None, None, ), # 3
    (4, TType.STRUCT, 'updates', (ConditionalUpdates, ConditionalUpdates.thrift_spec), None, ), # 4
  )

  def __init__(self, login=None, tableName=None, row=None, updates=None,):
    self.login = login
    self.tableName = tableName
    self.row = row
    self.updates = updates

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRING:
          self.row = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 4:
        if ftype == TType.STRUCT:
          self.updates = ConditionalUpdates()
          self.updates.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('updateRowConditionally_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    if self.row is not None:
      oprot.writeFieldBegin('row', TType.STRING, 3)
      oprot.writeString(self.row)
      oprot.writeFieldEnd()
    if self.updates is not None:
      oprot.writeFieldBegin('updates', TType.STRUCT, 4)
      self.updates.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class updateRowConditionally_result:
  """
  Attributes:
   - success
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    (0, TType.I32, 'success', None, None, ), # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, success=None, ouch1=None, ouch2=None, ouch3=None,):
    self.success = success
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.I32:
          self.success = iprot.readI32();
        else:
          iprot.skip(ftype)
      elif fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('updateRowConditionally_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.I32, 0)
      oprot.writeI32(self.success)
      oprot.writeFieldEnd()
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class createConditionalWriter_args:
  """
  Attributes:
   - login
   - tableName
   - options
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'login', None, None, ), # 1
    (2, TType.STRING, 'tableName', None, None, ), # 2
    (3, TType.STRUCT, 'options', (ConditionalWriterOptions, ConditionalWriterOptions.thrift_spec), None, ), # 3
  )

  def __init__(self, login=None, tableName=None, options=None,):
    self.login = login
    self.tableName = tableName
    self.options = options

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.login = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRING:
          self.tableName = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.options = ConditionalWriterOptions()
          self.options.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('createConditionalWriter_args')
    if self.login is not None:
      oprot.writeFieldBegin('login', TType.STRING, 1)
      oprot.writeString(self.login)
      oprot.writeFieldEnd()
    if self.tableName is not None:
      oprot.writeFieldBegin('tableName', TType.STRING, 2)
      oprot.writeString(self.tableName)
      oprot.writeFieldEnd()
    if self.options is not None:
      oprot.writeFieldBegin('options', TType.STRUCT, 3)
      self.options.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class createConditionalWriter_result:
  """
  Attributes:
   - success
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    (0, TType.STRING, 'success', None, None, ), # 0
    (1, TType.STRUCT, 'ouch1', (AccumuloException, AccumuloException.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (TableNotFoundException, TableNotFoundException.thrift_spec), None, ), # 3
  )

  def __init__(self, success=None, ouch1=None, ouch2=None, ouch3=None,):
    self.success = success
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.STRING:
          self.success = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = AccumuloException()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloSecurityException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = TableNotFoundException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('createConditionalWriter_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.STRING, 0)
      oprot.writeString(self.success)
      oprot.writeFieldEnd()
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class updateRowsConditionally_args:
  """
  Attributes:
   - conditionalWriter
   - updates
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'conditionalWriter', None, None, ), # 1
    (2, TType.MAP, 'updates', (TType.STRING,None,TType.STRUCT,(ConditionalUpdates, ConditionalUpdates.thrift_spec)), None, ), # 2
  )

  def __init__(self, conditionalWriter=None, updates=None,):
    self.conditionalWriter = conditionalWriter
    self.updates = updates

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.conditionalWriter = iprot.readString();
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.MAP:
          self.updates = {}
          (_ktype423, _vtype424, _size422 ) = iprot.readMapBegin()
          for _i426 in xrange(_size422):
            _key427 = iprot.readString();
            _val428 = ConditionalUpdates()
            _val428.read(iprot)
            self.updates[_key427] = _val428
          iprot.readMapEnd()
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('updateRowsConditionally_args')
    if self.conditionalWriter is not None:
      oprot.writeFieldBegin('conditionalWriter', TType.STRING, 1)
      oprot.writeString(self.conditionalWriter)
      oprot.writeFieldEnd()
    if self.updates is not None:
      oprot.writeFieldBegin('updates', TType.MAP, 2)
      oprot.writeMapBegin(TType.STRING, TType.STRUCT, len(self.updates))
      for kiter429,viter430 in self.updates.items():
        oprot.writeString(kiter429)
        viter430.write(oprot)
      oprot.writeMapEnd()
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class updateRowsConditionally_result:
  """
  Attributes:
   - success
   - ouch1
   - ouch2
   - ouch3
  """

  thrift_spec = (
    (0, TType.MAP, 'success', (TType.STRING,None,TType.I32,None), None, ), # 0
    (1, TType.STRUCT, 'ouch1', (UnknownWriter, UnknownWriter.thrift_spec), None, ), # 1
    (2, TType.STRUCT, 'ouch2', (AccumuloException, AccumuloException.thrift_spec), None, ), # 2
    (3, TType.STRUCT, 'ouch3', (AccumuloSecurityException, AccumuloSecurityException.thrift_spec), None, ), # 3
  )

  def __init__(self, success=None, ouch1=None, ouch2=None, ouch3=None,):
    self.success = success
    self.ouch1 = ouch1
    self.ouch2 = ouch2
    self.ouch3 = ouch3

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.MAP:
          self.success = {}
          (_ktype432, _vtype433, _size431 ) = iprot.readMapBegin()
          for _i435 in xrange(_size431):
            _key436 = iprot.readString();
            _val437 = iprot.readI32();
            self.success[_key436] = _val437
          iprot.readMapEnd()
        else:
          iprot.skip(ftype)
      elif fid == 1:
        if ftype == TType.STRUCT:
          self.ouch1 = UnknownWriter()
          self.ouch1.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.STRUCT:
          self.ouch2 = AccumuloException()
          self.ouch2.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 3:
        if ftype == TType.STRUCT:
          self.ouch3 = AccumuloSecurityException()
          self.ouch3.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('updateRowsConditionally_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.MAP, 0)
      oprot.writeMapBegin(TType.STRING, TType.I32, len(self.success))
      for kiter438,viter439 in self.success.items():
        oprot.writeString(kiter438)
        oprot.writeI32(viter439)
      oprot.writeMapEnd()
      oprot.writeFieldEnd()
    if self.ouch1 is not None:
      oprot.writeFieldBegin('ouch1', TType.STRUCT, 1)
      self.ouch1.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch2 is not None:
      oprot.writeFieldBegin('ouch2', TType.STRUCT, 2)
      self.ouch2.write(oprot)
      oprot.writeFieldEnd()
    if self.ouch3 is not None:
      oprot.writeFieldBegin('ouch3', TType.STRUCT, 3)
      self.ouch3.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class closeConditionalWriter_args:
  """
  Attributes:
   - conditionalWriter
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'conditionalWriter', None, None, ), # 1
  )

  def __init__(self, conditionalWriter=None,):
    self.conditionalWriter = conditionalWriter

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.conditionalWriter = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('closeConditionalWriter_args')
    if self.conditionalWriter is not None:
      oprot.writeFieldBegin('conditionalWriter', TType.STRING, 1)
      oprot.writeString(self.conditionalWriter)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class closeConditionalWriter_result:

  thrift_spec = (
  )

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('closeConditionalWriter_result')
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class getRowRange_args:
  """
  Attributes:
   - row
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRING, 'row', None, None, ), # 1
  )

  def __init__(self, row=None,):
    self.row = row

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRING:
          self.row = iprot.readString();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('getRowRange_args')
    if self.row is not None:
      oprot.writeFieldBegin('row', TType.STRING, 1)
      oprot.writeString(self.row)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class getRowRange_result:
  """
  Attributes:
   - success
  """

  thrift_spec = (
    (0, TType.STRUCT, 'success', (Range, Range.thrift_spec), None, ), # 0
  )

  def __init__(self, success=None,):
    self.success = success

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.STRUCT:
          self.success = Range()
          self.success.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('getRowRange_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.STRUCT, 0)
      self.success.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class getFollowing_args:
  """
  Attributes:
   - key
   - part
  """

  thrift_spec = (
    None, # 0
    (1, TType.STRUCT, 'key', (Key, Key.thrift_spec), None, ), # 1
    (2, TType.I32, 'part', None, None, ), # 2
  )

  def __init__(self, key=None, part=None,):
    self.key = key
    self.part = part

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 1:
        if ftype == TType.STRUCT:
          self.key = Key()
          self.key.read(iprot)
        else:
          iprot.skip(ftype)
      elif fid == 2:
        if ftype == TType.I32:
          self.part = iprot.readI32();
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('getFollowing_args')
    if self.key is not None:
      oprot.writeFieldBegin('key', TType.STRUCT, 1)
      self.key.write(oprot)
      oprot.writeFieldEnd()
    if self.part is not None:
      oprot.writeFieldBegin('part', TType.I32, 2)
      oprot.writeI32(self.part)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)

class getFollowing_result:
  """
  Attributes:
   - success
  """

  thrift_spec = (
    (0, TType.STRUCT, 'success', (Key, Key.thrift_spec), None, ), # 0
  )

  def __init__(self, success=None,):
    self.success = success

  def read(self, iprot):
    if iprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and isinstance(iprot.trans, TTransport.CReadableTransport) and self.thrift_spec is not None and fastbinary is not None:
      fastbinary.decode_binary(self, iprot.trans, (self.__class__, self.thrift_spec))
      return
    iprot.readStructBegin()
    while True:
      (fname, ftype, fid) = iprot.readFieldBegin()
      if ftype == TType.STOP:
        break
      if fid == 0:
        if ftype == TType.STRUCT:
          self.success = Key()
          self.success.read(iprot)
        else:
          iprot.skip(ftype)
      else:
        iprot.skip(ftype)
      iprot.readFieldEnd()
    iprot.readStructEnd()

  def write(self, oprot):
    if oprot.__class__ == TBinaryProtocol.TBinaryProtocolAccelerated and self.thrift_spec is not None and fastbinary is not None:
      oprot.trans.write(fastbinary.encode_binary(self, (self.__class__, self.thrift_spec)))
      return
    oprot.writeStructBegin('getFollowing_result')
    if self.success is not None:
      oprot.writeFieldBegin('success', TType.STRUCT, 0)
      self.success.write(oprot)
      oprot.writeFieldEnd()
    oprot.writeFieldStop()
    oprot.writeStructEnd()

  def validate(self):
    return


  def __repr__(self):
    L = ['%s=%r' % (key, value)
      for key, value in self.__dict__.iteritems()]
    return '%s(%s)' % (self.__class__.__name__, ', '.join(L))

  def __eq__(self, other):
    return isinstance(other, self.__class__) and self.__dict__ == other.__dict__

  def __ne__(self, other):
    return not (self == other)
