summaryrefslogtreecommitdiffstats
path: root/src/poem.rs
diff options
context:
space:
mode:
authorRory Dudley2024-05-19 18:50:06 -0600
committerRory Dudley2024-05-19 18:50:06 -0600
commit4b1b8061e79b42128df4f06fd1e439549bf9696b (patch)
tree80db43cf7295937751d61435fb4e60118b8a3ea9 /src/poem.rs
parent8756d3e7512c1416cc15a688c62b8f51f030b192 (diff)
downloaddwarvish-4b1b8061e79b42128df4f06fd1e439549bf9696b.tar.gz
Handle STDERR, in addition to STDOUT
This patch overhauls the reading and reciting of verses, such that the redirection of STDERR (in addition to STDOUT, which was already a feature), is now possible. Removed the 'stdout' argument from recite(), since it is no longer needed with how incantations function. A verse's couplet indicator is now a u8, instead of a bool, with certain values corresponding to types of couplets, for instance: ls | grep Ca | lolcat ^ ^ ^ | | 2: right side of a couplet | 3: both sides of a couplet 1: left side of a couplet Incantions are no longer hanlded in rune.rs, and the task macros have been removed. Now, a verse incants itself, matching on its own meter to determine how to handle the next verse. The following runes were added to help with handling STDERR: Write2 -> 2> WriteAll -> &> Addendum2 -> 2>> AddendumAll -> &>> The 'io' field in verse was changed from an Option<Rune>, to an array of Runes, since a single verse might have multiple IO operations. The following fields were added to Verse, to assist with handling STDERR: ip -> List of filenames to read into STDIN op -> List of filenames to send STDOUT to ep -> List of filenames to send STDERR to Keep track of channels when reading a poem. Channels are relating to IO operations. If channel is None, words get pushed to the verse's primary stanza (i.e. the verb or the clause). If a channel is selected, words are pushed to one of the aforementioned new fields in Verse. Read -> ip Write/Addedum -> op Write2/Addedum2 -> ep WriteAll/AddendumAll -> op and ep
Notes
Notes: This commit also added tests for the new Runes.
Diffstat (limited to 'src/poem.rs')
-rw-r--r--src/poem.rs151
1 files changed, 145 insertions, 6 deletions
diff --git a/src/poem.rs b/src/poem.rs
index a063a14..db57e55 100644
--- a/src/poem.rs
+++ b/src/poem.rs
@@ -67,10 +67,17 @@ mod tests {
assert!(poem.is_ok());
let mut verses = poem.unwrap().into_iter();
let verse = verses.next().unwrap();
- assert_eq!(verse.io, Rune::Read);
+ assert!(verse.io.contains(&Rune::Read));
assert_eq!(
verse.stanza,
- vec!["lolcat", "<", "src/main.rs"]
+ vec!["lolcat"]
+ .iter()
+ .map(|s| s.to_string())
+ .collect::<Vec<String>>()
+ );
+ assert_eq!(
+ verse.ip,
+ vec!["src/main.rs"]
.iter()
.map(|s| s.to_string())
.collect::<Vec<String>>()
@@ -86,10 +93,76 @@ mod tests {
assert!(poem.is_ok());
let mut verses = poem.unwrap().into_iter();
let verse = verses.next().unwrap();
- assert_eq!(verse.io, Rune::Write);
+ assert!(verse.io.contains(&Rune::Write));
assert_eq!(
verse.stanza,
- vec!["cat", "src/main.rs", "<", "/dev/null"]
+ vec!["cat", "src/main.rs"]
+ .iter()
+ .map(|s| s.to_string())
+ .collect::<Vec<String>>()
+ );
+ assert_eq!(
+ verse.op,
+ vec!["/dev/null"]
+ .iter()
+ .map(|s| s.to_string())
+ .collect::<Vec<String>>()
+ );
+ }
+
+ #[test]
+ fn it_parses_a_verse_with_the_write2_rune() {
+ let poem = Poem::read(
+ "cat src/main.rs 2> /dev/null".to_string(),
+ &Environment::new(),
+ );
+ assert!(poem.is_ok());
+ let mut verses = poem.unwrap().into_iter();
+ let verse = verses.next().unwrap();
+ assert!(verse.io.contains(&Rune::Write2));
+ assert_eq!(
+ verse.stanza,
+ vec!["cat", "src/main.rs"]
+ .iter()
+ .map(|s| s.to_string())
+ .collect::<Vec<String>>()
+ );
+ assert_eq!(
+ verse.ep,
+ vec!["/dev/null"]
+ .iter()
+ .map(|s| s.to_string())
+ .collect::<Vec<String>>()
+ );
+ }
+
+ #[test]
+ fn it_parses_a_verse_with_the_write_all_rune() {
+ let poem = Poem::read(
+ "cat src/main.rs &> /dev/null".to_string(),
+ &Environment::new(),
+ );
+ assert!(poem.is_ok());
+ let mut verses = poem.unwrap().into_iter();
+ let verse = verses.next().unwrap();
+ assert!(verse.io.contains(&Rune::WriteAll));
+ assert_eq!(
+ verse.stanza,
+ vec!["cat", "src/main.rs"]
+ .iter()
+ .map(|s| s.to_string())
+ .collect::<Vec<String>>()
+ );
+ assert_eq!(
+ verse.op,
+ vec!["/dev/null"]
+ .iter()
+ .map(|s| s.to_string())
+ .collect::<Vec<String>>()
+ );
+ assert_eq!(
+ verse.ep,
+ vec!["/dev/null"]
.iter()
.map(|s| s.to_string())
.collect::<Vec<String>>()
@@ -105,10 +178,76 @@ mod tests {
assert!(poem.is_ok());
let mut verses = poem.unwrap().into_iter();
let verse = verses.next().unwrap();
- assert_eq!(verse.io, Rune::Addendum);
+ assert!(verse.io.contains(&Rune::Addendum));
+ assert_eq!(
+ verse.stanza,
+ vec!["cat", "src/main.rs"]
+ .iter()
+ .map(|s| s.to_string())
+ .collect::<Vec<String>>()
+ );
+ assert_eq!(
+ verse.op,
+ vec!["/dev/null"]
+ .iter()
+ .map(|s| s.to_string())
+ .collect::<Vec<String>>()
+ );
+ }
+
+ #[test]
+ fn it_parses_a_verse_with_the_addendum2_rune() {
+ let poem = Poem::read(
+ "cat src/main.rs 2>> /dev/null".to_string(),
+ &Environment::new(),
+ );
+ assert!(poem.is_ok());
+ let mut verses = poem.unwrap().into_iter();
+ let verse = verses.next().unwrap();
+ assert!(verse.io.contains(&Rune::Addendum2));
+ assert_eq!(
+ verse.stanza,
+ vec!["cat", "src/main.rs"]
+ .iter()
+ .map(|s| s.to_string())
+ .collect::<Vec<String>>()
+ );
+ assert_eq!(
+ verse.ep,
+ vec!["/dev/null"]
+ .iter()
+ .map(|s| s.to_string())
+ .collect::<Vec<String>>()
+ );
+ }
+
+ #[test]
+ fn it_parses_a_verse_with_the_addendum_all_rune() {
+ let poem = Poem::read(
+ "cat src/main.rs &>> /dev/null".to_string(),
+ &Environment::new(),
+ );
+ assert!(poem.is_ok());
+ let mut verses = poem.unwrap().into_iter();
+ let verse = verses.next().unwrap();
+ assert!(verse.io.contains(&Rune::AddendumAll));
assert_eq!(
verse.stanza,
- vec!["cat", "src/main.rs", "<", "/dev/null"]
+ vec!["cat", "src/main.rs"]
+ .iter()
+ .map(|s| s.to_string())
+ .collect::<Vec<String>>()
+ );
+ assert_eq!(
+ verse.op,
+ vec!["/dev/null"]
+ .iter()
+ .map(|s| s.to_string())
+ .collect::<Vec<String>>()
+ );
+ assert_eq!(
+ verse.ep,
+ vec!["/dev/null"]
.iter()
.map(|s| s.to_string())
.collect::<Vec<String>>()