Skip to content

Commit

Permalink
Add integration test and files for it.
Browse files Browse the repository at this point in the history
  • Loading branch information
fmaccha committed Feb 13, 2024
1 parent dcd2a32 commit e3889fd
Showing 10 changed files with 318 additions and 0 deletions.
5 changes: 5 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -87,3 +87,8 @@ target/

# MSVC Windows builds of rustc generate these, which store debugging information
*.pdb

##########################

# Ignore the cache directory for tests
tests/cache_dir/
22 changes: 22 additions & 0 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

6 changes: 6 additions & 0 deletions Cargo.toml
Original file line number Diff line number Diff line change
@@ -40,3 +40,9 @@ chrono = "0.4.31"
lazy_static = "1.4.0"
bimap = "0.6.3"
openssl = { version = "0.10.63", features = ["vendored"] }

[dev-dependencies]
assert_cmd = "2.0.13"
digest = "0.10.7"
predicates = "3.1.0"
sha2 = "0.10.8"
37 changes: 37 additions & 0 deletions tests/common.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
// use sha2::Sha256;
use sha2::{Digest, Sha256};
use std::fs::File;
use std::io::{self, Read};
use std::path::Path;

pub struct Out {
pub stdout: String,
pub stderr: String,
}

pub fn tataki(targets: &[&str], options: &[&str]) -> Out {
let mut cmd = assert_cmd::Command::cargo_bin("tataki").expect("Failed to find 'tataki' binary");
cmd.current_dir("tests/");
let hoge = cmd.args(targets).args(options).assert().success();

Out {
stdout: String::from_utf8_lossy(&hoge.get_output().stdout).to_string(),
stderr: String::from_utf8_lossy(&hoge.get_output().stderr).to_string(),
}
}

pub fn calculate_checksum<P>(path: P) -> io::Result<String>
where
P: AsRef<Path>,
{
let mut file = File::open(path)?;
let mut hasher = Sha256::new();
let mut buffer = Vec::new();

file.read_to_end(&mut buffer)?;

hasher.update(&buffer);
let result = hasher.finalize();

Ok(format!("{:x}", result))
}
9 changes: 9 additions & 0 deletions tests/conf/module_order_test.conf
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
order:
- bam
- bcf
- bed
- cram
- fastq
- gff3
- gtf
- vcf
226 changes: 226 additions & 0 deletions tests/integration_tests.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,226 @@
mod common;

use std::fs;
use std::path::Path;

use common::{calculate_checksum, tataki};

/*
test cases:
- default
- -f yaml
- -f json --cache-dir
- -o file
- -c conf
- --dry-run
- --quiet
- --verbose
- -c cwl.conf
*/

#[test]
fn output_in_csv() {
let out = tataki(&["./inputs/toy.sam", "./inputs/toy.fa"], &[]);

let stdout = out.stdout;

let mut rdr = csv::Reader::from_reader(stdout.as_bytes());
let output_records = rdr
.records()
.collect::<Result<Vec<_>, csv::Error>>()
.expect("Failed to parse the output as CSV");

let mut expected_output_rdr =
csv::Reader::from_path(Path::new("tests/outputs/expected_output.csv"))
.expect("Failed to read the expected output file");
let expected_output_records = expected_output_rdr
.records()
.collect::<Result<Vec<_>, csv::Error>>()
.expect("Failed to parse the expected output as CSV");

assert_eq!(output_records, expected_output_records);
}

#[test]
fn output_in_yaml() {
let out = tataki(&["./inputs/toy.sam", "./inputs/toy.fa"], &["-f", "yaml"]);

let stdout = out.stdout;

let output_yaml: serde_yaml::Value =
serde_yaml::from_str(&stdout).expect("Failed to parse the output as YAML");

let expected_output_str = fs::read_to_string(Path::new("tests/outputs/expected_output.yaml"))
.expect("Failed to read the expected output file");
let expected_output_yaml: serde_yaml::Value = serde_yaml::from_str(&expected_output_str)
.expect("Failed to parse the expected output as YAML");

assert_eq!(
output_yaml, expected_output_yaml,
"The tool's YAML output did not match the expected output."
);
}

#[test]
fn output_in_json_and_can_keep_cache() {
let out = tataki(
&[
"./inputs/toy.sam",
"https://github.com/sapporo-wes/tataki/raw/main/tests/inputs/toy.fa",
],
&["--cache-dir", "./cache_dir/", "-f", "json"],
);

let stdout = out.stdout;

let output_json: serde_json::Value =
serde_json::from_str(&stdout).expect("Failed to parse the output as JSON");

let expected_output_str = fs::read_to_string(Path::new("tests/outputs/expected_output.json"))
.expect("Failed to read the expected output file");
let expected_output_json: serde_json::Value = serde_json::from_str(&expected_output_str)
.expect("Failed to parse the expected output as JSON");

assert_eq!(
output_json, expected_output_json,
"The tool's JSON output did not match the expected output."
);

let stderr = out.stderr;

let cache_dir = stderr
.split("Keeping temporary directory:")
.collect::<Vec<&str>>()[1]
.split('\n')
.collect::<Vec<&str>>()[0]
.trim();
let cache_dir = Path::new(cache_dir);

assert!(cache_dir.exists());

let toy_fa_path = cache_dir.join("toy.fa");

let toy_fa_sha256 =
calculate_checksum(toy_fa_path).expect("Failed to calculate the checksum of toy.fa");

assert_eq!(
toy_fa_sha256,
"b2f08eb3c17ade6f4d9933195acc89caf8eefb5b31f89b98f616e9c8e2f9405e"
);
}

#[test]

fn can_output_to_file() {
let _ = tataki(
&["./inputs/toy.sam", "./inputs/toy.fa"],
&["-o", "./cache_dir/output.csv"],
);

let output_path = Path::new("./tests/cache_dir/output.csv");
assert!(output_path.exists());

let output_sha256 =
calculate_checksum(output_path).expect("Failed to calculate the checksum of output.csv");

assert_eq!(
output_sha256,
"81afa82dcd25f408d0f9a1e3ef01f360c158bb3cdbe2e59e8b6f648a34c8972c"
);
}

#[test]
// Check if the output becomes null when a conf without sam and fasta is specified.
fn can_use_config_file() {
let out = tataki(
&["./inputs/toy.sam", "./inputs/toy.fa"],
&["-c", "./conf/module_order_test.conf"],
);

let stdout = out.stdout;

let mut rdr = csv::Reader::from_reader(stdout.as_bytes());
let output_records = rdr
.records()
.collect::<Result<Vec<_>, csv::Error>>()
.expect("Failed to parse the output as CSV");

let mut expected_output_rdr =
csv::Reader::from_path(Path::new("tests/outputs/expected_output_module_order.csv"))
.expect("Failed to read the expected output file");
let expected_output_records = expected_output_rdr
.records()
.collect::<Result<Vec<_>, csv::Error>>()
.expect("Failed to parse the expected output as CSV");

assert_eq!(output_records, expected_output_records);
}

#[test]
fn can_dry_run() {
let out = tataki(&["./inputs/toy.sam", "./inputs/toy.fa"], &["--dry-run"]);

let stdout = out.stdout;

let output_yaml: serde_yaml::Value =
serde_yaml::from_str(&stdout).expect("Failed to parse the output as YAML");

let expected_output_str = fs::read_to_string(Path::new("src/tataki.conf"))
.expect("Failed to read the expected output file");
let expected_output_yaml: serde_yaml::Value = serde_yaml::from_str(&expected_output_str)
.expect("Failed to parse the expected output as YAML");

assert_eq!(
output_yaml, expected_output_yaml,
"The tool's YAML output did not match the expected output."
);
}

#[test]
fn can_be_quiet() {
let out = tataki(&["./inputs/toy.sam", "./inputs/toy.fa"], &["--quiet"]);

let stderr = out.stderr;

assert_eq!(stderr, "");
}

#[test]
fn can_be_verbose() {
let out = tataki(&["./inputs/toy.sam", "./inputs/toy.fa"], &["--verbose"]);

let stderr = out.stderr;

assert!(stderr.contains("DEBUG"));
}

// TODO
/*
#[test]
fn can_run_cwl() {
let out = tataki(
&["./inputs/toy.bam", "./inputs/toy.fa"],
&["-c", "./inputs/cwl.conf"],
);
let stdout = out.stdout;
let mut rdr = csv::Reader::from_reader(stdout.as_bytes());
let output_records = rdr
.records()
.collect::<Result<Vec<_>, csv::Error>>()
.expect("Failed to parse the output as CSV");
let mut expected_output_rdr =
csv::Reader::from_path(Path::new("tests/outputs/expected_output_cwl.csv"))
.expect("Failed to read the expected output file");
let expected_output_records = expected_output_rdr
.records()
.collect::<Result<Vec<_>, csv::Error>>()
.expect("Failed to parse the expected output as CSV");
assert_eq!(output_records, expected_output_records);
}
*/
3 changes: 3 additions & 0 deletions tests/outputs/expected_output.csv
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
File Path,Edam ID,Label
./inputs/toy.sam,http://edamontology.org/format_2573,SAM
./inputs/toy.fa,http://edamontology.org/format_1929,FASTA
1 change: 1 addition & 0 deletions tests/outputs/expected_output.json
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
{"./inputs/toy.sam":{"id":"http://edamontology.org/format_2573","label":"SAM"},"https://github.com/sapporo-wes/tataki/raw/main/tests/inputs/toy.fa":{"id":"http://edamontology.org/format_1929","label":"FASTA"}}
6 changes: 6 additions & 0 deletions tests/outputs/expected_output.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
./inputs/toy.sam:
label: SAM
id: http://edamontology.org/format_2573
./inputs/toy.fa:
label: FASTA
id: http://edamontology.org/format_1929
3 changes: 3 additions & 0 deletions tests/outputs/expected_output_module_order.csv
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
File Path,Edam ID,Label
./inputs/toy.sam,,
./inputs/toy.fa,,

0 comments on commit e3889fd

Please sign in to comment.