/* * This file is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License, version 2, * as published by the Free Software Foundation. * * In addition to the permissions in the GNU General Public License, * the authors give you unlimited permission to link the compiled * version of this file into combinations with other programs, * and to distribute those combinations without any restriction * coming from the use of this file. (The General Public License * restrictions do apply in other respects; for example, they cover * modification of the file, and distribution when not linked into * a combined executable.) * * This file is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; see the file COPYING. If not, write to * the Free Software Foundation, 51 Franklin Street, Fifth Floor, * Boston, MA 02110-1301, USA. */ #include "test_lib.h" #include "test_helpers.h" #include "fileops.h" #include "git2/status.h" #define STATUS_FOLDER TEST_RESOURCES "/status" #define TEMP_STATUS_FOLDER TEMP_FOLDER "status" static const char *test_blob_oid = "d4fa8600b4f37d7516bef4816ae2c64dbf029e3a"; static int copy_status_repo(char *path_statusfiles, char *temp_path) { char current_workdir[GIT_PATH_MAX]; char gitted[GIT_PATH_MAX]; int error; error = p_getcwd(current_workdir, sizeof(current_workdir)); if (error < 0) return error; strcpy(path_statusfiles, current_workdir); git_path_join(path_statusfiles, path_statusfiles, TEMP_STATUS_FOLDER); error = copydir_recurs(STATUS_FOLDER, path_statusfiles); if (error < 0) return error; git_path_join(gitted, path_statusfiles, ".gitted"); git_path_join(temp_path, path_statusfiles, ".git"); copydir_recurs(gitted, temp_path); git_futils_rmdir_r(gitted, 1); return GIT_SUCCESS; } BEGIN_TEST(file0, "test retrieving OID from a file apart from the ODB") char path_statusfiles[GIT_PATH_MAX]; char temp_path[GIT_PATH_MAX]; git_oid expected_id, actual_id; must_pass(copy_status_repo(path_statusfiles, temp_path)); git_path_join(temp_path, path_statusfiles, "new_file"); must_pass(git_futils_exists(temp_path)); git_oid_fromstr(&expected_id, test_blob_oid); must_pass(git_status_hashfile(&actual_id, temp_path)); must_be_true(git_oid_cmp(&expected_id, &actual_id) == 0); git_futils_rmdir_r(TEMP_STATUS_FOLDER, 1); END_TEST static const char *entry_paths[] = { "current_file", "file_deleted", "modified_file", "new_file", "staged_changes", "staged_changes_file_deleted", "staged_changes_modified_file", "staged_delete_file_deleted", "staged_delete_modified_file", "staged_new_file", "staged_new_file_deleted_file", "staged_new_file_modified_file", "subdir/current_file", "subdir/deleted_file", "subdir/modified_file", "subdir/new_file", }; static const unsigned int entry_statuses[] = { GIT_STATUS_CURRENT, GIT_STATUS_WT_DELETED, GIT_STATUS_WT_MODIFIED, GIT_STATUS_WT_NEW, GIT_STATUS_INDEX_MODIFIED, GIT_STATUS_INDEX_MODIFIED | GIT_STATUS_WT_DELETED, GIT_STATUS_INDEX_MODIFIED | GIT_STATUS_WT_MODIFIED, GIT_STATUS_INDEX_DELETED, GIT_STATUS_INDEX_DELETED | GIT_STATUS_WT_NEW, GIT_STATUS_INDEX_NEW, GIT_STATUS_INDEX_NEW | GIT_STATUS_WT_DELETED, GIT_STATUS_INDEX_NEW | GIT_STATUS_WT_MODIFIED, GIT_STATUS_CURRENT, GIT_STATUS_WT_DELETED, GIT_STATUS_WT_MODIFIED, GIT_STATUS_WT_NEW, }; #define ENTRY_COUNT 16 static unsigned int get_expected_entry_status(const char *path) { int i; for (i = 0; i < ENTRY_COUNT; ++i) if (!strcmp(path, entry_paths[i])) return entry_statuses[i]; return (unsigned int)-1; } struct status_entry_counts { int wrong_status_flags_count; int entry_count; }; static int status_cb(const char *path, unsigned int status_flags, void *payload) { unsigned int expected_status_flags = get_expected_entry_status(path); struct status_entry_counts *counts = (struct status_entry_counts *)payload; counts->entry_count++; if (status_flags != expected_status_flags) counts->wrong_status_flags_count++; return GIT_SUCCESS; } BEGIN_TEST(statuscb0, "test retrieving status for worktree of repository") char path_statusfiles[GIT_PATH_MAX]; char temp_path[GIT_PATH_MAX]; git_repository *repo; struct status_entry_counts counts; must_pass(copy_status_repo(path_statusfiles, temp_path)); must_pass(git_repository_open(&repo, temp_path)); memset(&counts, 0x0, sizeof(struct status_entry_counts)); git_status_foreach(repo, status_cb, &counts); must_be_true(counts.entry_count == ENTRY_COUNT); must_be_true(counts.wrong_status_flags_count == 0); git_repository_free(repo); git_futils_rmdir_r(TEMP_STATUS_FOLDER, 1); END_TEST BEGIN_TEST(singlestatus0, "test retrieving status for single file") char path_statusfiles[GIT_PATH_MAX]; char temp_path[GIT_PATH_MAX]; git_repository *repo; unsigned int status_flags; int i; must_pass(copy_status_repo(path_statusfiles, temp_path)); must_pass(git_repository_open(&repo, temp_path)); for (i = 0; i < ENTRY_COUNT; ++i) { must_pass(git_status_file(&status_flags, repo, entry_paths[i])); must_be_true(status_flags == entry_statuses[i]); } git_repository_free(repo); git_futils_rmdir_r(TEMP_STATUS_FOLDER, 1); END_TEST BEGIN_SUITE(status) ADD_TEST(file0); ADD_TEST(statuscb0); ADD_TEST(singlestatus0); END_SUITE