From 5c1b6d9243c2363b2fd723810fe25f50a4e0f6e2 Mon Sep 17 00:00:00 2001 From: "Zed A. Shaw" Date: Sun, 4 Aug 2024 08:51:22 -0400 Subject: [PATCH] Way quicker and easier to simply use the .gitignore to figure out if an important file has changed. This is probably chock full of bugs and memory leaks but it is working. --- .gitignore | 2 ++ watchgit.cpp | 89 +++++++++++++--------------------------------------- 2 files changed, 23 insertions(+), 68 deletions(-) diff --git a/.gitignore b/.gitignore index 39151ec..e0b9aa3 100644 --- a/.gitignore +++ b/.gitignore @@ -11,3 +11,5 @@ subprojects *.csv *.exe *.dll +*~ +[0-9]* diff --git a/watchgit.cpp b/watchgit.cpp index 0404716..5141869 100644 --- a/watchgit.cpp +++ b/watchgit.cpp @@ -14,9 +14,11 @@ #include #include #include +#include using namespace std; using namespace fmt; +namespace fs = std::filesystem; #define BUF_MAX 1024 @@ -45,69 +47,6 @@ class GameEngine { }; -/* - * No idea what the semantics of this are. Will need - * to research git's dumb terminology to figure out why - * they have 4 different versions of the path for status. - */ -const char *unfuck_path(const git_status_entry *entry) { - if(entry->head_to_index != nullptr) { - if(entry->head_to_index->new_file.path) { - return entry->head_to_index->new_file.path; - } else { - return entry->head_to_index->old_file.path; - } - } - - if(entry->index_to_workdir != nullptr) { - if(entry->index_to_workdir->new_file.path) { - return entry->index_to_workdir->new_file.path; - } else { - return entry->index_to_workdir->old_file.path; - } - } - - return nullptr; -} - -void add_status(const git_status_entry *entry, unsigned int status_flags, set &updates) { - const char *path = unfuck_path(entry); - - if(status_flags & GIT_STATUS_WT_NEW - || status_flags & GIT_STATUS_INDEX_NEW) - { - updates.insert(string{path}); - } - - if(status_flags & GIT_STATUS_WT_MODIFIED - || status_flags & GIT_STATUS_INDEX_MODIFIED) - { - updates.insert(string{path}); - } - - // need to confirm this gets the new name - if(status_flags & GIT_STATUS_WT_RENAMED - || status_flags & GIT_STATUS_INDEX_RENAMED) - { - updates.insert(string{path}); - } -} - -void list_git_changes(set &updates, git_repository* repo) { - git_status_options opts = GIT_STATUS_OPTIONS_INIT; - git_status_list *statuses = nullptr; - - //TODO: does this leak? - int err = git_status_list_new(&statuses, repo, &opts); - dbc::check(err == 0, git_error_last()->message); - size_t count = git_status_list_entrycount(statuses); - - for(size_t i=0; i < count; i++) { - const git_status_entry *entry = git_status_byindex(statuses, i); - add_status(entry, entry->status, updates); - } -} - class UpdateListener : public efsw::FileWatchListener { public: @@ -122,11 +61,25 @@ class UpdateListener : public efsw::FileWatchListener { efsw::Action action, std::string oldFilename) override { - set updates; - list_git_changes(updates, repo); - bool in_git = updates.contains(filename); - // this makes it so we only get it set one time when somethign is in git - changes = changes || in_git; + + // this is some gnarly BS here, probably tons + // of memory leaks for now but it's working + int ignored = 1; + auto the_path = fs::path(dir) / fs::path(filename); + string full_path = the_path.lexically_normal().string(); + + std::replace(full_path.begin(), + full_path.end(), '\\', '/'); + + int rc = git_ignore_path_is_ignored(&ignored, repo, full_path.c_str()); + + dbc::check(rc == 0, "git ignored failed."); + + if(!ignored) { + println("filename={}, ignored={}", full_path.c_str(), ignored); + + changes = changes || !ignored; + } } void reset_state() {