DEV: Correctly pluralize error messages (#26469)

This commit is contained in:
Gerhard Schlager 2024-04-04 15:02:09 +02:00 committed by GitHub
parent 79cf7c0935
commit 82c62fe44f
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
9 changed files with 88 additions and 42 deletions

View File

@ -88,7 +88,7 @@ class UsernameValidator
return unless errors.empty?
if username_grapheme_clusters.size < User.username_length.begin
self.errors << I18n.t(:"user.username.short", min: User.username_length.begin)
self.errors << I18n.t(:"user.username.short", count: User.username_length.begin)
end
end
@ -96,7 +96,7 @@ class UsernameValidator
return unless errors.empty?
if username_grapheme_clusters.size > User.username_length.end
self.errors << I18n.t(:"user.username.long", max: User.username_length.end)
self.errors << I18n.t(:"user.username.long", count: User.username_length.end)
elsif username.length > MAX_CHARS
self.errors << I18n.t(:"user.username.too_long")
end

View File

@ -134,8 +134,12 @@ en:
number_value_not_valid_min: "Value must be larger than or equal to %{min}."
number_value_not_valid_max: "Value must be smaller than or equal to %{max}."
string_value_not_valid_min_max: "Value must be between %{min} and %{max} characters long."
string_value_not_valid_min: "Value must be at least %{min} characters long."
string_value_not_valid_max: "Value must be at most %{max} characters long."
string_value_not_valid_min:
one: "Value must be at least %{count} character long."
other: "Value must be at least %{count} characters long."
string_value_not_valid_max:
one: "Value must be at most %{count} character long."
other: "Value must be at most %{count} characters long."
objects:
humanize_required: "The property at JSON Pointer '%{property_json_pointer}' must be present."
required: "must be present"
@ -159,10 +163,18 @@ en:
humanize_not_valid_categories_value: "The property at JSON Pointer '%{property_json_pointer}' must be an array of valid category ids."
not_valid_categories_value: "must be an array of valid category ids"
humanize_categories_value_not_valid_min: "The property at JSON Pointer '%{property_json_pointer}' must have at least %{min} category ids."
categories_value_not_valid_min: "must have at least %{min} category ids"
humanize_categories_value_not_valid_max: "The property at JSON Pointer '%{property_json_pointer}' must have at most %{max} category ids."
categories_value_not_valid_max: "must have at most %{max} category ids"
humanize_categories_value_not_valid_min:
one: "The property at JSON Pointer '%{property_json_pointer}' must have at least %{count} category id."
other: "The property at JSON Pointer '%{property_json_pointer}' must have at least %{count} category ids."
categories_value_not_valid_min:
one: "must have at least %{count} category id"
other: "must have at least %{count} category ids"
humanize_categories_value_not_valid_max:
one: "The property at JSON Pointer '%{property_json_pointer}' must have at most %{count} category id."
other: "The property at JSON Pointer '%{property_json_pointer}' must have at most %{count} category ids."
categories_value_not_valid_max:
one: "must have at most %{count} category id"
other: "must have at most %{count} category ids"
humanize_not_valid_topic_value: "The property at JSON Pointer '%{property_json_pointer}' must be a valid topic id."
not_valid_topic_value: "must be a valid topic id"
@ -172,25 +184,49 @@ en:
humanize_not_valid_groups_value: "The property at JSON Pointer '%{property_json_pointer}' must be an array of valid group ids."
not_valid_groups_value: "must be an array of valid group ids"
humanize_groups_value_not_valid_min: "The property at JSON Pointer '%{property_json_pointer}' must have at least %{min} group ids."
groups_value_not_valid_min: "must have at least %{min} group ids"
humanize_groups_value_not_valid_max: "The property at JSON Pointer '%{property_json_pointer}' must have at most %{max} group ids."
groups_value_not_valid_max: "must have at most %{max} group ids"
humanize_groups_value_not_valid_min:
one: "The property at JSON Pointer '%{property_json_pointer}' must have at least %{count} group id."
other: "The property at JSON Pointer '%{property_json_pointer}' must have at least %{count} group ids."
groups_value_not_valid_min:
one: "must have at least %{count} group id"
other: "must have at least %{count} group ids"
humanize_groups_value_not_valid_max:
one: "The property at JSON Pointer '%{property_json_pointer}' must have at most %{count} group id."
other: "The property at JSON Pointer '%{property_json_pointer}' must have at most %{count} group ids."
groups_value_not_valid_max:
one: "must have at most %{count} group id"
other: "must have at most %{count} group ids"
humanize_not_valid_tags_value: "The property at JSON Pointer '%{property_json_pointer}' must be an array of valid tag names."
not_valid_tags_value: "must be an array of valid tag names"
humanize_tags_value_not_valid_min: "The property at JSON Pointer '%{property_json_pointer}' must have at least %{min} tag names."
tags_value_not_valid_min: "must have at least %{min} tag names"
humanize_tags_value_not_valid_max: "The property at JSON Pointer '%{property_json_pointer}' must have at most %{max} tag names."
tags_value_not_valid_max: "must have at most %{max} tag names"
humanize_tags_value_not_valid_min:
one: "The property at JSON Pointer '%{property_json_pointer}' must have at least %{count} tag name."
other: "The property at JSON Pointer '%{property_json_pointer}' must have at least %{count} tag names."
tags_value_not_valid_min:
one: "must have at least %{count} tag name"
other: "must have at least %{count} tag names"
humanize_tags_value_not_valid_max:
one: "The property at JSON Pointer '%{property_json_pointer}' must have at most %{count} tag name."
other: "The property at JSON Pointer '%{property_json_pointer}' must have at most %{count} tag names."
tags_value_not_valid_max:
one: "must have at most %{count} tag name"
other: "must have at most %{count} tag names"
humanize_not_valid_upload_value: "The property at JSON Pointer '%{property_json_pointer}' must be a valid upload id."
not_valid_upload_value: "must be a valid upload id"
humanize_string_value_not_valid_min: "The property at JSON Pointer '%{property_json_pointer}' must be at least %{min} characters long."
string_value_not_valid_min: "must be at least %{min} characters long"
humanize_string_value_not_valid_max: "The property at JSON Pointer '%{property_json_pointer}' must be at most %{max} characters long."
string_value_not_valid_max: "must be at most %{max} characters long"
humanize_string_value_not_valid_min:
one: "The property at JSON Pointer '%{property_json_pointer}' must be at least %{count} character long."
other: "The property at JSON Pointer '%{property_json_pointer}' must be at least %{count} characters long."
string_value_not_valid_min:
one: "must be at least %{count} character long"
other: "must be at least %{count} characters long"
humanize_string_value_not_valid_max:
one: "The property at JSON Pointer '%{property_json_pointer}' must be at most %{count} character long."
other: "The property at JSON Pointer '%{property_json_pointer}' must be at most %{count} characters long."
string_value_not_valid_max:
one: "must be at most %{count} character long"
other: "must be at most %{count} characters long"
humanize_number_value_not_valid_min: "The property at JSON Pointer '%{property_json_pointer}' must be larger than or equal to %{min}."
number_value_not_valid_min: "must be larger than or equal to %{min}"
@ -240,7 +276,9 @@ en:
format: ! "%{attribute} %{message}"
format_with_full_message: "<b>%{attribute}</b>: %{message}"
messages:
too_long_validation: "is limited to %{max} characters; you entered %{length}."
too_long_validation:
one: "is limited to %{count} character; you entered %{length}."
other: "is limited to %{count} characters; you entered %{length}."
invalid_boolean: "Invalid boolean."
taken: "has already been taken"
accepted: must be accepted
@ -2604,8 +2642,12 @@ en:
must_include_latest: "Top menu must include the 'latest' tab."
invalid_string: "Invalid value."
invalid_string_min_max: "Must be between %{min} and %{max} characters."
invalid_string_min: "Must be at least %{min} characters."
invalid_string_max: "Must be no more than %{max} characters."
invalid_string_min:
one: "Must be at least %{count} character."
other: "Must be at least %{count} characters."
invalid_string_max:
one: "Must be no more than %{count} character."
other: "Must be no more than %{count} characters."
invalid_json: "Invalid JSON."
invalid_reply_by_email_address: "Value must contain '%{reply_key}' and be different from the notification email."
invalid_alternative_reply_by_email_addresses: "All values must contain '%{reply_key}' and be different from the notification email."
@ -2897,8 +2939,12 @@ en:
new_user_typed_too_fast: "New user typed too fast"
content_matches_auto_silence_regex: "Content matches auto silence regex"
username:
short: "must be at least %{min} characters"
long: "must be no more than %{max} characters"
short:
one: "must be at least %{count} character"
other: "must be at least %{count} characters"
long:
one: "must be no more than %{count} character"
other: "must be no more than %{count} characters"
too_long: "is too long"
characters: "must only include numbers, letters, dashes, dots, and underscores"
unique: "must be unique"

View File

@ -169,22 +169,22 @@ class ThemeSettingsObjectValidator
end
if (min = validations&.dig(:min)) && value.length < min
add_error(property_name, :"#{type}_value_not_valid_min", min:)
add_error(property_name, :"#{type}_value_not_valid_min", count: min)
return false
end
if (max = validations&.dig(:max)) && value.length > max
add_error(property_name, :"#{type}_value_not_valid_max", max:)
add_error(property_name, :"#{type}_value_not_valid_max", count: max)
return false
end
when "string"
if (min = validations&.dig(:min_length)) && value.length < min
add_error(property_name, :string_value_not_valid_min, min:)
add_error(property_name, :string_value_not_valid_min, count: min)
return false
end
if (max = validations&.dig(:max_length)) && value.length > max
add_error(property_name, :string_value_not_valid_max, max:)
add_error(property_name, :string_value_not_valid_max, count: max)
return false
end

View File

@ -41,9 +41,9 @@ class StringSettingValidator
if @opts[:min] && @opts[:max]
I18n.t("site_settings.errors.invalid_string_min_max", min: @opts[:min], max: @opts[:max])
elsif @opts[:min]
I18n.t("site_settings.errors.invalid_string_min", min: @opts[:min])
I18n.t("site_settings.errors.invalid_string_min", count: @opts[:min])
else
I18n.t("site_settings.errors.invalid_string_max", max: @opts[:max])
I18n.t("site_settings.errors.invalid_string_max", count: @opts[:max])
end
elsif @json_fail
I18n.t("site_settings.errors.invalid_json")

View File

@ -8,7 +8,7 @@ class StrippedLengthValidator < ActiveModel::EachValidator
record.errors.add attribute,
I18n.t(
"errors.messages.too_long_validation",
max: range.end,
count: range.end,
length: value.length,
)
else

View File

@ -777,7 +777,7 @@ RSpec.describe ThemeSettingsObjectValidator do
expect(errors.keys).to eq(["/tags_property"])
expect(errors["/tags_property"].full_messages).to contain_exactly(
"must have at least 1 tag names",
"must have at least 1 tag name",
)
errors =
@ -912,7 +912,7 @@ RSpec.describe ThemeSettingsObjectValidator do
expect(errors.keys).to eq(["/group_property"])
expect(errors["/group_property"].full_messages).to contain_exactly(
"must have at least 1 group ids",
"must have at least 1 group id",
)
errors =
@ -1154,7 +1154,7 @@ RSpec.describe ThemeSettingsObjectValidator do
expect(errors.keys).to eq(["/category_property"])
expect(errors["/category_property"].full_messages).to contain_exactly(
"must have at least 1 category ids",
"must have at least 1 category id",
)
end

View File

@ -29,7 +29,7 @@ RSpec.describe ThemeSettingsValidator do
)
expect(errors).to contain_exactly(
"The property at JSON Pointer '/0/name' must be at most 1 characters long.",
"The property at JSON Pointer '/0/name' must be at most 1 character long.",
)
end
end

View File

@ -47,7 +47,7 @@ RSpec.describe UsernameValidator do
expect_invalid(
*usernames,
error_message: I18n.t(:"user.username.short", min: min_username_length),
error_message: I18n.t(:"user.username.short", count: min_username_length),
)
end
@ -62,7 +62,7 @@ RSpec.describe UsernameValidator do
expect_invalid(
"a" * (max_username_length + 1),
error_message: I18n.t(:"user.username.long", max: max_username_length),
error_message: I18n.t(:"user.username.long", count: max_username_length),
failure_reason: "Should be invalid as username length > #{max_username_length}",
)
end
@ -154,7 +154,7 @@ RSpec.describe UsernameValidator do
expect_invalid(
*usernames,
error_message: I18n.t(:"user.username.short", min: min_username_length),
error_message: I18n.t(:"user.username.short", count: min_username_length),
)
end
@ -170,7 +170,7 @@ RSpec.describe UsernameValidator do
expect_invalid(
"ם" * (max_username_length + 1),
"äl" * (max_username_length + 1),
error_message: I18n.t(:"user.username.long", max: max_username_length),
error_message: I18n.t(:"user.username.long", count: max_username_length),
failure_reason: "Should be invalid as username length are > #{max_username_length}",
)
end

View File

@ -1739,7 +1739,7 @@ RSpec.describe UsersController do
body = response.parsed_body
expect(body["errors"].first).to include(
I18n.t("user.username.short", min: User.username_length.begin),
I18n.t("user.username.short", count: User.username_length.begin),
)
expect(user.reload.username).to eq(old_username)
@ -1893,7 +1893,7 @@ RSpec.describe UsersController do
it 'should return the "too long" message' do
expect(response.status).to eq(200)
expect(response.parsed_body["errors"]).to include(
I18n.t(:"user.username.long", max: SiteSetting.max_username_length),
I18n.t(:"user.username.long", count: SiteSetting.max_username_length),
)
end
end