Skip to content

Commit

Permalink
Add cli integration tests
Browse files Browse the repository at this point in the history
  • Loading branch information
JamyGolden committed Apr 1, 2024
1 parent 5f02c50 commit 00e09bf
Show file tree
Hide file tree
Showing 6 changed files with 344 additions and 1 deletion.
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -1 +1,2 @@
/target
test_operation_render_out.txt
2 changes: 1 addition & 1 deletion ribboncurls-cli/src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -60,7 +60,7 @@ fn main() -> Result<()> {
)?;
}
_ => {
println!("Basic usage: {BIN_NAME} build <mustache-file-path> <yaml-data-file-path>");
println!("Basic usage: {BIN_NAME} render <mustache-file-path> <yaml-data-file-path>");
println!("For more information try `{BIN_NAME} --help` or visit: {HOMEPAGE}");
exit(1);
}
Expand Down
1 change: 1 addition & 0 deletions ribboncurls-cli/tests/fixtures/data-lastname.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
lastname: Doe
1 change: 1 addition & 0 deletions ribboncurls-cli/tests/fixtures/data-name.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
name: Jessica
1 change: 1 addition & 0 deletions ribboncurls-cli/tests/fixtures/variables.mustache
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
Hello, {{name}} {{lastname}}!
339 changes: 339 additions & 0 deletions ribboncurls-cli/tests/operation_render.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,339 @@
use anyhow::Result;
use std::error::Error;
use std::fs;
use std::path::PathBuf;
use std::process::Command;

const COMMAND_PATH: &str = "../target/debug/ribboncurls";
const SUBCOMMAND_PATH: &str = "render";

#[test]
fn test_operation_render_no_data() -> Result<()> {
// -------
// Arrange
// -------
let mustache_filepath = String::from("./tests/fixtures/variables.mustache");

// ---
// Act
// ---
let (_, stderr) = run_command(vec![
COMMAND_PATH.to_string(),
SUBCOMMAND_PATH.to_string(),
mustache_filepath,
])
.unwrap();

// ------
// Assert
// ------
assert!(
stderr.contains("the following required arguments were not provided"),
"stderr does not contain the expected output"
);
assert!(
stderr
.contains("Usage: ribboncurls render <--data <YAML_STRING>|--data-file <FILE>> <FILE>"),
"stderr does not contain the expected output"
);

Ok(())
}

#[test]
fn test_operation_render_single_data() -> Result<()> {
// -------
// Arrange
// -------
let mustache_filepath = String::from("./tests/fixtures/variables.mustache");
let yaml_data = "name: World";

// ---
// Act
// ---
let (stdout, stderr) = run_command(vec![
COMMAND_PATH.to_string(),
SUBCOMMAND_PATH.to_string(),
format!("--data={}", yaml_data),
mustache_filepath,
])
.unwrap();

// ------
// Assert
// ------
assert!(
stdout.contains("Hello, World !"),
"stdout does not contain the expected output"
);
assert!(
stderr.is_empty(),
"stderr does not contain the expected output"
);

Ok(())
}

#[test]
fn test_operation_render_multiple_data() -> Result<()> {
// -------
// Arrange
// -------
let mustache_filepath = String::from("./tests/fixtures/variables.mustache");
let yaml_data_name = "name: Gillian";
let yaml_data_lastname = "lastname: Doe";

// ---
// Act
// ---
let (stdout, stderr) = run_command(vec![
COMMAND_PATH.to_string(),
SUBCOMMAND_PATH.to_string(),
format!("--data={}", yaml_data_name),
format!("--data={}", yaml_data_lastname),
mustache_filepath,
])
.unwrap();

// ------
// Assert
// ------
assert!(
stdout.contains("Hello, Gillian Doe!"),
"stdout does not contain the expected output"
);
assert!(
stderr.is_empty(),
"stderr does not contain the expected output"
);

Ok(())
}

#[test]
fn test_operation_render_single_datafile() -> Result<()> {
// -------
// Arrange
// -------
let mustache_filepath = String::from("./tests/fixtures/variables.mustache");

// ---
// Act
// ---
let (stdout, stderr) = run_command(vec![
COMMAND_PATH.to_string(),
SUBCOMMAND_PATH.to_string(),
format!(
"--data-file={}",
PathBuf::from("./tests/fixtures/data-name.yaml").display()
),
mustache_filepath,
])
.unwrap();

// ------
// Assert
// ------
assert!(
stdout.contains("Hello, Jessica !"),
"stdout does not contain the expected output"
);
assert!(
stderr.is_empty(),
"stderr does not contain the expected output"
);

Ok(())
}

#[test]
fn test_operation_render_multiple_datafile() -> Result<()> {
// -------
// Arrange
// -------
let mustache_filepath = String::from("./tests/fixtures/variables.mustache");

// ---
// Act
// ---
let (stdout, stderr) = run_command(vec![
COMMAND_PATH.to_string(),
SUBCOMMAND_PATH.to_string(),
format!(
"--data-file={}",
PathBuf::from("./tests/fixtures/data-name.yaml").display()
),
format!(
"--data-file={}",
PathBuf::from("./tests/fixtures/data-lastname.yaml").display()
),
mustache_filepath,
])
.unwrap();

// ------
// Assert
// ------
assert!(
stdout.contains("Hello, Jessica Doe!"),
"stdout does not contain the expected output"
);
assert!(
stderr.is_empty(),
"stderr does not contain the expected output"
);

Ok(())
}

#[test]
fn test_operation_render_mixture_of_data_and_datafile() -> Result<()> {
// -------
// Arrange
// -------
let mustache_filepath = String::from("./tests/fixtures/variables.mustache");

// ---
// Act
// ---
let (stdout, stderr) = run_command(vec![
COMMAND_PATH.to_string(),
SUBCOMMAND_PATH.to_string(),
format!(
"--data-file={}",
PathBuf::from("./tests/fixtures/data-name.yaml").display()
),
"--data=lastname: Dodrio".to_string(),
mustache_filepath,
])
.unwrap();

// ------
// Assert
// ------
assert!(
stdout.contains("Hello, Jessica Dodrio!"),
"stdout does not contain the expected output"
);
assert!(
stderr.is_empty(),
"stderr does not contain the expected output"
);

Ok(())
}

#[test]
fn test_operation_render_using_stdin_as_template() -> Result<()> {
// -------
// Arrange
// -------
let template = "Howzit, {{name}} {{lastname}}!";
let command_str = format!(
"echo '{}' | {} {} --data-file='{}' --data='lastname: Dodrio' -",
template,
COMMAND_PATH,
SUBCOMMAND_PATH,
PathBuf::from("./tests/fixtures/data-name.yaml").display(),
);

// ---
// Act
// ---
let (stdout, stderr) = run_command_through_sh(&command_str).unwrap();

// ------
// Assert
// ------
assert!(
stdout.contains("Howzit, Jessica Dodrio!"),
"stdout does not contain the expected output"
);
assert!(
stderr.is_empty(),
"stderr does not contain the expected output"
);

Ok(())
}

#[test]
fn test_operation_render_out() -> Result<()> {
// -------
// Arrange
// -------
let mustache_filepath = String::from("./tests/fixtures/variables.mustache");
let yaml_data = "name: World";
let out_path = PathBuf::from("test_operation_render_out.txt");

// ---
// Act
// ---
let (stdout, stderr) = run_command(vec![
COMMAND_PATH.to_string(),
SUBCOMMAND_PATH.to_string(),
format!("--data={}", yaml_data),
format!("--out={}", out_path.display()),
mustache_filepath,
])
.unwrap();

println!("stdout: {}", stdout);

// ------
// Assert
// ------
assert!(
fs::read_to_string(&out_path)?.contains("Hello, World !"),
"stdout does not contain the expected output"
);
assert!(
stdout.contains(format!("Rendered output to: {}", out_path.display()).as_str()),
"stdout does not contain the expected output"
);
assert!(
stderr.is_empty(),
"stderr does not contain the expected output"
);

Ok(())
}

pub fn run_command(command_vec: Vec<String>) -> Result<(String, String), Box<dyn Error>> {
let output = Command::new(COMMAND_PATH)
.args(&command_vec[1..])
.output()
.expect("Failed to execute command");

if !output.stderr.is_empty() {
println!(
"Init command stderr: {}",
String::from_utf8_lossy(&output.stderr)
);
}

Ok((
String::from_utf8(output.stdout)?,
String::from_utf8(output.stderr)?,
))
}

pub fn run_command_through_sh(command_str: &str) -> Result<(String, String), Box<dyn Error>> {
let output = Command::new("sh")
.arg("-c")
.arg(command_str)
.output()
.expect("Failed to execute command");

if !output.stderr.is_empty() {
println!(
"Init command stderr: {}",
String::from_utf8_lossy(&output.stderr)
);
}

Ok((
String::from_utf8(output.stdout)?,
String::from_utf8(output.stderr)?,
))
}

0 comments on commit 00e09bf

Please sign in to comment.