Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion Cargo.toml
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
[package]
name = "docxtools"
version = "0.9.1-SNAPSHOT"
version = "0.10.0-SNAPSHOT"
edition = "2021"
authors = ["David Bosschaert <david.bosschaert@gmail.com>"]
license = "Apache-2.0"
Expand Down
33 changes: 23 additions & 10 deletions src/file_util.rs
Original file line number Diff line number Diff line change
@@ -1,24 +1,37 @@
use std::path::Path;
use std::path::{MAIN_SEPARATOR, MAIN_SEPARATOR_STR, Path};

pub struct FileUtil {
}

impl FileUtil {
pub fn normalize_path(s: &str) -> String {
let src_char = if MAIN_SEPARATOR == '/' {
"\\"
} else {
"/"
};

s.replace(src_char, MAIN_SEPARATOR_STR)
}

pub fn get_sub_path(path: &Path, base_dir: &str) -> String {
let nbase_dir = FileUtil::normalize_path(base_dir);

let base;
if base_dir.ends_with("/") {
base = base_dir.to_owned();
if nbase_dir.ends_with(MAIN_SEPARATOR_STR) {
base = nbase_dir;
} else {
base = base_dir.to_owned() + "/";
base = nbase_dir + MAIN_SEPARATOR_STR;
}

let sub_path;

let full_path = path.to_string_lossy();
if full_path.starts_with(&base) {
sub_path = &full_path[base.len()..];
let nfull_path = FileUtil::normalize_path(&full_path);
if nfull_path.starts_with(&base) {
sub_path = &nfull_path[base.len()..];
} else {
sub_path = &full_path;
sub_path = &nfull_path;
}

sub_path.to_owned()
Expand All @@ -34,20 +47,20 @@ mod tests {
fn test_get_sub_path() {
let p = Path::new("/some/where/on/the/rainbow.docx");
let b = "/some/where/on/";
assert_eq!("the/rainbow.docx", FileUtil::get_sub_path(p, b));
assert_eq!(FileUtil::normalize_path("the/rainbow.docx"), FileUtil::get_sub_path(p, b));
}

#[test]
fn test_get_sub_path1() {
let p = Path::new("/some/where/on/the/rainbow.docx");
let b = "/some/where/on";
assert_eq!("the/rainbow.docx", FileUtil::get_sub_path(p, b));
assert_eq!(FileUtil::normalize_path("the/rainbow.docx"), FileUtil::get_sub_path(p, b));
}

#[test]
fn test_get_sub_path2() {
let b = "/some/where/on/";
let p = Path::new("/elsewhere/cloud.docx");
assert_eq!("/elsewhere/cloud.docx", FileUtil::get_sub_path(p, b));
assert_eq!(FileUtil::normalize_path("/elsewhere/cloud.docx"), FileUtil::get_sub_path(p, b));
}
}
14 changes: 7 additions & 7 deletions src/xml_util.rs
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ use regex::Regex;
use std::collections::{BTreeMap, HashMap};
use std::fs::{File, self};
use std::io::{BufReader, BufWriter};
use std::path::{Path, PathBuf};
use std::path::{Path, PathBuf, MAIN_SEPARATOR, MAIN_SEPARATOR_STR};
use std::str;
use uuid::Uuid;
use unicase::UniCase;
Expand Down Expand Up @@ -154,15 +154,15 @@ impl XMLUtil {

let mut rels_files = vec!();
for f in files {
let last_slash = f.rfind('/').expect(&f);
let last_slash = f.rfind(MAIN_SEPARATOR).expect(&f);
let mut new_fn = String::new();
new_fn.push_str(&f[..last_slash]);
new_fn.push_str("/_");
new_fn.push_str(rels_extension);
new_fn.push_str(&f[last_slash..]);
new_fn.push('.');
new_fn.push_str(rels_extension);
rels_files.push(new_fn);
rels_files.push(FileUtil::normalize_path(&new_fn));
}

rels_files
Expand All @@ -175,9 +175,9 @@ impl XMLUtil {
/// `pattern` and `replacement` are used to search/replace operations.
/// `output_file` optionally specifies a different output file for replacement operations.
fn snr_xml(mode: Mode, dir: &str, src_file: &str, files: Option<Vec<String>>, output_file: Option<&str>) {
let mut base_dir = dir.to_owned();
if !dir.ends_with("/") {
base_dir.push('/');
let mut base_dir = FileUtil::normalize_path(dir);
if !base_dir.ends_with(MAIN_SEPARATOR_STR) {
base_dir.push(MAIN_SEPARATOR);
}

for entry in WalkDir::new(dir).into_iter()
Expand Down Expand Up @@ -838,7 +838,7 @@ impl XMLUtil {
} else {
rel_pn = pn;
}
mappings.insert(rel_pn.to_string(),
mappings.insert(FileUtil::normalize_path(rel_pn),
str::from_utf8(cv.value.as_ref()).unwrap().to_string());
}
}
Expand Down
10 changes: 5 additions & 5 deletions src/zip_util.rs
Original file line number Diff line number Diff line change
Expand Up @@ -151,7 +151,7 @@ impl ZipUtil {
mod tests {
use crate::file_util::FileUtil;
use super::ZipUtil;
use std::{path::Path, fs, io};
use std::{path::MAIN_SEPARATOR_STR, path::Path, fs, io};
use walkdir::WalkDir;
use testdir::testdir;

Expand All @@ -165,13 +165,13 @@ mod tests {
let wd = WalkDir::new(&outdir);
let extracts: Vec<String> = wd.into_iter()
.map(|e| FileUtil::get_sub_path(&e.unwrap().path(), &outdir.to_string_lossy()))
.filter(|e| !e.starts_with("/"))
.filter(|e| !e.starts_with(MAIN_SEPARATOR_STR))
.filter(|e| e.contains('.'))
.collect();

assert!(extracts.contains(&"foo.test.txt".into()));
assert!(extracts.contains(&"empty.file".into()));
assert!(extracts.contains(&"sub/sub/[Content_Types].xml".into()));
assert!(extracts.contains(&FileUtil::normalize_path("sub/sub/[Content_Types].xml")));
assert_eq!(3, extracts.len(), "Should be only 3 files");

let empty_file = Path::new(&outdir).join("empty.file");
Expand Down Expand Up @@ -209,14 +209,14 @@ mod tests {

let extracts: Vec<String> = WalkDir::new(&expldir).into_iter()
.map(|e| FileUtil::get_sub_path(&e.unwrap().path(), &expldir.to_string_lossy()))
.filter(|e| !e.starts_with("/"))
.filter(|e| !e.starts_with(MAIN_SEPARATOR_STR))
.filter(|e| e.contains('.'))
.collect();

assert_eq!(3, extracts.len());
assert!(extracts.contains(&"foo.test.txt".into()));
assert!(extracts.contains(&"empty.file".into()));
assert!(extracts.contains(&"sub/sub/[Content_Types].xml".into()));
assert!(extracts.contains(&FileUtil::normalize_path("sub/sub/[Content_Types].xml")));

let empty_file = Path::new(&expldir).join("empty.file");
assert!(empty_file.is_file());
Expand Down