diff options
| author | Miquel Sabaté Solà <mssola@mssola.com> | 2026-01-27 22:04:47 +0100 |
|---|---|---|
| committer | Miquel Sabaté Solà <mssola@mssola.com> | 2026-01-27 22:04:47 +0100 |
| commit | 3febb9da3e91dc11cd46f282d0edff2ea5890731 (patch) | |
| tree | 5530278154bf17d639071c9bc97cfba5a839e2b2 | |
| parent | 108bc6f0446c351b421ba62367e0f4eaf6c62461 (diff) | |
| download | mihi-3febb9da3e91dc11cd46f282d0edff2ea5890731.tar.gz mihi-3febb9da3e91dc11cd46f282d0edff2ea5890731.zip | |
words: add the 'rel' subcommand
This is a more general way to establish the relationship between two
words.
Signed-off-by: Miquel Sabaté Solà <mssola@mssola.com>
| -rw-r--r-- | crates/cli/src/words.rs | 81 | ||||
| -rw-r--r-- | lib/mihi/src/lib.rs | 13 |
2 files changed, 94 insertions, 0 deletions
diff --git a/crates/cli/src/words.rs b/crates/cli/src/words.rs index 1567612..1aed8e3 100644 --- a/crates/cli/src/words.rs +++ b/crates/cli/src/words.rs @@ -80,6 +80,7 @@ fn help(msg: Option<&str>) { println!(" edit\t\t\tEdit information from a word."); println!(" ls\t\t\tList the words from the database."); println!(" poke\t\t\tUpdate the timestamp for a word."); + println!(" rel\t\t\tEstablish a relationship between two words."); println!(" rm\t\t\tRemove a word from the database."); println!(" show\t\t\tShow information from a word."); } @@ -964,6 +965,83 @@ fn poke(mut args: IntoIter<String>) -> i32 { } } +fn rel(args: IntoIter<String>) -> i32 { + if args.len() > 0 { + help(Some( + "error: words: no arguments were expected for this command", + )); + return 1; + } + + println!("The word:"); + let source_enunciate = match select_single_word(None) { + Ok(word) => word, + Err(e) => { + println!("error: words: {e}."); + return 1; + } + }; + let source = match mihi::find_by(source_enunciate.as_str()) { + Ok(word) => word, + Err(e) => { + println!("error: words: {e}"); + return 1; + } + }; + + let kinds = vec![ + RelationKind::Comparative, + RelationKind::Superlative, + RelationKind::Adverb, + RelationKind::Alternative, + RelationKind::Gendered, + ]; + let Ok(relation) = Select::new("has a...", kinds).prompt() else { + return 1; + }; + + println!("which is the word:"); + let dest_enunciate = match select_single_word(None) { + Ok(word) => word, + Err(e) => { + println!("error: words: {e}."); + return 1; + } + }; + let dest = match mihi::find_by(dest_enunciate.as_str()) { + Ok(word) => word, + Err(e) => { + println!("error: words: {e}"); + return 1; + } + }; + + match mihi::add_word_relationship(source.id as i64, dest.id as i64, relation.clone()) { + Ok(_) => { + // If the relation was actually an alternative word, then the + // relationship goes both ways. Add the same relationship but with + // the direction changed. + if matches!(relation, RelationKind::Alternative | RelationKind::Gendered) { + if let Err(e) = + mihi::add_word_relationship(dest.id as i64, source.id as i64, relation.clone()) + { + println!("errors: words: {e}"); + return 1; + } + } + println!( + "Success: '{}' has now been marked as '{relation}' to '{}'", + dest.enunciated, source.enunciated + ); + 0 + } + Err(e) => { + println!("errors: words: {e}"); + 1 + } + } +} + fn show(mut args: IntoIter<String>) -> i32 { if args.len() > 1 { help(Some( @@ -1093,6 +1171,9 @@ pub fn run(args: Vec<String>) { "poke" => { std::process::exit(poke(it)); } + "rel" => { + std::process::exit(rel(it)); + } "rm" => { std::process::exit(rm(it)); } diff --git a/lib/mihi/src/lib.rs b/lib/mihi/src/lib.rs index 1aabf29..237fe84 100644 --- a/lib/mihi/src/lib.rs +++ b/lib/mihi/src/lib.rs @@ -284,6 +284,19 @@ pub enum RelationKind { Gendered, } +// Needed for inquire's (Multi)Select. +impl std::fmt::Display for RelationKind { + fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result { + match self { + Self::Comparative => write!(f, "comparative form"), + Self::Superlative => write!(f, "superlative form"), + Self::Adverb => write!(f, "adverbial form"), + Self::Alternative => write!(f, "alternative word"), + Self::Gendered => write!(f, "alternative word because of gender"), + } + } +} + impl TryFrom<isize> for RelationKind { type Error = String; |
