Skip to content

Commit c59155c

Browse files
committed
test: add comprehensive tests for cp/mv/mirror commands
- Add 8 new tests for cp command (path parsing, args, serialization) - Add 6 new tests for mv command (path parsing, args, serialization) - Add 6 new tests for mirror command (compare logic, args, serialization) - Add S3 integration tests for mb/rb/ls/stat commands (requires RustFS) Total tests increased from 206 to 241 (+35 tests)
1 parent 67476b3 commit c59155c

File tree

4 files changed

+559
-0
lines changed

4 files changed

+559
-0
lines changed

crates/cli/src/commands/cp.rs

Lines changed: 83 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -588,4 +588,87 @@ mod tests {
588588
let result = parse_path("myalias/bucket/file.txt").unwrap();
589589
assert!(matches!(result, ParsedPath::Remote(_)));
590590
}
591+
592+
#[test]
593+
fn test_parse_local_absolute_path() {
594+
let result = parse_path("/home/user/file.txt").unwrap();
595+
assert!(matches!(result, ParsedPath::Local(_)));
596+
if let ParsedPath::Local(p) = result {
597+
assert!(p.is_absolute());
598+
}
599+
}
600+
601+
#[test]
602+
fn test_parse_local_relative_path() {
603+
let result = parse_path("../file.txt").unwrap();
604+
assert!(matches!(result, ParsedPath::Local(_)));
605+
}
606+
607+
#[test]
608+
fn test_parse_remote_path_bucket_only() {
609+
let result = parse_path("myalias/bucket/").unwrap();
610+
assert!(matches!(result, ParsedPath::Remote(_)));
611+
if let ParsedPath::Remote(r) = result {
612+
assert_eq!(r.alias, "myalias");
613+
assert_eq!(r.bucket, "bucket");
614+
assert!(r.key.is_empty());
615+
}
616+
}
617+
618+
#[test]
619+
fn test_parse_remote_path_with_deep_key() {
620+
let result = parse_path("myalias/bucket/dir1/dir2/file.txt").unwrap();
621+
assert!(matches!(result, ParsedPath::Remote(_)));
622+
if let ParsedPath::Remote(r) = result {
623+
assert_eq!(r.alias, "myalias");
624+
assert_eq!(r.bucket, "bucket");
625+
assert_eq!(r.key, "dir1/dir2/file.txt");
626+
}
627+
}
628+
629+
#[test]
630+
fn test_cp_args_defaults() {
631+
let args = CpArgs {
632+
source: "src".to_string(),
633+
target: "dst".to_string(),
634+
recursive: false,
635+
preserve: false,
636+
continue_on_error: false,
637+
overwrite: true,
638+
dry_run: false,
639+
storage_class: None,
640+
content_type: None,
641+
};
642+
assert!(args.overwrite);
643+
assert!(!args.recursive);
644+
assert!(!args.dry_run);
645+
}
646+
647+
#[test]
648+
fn test_cp_output_serialization() {
649+
let output = CpOutput {
650+
status: "success",
651+
source: "src/file.txt".to_string(),
652+
target: "dst/file.txt".to_string(),
653+
size_bytes: Some(1024),
654+
size_human: Some("1 KiB".to_string()),
655+
};
656+
let json = serde_json::to_string(&output).unwrap();
657+
assert!(json.contains("\"status\":\"success\""));
658+
assert!(json.contains("\"size_bytes\":1024"));
659+
}
660+
661+
#[test]
662+
fn test_cp_output_skips_none_fields() {
663+
let output = CpOutput {
664+
status: "success",
665+
source: "src".to_string(),
666+
target: "dst".to_string(),
667+
size_bytes: None,
668+
size_human: None,
669+
};
670+
let json = serde_json::to_string(&output).unwrap();
671+
assert!(!json.contains("size_bytes"));
672+
assert!(!json.contains("size_human"));
673+
}
591674
}

crates/cli/src/commands/mirror.rs

Lines changed: 105 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -538,4 +538,109 @@ mod tests {
538538
let f3 = entries.iter().find(|e| e.key == "file3.txt").unwrap();
539539
assert_eq!(f3.status, DiffStatus::OnlySecond);
540540
}
541+
542+
#[test]
543+
fn test_compare_empty_source() {
544+
let source: HashMap<String, FileInfo> = HashMap::new();
545+
let mut target = HashMap::new();
546+
target.insert(
547+
"file.txt".to_string(),
548+
FileInfo {
549+
size: Some(100),
550+
modified: None,
551+
etag: Some("abc".to_string()),
552+
},
553+
);
554+
555+
let entries = compare_objects_internal(&source, &target);
556+
assert_eq!(entries.len(), 1);
557+
assert_eq!(entries[0].status, DiffStatus::OnlySecond);
558+
}
559+
560+
#[test]
561+
fn test_compare_empty_target() {
562+
let mut source = HashMap::new();
563+
source.insert(
564+
"file.txt".to_string(),
565+
FileInfo {
566+
size: Some(100),
567+
modified: None,
568+
etag: Some("abc".to_string()),
569+
},
570+
);
571+
let target: HashMap<String, FileInfo> = HashMap::new();
572+
573+
let entries = compare_objects_internal(&source, &target);
574+
assert_eq!(entries.len(), 1);
575+
assert_eq!(entries[0].status, DiffStatus::OnlyFirst);
576+
}
577+
578+
#[test]
579+
fn test_compare_both_empty() {
580+
let source: HashMap<String, FileInfo> = HashMap::new();
581+
let target: HashMap<String, FileInfo> = HashMap::new();
582+
583+
let entries = compare_objects_internal(&source, &target);
584+
assert!(entries.is_empty());
585+
}
586+
587+
#[test]
588+
fn test_compare_different_sizes() {
589+
let mut source = HashMap::new();
590+
source.insert(
591+
"file.txt".to_string(),
592+
FileInfo {
593+
size: Some(100),
594+
modified: None,
595+
etag: Some("abc".to_string()),
596+
},
597+
);
598+
599+
let mut target = HashMap::new();
600+
target.insert(
601+
"file.txt".to_string(),
602+
FileInfo {
603+
size: Some(200), // Different size
604+
modified: None,
605+
etag: Some("def".to_string()),
606+
},
607+
);
608+
609+
let entries = compare_objects_internal(&source, &target);
610+
assert_eq!(entries.len(), 1);
611+
assert_eq!(entries[0].status, DiffStatus::Different);
612+
}
613+
614+
#[test]
615+
fn test_mirror_args_defaults() {
616+
let args = MirrorArgs {
617+
source: "src".to_string(),
618+
target: "dst".to_string(),
619+
remove: false,
620+
overwrite: false,
621+
dry_run: false,
622+
parallel: 4,
623+
quiet: false,
624+
};
625+
assert_eq!(args.parallel, 4);
626+
assert!(!args.remove);
627+
assert!(!args.overwrite);
628+
}
629+
630+
#[test]
631+
fn test_mirror_output_serialization() {
632+
let output = MirrorOutput {
633+
source: "src/".to_string(),
634+
target: "dst/".to_string(),
635+
copied: 10,
636+
removed: 2,
637+
skipped: 5,
638+
errors: 0,
639+
dry_run: false,
640+
};
641+
let json = serde_json::to_string(&output).unwrap();
642+
assert!(json.contains("\"copied\":10"));
643+
assert!(json.contains("\"removed\":2"));
644+
assert!(json.contains("\"dry_run\":false"));
645+
}
541646
}

crates/cli/src/commands/mv.rs

Lines changed: 57 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -303,4 +303,61 @@ mod tests {
303303
let remote = parse_path("myalias/bucket/file.txt").unwrap();
304304
assert!(matches!(remote, ParsedPath::Remote(_)));
305305
}
306+
307+
#[test]
308+
fn test_parse_local_absolute_path() {
309+
let result = parse_path("/tmp/file.txt").unwrap();
310+
assert!(matches!(result, ParsedPath::Local(_)));
311+
}
312+
313+
#[test]
314+
fn test_parse_remote_path_components() {
315+
let result = parse_path("s3/mybucket/path/to/file.txt").unwrap();
316+
if let ParsedPath::Remote(r) = result {
317+
assert_eq!(r.alias, "s3");
318+
assert_eq!(r.bucket, "mybucket");
319+
assert_eq!(r.key, "path/to/file.txt");
320+
} else {
321+
panic!("Expected Remote path");
322+
}
323+
}
324+
325+
#[test]
326+
fn test_mv_args_defaults() {
327+
let args = MvArgs {
328+
source: "src".to_string(),
329+
target: "dst".to_string(),
330+
recursive: false,
331+
continue_on_error: false,
332+
dry_run: false,
333+
};
334+
assert!(!args.recursive);
335+
assert!(!args.dry_run);
336+
assert!(!args.continue_on_error);
337+
}
338+
339+
#[test]
340+
fn test_mv_output_serialization() {
341+
let output = MvOutput {
342+
status: "success",
343+
source: "src/file.txt".to_string(),
344+
target: "dst/file.txt".to_string(),
345+
size_bytes: Some(2048),
346+
};
347+
let json = serde_json::to_string(&output).unwrap();
348+
assert!(json.contains("\"status\":\"success\""));
349+
assert!(json.contains("\"size_bytes\":2048"));
350+
}
351+
352+
#[test]
353+
fn test_mv_output_skips_none_size() {
354+
let output = MvOutput {
355+
status: "success",
356+
source: "src".to_string(),
357+
target: "dst".to_string(),
358+
size_bytes: None,
359+
};
360+
let json = serde_json::to_string(&output).unwrap();
361+
assert!(!json.contains("size_bytes"));
362+
}
306363
}

0 commit comments

Comments
 (0)