file.cc (1890B)
1 #include "file.hh" 2 3 #include <stdio.h> 4 #include <sys/wait.h> 5 #include <set> 6 #include <unordered_map> 7 8 9 void 10 filehandler_t::write_out(const nodetree_t& tree) 11 { 12 tree.print(out); 13 out.close(); 14 } 15 16 void 17 filehandler_t::read_in(const nodetree_t& tree) 18 { 19 static ::std::unordered_map<::std::string, ::std::set<::std::string>> names_per_directory; 20 21 ::std::vector<file_ptr_t> files = tree.get_files(); 22 ::std::vector<::std::string> filenames; 23 24 in.open(tmpfile.c_str()); 25 26 bool conflict_found = false; 27 28 for (auto& file : files) { 29 ::std::string name; 30 ::std::getline(in, name); 31 32 if (!in) 33 throw ::std::runtime_error("amount of names must match amount of files"); 34 35 if (name.empty()) 36 throw ::std::runtime_error("file names must be non-empty"); 37 38 auto dirname = file->get_path().parent_path().string(); 39 auto filename = file->get_path().filename().string(); 40 if (names_per_directory.count(dirname)) { 41 if (names_per_directory[dirname].find(name) != names_per_directory[dirname].end()) 42 conflict_found = true; 43 44 names_per_directory[dirname].insert(filename); 45 } else { 46 ::std::set<::std::string> set; 47 set.insert(filename); 48 names_per_directory[dirname] = set; 49 } 50 51 file->set_name(name); 52 } 53 54 in.close(); 55 56 if (conflict_found) 57 throw ::std::runtime_error("files within the same directory must have different names"); 58 } 59 60 void 61 filehandler_t::edit() const 62 { 63 int ret = system((::std::string("$EDITOR ") + tmpfile).c_str()); 64 if (WEXITSTATUS(ret) != 0) 65 throw ::std::runtime_error("renaming canceled"); 66 } 67 68 void 69 filehandler_t::propagate_rename(const nodetree_t& tree) const 70 { 71 ::std::vector<file_ptr_t> files = tree.get_files(); 72 for (auto& file : files) 73 file->rename(); 74 }