use std::collections::BTreeMap;
#[derive(Debug, Clone, PartialEq, Eq)]
#[non_exhaustive]
pub enum CompletionTarget {
Prompt(String),
ResourceTemplate(String),
}
#[derive(Debug, Clone, PartialEq, Eq)]
#[non_exhaustive]
pub struct CompletionRequest {
pub target: CompletionTarget,
pub argument: String,
pub value: String,
pub resolved: BTreeMap<String, String>,
}
impl CompletionRequest {
pub fn new(
target: CompletionTarget,
argument: impl Into<String>,
value: impl Into<String>,
) -> Self {
Self {
target,
argument: argument.into(),
value: value.into(),
resolved: BTreeMap::new(),
}
}
pub fn with_resolved(mut self, resolved: BTreeMap<String, String>) -> Self {
self.resolved = resolved;
self
}
}
#[derive(Debug, Clone, Default, PartialEq, Eq)]
#[non_exhaustive]
pub struct Completion {
pub values: Vec<String>,
pub total: Option<u32>,
pub has_more: Option<bool>,
}
impl Completion {
pub fn none() -> Self {
Self::default()
}
pub fn new(values: impl IntoIterator<Item = String>) -> Self {
Self {
values: values.into_iter().collect(),
..Self::default()
}
}
pub fn with_total(mut self, total: u32) -> Self {
self.total = Some(total);
self
}
pub fn with_has_more(mut self, has_more: bool) -> Self {
self.has_more = Some(has_more);
self
}
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn completions_default_to_suggesting_nothing() {
let empty = Completion::none();
assert!(empty.values.is_empty());
assert_eq!(empty.total, None);
assert_eq!(empty.has_more, None);
assert_eq!(empty, Completion::default());
}
#[test]
fn requests_carry_previously_resolved_arguments() {
let request = CompletionRequest::new(
CompletionTarget::ResourceTemplate("note/{folder}/{name}".to_string()),
"name",
"dai",
)
.with_resolved(BTreeMap::from([(
"folder".to_string(),
"journal".to_string(),
)]));
assert_eq!(
request.resolved.get("folder").map(String::as_str),
Some("journal")
);
assert_eq!(request.value, "dai");
}
}