Translation args in templates

This commit is contained in:
Pascal Engélibert 2022-12-04 18:06:29 +01:00
commit 800036ce49
Signed by: tuxmain
GPG key ID: 3504BC6D362F7DCA
7 changed files with 76 additions and 26 deletions

View file

@ -1,7 +1,9 @@
use crate::{config::Config, db::*, queries::*};
use crate::{config::Config, db::*, locales::Locales, queries::*};
use fluent_bundle::FluentArgs;
use log::error;
use std::{net::IpAddr, str::FromStr};
use unic_langid::LanguageIdentifier;
pub fn new_pending_comment(
comment: &Comment,
@ -173,27 +175,45 @@ pub fn get_client_addr<State>(
))
}
pub fn check_comment(config: &Config, comment: &CommentForm, errors: &mut Vec<String>) {
pub fn check_comment(
config: &Config,
locales: &Locales,
langs: &[LanguageIdentifier],
comment: &CommentForm,
errors: &mut Vec<String>,
) {
if comment.author.len() > config.comment_author_max_len {
errors.push(format!(
"Author name length is {} but maximum is {}.",
comment.author.len(),
config.comment_author_max_len
));
let mut args = FluentArgs::new();
args.set("len", comment.author.len());
args.set("max_len", config.comment_author_max_len);
errors.push(
locales
.tr(langs, "error-comment-author_name_too_long", Some(&args))
.unwrap()
.to_string(),
);
}
if comment.email.len() > config.comment_email_max_len {
errors.push(format!(
"E-mail length is {} but maximum is {}.",
comment.email.len(),
config.comment_email_max_len
));
let mut args = FluentArgs::new();
args.set("len", comment.email.len());
args.set("max_len", config.comment_email_max_len);
errors.push(
locales
.tr(langs, "error-comment-email_too_long", Some(&args))
.unwrap()
.to_string(),
);
}
if comment.text.len() > config.comment_text_max_len {
errors.push(format!(
"Comment length is {} but maximum is {}.",
comment.text.len(),
config.comment_text_max_len
));
let mut args = FluentArgs::new();
args.set("len", comment.text.len());
args.set("max_len", config.comment_text_max_len);
errors.push(
locales
.tr(langs, "error-comment-text_too_long", Some(&args))
.unwrap()
.to_string(),
);
}
}

View file

@ -1,6 +1,6 @@
use crate::config::Config;
use fluent_bundle::{bundle::FluentBundle, FluentArgs, FluentResource};
use fluent_bundle::{bundle::FluentBundle, FluentArgs, FluentResource, FluentValue};
use fluent_langneg::{
accepted_languages, negotiate::filter_matches, negotiate_languages, NegotiationStrategy,
};
@ -101,3 +101,20 @@ pub fn get_time_lang(langs: &[LanguageIdentifier]) -> Option<String> {
}
None
}
pub fn tera_to_fluent(val: &tera::Value) -> FluentValue {
match val {
tera::Value::Null => FluentValue::None,
tera::Value::Number(v) => {
if v.is_i64() {
FluentValue::Number(v.as_i64().unwrap().into())
} else if v.is_u64() {
FluentValue::Number(v.as_u64().unwrap().into())
} else {
FluentValue::Number(v.as_f64().unwrap().into())
}
}
tera::Value::String(v) => FluentValue::String(v.into()),
_ => FluentValue::Error,
}
}

View file

@ -34,7 +34,6 @@ async fn main() {
let config = Box::leak(Box::new(config));
let locales = Box::leak(Box::new(locales::Locales::new(config)));
// TODO args
templates.tera.register_function(
"tr",
Box::new(
@ -53,7 +52,10 @@ async fn main() {
.ok_or_else(|| tera::Error::from("Missing argument `k`"))?
.as_str()
.ok_or_else(|| tera::Error::from("Argument `k` must be string"))?;
let res = locales.tr(&langs, key, None);
let args_iter = fluent_bundle::FluentArgs::from_iter(
args.iter().map(|(k, v)| (k, locales::tera_to_fluent(v))),
);
let res = locales.tr(&langs, key, Some(&args_iter));
if res.is_none() {
warn!("(calling `tr` in template) translation key `{key}` not found");
}

View file

@ -286,7 +286,7 @@ async fn handle_post_comments(
return Err(tide::Error::from_str(404, "No topic"))
};
helpers::check_comment(config, &query.comment, &mut errors);
helpers::check_comment(config, locales, &client_langs, &query.comment, &mut errors);
if let Some(client_addr) = &client_addr {
if antispam_enabled {
@ -360,7 +360,7 @@ async fn handle_post_comments(
return Err(tide::Error::from_str(403, "Forbidden"));
}
helpers::check_comment(config, &query.comment, &mut errors);
helpers::check_comment(config, locales, &client_langs, &query.comment, &mut errors);
let comment_id = if let Ok(comment_id) = CommentId::from_base64(&query.id) {
comment_id