Add validating to length-validated fields on edit

Can't just replace edit logic with overwrite logic because partial editing is used in enabling/disabling. So need to replicate logic in a sensible way.
This commit is contained in:
jude 2022-12-18 13:38:43 +00:00
parent 6e65e4ff3d
commit 3150c7267d
4 changed files with 86 additions and 36 deletions

View File

@ -386,33 +386,40 @@ pub async fn edit_reminder(
let user_id =
cookies.get_private("userid").map(|c| c.value().parse::<u64>().ok()).flatten().unwrap();
if reminder.message_ok() {
update_field!(pool.inner(), error, reminder.[
content,
embed_author,
embed_description,
embed_footer,
embed_title,
embed_fields,
username
]);
} else {
error.push("Message exceeds limits.".to_string());
}
update_field!(pool.inner(), error, reminder.[
attachment,
attachment_name,
avatar,
content,
embed_author,
embed_author_url,
embed_color,
embed_description,
embed_footer,
embed_footer_url,
embed_image_url,
embed_thumbnail_url,
embed_title,
embed_fields,
enabled,
expires,
name,
restartable,
tts,
username,
utc_time
]);
if reminder.interval_days.is_some()
|| reminder.interval_months.is_some()
|| reminder.interval_seconds.is_some()
if reminder.interval_days.flatten().is_some()
|| reminder.interval_months.flatten().is_some()
|| reminder.interval_seconds.flatten().is_some()
{
if check_guild_subscription(&serenity_context.inner(), id).await
|| check_subscription(&serenity_context.inner(), user_id).await

View File

@ -50,6 +50,10 @@ fn id_default() -> u32 {
0
}
fn interval_default() -> Unset<Option<u32>> {
None
}
fn deserialize_optional_field<'de, T, D>(deserializer: D) -> Result<Option<Option<T>>, D::Error>
where
D: Deserializer<'de>,
@ -229,13 +233,13 @@ pub struct PatchReminder {
#[serde(default)]
#[serde(deserialize_with = "deserialize_optional_field")]
expires: Unset<Option<NaiveDateTime>>,
#[serde(default)]
#[serde(default = "interval_default")]
#[serde(deserialize_with = "deserialize_optional_field")]
interval_seconds: Unset<Option<u32>>,
#[serde(default)]
#[serde(default = "interval_default")]
#[serde(deserialize_with = "deserialize_optional_field")]
interval_days: Unset<Option<u32>>,
#[serde(default)]
#[serde(default = "interval_default")]
#[serde(deserialize_with = "deserialize_optional_field")]
interval_months: Unset<Option<u32>>,
#[serde(default)]
@ -251,6 +255,30 @@ pub struct PatchReminder {
utc_time: Unset<NaiveDateTime>,
}
impl PatchReminder {
fn message_ok(&self) -> bool {
self.content.as_ref().map_or(true, |c| c.len() <= MAX_CONTENT_LENGTH)
&& self.embed_author.as_ref().map_or(true, |c| c.len() <= MAX_EMBED_AUTHOR_LENGTH)
&& self
.embed_description
.as_ref()
.map_or(true, |c| c.len() <= MAX_EMBED_DESCRIPTION_LENGTH)
&& self.embed_footer.as_ref().map_or(true, |c| c.len() <= MAX_EMBED_FOOTER_LENGTH)
&& self.embed_title.as_ref().map_or(true, |c| c.len() <= MAX_EMBED_TITLE_LENGTH)
&& self.embed_fields.as_ref().map_or(true, |c| {
c.0.len() <= MAX_EMBED_FIELDS
&& c.0.iter().all(|f| {
f.title.len() <= MAX_EMBED_FIELD_TITLE_LENGTH
&& f.value.len() <= MAX_EMBED_FIELD_VALUE_LENGTH
})
})
&& self
.username
.as_ref()
.map_or(true, |c| c.as_ref().map_or(true, |v| v.len() <= MAX_USERNAME_LENGTH))
}
}
pub fn generate_uid() -> String {
let mut generator: OsRng = Default::default();

View File

@ -22,25 +22,38 @@ function update_interval(element) {
let minutes = element.querySelector('input[name="interval_minutes"]');
let seconds = element.querySelector('input[name="interval_seconds"]');
months.value = months.value.padStart(1, "0");
days.value = days.value.padStart(1, "0");
hours.value = hours.value.padStart(2, "0");
minutes.value = minutes.value.padStart(2, "0");
seconds.value = seconds.value.padStart(2, "0");
let interval = get_interval(element);
if (seconds.value >= 60) {
let quotient = Math.floor(seconds.value / 60);
let remainder = seconds.value % 60;
if (interval.months === null && interval.days === null && interval.seconds === null) {
months.value = "";
days.value = "";
hours.value = "";
minutes.value = "";
seconds.value = "";
} else {
months.value = months.value.padStart(1, "0");
days.value = days.value.padStart(1, "0");
hours.value = hours.value.padStart(2, "0");
minutes.value = minutes.value.padStart(2, "0");
seconds.value = seconds.value.padStart(2, "0");
seconds.value = String(remainder).padStart(2, "0");
minutes.value = String(Number(minutes.value) + Number(quotient)).padStart(2, "0");
}
if (minutes.value >= 60) {
let quotient = Math.floor(minutes.value / 60);
let remainder = minutes.value % 60;
if (seconds.value >= 60) {
let quotient = Math.floor(seconds.value / 60);
let remainder = seconds.value % 60;
minutes.value = String(remainder).padStart(2, "0");
hours.value = String(Number(hours.value) + Number(quotient)).padStart(2, "0");
seconds.value = String(remainder).padStart(2, "0");
minutes.value = String(Number(minutes.value) + Number(quotient)).padStart(
2,
"0"
);
}
if (minutes.value >= 60) {
let quotient = Math.floor(minutes.value / 60);
let remainder = minutes.value % 60;
minutes.value = String(remainder).padStart(2, "0");
hours.value = String(Number(hours.value) + Number(quotient)).padStart(2, "0");
}
}
}

View File

@ -355,6 +355,8 @@ function deserialize_reminder(reminder, frame, mode) {
}
}
update_interval(frame);
const lastChild = frame.querySelector("div.embed-multifield-box .embed-field-box");
for (let field of reminder["embed_fields"]) {
@ -838,13 +840,6 @@ $deleteTemplateBtn.addEventListener("click", (ev) => {
});
});
document.querySelectorAll("textarea.autoresize").forEach((element) => {
element.addEventListener("input", () => {
element.style.height = "";
element.style.height = element.scrollHeight + 3 + "px";
});
});
let $img;
const $urlModal = document.querySelector("div#addImageModal");
const $urlInput = $urlModal.querySelector("input");
@ -900,6 +895,13 @@ document.addEventListener("remindersLoaded", () => {
window.getComputedStyle($discordFrame).borderLeftColor;
});
});
document.querySelectorAll("textarea.autoresize").forEach((element) => {
element.addEventListener("input", () => {
element.style.height = "";
element.style.height = element.scrollHeight + 3 + "px";
});
});
});
function check_embed_fields() {