/* Copyright (C) Sean McArdle - All Rights Reserved * Unauthorized copying of this file, via any medium is probably fine. * Written by Sean McArdle , Jun 21, 2017 */ #include #include #include #include #include #include #include "efsw/efsw.hpp" #include "parg.h" const char * VERSION_STRING = "0.0.1"; class UpdateListener : public efsw::FileWatchListener { std::string getGmTime () { char tstr[100]; time_t now; time(&now); std::strftime(tstr, sizeof(tstr), "%FT%TZ", std::gmtime(&now)); return tstr; }; public: UpdateListener() {} void handleFileAction( efsw::WatchID watchid, const std::string& dir, const std::string& filename, efsw::Action action, std::string oldFilename = "" ) { switch( action ) { case efsw::Actions::Add: std::cout << getGmTime() << " DIR (" << dir << ") FILE (" << filename << ") has event Added" << '\n'; break; case efsw::Actions::Delete: std::cout << getGmTime() << " DIR (" << dir << ") FILE (" << filename << ") has event Delete" << '\n'; break; case efsw::Actions::Modified: std::cout << getGmTime() << " DIR (" << dir << ") FILE (" << filename << ") has event Modified" << '\n'; break; case efsw::Actions::Moved: std::cout << getGmTime() << " DIR (" << dir << ") FILE (" << filename << ") has event Moved from (" << oldFilename << ")" << '\n'; break; default: std::cout << "Should never happen!" << '\n'; } } }; int main(int argc, char *argv[]) { using namespace std; struct parg_state ps; parg_init(&ps); int c = 0; bool showHelp = false; vector watch_inode; while (-1 != (c = parg_getopt(&ps, argc, argv, "f:d:v:h"))) { switch (c) { case 1: printf("nonoption '%s'\n", ps.optarg); showHelp = true; break; case 'f': case 'd': if (NULL == ps.optarg) break; watch_inode.push_back(std::string(ps.optarg)); break; case 'h': showHelp = true; break; case 'v': printf("Version: %s \n", VERSION_STRING); return 0; break; default: break; } } if (showHelp) { cout << R"(fscanary usage: fscanary.exe [options] -f watch change events on specified file -d watch for filesystem events on directory and child objects -h show this help dialog note: multiple file and directory paths can be specified )" << '\n'; return 0; } auto fwatcher = new efsw::FileWatcher(); auto listener = new UpdateListener(); vector watchers; watchers.resize(watch_inode.size() * 2); // Add a folder to watch, and get the efsw::WatchID // It will watch the /tmp folder recursively ( the third parameter indicates that is recursive ) // Reporting the files and directories changes to the instance of the listener for (auto f : watch_inode) { fprintf(stderr, "Watch: %s\n", f.c_str()); watchers.push_back(fwatcher->addWatch(f, listener, true)); } // Start watching the directories asynchronously fwatcher->watch(); while (true) { std::this_thread::sleep_for(std::chrono::milliseconds(100)); } return 0; }