use bytes::Bytes;
use futures::stream::{Stream, StreamExt};
use serde_json::json;
use url::Url;
use super::options::{Options, SerializableOptions};
use crate::{DeepgramError, Speak};
static FLUX_SPEAK_URL_PATH: &str = "v2/speak";
impl Speak<'_> {
pub async fn flux_speak_to_file(
&self,
text: &str,
options: &Options,
output_file: &std::path::Path,
) -> Result<(), DeepgramError> {
let mut audio = self.flux_speak_to_stream(text, options).await?;
let mut file = std::fs::File::create(output_file)?;
while let Some(chunk) = audio.next().await {
std::io::copy(&mut chunk?.as_ref(), &mut file)?;
}
Ok(())
}
pub async fn flux_speak_to_stream(
&self,
text: &str,
options: &Options,
) -> Result<impl Stream<Item = Result<Bytes, DeepgramError>>, DeepgramError> {
let response = self
.0
.client
.post(self.flux_speak_rest_url())
.query(&SerializableOptions(options))
.json(&json!({ "text": text }))
.send()
.await?;
if let Err(err) = response.error_for_status_ref() {
let status = response.status();
let error_text = response.text().await.unwrap_or_else(|_| status.to_string());
return Err(DeepgramError::DeepgramApiError {
body: error_text,
err,
});
}
Ok(response.bytes_stream().map(|chunk| Ok(chunk?)))
}
fn flux_speak_rest_url(&self) -> Url {
self.0
.base_url
.join(FLUX_SPEAK_URL_PATH)
.expect("base_url is checked to be a valid base_url when constructing Deepgram client")
}
}
#[cfg(test)]
mod tests {
use crate::Deepgram;
#[test]
fn flux_speak_rest_url() {
let dg = Deepgram::new("token").unwrap();
assert_eq!(
&dg.text_to_speech().flux_speak_rest_url().to_string(),
"https://api.deepgram.com/v2/speak"
);
}
#[test]
fn flux_speak_rest_url_custom_host() {
let dg = Deepgram::with_base_url_and_api_key("http://localhost:8080", "token").unwrap();
assert_eq!(
&dg.text_to_speech().flux_speak_rest_url().to_string(),
"http://localhost:8080/v2/speak"
);
}
}