icedb  version 0.5.1
Snow particle scattering database API
fs_backend.cpp
Go to the documentation of this file.
1 #include "../icedb/fs_backend.hpp"
2 #include "../icedb/compat/gsl/gsl_assert"
3 #include "../private/hdf5_load.h"
4 #include <algorithm>
5 #include <atomic>
6 #include <sstream>
7 #include <string>
8 #include <iostream>
9 namespace icedb {
10  namespace fs {
11  namespace impl {
13  = { ".hdf5", ".nc", ".h5", ".cdf", ".hdf" };
14 
15 
16  sfs::path resolveSymLinks(const sfs::path &base)
17  {
18  sfs::path res = base;
19  while (sfs::is_symlink(res) && sfs::exists(res))
20  {
21  res = sfs::read_symlink(res);
22  }
23  return res;
24  }
25 
27  const sfs::path &base,
28  const ExtensionsMatching_Type &valid_extensions)
29  {
30  std::string sBase = base.string();
31  std::replace(sBase.begin(), sBase.end(), '\\', '/');
32 
33  std::vector<std::pair<sfs::path, std::string> > res;
34  auto sbase = resolveSymlinkPathandForceExists(base.string());
35  if (sfs::is_regular_file(sbase)) {
36  if (valid_extensions.count(base.extension()) > 0) {
37  res.push_back(std::pair<sfs::path, std::string>(sbase, "/"));
38  }
39  }
40  else {
41  for (const auto& p : sfs::recursive_directory_iterator(base)) {
42  auto sp = resolveSymLinks(p.path());
43  if (!sfs::exists(sp)) continue;
44  if (sfs::is_regular_file(sp)) {
45  if (valid_extensions.count(sp.extension()) > 0) {
46  std::string sP = p.path().string();
47  std::replace(sP.begin(), sP.end(), '\\', '/');
48  Expects(sP.find(sBase) == 0);
49  std::string relPath = sP.substr(sBase.length());
50  // Remove any '/'s from the beginning of the string
51  relPath = relPath.substr(relPath.find_first_not_of('/'));
52 
55  /*
56  std::string sP = p.path().string();
57  std::replace(sP.begin(), sP.end(), '\\', '/');
58  std::string sBase = base.string();
59  //Expects(sP.substr(0, sBase.size()) == sBase);
60  Expects(sP.size() >= sBase.size() + 1);
61  std::string relpath = sP.substr(sBase.size() + 1);
62  */
63 
64  res.push_back(std::pair<sfs::path, std::string>(p, relPath));
65  }
66  }
67  }
68  }
69  return res;
70  }
71 
72 
73  sfs::path resolveSymlinkPathandForceExists(const std::string &location) {
74  sfs::path res;
75  sfs::path pBase(location);
76  Expects(sfs::exists(pBase));
77  res = fs::impl::resolveSymLinks(pBase);
78  Expects(sfs::exists(res));
79  return res;
80  }
81 
83  // Find any hdf5 files underneath the current base location (recursive)
84  // and create a key/value map showing where to mount these files.
87  // Ensure that the candidate files are actually HDF5 files
88  for (const auto & cand : mountFilesCands) {
89  // Returns >0 if a valid HDF5 file. = 0 if not. -1 on error (nonexistent file).
90  htri_t isval = H5Fis_hdf5(cand.first.string().c_str());
91  Expects(isval >= 0 && "File should exist at this point." && cand.first.string().c_str());
92  if (isval > 0)
93  mountFiles.push_back(cand);
94  if (isval == 0)
95  std::cerr << "File " << cand.first.string() << " is somehow invalid." << std::endl;
96  }
97  return mountFiles;
98  }
99 
100  std::string getUniqueVROOTname() {
101  static std::atomic<int> i{ 0 };
102  int j = i++;
103  std::ostringstream out;
104  out << "VIRTUAL-" << j;
105  return std::string(out.str());
106  }
107 
108  }
109  }
110 }
CollectedFilesRet_Type collectDatasetFiles(const sfs::path &base, const ExtensionsMatching_Type &valid_extensions)
Definition: fs_backend.cpp:26
sfs::path resolveSymLinks(const sfs::path &base)
Finds out where a symbolic link points to.
Definition: fs_backend.cpp:16
sfs::path resolveSymlinkPathandForceExists(const std::string &location)
Like resolveSymLinks, but throw if the resulting path does not exist.
Definition: fs_backend.cpp:73
std::set< sfs::path > ExtensionsMatching_Type
Definition: fs_backend.hpp:39
std::vector< std::pair< sfs::path, std::string > > CollectedFilesRet_Type
File path, relative mount point.
Definition: fs_backend.hpp:45
const ExtensionsMatching_Type common_hdf5_extensions
Definition: fs_backend.cpp:13
CollectedFilesRet_Type collectActualHDF5files(const sfs::path &pBaseS)
Like collectDatasetFiles for HDF5 files, but then check that these files are, indeed, HDF5 files.
Definition: fs_backend.cpp:82
std::string getUniqueVROOTname()
Generate a unique string, used in memort-only HDF5 file trees.
Definition: fs_backend.cpp:100