[feat] Add known fileformats
All checks were successful
continuous-integration/drone/push Build is passing
All checks were successful
continuous-integration/drone/push Build is passing
Reliably stripping (multiple) archive extensions (e.g. .tar.gz) is not supported by std::filesystem::path. Dots in the regular root folder name can cause issues. fileformats.hpp adds well-known format extensions which are used for stripping the extension. Note that this is not used by libarchive or xwim to determine the filters/formats for extraction. This is done by libarchive's `bidding`.
This commit is contained in:
parent
064c936f11
commit
e59968444e
7 changed files with 48 additions and 17 deletions
|
@ -1,5 +1,5 @@
|
|||
project('xwim', 'cpp',
|
||||
version: '0.1',
|
||||
version: '0.2',
|
||||
default_options: ['cpp_std=c++17'])
|
||||
|
||||
subdir('src')
|
||||
|
|
|
@ -14,6 +14,7 @@ namespace logger = spdlog;
|
|||
#include "archive_sys.hpp"
|
||||
#include "archive.hpp"
|
||||
#include "spec.hpp"
|
||||
#include "fileformats.hpp"
|
||||
|
||||
namespace xwim {
|
||||
|
||||
|
@ -22,9 +23,7 @@ static void _spec_is_root_filename(ArchiveSpec* spec,
|
|||
std::filesystem::path* filepath) {
|
||||
auto entry_path = entry.path();
|
||||
auto norm_stem = filepath->filename();
|
||||
|
||||
while (norm_stem.has_extension())
|
||||
norm_stem = norm_stem.stem();
|
||||
norm_stem = xwim::stem(norm_stem);
|
||||
|
||||
if (*entry_path.begin() != norm_stem) {
|
||||
logger::debug("Archive root does not match archive name");
|
||||
|
|
|
@ -1,5 +1,4 @@
|
|||
#ifndef ARCHIVE_H
|
||||
#define ARCHIVE_H
|
||||
#pragma once
|
||||
|
||||
#include <archive.h>
|
||||
#include <fmt/format.h>
|
||||
|
@ -42,5 +41,3 @@ class ArchiveException : public std::exception {
|
|||
};
|
||||
|
||||
} // namespace xwim
|
||||
|
||||
#endif
|
||||
|
|
38
src/fileformats.hpp
Normal file
38
src/fileformats.hpp
Normal file
|
@ -0,0 +1,38 @@
|
|||
#pragma once
|
||||
|
||||
#include <spdlog/spdlog.h>
|
||||
namespace logger = spdlog;
|
||||
|
||||
/** Common archive formats understood by xwim
|
||||
*
|
||||
* The underlying libarchive backend retrieves format information by a process
|
||||
* called `bidding`. Hence, this information is mainly used to strip extensions.
|
||||
*
|
||||
* Stripping extensions via `std::filesystem::path` does not work reliably since
|
||||
* it gets easily confused by dots in the regular file name.
|
||||
*/
|
||||
|
||||
#include <filesystem>
|
||||
#include <set>
|
||||
#include <string>
|
||||
|
||||
namespace xwim {
|
||||
|
||||
const std::set<std::string> fileformats{
|
||||
".7z", ".7zip", ".jar", ".tgz", ".bz2", ".bzip2", ".gz",
|
||||
".gzip", ".rar", ".tar", ".tar.gz", ".tar.bz2", ".tar.xz", ".zip"};
|
||||
|
||||
inline std::filesystem::path stem(std::filesystem::path& path) {
|
||||
std::filesystem::path p_stem {path};
|
||||
logger::trace("Stemming {}", p_stem.string());
|
||||
|
||||
while( fileformats.find(p_stem.extension().string()) != fileformats.end() ) {
|
||||
p_stem = p_stem.stem();
|
||||
logger::trace("Stemmed to {}", p_stem.string());
|
||||
}
|
||||
|
||||
logger::trace("Finished stemming {}", p_stem.string());
|
||||
return p_stem;
|
||||
}
|
||||
|
||||
} // namespace xwim
|
|
@ -9,6 +9,7 @@ namespace logger = spdlog;
|
|||
|
||||
#include "archive.hpp"
|
||||
#include "spec.hpp"
|
||||
#include "fileformats.hpp"
|
||||
|
||||
int main(int argc, char** argv) {
|
||||
logger::set_level(logger::level::trace);
|
||||
|
@ -25,10 +26,7 @@ int main(int argc, char** argv) {
|
|||
if (!archive_spec.has_single_root || !archive_spec.is_root_filename) {
|
||||
extract_spec.make_dir = true;
|
||||
|
||||
std::filesystem::path stem = filepath.stem();
|
||||
|
||||
while (stem.has_extension())
|
||||
stem = stem.stem();
|
||||
std::filesystem::path stem = xwim::stem(filepath);
|
||||
|
||||
extract_spec.dirname = stem;
|
||||
}
|
||||
|
|
|
@ -1,9 +1,11 @@
|
|||
src = ['main.cpp',
|
||||
'archive.cpp',
|
||||
'archive_sys.cpp']
|
||||
|
||||
inc = ['archive.hpp',
|
||||
'spec.hpp',
|
||||
'archive_sys.hpp']
|
||||
'archive_sys.hpp',
|
||||
'fileformats.hpp']
|
||||
|
||||
libs = [dependency('libarchive', required: true),
|
||||
dependency('fmt', required: true),
|
||||
|
|
|
@ -1,5 +1,4 @@
|
|||
#ifndef SPEC_H
|
||||
#define SPEC_H
|
||||
#pragma once
|
||||
|
||||
#include <archive.h>
|
||||
#include <fmt/core.h>
|
||||
|
@ -55,5 +54,3 @@ struct fmt::formatter<xwim::ExtractSpec> {
|
|||
spec.make_dir, spec.dirname.string(), spec.extract_subarchive);
|
||||
}
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
Loading…
Reference in a new issue