refdb.clearCache();
}
+ @Override
+ public void notifyIndexChanged() {
+ // we do not support non-bare repositories yet
+ }
+
@Override
public String toString() {
return "DhtRepostitory[" + key + " / " + name + "]";
/*
* Copyright (C) 2008-2009, Google Inc.
+ * Copyright (C) 2011, Matthias Sohn <matthias.sohn@sap.com>
* and other copyright owners as documented in the project's IP log.
*
* This program and the accompanying materials are made available
import static org.junit.Assert.assertNotSame;
import static org.junit.Assert.assertSame;
import static org.junit.Assert.assertTrue;
+import static org.junit.Assert.fail;
import java.io.File;
+import org.eclipse.jgit.events.IndexChangedEvent;
+import org.eclipse.jgit.events.IndexChangedListener;
+import org.eclipse.jgit.events.ListenerList;
import org.eclipse.jgit.lib.FileMode;
import org.eclipse.jgit.lib.ObjectId;
import org.eclipse.jgit.lib.RepositoryTestCase;
}
}
+ @Test
+ public void testBuildOneFile_Commit_IndexChangedEvent()
+ throws Exception {
+ final class ReceivedEventMarkerException extends RuntimeException {
+ private static final long serialVersionUID = 1L;
+ // empty
+ }
+
+ final String path = "a-file-path";
+ final FileMode mode = FileMode.REGULAR_FILE;
+ // "old" date in 2008
+ final long lastModified = 1218123387057L;
+ final int length = 1342;
+ DirCacheEntry entOrig;
+ boolean receivedEvent = false;
+
+ DirCache dc = db.lockDirCache();
+ IndexChangedListener listener = new IndexChangedListener() {
+
+ public void onIndexChanged(IndexChangedEvent event) {
+ throw new ReceivedEventMarkerException();
+ }
+ };
+
+ ListenerList l = db.getListenerList();
+ l.addIndexChangedListener(listener);
+ DirCacheBuilder b = dc.builder();
+
+ entOrig = new DirCacheEntry(path);
+ entOrig.setFileMode(mode);
+ entOrig.setLastModified(lastModified);
+ entOrig.setLength(length);
+ b.add(entOrig);
+ try {
+ b.commit();
+ } catch (ReceivedEventMarkerException e) {
+ receivedEvent = true;
+ }
+ if (!receivedEvent)
+ fail("did not receive IndexChangedEvent");
+
+ // do the same again, as this doesn't change index compared to first
+ // round we should get no event this time
+ dc = db.lockDirCache();
+ listener = new IndexChangedListener() {
+
+ public void onIndexChanged(IndexChangedEvent event) {
+ throw new ReceivedEventMarkerException();
+ }
+ };
+
+ l = db.getListenerList();
+ l.addIndexChangedListener(listener);
+ b = dc.builder();
+
+ entOrig = new DirCacheEntry(path);
+ entOrig.setFileMode(mode);
+ entOrig.setLastModified(lastModified);
+ entOrig.setLength(length);
+ b.add(entOrig);
+ try {
+ b.commit();
+ } catch (ReceivedEventMarkerException e) {
+ fail("unexpected IndexChangedEvent");
+ }
+ }
+
@Test
public void testFindSingleFile() throws Exception {
final String path = "a-file-path";
/*
* Copyright (C) 2008-2010, Google Inc.
* Copyright (C) 2008, Shawn O. Pearce <spearce@spearce.org>
+ * Copyright (C) 2011, Matthias Sohn <matthias.sohn@sap.com>
* and other copyright owners as documented in the project's IP log.
*
* This program and the accompanying materials are made available
import org.eclipse.jgit.JGitText;
import org.eclipse.jgit.errors.CorruptObjectException;
import org.eclipse.jgit.errors.UnmergedPathException;
+import org.eclipse.jgit.events.IndexChangedEvent;
+import org.eclipse.jgit.events.IndexChangedListener;
import org.eclipse.jgit.lib.Constants;
import org.eclipse.jgit.lib.ObjectId;
import org.eclipse.jgit.lib.ObjectInserter;
private static final DirCacheEntry[] NO_ENTRIES = {};
+ private static final byte[] NO_CHECKSUM = {};
+
static final Comparator<DirCacheEntry> ENT_CMP = new Comparator<DirCacheEntry>() {
public int compare(final DirCacheEntry o1, final DirCacheEntry o2) {
final int cr = cmp(o1, o2);
return c;
}
+ /**
+ * Create a new in-core index representation, lock it, and read from disk.
+ * <p>
+ * The new index will be locked and then read before it is returned to the
+ * caller. Read failures are reported as exceptions and therefore prevent
+ * the method from returning a partially populated index. On read failure,
+ * the lock is released.
+ *
+ * @param indexLocation
+ * location of the index file on disk.
+ * @param fs
+ * the file system abstraction which will be necessary to perform
+ * certain file system operations.
+ * @param indexChangedListener
+ * listener to be informed when DirCache is committed
+ * @return a cache representing the contents of the specified index file (if
+ * it exists) or an empty cache if the file does not exist.
+ * @throws IOException
+ * the index file is present but could not be read, or the lock
+ * could not be obtained.
+ * @throws CorruptObjectException
+ * the index file is using a format or extension that this
+ * library does not support.
+ */
+ public static DirCache lock(final File indexLocation, final FS fs,
+ IndexChangedListener indexChangedListener)
+ throws CorruptObjectException,
+ IOException {
+ DirCache c = lock(indexLocation, fs);
+ c.registerIndexChangedListener(indexChangedListener);
+ return c;
+ }
+
/** Location of the current version of the index file. */
private final File liveFile;
/** Keep track of whether the index has changed or not */
private FileSnapshot snapshot;
+ /** index checksum when index was read from disk */
+ private byte[] readIndexChecksum;
+
+ /** index checksum when index was written to disk */
+ private byte[] writeIndexChecksum;
+
+ /** listener to be informed on commit */
+ private IndexChangedListener indexChangedListener;
+
/**
* Create a new in-core index representation.
* <p>
sortedEntries = NO_ENTRIES;
entryCnt = 0;
tree = null;
+ readIndexChecksum = NO_CHECKSUM;
}
private void readFrom(final InputStream inStream) throws IOException,
}
}
- final byte[] exp = md.digest();
- if (!Arrays.equals(exp, hdr)) {
+ readIndexChecksum = md.digest();
+ if (!Arrays.equals(readIndexChecksum, hdr)) {
throw new CorruptObjectException(JGitText.get().DIRCChecksumMismatch);
}
}
dos.write(tmp, 0, 8);
bb.writeTo(dos, null);
}
-
- os.write(foot.digest());
+ writeIndexChecksum = foot.digest();
+ os.write(writeIndexChecksum);
os.close();
}
if (!tmp.commit())
return false;
snapshot = tmp.getCommitSnapshot();
+ if (indexChangedListener != null
+ && !Arrays.equals(readIndexChecksum, writeIndexChecksum))
+ indexChangedListener.onIndexChanged(new IndexChangedEvent());
return true;
}
}
return false;
}
+
+ private void registerIndexChangedListener(IndexChangedListener listener) {
+ this.indexChangedListener = listener;
+ }
}
import org.eclipse.jgit.errors.MissingObjectException;
import org.eclipse.jgit.errors.NoWorkTreeException;
import org.eclipse.jgit.errors.RevisionSyntaxException;
+import org.eclipse.jgit.events.IndexChangedEvent;
+import org.eclipse.jgit.events.IndexChangedListener;
import org.eclipse.jgit.events.ListenerList;
import org.eclipse.jgit.events.RepositoryEvent;
import org.eclipse.jgit.revwalk.RevBlob;
*/
public DirCache lockDirCache() throws NoWorkTreeException,
CorruptObjectException, IOException {
- return DirCache.lock(getIndexFile(), getFS());
+ // we want DirCache to inform us so that we can inform registered
+ // listeners about index changes
+ IndexChangedListener l = new IndexChangedListener() {
+
+ public void onIndexChanged(IndexChangedEvent event) {
+ notifyIndexChanged();
+ }
+ };
+ return DirCache.lock(getIndexFile(), getFS(), l);
}
static byte[] gitInternalSlash(byte[] bytes) {
*/
public abstract void scanForRepoChanges() throws IOException;
+ /**
+ * Notify that the index changed
+ */
+ public abstract void notifyIndexChanged();
+
/**
* @param refName
*
File indexFile = getIndexFile();
if (snapshot == null)
snapshot = FileSnapshot.save(indexFile);
- else if (snapshot.isModified(indexFile)) {
- snapshot = FileSnapshot.save(indexFile);
- fireEvent(new IndexChangedEvent());
- }
+ else if (snapshot.isModified(indexFile))
+ notifyIndexChanged();
+ }
+
+ @Override
+ public void notifyIndexChanged() {
+ snapshot = FileSnapshot.save(getIndexFile());
+ fireEvent(new IndexChangedEvent());
}
/**