docs: private void scheduleSnapshotForLater(
              final String requestObj,
              final String requestId,
              final boolean isFirstAttempt
              ) throws Exception {
          /*
           * Only need to send the queue response the first time we attempt to schedule the snapshot
           * for later. It may be necessary to reschedule via this function multiple times.
           */
          if (isFirstAttempt) {
              SNAP_LOG.info("A user snapshot request could not be immediately fulfilled and will be reattempted later");
              /*
               * Construct a result to send to the client right now via ZK
               * saying we queued it to run later
               */
              VoltTable result = SnapshotUtil.constructNodeResultsTable();
              result.addRow(-1,
                      CoreUtils.getHostnameOrAddress(),
                      "",
                      "SUCCESS",
                      "SNAPSHOT REQUEST QUEUED");
              final ClientResponseImpl queuedResponse =
                  new ClientResponseImpl(ClientResponseImpl.SUCCESS,
                                         new VoltTable[] { result },
                                         "Snapshot request could not be fulfilled because a snapshot " +
                                           "is in progress. It was queued for execution",
                                         0);
              ByteBuffer buf = ByteBuffer.allocate(queuedResponse.getSerializedSize());
              m_zk.create(VoltZK.user_snapshot_response + requestId,
                          queuedResponse.flattenToBuffer(buf).array(),
                          Ids.OPEN_ACL_UNSAFE,
                          CreateMode.PERSISTENT);
          }
  
          /*
           * Now queue the request for later
           */
          final Runnable r = new Runnable() {
              @Override
              public void run() {
                  try {
                      /*
                       * Construct a callback to handle the response to the
                       * @SnapshotSave invocation that will reattempt the user snapshot
                       */
                      final long handle = m_nextCallbackHandle++;
                      m_procedureCallbacks.put(handle, new ProcedureCallback() {
                          @Override
                          public void clientCallback(ClientResponse clientResponse) {
                              m_lastInitiationTs = null;
                              try {
                                  /*
                                   * If there is an error then we are done
                                   * attempting this user snapshot. The params must be bad
                                   * or things are broken.
                                   */
                                  if (clientResponse.getStatus() != ClientResponse.SUCCESS) {
                                      SNAP_LOG.error(clientResponse.getStatusString());
                                      //Reset the watch, in case this is recoverable
                                      userSnapshotRequestExistenceCheck(true);
                                      return;
                                  }
  
                                  VoltTable results[] = clientResponse.getResults();
                                  //Do this check to avoid an NPE
                                  if (results == null || results.length == 0 || results[0].getRowCount() < 1) {
                                      SNAP_LOG.error("Queued user snapshot request reattempt received an unexpected response" +
                                              " and will not be reattempted. The client response is (status: " +
                                              clientResponse.getStatus() + " " + clientResponse.getStatusString() +
                                              " result: " + (results != null && results.length > 0 ? results[0] : "null") +
                                              ")");
                                      /*
                                       * Don't think this should happen, reset the watch to allow later requests
                                       */
                                      userSnapshotRequestExistenceCheck(true);
                                      return;
                                  }
  
                                  VoltTable result = results[0];
                                  boolean snapshotInProgress = false;
                                  boolean haveFailure = false;
                                  while (result.advanceRow()) {
                                      if (result.getString("RESULT").equals("FAILURE")) {
                                          if (result.getString("ERR_MSG").equals("SNAPSHOT IN PROGRESS")) {
                                              snapshotInProgress = true;
                                          } else {
                                              haveFailure = true;
                                          }
                                      }
                                  }
  
                                  /*
                                   * If a snapshot was in progress, reattempt later, otherwise,
                                   * if there was a failure, abort the attempt and log.
                                   */
                                  if (snapshotInProgress) {
                                      SNAP_LOG.info("Queued user snapshot was reattempted, but a snapshot was " +
                                              " still in progress. It will be reattempted.");
                                      //Turtles all the way down
                                      scheduleSnapshotForLater(
                                              requestObj,
                                              requestId,
                                              false);
                                  } else if (haveFailure) {
                                      SNAP_LOG.info("Queued user snapshot was attempted, but there was a failure.");
                                      try {
                                          ClientResponseImpl rimpl = (ClientResponseImpl)clientResponse;
                                          saveResponseToZKAndReset(requestId, rimpl);
                                      }
                                      catch (NodeExistsException e) {
                                          // used to pass null as request ID to avoid this check if the request ID
                                          // already existed, this gives us the same behavior with a pre-existing
                                          // request ID
                                      }
                                      //Log the details of the failure, after resetting the watch in case of some odd NPE
                                      result.resetRowPosition();
                                      SNAP_LOG.info(result);
                                  } else {
                                      try {
                                          SNAP_LOG.debug("Queued user snapshot was successfully requested, saving to path " +
                                                  VoltZK.user_snapshot_response + requestId);
                                          /*
                                           * Snapshot was started no problem, reset the watch for new requests
                                           */
                                          ClientResponseImpl rimpl = (ClientResponseImpl)clientResponse;
                                          saveResponseToZKAndReset(requestId, rimpl);
                                      }
                                      catch (NodeExistsException e) {
                                          // used to pass null as request ID to avoid this check if the request ID
                                          // already existed, this gives us the same behavior with a pre-existing
                                          // request ID
                                      }
                                      return;
                                  }
                              } catch (Exception e) {
                                  SNAP_LOG.error("Error processing procedure callback for user snapshot", e);
                                  try {
                                      userSnapshotRequestExistenceCheck(true);
                                  } catch (Exception e1) {
                                      VoltDB.crashLocalVoltDB(
                                              "Error resetting watch for user snapshot requests", true, e1);
                                  }
                              }
                          }
                      });
  
                      initiateSnapshotSave(handle, new Object[]{requestObj}, false);
                  } catch (Exception e) {
                      try {
                          userSnapshotRequestExistenceCheck(true);
                      } catch (Exception e1) {
                          VoltDB.crashLocalVoltDB("Error checking for existence of user snapshots", true, e1);
                      }
                  }
              }
          };
          m_es.schedule(r, m_userSnapshotRetryInterval, TimeUnit.SECONDS);
      }