예제 #1
0
 /**
  * Open an old, stored version of a map.
  *
  * @param version the version
  * @return the read-only map
  */
 @SuppressWarnings("unchecked")
 <T extends BTreeMap<?, ?>> T openMapVersion(long version) {
   BTreeChunk c = getChunkForVersion(version);
   DataUtils.checkArgument(c != null, "Unknown version {0}", version);
   BTreeMap<?, ?> m = map.openReadOnly();
   m.setRootPos(c.rootPagePos, version);
   return (T) m;
 }
예제 #2
0
  /**
   * Revert to the beginning of the given version. All later changes (stored or not) are forgotten.
   * All maps that were created later are closed. A rollback to a version before the last stored
   * version is immediately persisted. Rollback to version 0 means all data is removed.
   *
   * @param version the version to revert to
   */
  public synchronized void rollbackTo(long version) {
    checkOpen();
    if (version == 0) {
      // special case: remove all data
      map.close();
      chunks.clear();
      currentVersion = version;
      return;
    }
    DataUtils.checkArgument(isKnownVersion(version), "Unknown version {0}", version);
    map.internalRollbackTo(version);

    boolean loadFromFile = false;
    // find out which chunks to remove,
    // and which is the newest chunk to keep
    // (the chunk list can have gaps)
    ArrayList<Integer> remove = new ArrayList<Integer>();
    BTreeChunk keep = null;
    for (BTreeChunk c : chunks.values()) {
      if (c.version > version) {
        remove.add(c.id);
      } else if (keep == null || keep.id < c.id) {
        keep = c;
      }
    }
    if (remove.size() > 0) {
      // remove the youngest first, so we don't create gaps
      // (in case we remove many chunks)
      Collections.sort(remove, Collections.reverseOrder());
      map.removeUnusedOldVersions();
      loadFromFile = true;
      for (int id : remove) {
        BTreeChunk c = chunks.remove(id);
        c.fileStorage.close();
        c.fileStorage.delete();
      }
      lastChunkId = keep.id;
      setLastChunk(keep);
    }
    if (createVersion >= version) {
      map.close();
    } else {
      if (loadFromFile) {
        map.setRootPos(lastChunk.rootPagePos, lastChunk.version);
      }
    }
    currentVersion = version;
  }