docs: public void prepRequest(Request request, long txnId) {
          // LOG.info("Prep>>> cxid = " + request.cxid + " type = " +
          // request.type + " id = 0x" + Long.toHexString(request.sessionId));
          TxnHeader txnHeader = null;
          Record txn = null;
          try {
              switch (request.type) {
              case OpCode.create:
                  txnHeader = new TxnHeader(request.sessionId, request.cxid,
                          txnId, getTime(), OpCode.create);
                  CreateRequest createRequest = new CreateRequest();
                  ZooKeeperServer.byteBuffer2Record(request.request,
                          createRequest);
                  String path = createRequest.getPath();
                  int lastSlash = path.lastIndexOf('/');
                  if (lastSlash == -1 || path.indexOf('\0') != -1) {
                      LOG.info("Invalid path " + path + " with session 0x"
                              + Long.toHexString(request.sessionId));
                      throw new KeeperException.BadArgumentsException(path);
                  }
                  if (!fixupACL(request.authInfo, createRequest.getAcl())) {
                      throw new KeeperException.InvalidACLException(path);
                  }
                  String parentPath = path.substring(0, lastSlash);
                  ChangeRecord parentRecord = getRecordForPath(parentPath);
  
                  checkACL(parentRecord.acl, ZooDefs.Perms.CREATE,
                          request.authInfo);
                  int parentCVersion = parentRecord.stat.getCversion();
                  CreateMode createMode = CreateMode.fromFlag(createRequest
                          .getFlags());
                  if (createMode.isSequential()) {
                      path = path + String.format("%010d", parentCVersion);
                  }
                  try {
                      PathUtils.validatePath(path);
                  } catch (IllegalArgumentException ie) {
                      LOG.info("Invalid path " + path + " with session 0x"
                              + Long.toHexString(request.sessionId));
                      throw new KeeperException.BadArgumentsException(path);
                  }
                  try {
                      if (getRecordForPath(path) != null) {
                          throw new KeeperException.NodeExistsException(path);
                      }
                  } catch (KeeperException.NoNodeException e) {
                      // ignore this one
                  }
                  boolean ephemeralParent = parentRecord.stat.getEphemeralOwner() != 0;
                  if (ephemeralParent) {
                      throw new KeeperException.NoChildrenForEphemeralsException(
                              path);
                  }
                  txn = new CreateTxn(path, createRequest.getData(),
                          createRequest.getAcl(), createMode.isEphemeral());
                  StatPersisted s = new StatPersisted();
                  if (createMode.isEphemeral()) {
                      s.setEphemeralOwner(request.sessionId);
                  }
                  parentRecord = parentRecord.duplicate(txnHeader.getZxid());
                  parentRecord.childCount++;
                  parentRecord.stat
                          .setCversion(parentRecord.stat.getCversion() + 1);
                  addChangeRecord(parentRecord);
                  addChangeRecord(new ChangeRecord(txnHeader.getZxid(), path, s,
                          0, createRequest.getAcl()));
  
                  break;
              case OpCode.delete:
                  txnHeader = new TxnHeader(request.sessionId, request.cxid,
                          txnId, getTime(), OpCode.delete);
                  DeleteRequest deleteRequest = new DeleteRequest();
                  ZooKeeperServer.byteBuffer2Record(request.request,
                          deleteRequest);
                  path = deleteRequest.getPath();
                  lastSlash = path.lastIndexOf('/');
                  if (lastSlash == -1 || path.indexOf('\0') != -1
                          || getZKDatabase().isSpecialPath(path)) {
                      throw new KeeperException.BadArgumentsException(path);
                  }
                  parentPath = path.substring(0, lastSlash);
                  parentRecord = getRecordForPath(parentPath);
                  ChangeRecord nodeRecord = getRecordForPath(path);
                  checkACL(parentRecord.acl, ZooDefs.Perms.DELETE,
                          request.authInfo);
                  int version = deleteRequest.getVersion();
                  if (version != -1 && nodeRecord.stat.getVersion() != version) {
                      throw new KeeperException.BadVersionException(path);
                  }
                  if (nodeRecord.childCount > 0) {
                      throw new KeeperException.NotEmptyException(path);
                  }
                  txn = new DeleteTxn(path);
                  parentRecord = parentRecord.duplicate(txnHeader.getZxid());
                  parentRecord.childCount--;
                  parentRecord.stat
                          .setCversion(parentRecord.stat.getCversion() + 1);
                  addChangeRecord(parentRecord);
                  addChangeRecord(new ChangeRecord(txnHeader.getZxid(), path,
                          null, -1, null));
                  break;
              case OpCode.setData:
                  txnHeader = new TxnHeader(request.sessionId, request.cxid,
                          txnId, getTime(), OpCode.setData);
                  SetDataRequest setDataRequest = new SetDataRequest();
                  ZooKeeperServer.byteBuffer2Record(request.request,
                          setDataRequest);
                  path = setDataRequest.getPath();
                  nodeRecord = getRecordForPath(path);
                  checkACL(nodeRecord.acl, ZooDefs.Perms.WRITE, request.authInfo);
                  version = setDataRequest.getVersion();
                  int currentVersion = nodeRecord.stat.getVersion();
                  if (version != -1 && version != currentVersion) {
                      throw new KeeperException.BadVersionException(path);
                  }
                  version = currentVersion + 1;
                  txn = new SetDataTxn(path, setDataRequest.getData(), version);
                  nodeRecord = nodeRecord.duplicate(txnHeader.getZxid());
                  nodeRecord.stat.setVersion(version);
                  addChangeRecord(nodeRecord);
                  break;
              case OpCode.setACL:
                  txnHeader = new TxnHeader(request.sessionId, request.cxid,
                          txnId, getTime(), OpCode.setACL);
                  SetACLRequest setAclRequest = new SetACLRequest();
                  ZooKeeperServer.byteBuffer2Record(request.request,
                          setAclRequest);
                  path = setAclRequest.getPath();
                  if (!fixupACL(request.authInfo, setAclRequest.getAcl())) {
                      throw new KeeperException.InvalidACLException(path);
                  }
                  nodeRecord = getRecordForPath(path);
                  checkACL(nodeRecord.acl, ZooDefs.Perms.ADMIN, request.authInfo);
                  version = setAclRequest.getVersion();
                  currentVersion = nodeRecord.stat.getAversion();
                  if (version != -1 && version != currentVersion) {
                      throw new KeeperException.BadVersionException(path);
                  }
                  version = currentVersion + 1;
                  txn = new SetACLTxn(path, setAclRequest.getAcl(), version);
                  nodeRecord = nodeRecord.duplicate(txnHeader.getZxid());
                  nodeRecord.stat.setAversion(version);
                  addChangeRecord(nodeRecord);
                  break;
              case OpCode.createSession:
                  txnHeader = new TxnHeader(request.sessionId, request.cxid,
                          txnId, getTime(), OpCode.createSession);
                  request.request.rewind();
                  int to = request.request.getInt();
                  txn = new CreateSessionTxn((Long)request.getOwner());
                  request.request.rewind();
                  sessionTracker.addSession(request.sessionId,
                          (Long) request.getOwner());
                  break;
              case OpCode.closeSession:
                  txnHeader = new TxnHeader(request.sessionId, request.cxid,
                          txnId, getTime(), OpCode.closeSession);
                  // We don't want to do this check since the session expiration
                  // thread
                  // queues up this operation without being the session owner.
                  // this request is the last of the session so it should be ok
                  // zks.sessionTracker.checkSession(request.sessionId,
                  // request.getOwner());
                  HashSet<String> es = getZKDatabase().getEphemerals(
                          request.sessionId);
                  synchronized (outstandingChanges) {
                      for (ChangeRecord c : outstandingChanges) {
                          if (c.stat == null) {
                              // Doing a delete
                              es.remove(c.path);
                          } else if (c.stat.getEphemeralOwner() == request.sessionId) {
                              es.add(c.path);
                          }
                      }
                      for (String path2Delete : es) {
                          addChangeRecord(new ChangeRecord(txnHeader.getZxid(),
                                  path2Delete, null, 0, null));
                      }
                  }
                  sessionTracker.removeSession(request.sessionId);
                  LOG.info("Processed session termination for sessionid: 0x"
                          + Long.toHexString(request.sessionId));
                  break;
              case OpCode.sync:
              case OpCode.exists:
              case OpCode.getData:
              case OpCode.getACL:
              case OpCode.getChildren:
              case OpCode.getChildren2:
              case OpCode.ping:
              case OpCode.setWatches:
              default:
              }
          } catch (KeeperException e) {
              if (txnHeader != null) {
                  txnHeader.setType(OpCode.error);
                  txn = new ErrorTxn(e.code().intValue());
              }
              LOG.debug("Got user-level KeeperException when processing "
                      + request.toString() + " Error Path:" + e.getPath()
                      + " Error:" + e.getMessage());
              request.setException(e);
          } catch (Exception e) {
              // log at error level as we are returning a marshalling
              // error to the user
              LOG.error("Failed to process " + request, e);
  
              StringBuilder sb = new StringBuilder();
              ByteBuffer bb = request.request;
              if (bb != null) {
                  bb.rewind();
                  while (bb.hasRemaining()) {
                      sb.append(Integer.toHexString(bb.get() & 0xff));
                  }
              } else {
                  sb.append("request buffer is null");
              }
  
              LOG.error("Dumping request buffer: 0x" + sb.toString());
              if (txnHeader != null) {
                  txnHeader.setType(OpCode.error);
                  txn = new ErrorTxn(Code.MARSHALLINGERROR.intValue());
              }
          }
          request.hdr = txnHeader;
          request.txn = txn;
          request.zxid = txnId;
          executeRequest(request);
      }