files.hpp 3.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173
  1. #ifndef _FY_FILES_HPP_
  2. #define _FY_FILES_HPP_
  3. #include <stdio.h>
  4. #include <unistd.h>
  5. #include <sys/stat.h>
  6. #include <time.h>
  7. #include <stdint.h>
  8. #include <string>
  9. #include <vector>
  10. #include <fstream>
  11. #include <sstream>
  12. #include "base/strings.hpp"
  13. #include "base/os.hpp"
  14. #include "utils/Log.h"
  15. namespace base {
  16. inline bool remove(const char* file) {
  17. return unlink(file) == 0;
  18. }
  19. //文件存在返回真,否则假
  20. inline bool exists(const char* path) {
  21. if (path == NULL) {
  22. return false;
  23. }
  24. if (access(path, F_OK) == 0) {
  25. return true;
  26. }
  27. return false;
  28. }
  29. inline bool write_all(const std::string& file_path, const std::string& content) {
  30. std::ofstream ofs(file_path.c_str(), std::ios::binary | std::ios::out);
  31. if (!ofs.is_open()) {
  32. return false;
  33. }
  34. ofs << content;
  35. ofs.flush();
  36. return ofs.good();
  37. }
  38. inline std::string read_all(const std::string& file) {
  39. std::ifstream ifs(file, std::ios::binary | std::ios::in);
  40. if (!ifs.is_open()) {
  41. return "";
  42. }
  43. std::stringstream ss;
  44. ss << ifs.rdbuf();
  45. return ss.str();
  46. }
  47. // 文件大小
  48. inline int64_t size_of(const std::string &file) {
  49. long filesize = -1;
  50. struct stat statbuff;
  51. if(stat(file.c_str(), &statbuff) < 0){
  52. return filesize;
  53. } else {
  54. filesize = statbuff.st_size;
  55. }
  56. return filesize;
  57. }
  58. inline int copy_file(const std::string &source,
  59. const std::string &target,
  60. void *user_data,
  61. void (*progress)(const void* user_data, int64_t now, int64_t all)) {
  62. if (!exists(source.c_str())) {
  63. LOGE("%s file not exist", source.c_str());
  64. return -1;
  65. }
  66. FILE* in = fopen(source.c_str(), "rb");
  67. if (in == NULL) {
  68. LOGE("failed to open file %s", source.c_str());
  69. return -2;
  70. }
  71. FILE* out = fopen(target.c_str(), "wb");
  72. if (out == NULL) {
  73. LOGE("failed to create file %s", target.c_str());
  74. return -3;
  75. }
  76. int64_t all = size_of(source.c_str());
  77. if (all < 0) {
  78. LOGE("unknown file size");
  79. return -4;
  80. }
  81. int64_t now = 0;
  82. char buf[4096] = {0};
  83. int read_ret = 0;
  84. int write_ret = 0;
  85. if (progress) {
  86. progress(user_data, now, all);
  87. }
  88. while (!feof(in)) {
  89. read_ret = fread(buf, 1, int(sizeof(buf)), in);
  90. if (read_ret < 0) {
  91. fclose(in);
  92. fclose(out);
  93. LOGE("failed to read %s", source.c_str());
  94. return -5;
  95. }
  96. write_ret = fwrite(buf, 1, read_ret, out);
  97. if (write_ret != read_ret) {
  98. fclose(in);
  99. fclose(out);
  100. LOGE("failed to write %s", target.c_str());
  101. return -6;
  102. }
  103. now += write_ret;
  104. if (progress) {
  105. progress(user_data, now, all);
  106. }
  107. }
  108. if (now != all) {
  109. LOGE("copy_file failed");
  110. return -7;
  111. }
  112. fflush(out);
  113. fclose(in);
  114. fclose(out);
  115. return 0;
  116. }
  117. inline bool _match(const std::string &str, const std::string &pattern) {
  118. if (pattern.compare("*") == 0) {
  119. return true;
  120. }
  121. std::string::size_type pos = pattern.find("*"); //*.mp3
  122. if (pos == 0) {
  123. return endswith(str, pattern.substr(1, pattern.size() - 1));
  124. } else if (pos == (pattern.size() - 1)) {
  125. return startswith(str, pattern.substr(0, pattern.size() - 1));
  126. }
  127. return true;
  128. }
  129. inline std::vector<std::string> list(const std::string &path, const std::string &pattern, bool recursive) {
  130. std::vector<std::string> ret;
  131. DIR *d;
  132. struct dirent *entry;
  133. if ((d = opendir(path.c_str())) == NULL) {
  134. //can't open dir
  135. return ret;
  136. }
  137. while ((entry = readdir(d)) != NULL) {
  138. if ((strcmp(".", entry->d_name) == 0) || (strcmp("..", entry->d_name) == 0)) {
  139. continue;
  140. }
  141. if ((entry->d_type == DT_DIR) && recursive) {
  142. std::vector<std::string> sub = list(base::path::join(path, entry->d_name), pattern, recursive);
  143. ret.insert(ret.end(), sub.begin(), sub.end());
  144. } else {
  145. if (!_match(entry->d_name, pattern)) {
  146. continue;
  147. }
  148. ret.push_back(base::path::join(path, entry->d_name));
  149. }
  150. }
  151. closedir(d);
  152. return ret;
  153. }
  154. } /* namespace base */
  155. #endif /* _FY_FILES_HPP_ */