/**
   * Tests start and end with regard to locking. Going to cut down the timeout to a very short
   * period, the lock should expire
   *
   * @throws Exception
   */
  public void testLockTimeout() throws Exception {

    RetryingTransactionHelper trx = transactionService.getRetryingTransactionHelper();

    /** Simulates a client starting a transfer and then "going away"; */
    RetryingTransactionCallback<Object> startWithoutAnythingElse =
        new RetryingTransactionCallback<Object>() {

          public Object execute() throws Throwable {

            ftTransferReceiver.start("1234", true, ftTransferReceiver.getVersion());
            return null;
          }
        };

    RetryingTransactionCallback<Object> slowTransfer =
        new RetryingTransactionCallback<Object>() {

          public Object execute() throws Throwable {

            String transferId =
                ftTransferReceiver.start("1234", true, ftTransferReceiver.getVersion());
            Thread.sleep(1000);
            try {
              ftTransferReceiver.saveSnapshot(transferId, null);
              fail("did not timeout");
            } catch (TransferException te) {
              // expect to go here with a timeout
            }
            return null;
          }
        };

    long lockRefreshTime = ftTransferReceiver.getLockRefreshTime();
    long lockTimeOut = ftTransferReceiver.getLockTimeOut();

    try {
      ftTransferReceiver.setLockRefreshTime(500);
      ftTransferReceiver.setLockTimeOut(200);

      /**
       * This test simulates a client that starts a transfer and then "goes away". We kludge the
       * timeouts to far shorter than normal to make the test run in a reasonable time.
       */
      for (int i = 0; i < 3; i++) {
        trx.doInTransaction(startWithoutAnythingElse, false, true);
        Thread.sleep(1000);
      }
      trx.doInTransaction(slowTransfer, false, true);
    } finally {
      ftTransferReceiver.setLockRefreshTime(lockRefreshTime);
      ftTransferReceiver.setLockTimeOut(lockTimeOut);
    }
  }
  /**
   * Tests start and end with regard to locking.
   *
   * @throws Exception
   */
  public void testStartAndEnd() throws Exception {

    RetryingTransactionHelper trx = transactionService.getRetryingTransactionHelper();

    RetryingTransactionCallback<Object> cb =
        new RetryingTransactionCallback<Object>() {

          public Object execute() throws Throwable {

            String transferId =
                ftTransferReceiver.start("1234", true, ftTransferReceiver.getVersion());
            File stagingFolder = null;
            try {

              stagingFolder = ftTransferReceiver.getStagingFolder(transferId);
              assertTrue(ftTransferReceiver.getStagingFolder(transferId).exists());
              NodeRef tempFolder = ftTransferReceiver.getTempFolder(transferId);
              assertNotNull("tempFolder is null", tempFolder);

              Thread.sleep(1000);
              try {
                ftTransferReceiver.start("1234", true, ftTransferReceiver.getVersion());
                fail("Successfully started twice!");
              } catch (TransferException ex) {
                // Expected
              }

              Thread.sleep(300);
              try {
                ftTransferReceiver.start("1234", true, ftTransferReceiver.getVersion());
                fail("Successfully started twice!");
              } catch (TransferException ex) {
                // Expected
              }

              try {
                ftTransferReceiver.end(
                    new NodeRef(StoreRef.STORE_REF_WORKSPACE_SPACESSTORE, GUID.generate())
                        .toString());
                // FIXME: This test is failing
                //                            fail("Successfully ended with transfer id that doesn't
                // own lock.");
              } catch (TransferException ex) {
                // Expected
              }
            } finally {

              ftTransferReceiver.end(transferId);

              /** Check clean-up */
              if (stagingFolder != null) {
                assertFalse(stagingFolder.exists());
              }
            }

            return null;
          }
        };

    long oldRefreshTime = ftTransferReceiver.getLockRefreshTime();
    try {
      ftTransferReceiver.setLockRefreshTime(500);

      for (int i = 0; i < 5; i++) {

        trx.doInTransaction(cb, false, true);
      }
    } finally {
      ftTransferReceiver.setLockRefreshTime(oldRefreshTime);
    }
  }