use crates::regex::Regex;
use impl_prelude::*;
#[derive(Debug, Default, Clone, Copy)]
pub struct RejectConflictPaths;
lazy_static! {
static ref CONFLICT_FILE_PATH: Regex =
Regex::new("^(?P<base>.*)\
(?P<kind>_(BACKUP|BASE|LOCAL|REMOTE))\
(?P<pid>_[0-9]+)\
(?P<ext>(\\..*)?)$").unwrap();
}
const ORIG_SUFFIX: &str = ".orig";
impl RejectConflictPaths {
pub fn new() -> Self {
Self {}
}
fn check_conflict_path_name(ctx: &CheckGitContext, path: &str) -> Result<bool> {
if let Some(file_path) = CONFLICT_FILE_PATH.captures(path) {
let base = file_path.name("base")
.expect("the conflict file path regex should have a 'base' group");
let ext = file_path.name("ext")
.expect("the conflict file path regex should have a 'ext' group");
let basepath = format!("{}{}", base.as_str(), ext.as_str());
Self::check_for_path(ctx, &basepath)
} else {
Ok(false)
}
}
fn check_orig_path_name(ctx: &CheckGitContext, path: &str) -> Result<bool> {
if path.ends_with(ORIG_SUFFIX) {
let basepath = path.trim_right_matches(ORIG_SUFFIX);
Self::check_for_path(ctx, basepath)
} else {
Ok(false)
}
}
fn check_for_path(ctx: &CheckGitContext, path: &str) -> Result<bool> {
let cat_file = ctx.git()
.arg("cat-file")
.arg("-e")
.arg(format!(":{}", path))
.output()
.chain_err(|| "failed to contruct cat-file command")?;
Ok(cat_file.status.success())
}
}
impl ContentCheck for RejectConflictPaths {
fn name(&self) -> &str {
"reject-conflict-paths"
}
fn check(&self, ctx: &CheckGitContext, content: &Content) -> Result<CheckResult> {
let mut result = CheckResult::new();
for diff in content.diffs() {
match diff.status {
StatusChange::Added |
StatusChange::Modified(_) => (),
_ => continue,
}
if Self::check_conflict_path_name(ctx, diff.name.as_str())? {
result.add_error(format!("{}it appears as though `{}` is a merge conflict \
resolution file and cannot be added.",
commit_prefix_str(content, "not allowed;"),
diff.name));
}
if Self::check_orig_path_name(ctx, diff.name.as_str())? {
result.add_error(format!("{}it appears as though `{}` is a merge conflict \
backup file and cannot be added.",
commit_prefix_str(content, "not allowed;"),
diff.name));
}
}
Ok(result)
}
}
#[cfg(test)]
mod tests {
use checks::RejectConflictPaths;
use checks::test::*;
const MERGE_CONFLICT_NO_BASE: &str = "52710df4a433731545ef99440edeb431b3160fc6";
const MERGE_CONFLICT_ORIG_NO_BASE: &str = "672a6a32b045bec6f93b9b1b5252611f40437a07";
const MERGE_CONFLICT_NO_EXT: &str = "f31b2e2cb75083d174097db7054cbc9e5836bad7";
const MERGE_CONFLICT_WITH_EXT: &str = "59f02bdb6c404c8f7cfb32700645c149148c089b";
const MERGE_CONFLICT_TWO_EXT: &str = "e9421eadfcac3c67a090444ef2ac859e86a8a2e0";
const MERGE_CONFLICT_ORIG_EXT: &str = "4abcf323b81c757e668ce1936f475b085d6852e8";
const MERGE_CONFLICT_NO_EXT_FIXED: &str = "63c923b5be729f672eddcd4b1e979a7d3d22606f";
const MERGE_CONFLICT_WITH_EXT_FIXED: &str = "8fcdd0d920ef47d0294229fdad4b3abd3ebdc43b";
const MERGE_CONFLICT_TWO_EXT_FIXED: &str = "0bf291f1f8a320abfb63776c56e1d1497231e24e";
const MERGE_CONFLICT_ORIG_EXT_FIXED: &str = "e1fd80490cd7f6556120aad6309d8fb95818b6ef";
#[test]
fn test_reject_conflict_paths_no_base() {
let check = RejectConflictPaths;
run_check_ok("test_reject_conflict_paths_no_base", MERGE_CONFLICT_NO_BASE, check);
}
#[test]
fn test_reject_conflict_paths_no_base_topic() {
let check = RejectConflictPaths;
run_topic_check_ok("test_reject_conflict_paths_no_base_topic",
MERGE_CONFLICT_NO_BASE,
check);
}
#[test]
fn test_reject_conflict_paths_orig_no_base() {
let check = RejectConflictPaths;
run_check_ok("test_reject_conflict_paths_orig_no_base", MERGE_CONFLICT_ORIG_NO_BASE, check);
}
#[test]
fn test_reject_conflict_paths_orig_no_base_topic() {
let check = RejectConflictPaths;
run_topic_check_ok("test_reject_conflict_paths_orig_no_base_topic",
MERGE_CONFLICT_ORIG_NO_BASE,
check);
}
#[test]
fn test_reject_conflict_paths_no_ext() {
let check = RejectConflictPaths;
let result = run_check("test_reject_conflict_paths_no_ext", MERGE_CONFLICT_NO_EXT, check);
test_result_errors(result, &[
"commit f31b2e2cb75083d174097db7054cbc9e5836bad7 not allowed; it appears as though \
`no_ext_BACKUP_12345` is a merge conflict resolution file and cannot be added.",
"commit f31b2e2cb75083d174097db7054cbc9e5836bad7 not allowed; it appears as though \
`no_ext_BASE_12345` is a merge conflict resolution file and cannot be added.",
"commit f31b2e2cb75083d174097db7054cbc9e5836bad7 not allowed; it appears as though \
`no_ext_LOCAL_12345` is a merge conflict resolution file and cannot be added.",
"commit f31b2e2cb75083d174097db7054cbc9e5836bad7 not allowed; it appears as though \
`no_ext_REMOTE_12345` is a merge conflict resolution file and cannot be added.",
]);
}
#[test]
fn test_reject_conflict_paths_no_ext_topic() {
let check = RejectConflictPaths;
let result = run_topic_check("test_reject_conflict_paths_no_ext_topic", MERGE_CONFLICT_NO_EXT, check);
test_result_errors(result, &[
"it appears as though `no_ext_BACKUP_12345` is a merge conflict resolution file and \
cannot be added.",
"it appears as though `no_ext_BASE_12345` is a merge conflict resolution file and \
cannot be added.",
"it appears as though `no_ext_LOCAL_12345` is a merge conflict resolution file and \
cannot be added.",
"it appears as though `no_ext_REMOTE_12345` is a merge conflict resolution file and \
cannot be added.",
]);
}
#[test]
fn test_reject_conflict_paths_no_ext_topic_fixed() {
let check = RejectConflictPaths;
run_topic_check_ok("test_reject_conflict_paths_no_ext_topic_fixed",
MERGE_CONFLICT_NO_EXT_FIXED,
check);
}
#[test]
fn test_reject_conflict_paths_with_ext() {
let check = RejectConflictPaths;
let result = run_check("test_reject_conflict_paths_with_ext", MERGE_CONFLICT_WITH_EXT, check);
test_result_errors(result, &[
"commit 59f02bdb6c404c8f7cfb32700645c149148c089b not allowed; it appears as though \
`conflict_with_BACKUP_12345.ext` is a merge conflict resolution file and cannot be \
added.",
"commit 59f02bdb6c404c8f7cfb32700645c149148c089b not allowed; it appears as though \
`conflict_with_BASE_12345.ext` is a merge conflict resolution file and cannot be \
added.",
"commit 59f02bdb6c404c8f7cfb32700645c149148c089b not allowed; it appears as though \
`conflict_with_LOCAL_12345.ext` is a merge conflict resolution file and cannot be \
added.",
"commit 59f02bdb6c404c8f7cfb32700645c149148c089b not allowed; it appears as though \
`conflict_with_REMOTE_12345.ext` is a merge conflict resolution file and cannot be \
added.",
]);
}
#[test]
fn test_reject_conflict_paths_with_ext_topic() {
let check = RejectConflictPaths;
let result = run_topic_check("test_reject_conflict_paths_with_ext_topic", MERGE_CONFLICT_WITH_EXT, check);
test_result_errors(result, &[
"it appears as though `conflict_with_BACKUP_12345.ext` is a merge conflict resolution \
file and cannot be added.",
"it appears as though `conflict_with_BASE_12345.ext` is a merge conflict resolution \
file and cannot be added.",
"it appears as though `conflict_with_LOCAL_12345.ext` is a merge conflict resolution \
file and cannot be added.",
"it appears as though `conflict_with_REMOTE_12345.ext` is a merge conflict resolution \
file and cannot be added.",
]);
}
#[test]
fn test_reject_conflict_paths_with_ext_topic_fixed() {
let check = RejectConflictPaths;
run_topic_check_ok("test_reject_conflict_paths_with_ext_topic_fixed",
MERGE_CONFLICT_WITH_EXT_FIXED,
check);
}
#[test]
fn test_reject_conflict_paths_two_ext() {
let check = RejectConflictPaths;
let result = run_check("test_reject_conflict_paths_two_ext", MERGE_CONFLICT_TWO_EXT, check);
test_result_errors(result, &[
"commit e9421eadfcac3c67a090444ef2ac859e86a8a2e0 not allowed; it appears as though \
`conflict_with.two_BACKUP_12345.ext` is a merge conflict resolution file and cannot \
be added.",
"commit e9421eadfcac3c67a090444ef2ac859e86a8a2e0 not allowed; it appears as though \
`conflict_with.two_BASE_12345.ext` is a merge conflict resolution file and cannot be \
added.",
"commit e9421eadfcac3c67a090444ef2ac859e86a8a2e0 not allowed; it appears as though \
`conflict_with.two_LOCAL_12345.ext` is a merge conflict resolution file and cannot be \
added.",
"commit e9421eadfcac3c67a090444ef2ac859e86a8a2e0 not allowed; it appears as though \
`conflict_with.two_REMOTE_12345.ext` is a merge conflict resolution file and cannot \
be added.",
]);
}
#[test]
fn test_reject_conflict_paths_two_ext_topic() {
let check = RejectConflictPaths;
let result = run_topic_check("test_reject_conflict_paths_two_ext_topic", MERGE_CONFLICT_TWO_EXT, check);
test_result_errors(result, &[
"it appears as though `conflict_with.two_BACKUP_12345.ext` is a merge conflict \
resolution file and cannot be added.",
"it appears as though `conflict_with.two_BASE_12345.ext` is a merge conflict \
resolution file and cannot be added.",
"it appears as though `conflict_with.two_LOCAL_12345.ext` is a merge conflict \
resolution file and cannot be added.",
"it appears as though `conflict_with.two_REMOTE_12345.ext` is a merge conflict \
resolution file and cannot be added.",
]);
}
#[test]
fn test_reject_conflict_paths_two_ext_topic_fixed() {
let check = RejectConflictPaths;
run_topic_check_ok("test_reject_conflict_paths_two_ext_topic_fixed",
MERGE_CONFLICT_TWO_EXT_FIXED,
check);
}
#[test]
fn test_reject_conflict_paths_orig_ext() {
let check = RejectConflictPaths;
let result = run_check("test_reject_conflict_paths_orig_ext", MERGE_CONFLICT_ORIG_EXT, check);
test_result_errors(result, &[
"commit 4abcf323b81c757e668ce1936f475b085d6852e8 not allowed; it appears as though \
`orig_file.ext.orig` is a merge conflict backup file and cannot be added.",
]);
}
#[test]
fn test_reject_conflict_paths_orig_ext_topic() {
let check = RejectConflictPaths;
let result = run_topic_check("test_reject_conflict_paths_orig_ext_topic", MERGE_CONFLICT_ORIG_EXT, check);
test_result_errors(result, &[
"it appears as though `orig_file.ext.orig` is a merge conflict backup file and cannot \
be added.",
]);
}
#[test]
fn test_reject_conflict_paths_orig_ext_topic_fixed() {
let check = RejectConflictPaths;
run_topic_check_ok("test_reject_conflict_paths_orig_ext_topic_fixed",
MERGE_CONFLICT_ORIG_EXT_FIXED,
check);
}
}