mirror of
https://github.com/discourse/discourse.git
synced 2025-02-25 18:55:32 -06:00
DEV: First pass of ThemeSettingsObjectValidator (#25624)
Why this change? This is a first pass at adding an objects validator which main's job is to validate an object against a defined schema which we will support. In this pass, we are simply validating that properties that has been marked as required are present in the object.
This commit is contained in:
parent
ae24e04a5e
commit
64b4e0d08d
@ -134,6 +134,8 @@ en:
|
||||
string_value_not_valid_min_max: "It must be between %{min} and %{max} characters long."
|
||||
string_value_not_valid_min: "It must be at least %{min} characters long."
|
||||
string_value_not_valid_max: "It must be at most %{max} characters long."
|
||||
objects:
|
||||
required: "must be present"
|
||||
locale_errors:
|
||||
top_level_locale: "The top level key in a locale file must match the locale name"
|
||||
invalid_yaml: "Translation YAML invalid"
|
||||
|
39
lib/theme_settings_object_validator.rb
Normal file
39
lib/theme_settings_object_validator.rb
Normal file
@ -0,0 +1,39 @@
|
||||
# frozen_string_literal: true
|
||||
|
||||
class ThemeSettingsObjectValidator
|
||||
def initialize(schema:, object:)
|
||||
@object = object
|
||||
@schema_name = schema[:name]
|
||||
@properties = schema[:properties]
|
||||
@errors = {}
|
||||
end
|
||||
|
||||
def validate
|
||||
validate_required_properties
|
||||
|
||||
@properties.each do |property_name, property_attributes|
|
||||
if property_attributes[:type] == "objects"
|
||||
@object[property_name]&.each do |child_object|
|
||||
@errors[property_name] ||= []
|
||||
|
||||
@errors[property_name].push(
|
||||
self.class.new(schema: property_attributes[:schema], object: child_object).validate,
|
||||
)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
@errors
|
||||
end
|
||||
|
||||
private
|
||||
|
||||
def validate_required_properties
|
||||
@properties.each do |property_name, property_attributes|
|
||||
if property_attributes[:required] && @object[property_name].nil?
|
||||
@errors[property_name] ||= []
|
||||
@errors[property_name] << I18n.t("themes.settings_errors.objects.required")
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
72
spec/lib/theme_settings_object_validator_spec.rb
Normal file
72
spec/lib/theme_settings_object_validator_spec.rb
Normal file
@ -0,0 +1,72 @@
|
||||
# frozen_string_literal: true
|
||||
|
||||
RSpec.describe ThemeSettingsObjectValidator do
|
||||
describe "#validate" do
|
||||
it "should return the right array of error messages when properties are required but missing" do
|
||||
schema = {
|
||||
name: "section",
|
||||
properties: {
|
||||
title: {
|
||||
type: "string",
|
||||
required: true,
|
||||
},
|
||||
description: {
|
||||
type: "string",
|
||||
required: true,
|
||||
},
|
||||
links: {
|
||||
type: "objects",
|
||||
schema: {
|
||||
name: "link",
|
||||
properties: {
|
||||
name: {
|
||||
type: "string",
|
||||
required: true,
|
||||
},
|
||||
child_links: {
|
||||
type: "objects",
|
||||
schema: {
|
||||
name: "child_link",
|
||||
properties: {
|
||||
title: {
|
||||
type: "string",
|
||||
required: true,
|
||||
},
|
||||
not_required: {
|
||||
type: "string",
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
}
|
||||
|
||||
errors = described_class.new(schema:, object: {}).validate
|
||||
|
||||
expect(errors).to eq(title: ["must be present"], description: ["must be present"])
|
||||
|
||||
errors =
|
||||
described_class.new(
|
||||
schema: schema,
|
||||
object: {
|
||||
links: [{ child_links: [{}, {}] }, {}],
|
||||
},
|
||||
).validate
|
||||
|
||||
expect(errors).to eq(
|
||||
title: ["must be present"],
|
||||
description: ["must be present"],
|
||||
links: [
|
||||
{
|
||||
name: ["must be present"],
|
||||
child_links: [{ title: ["must be present"] }, { title: ["must be present"] }],
|
||||
},
|
||||
{ name: ["must be present"] },
|
||||
],
|
||||
)
|
||||
end
|
||||
end
|
||||
end
|
Loading…
Reference in New Issue
Block a user