Closed dessalines closed 4 years ago
I recently added this to lemmy in https://github.com/LemmyNet/lemmy/pull/1027
If anyone's interested in a quick way to do this, here's the relevant code:
pub fn captcha_espeak_wav_base64(captcha: &str) -> Result<String, LemmyError> {
let mut built_text = String::new();
// Building proper speech text for espeak
for mut c in captcha.chars() {
let new_str = if c.is_alphabetic() {
if c.is_lowercase() {
c.make_ascii_uppercase();
format!("lower case {} ... ", c)
} else {
c.make_ascii_uppercase();
format!("capital {} ... ", c)
}
} else {
format!("{} ...", c)
};
built_text.push_str(&new_str);
}
espeak_wav_base64(&built_text)
}
pub fn espeak_wav_base64(text: &str) -> Result<String, LemmyError> {
// Make a temp file path
let uuid = uuid::Uuid::new_v4().to_string();
let file_path = format!("/tmp/lemmy_espeak_{}.wav", &uuid);
// Write the wav file
Command::new("espeak")
.arg("-w")
.arg(&file_path)
.arg(text)
.status()?;
// Read the wav file bytes
let bytes = std::fs::read(&file_path)?;
// Delete the file
std::fs::remove_file(file_path)?;
// Convert to base64
let base64 = base64::encode(bytes);
Ok(base64)
}
Hi @dessalines thank you for your feature request and your example code. I now have implemented audio generation. I have improved your suggestion a bit:
An example is in the example directory.
Sounds good, I'll watch the repo for the next release which includes this, thanks!
Just published the new version to crates.io.
https://github.com/LemmyNet/lemmy-ui/issues/514
Is hound adding a "end of wav file" thing to each letter? Since I've started using this, chromium and safari, when listening to a base64 encoded wave file, only plays the first letter, then stops abruptly before the full duration. The full playback works on firefox.
Here's my converting code, which works fine in FF but not chrome. Makes me think the full appended bytes are malformed in some way, that FF is able to push through.
pub(crate) fn captcha_as_wav_base64(captcha: &Captcha) -> String {
let letters = captcha.as_wav();
let mut concat_letters: Vec<u8> = Vec::new();
for letter in letters {
let bytes = letter.unwrap_or_default();
concat_letters.extend(bytes);
}
// Convert to base64
base64::encode(concat_letters)
}
Obvi I understand if this would be better as a part of a different library, but to make this crate visually-impaired compatible, it would be good if it could also generate a short audio file along with the picture. No captcha solution is complete without audio.