summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorVicent Martí <vicent@github.com>2013-10-04 08:50:44 -0700
committerVicent Martí <vicent@github.com>2013-10-04 08:50:44 -0700
commitec5fe2da8b4afe0b65156477f3cfbb30b9a25643 (patch)
treef500bafe60706821b7539c109d6386fd6cfe73f5
parent146b4d1c5f98aa14df086503f996d131d40b92f8 (diff)
parentda7b78fa446b31e7e197d51129d9bd005acc69da (diff)
downloadlibgit2-ec5fe2da8b4afe0b65156477f3cfbb30b9a25643.tar.gz
Merge pull request #1892 from libgit2/ntk/topic/index_read
Make git_index_read() cope with external additions and removals of the index file
-rw-r--r--include/git2/index.h3
-rw-r--r--src/index.c5
-rw-r--r--tests-clar/index/tests.c66
3 files changed, 64 insertions, 10 deletions
diff --git a/include/git2/index.h b/include/git2/index.h
index 131d04945..8064a62ff 100644
--- a/include/git2/index.h
+++ b/include/git2/index.h
@@ -225,6 +225,9 @@ GIT_EXTERN(int) git_index_set_caps(git_index *index, unsigned int caps);
* Update the contents of an existing index object in memory
* by reading from the hard disk.
*
+ * If the file doesn't exist on the filesystem, the index
+ * will be cleared from its current content.
+ *
* @param index an existing index object
* @return 0 or an error code
*/
diff --git a/src/index.c b/src/index.c
index 21a8d31d1..c923f1675 100644
--- a/src/index.c
+++ b/src/index.c
@@ -461,9 +461,10 @@ int git_index_read(git_index *index)
return create_index_error(-1,
"Failed to read index: The index is in-memory only");
- if (!index->on_disk || git_path_exists(index->index_file_path) == false) {
+ index->on_disk = git_path_exists(index->index_file_path);
+
+ if (!index->on_disk) {
git_index_clear(index);
- index->on_disk = 0;
return 0;
}
diff --git a/tests-clar/index/tests.c b/tests-clar/index/tests.c
index 9090d4d8a..009d393d7 100644
--- a/tests-clar/index/tests.c
+++ b/tests-clar/index/tests.c
@@ -99,11 +99,11 @@ void test_index_tests__default_test_index(void)
entries = (git_index_entry **)index->entries.contents;
for (i = 0; i < ARRAY_SIZE(test_entries); ++i) {
- git_index_entry *e = entries[test_entries[i].index];
+ git_index_entry *e = entries[test_entries[i].index];
- cl_assert_equal_s(e->path, test_entries[i].path);
- cl_assert(e->mtime.seconds == test_entries[i].mtime);
- cl_assert(e->file_size == test_entries[i].file_size);
+ cl_assert_equal_s(e->path, test_entries[i].path);
+ cl_assert(e->mtime.seconds == test_entries[i].mtime);
+ cl_assert(e->file_size == test_entries[i].file_size);
}
git_index_free(index);
@@ -131,10 +131,10 @@ void test_index_tests__find_in_existing(void)
cl_git_pass(git_index_open(&index, TEST_INDEX_PATH));
for (i = 0; i < ARRAY_SIZE(test_entries); ++i) {
- size_t idx;
+ size_t idx;
- cl_assert(!git_index_find(&idx, index, test_entries[i].path));
- cl_assert(idx == test_entries[i].index);
+ cl_assert(!git_index_find(&idx, index, test_entries[i].path));
+ cl_assert(idx == test_entries[i].index);
}
git_index_free(index);
@@ -148,7 +148,7 @@ void test_index_tests__find_in_empty(void)
cl_git_pass(git_index_open(&index, "fake-index"));
for (i = 0; i < ARRAY_SIZE(test_entries); ++i) {
- cl_assert(GIT_ENOTFOUND == git_index_find(NULL, index, test_entries[i].path));
+ cl_assert(GIT_ENOTFOUND == git_index_find(NULL, index, test_entries[i].path));
}
git_index_free(index);
@@ -484,3 +484,53 @@ void test_index_tests__elocked(void)
git_index_free(index);
git_repository_free(repo);
}
+
+void test_index_tests__reload_from_disk(void)
+{
+ git_repository *repo;
+ git_index *read_index;
+ git_index *write_index;
+
+ cl_set_cleanup(&cleanup_myrepo, NULL);
+
+ cl_git_pass(git_futils_mkdir("./myrepo", NULL, 0777, GIT_MKDIR_PATH));
+ cl_git_mkfile("./myrepo/a.txt", "a\n");
+ cl_git_mkfile("./myrepo/b.txt", "b\n");
+
+ cl_git_pass(git_repository_init(&repo, "./myrepo", 0));
+ cl_git_pass(git_repository_index(&write_index, repo));
+ cl_assert_equal_i(false, write_index->on_disk);
+
+ cl_git_pass(git_index_open(&read_index, write_index->index_file_path));
+ cl_assert_equal_i(false, read_index->on_disk);
+
+ /* Stage two new files agaisnt the write_index */
+ cl_git_pass(git_index_add_bypath(write_index, "a.txt"));
+ cl_git_pass(git_index_add_bypath(write_index, "b.txt"));
+
+ cl_assert_equal_sz(2, git_index_entrycount(write_index));
+
+ /* Persist the index changes to disk */
+ cl_git_pass(git_index_write(write_index));
+ cl_assert_equal_i(true, write_index->on_disk);
+
+ /* Sync the changes back into the read_index */
+ cl_assert_equal_sz(0, git_index_entrycount(read_index));
+
+ cl_git_pass(git_index_read(read_index));
+ cl_assert_equal_i(true, read_index->on_disk);
+
+ cl_assert_equal_sz(2, git_index_entrycount(read_index));
+
+ /* Remove the index file from the filesystem */
+ cl_git_pass(p_unlink(write_index->index_file_path));
+
+ /* Sync the changes back into the read_index */
+ cl_git_pass(git_index_read(read_index));
+ cl_assert_equal_i(false, read_index->on_disk);
+ cl_assert_equal_sz(0, git_index_entrycount(read_index));
+
+ git_index_free(read_index);
+ git_index_free(write_index);
+ git_repository_free(repo);
+}