Skip to content

Commit

Permalink
[wip] Add schema fragment for error structs
Browse files Browse the repository at this point in the history
  • Loading branch information
jonasschmidt committed May 6, 2021
1 parent 56fb1e4 commit a1afc40
Show file tree
Hide file tree
Showing 31 changed files with 102 additions and 46 deletions.
2 changes: 1 addition & 1 deletion lib/ex_json_schema/validator.ex
Original file line number Diff line number Diff line change
Expand Up @@ -70,7 +70,7 @@ defmodule ExJsonSchema.Validator do
end

def validation_errors(%Root{}, false, _data, path) do
[%Error{error: %Error.False{}, path: path}]
[%Error{error: %Error.False{}, fragment: false, path: path}]
end

def validation_errors(root = %Root{}, schema = %{}, data, path) do
Expand Down
2 changes: 1 addition & 1 deletion lib/ex_json_schema/validator/all_of.ex
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@ defmodule ExJsonSchema.Validator.AllOf do

case Enum.empty?(invalid) do
true -> []
false -> [%Error{error: %Error.AllOf{invalid: invalid}}]
false -> [%Error{error: %Error.AllOf{invalid: invalid}, fragment: all_of}]
end
end
end
2 changes: 1 addition & 1 deletion lib/ex_json_schema/validator/any_of.ex
Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,7 @@ defmodule ExJsonSchema.Validator.AnyOf do

case Enum.empty?(invalid) do
true -> []
false -> [%Error{error: %Error.AnyOf{invalid: invalid}}]
false -> [%Error{error: %Error.AnyOf{invalid: invalid}, fragment: any_of}]
end
end

Expand Down
2 changes: 1 addition & 1 deletion lib/ex_json_schema/validator/const.ex
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ defmodule ExJsonSchema.Validator.Const do
if const == data do
[]
else
[%Error{error: %Error.Const{expected: const}}]
[%Error{error: %Error.Const{expected: const}, fragment: const}]
end
end
end
11 changes: 7 additions & 4 deletions lib/ex_json_schema/validator/contains.ex
Original file line number Diff line number Diff line change
Expand Up @@ -22,8 +22,8 @@ defmodule ExJsonSchema.Validator.Contains do
[]
end

defp do_validate(_, _, [], _) do
[%Error{error: %Error.Contains{empty?: true, invalid: []}}]
defp do_validate(_, contains, [], _) do
[%Error{error: %Error.Contains{empty?: true, invalid: []}, fragment: contains}]
end

defp do_validate(root, contains, data, path) when is_list(data) do
Expand All @@ -41,8 +41,11 @@ defmodule ExJsonSchema.Validator.Contains do
|> Validator.map_to_invalid_errors()

case Enum.empty?(invalid) do
true -> []
false -> [%Error{error: %Error.Contains{empty?: false, invalid: invalid}}]
true ->
[]

false ->
[%Error{error: %Error.Contains{empty?: false, invalid: invalid}, fragment: contains}]
end
end

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,25 +21,38 @@ defmodule ExJsonSchema.Validator.ContentEncodingContentMediaType do
[]
end

defp validate_content_encoding("base64", data) when is_bitstring(data) do
defp validate_content_encoding("base64" = encoding, data) when is_bitstring(data) do
case Base.decode64(data) do
{:ok, decoded_data} -> {[], decoded_data}
:error -> {[%Error{error: %Error.ContentEncoding{expected: "base64"}}], data}
{:ok, decoded_data} ->
{[], decoded_data}

:error ->
{[%Error{error: %Error.ContentEncoding{expected: "base64"}, fragment: encoding}], data}
end
end

defp validate_content_encoding(_, data) do
{[], data}
end

defp validate_content_media_type(%{"contentMediaType" => "application/json"}, data, errors)
defp validate_content_media_type(
%{"contentMediaType" => "application/json" = content_media_type},
data,
errors
)
when is_bitstring(data) do
case ExJsonSchema.Schema.decode_json(data) do
{:ok, _} ->
errors

{:error, _} ->
errors ++ [%Error{error: %Error.ContentMediaType{expected: "application/json"}}]
errors ++
[
%Error{
error: %Error.ContentMediaType{expected: "application/json"},
fragment: content_media_type
}
]
end
end

Expand Down
7 changes: 6 additions & 1 deletion lib/ex_json_schema/validator/dependencies.ex
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,12 @@ defmodule ExJsonSchema.Validator.Dependencies do
[]

missing ->
[%Error{error: %Error.Dependencies{property: property, missing: missing}}]
[
%Error{
error: %Error.Dependencies{property: property, missing: missing},
fragment: dependencies
}
]
end
end
end
2 changes: 1 addition & 1 deletion lib/ex_json_schema/validator/enum.ex
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ defmodule ExJsonSchema.Validator.Enum do
defp do_validate(enum, data) when is_list(enum) do
case Enum.any?(enum, &(&1 == data)) do
true -> []
false -> [%Error{error: %Error.Enum{}}]
false -> [%Error{error: %Error.Enum{}, fragment: enum}]
end
end

Expand Down
2 changes: 1 addition & 1 deletion lib/ex_json_schema/validator/error.ex
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
defmodule ExJsonSchema.Validator.Error do
defstruct [:error, :path]
defstruct [:error, :fragment, :path]

defmodule AdditionalItems do
defstruct([:additional_indices])
Expand Down
2 changes: 1 addition & 1 deletion lib/ex_json_schema/validator/exclusive_maximum.ex
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ defmodule ExJsonSchema.Validator.ExclusiveMaximum do
if data < maximum do
[]
else
[%Error{error: %Error.Maximum{expected: maximum, exclusive?: true}}]
[%Error{error: %Error.Maximum{expected: maximum, exclusive?: true}, fragment: maximum}]
end
end

Expand Down
2 changes: 1 addition & 1 deletion lib/ex_json_schema/validator/exclusive_minimum.ex
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,7 @@ defmodule ExJsonSchema.Validator.ExclusiveMinimum do
if data > minimum do
[]
else
[%Error{error: %Error.Minimum{expected: minimum, exclusive?: true}}]
[%Error{error: %Error.Minimum{expected: minimum, exclusive?: true}, fragment: minimum}]
end
end

Expand Down
8 changes: 4 additions & 4 deletions lib/ex_json_schema/validator/format.ex
Original file line number Diff line number Diff line change
Expand Up @@ -78,14 +78,14 @@ defmodule ExJsonSchema.Validator.Format do
] do
case Regex.match?(@formats[format], data) do
true -> []
false -> [%Error{error: %Error.Format{expected: format}}]
false -> [%Error{error: %Error.Format{expected: format}, fragment: format}]
end
end

defp do_validate(_, "regex", data) do
defp do_validate(_, "regex" = format, data) do
case Regex.compile(data) do
{:ok, _} -> []
{:error, _} -> [%Error{error: %Error.Format{expected: "regex"}}]
{:error, _} -> [%Error{error: %Error.Format{expected: "regex"}, fragment: format}]
end
end

Expand All @@ -103,7 +103,7 @@ defmodule ExJsonSchema.Validator.Format do
defp validate_with_custom_validator({mod, fun}, format, data) do
case apply(mod, fun, [format, data]) do
true -> []
false -> [%Error{error: %Error.Format{expected: format}}]
false -> [%Error{error: %Error.Format{expected: format}, fragment: format}]
end
end
end
7 changes: 5 additions & 2 deletions lib/ex_json_schema/validator/if_then_else.ex
Original file line number Diff line number Diff line change
Expand Up @@ -56,8 +56,11 @@ defmodule ExJsonSchema.Validator.IfThenElse do

defp validation_errors(root, schema, data, branch) do
case Validator.validation_errors(root, schema, data) do
[] -> []
errors -> [%Error{error: %Error.IfThenElse{branch: branch, errors: errors}}]
[] ->
[]

errors ->
[%Error{error: %Error.IfThenElse{branch: branch, errors: errors}, fragment: schema}]
end
end
end
5 changes: 3 additions & 2 deletions lib/ex_json_schema/validator/items.ex
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,7 @@ defmodule ExJsonSchema.Validator.Items do
end

defp do_validate(_, %{"items" => false}, _, _) do
[%Error{error: %Error.ItemsNotAllowed{}}]
[%Error{error: %Error.ItemsNotAllowed{}, fragment: false}]
end

defp do_validate(root, %{"items" => schema = %{}}, items, path) when is_list(items) do
Expand Down Expand Up @@ -58,7 +58,8 @@ defmodule ExJsonSchema.Validator.Items do
defp validate_items(_root, {[], false}, items, {errors, index}, _) do
[
%Error{
error: %Error.AdditionalItems{additional_indices: index..(index + Enum.count(items) - 1)}
error: %Error.AdditionalItems{additional_indices: index..(index + Enum.count(items) - 1)},
fragment: false
}
| errors
]
Expand Down
2 changes: 1 addition & 1 deletion lib/ex_json_schema/validator/max_items.ex
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ defmodule ExJsonSchema.Validator.MaxItems do
if count <= max_items do
[]
else
[%Error{error: %Error.MaxItems{expected: max_items, actual: count}}]
[%Error{error: %Error.MaxItems{expected: max_items, actual: count}, fragment: max_items}]
end
end

Expand Down
7 changes: 6 additions & 1 deletion lib/ex_json_schema/validator/max_length.ex
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,12 @@ defmodule ExJsonSchema.Validator.MaxLength do
if length <= max_length do
[]
else
[%Error{error: %Error.MaxLength{expected: max_length, actual: length}}]
[
%Error{
error: %Error.MaxLength{expected: max_length, actual: length},
fragment: max_length
}
]
end
end

Expand Down
7 changes: 6 additions & 1 deletion lib/ex_json_schema/validator/max_properties.ex
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,12 @@ defmodule ExJsonSchema.Validator.MaxProperties do
if map_size(data) <= max_properties do
[]
else
[%Error{error: %Error.MaxProperties{expected: max_properties, actual: map_size(data)}}]
[
%Error{
error: %Error.MaxProperties{expected: max_properties, actual: map_size(data)},
fragment: max_properties
}
]
end
end

Expand Down
2 changes: 1 addition & 1 deletion lib/ex_json_schema/validator/maximum.ex
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,7 @@ defmodule ExJsonSchema.Validator.Maximum do
if valid do
[]
else
[%Error{error: %Error.Maximum{expected: maximum, exclusive?: exclusive}}]
[%Error{error: %Error.Maximum{expected: maximum, exclusive?: exclusive}, fragment: maximum}]
end
end

Expand Down
2 changes: 1 addition & 1 deletion lib/ex_json_schema/validator/min_items.ex
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ defmodule ExJsonSchema.Validator.MinItems do
if count >= min_items do
[]
else
[%Error{error: %Error.MinItems{expected: min_items, actual: count}}]
[%Error{error: %Error.MinItems{expected: min_items, actual: count}, fragment: min_items}]
end
end

Expand Down
7 changes: 6 additions & 1 deletion lib/ex_json_schema/validator/min_length.ex
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,12 @@ defmodule ExJsonSchema.Validator.MinLength do
if length >= min_length do
[]
else
[%Error{error: %Error.MinLength{expected: min_length, actual: length}}]
[
%Error{
error: %Error.MinLength{expected: min_length, actual: length},
fragment: min_length
}
]
end
end

Expand Down
7 changes: 6 additions & 1 deletion lib/ex_json_schema/validator/min_properties.ex
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,12 @@ defmodule ExJsonSchema.Validator.MinProperties do
if map_size(data) >= min_properties do
[]
else
[%Error{error: %Error.MinProperties{expected: min_properties, actual: map_size(data)}}]
[
%Error{
error: %Error.MinProperties{expected: min_properties, actual: map_size(data)},
fragment: min_properties
}
]
end
end

Expand Down
2 changes: 1 addition & 1 deletion lib/ex_json_schema/validator/minimum.ex
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,7 @@ defmodule ExJsonSchema.Validator.Minimum do
if valid do
[]
else
[%Error{error: %Error.Minimum{expected: minimum, exclusive?: exclusive}}]
[%Error{error: %Error.Minimum{expected: minimum, exclusive?: exclusive}, fragment: minimum}]
end
end

Expand Down
6 changes: 3 additions & 3 deletions lib/ex_json_schema/validator/multiple_of.ex
Original file line number Diff line number Diff line change
Expand Up @@ -23,9 +23,9 @@ defmodule ExJsonSchema.Validator.MultipleOf do
[]
end

defp do_validate(0, _) do
defp do_validate(0 = multiple_of, _) do
# "Expected multipleOf to be > 1."
[%Error{error: %Error.MultipleOf{expected: 0}}]
[%Error{error: %Error.MultipleOf{expected: 0}, fragment: multiple_of}]
end

defp do_validate(_, data) when not is_number(data) do
Expand All @@ -36,7 +36,7 @@ defmodule ExJsonSchema.Validator.MultipleOf do
if Float.ceil(data / multiple_of) == Float.floor(data / multiple_of) do
[]
else
[%Error{error: %Error.MultipleOf{expected: multiple_of}}]
[%Error{error: %Error.MultipleOf{expected: multiple_of}, fragment: multiple_of}]
end
end

Expand Down
2 changes: 1 addition & 1 deletion lib/ex_json_schema/validator/not.ex
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ defmodule ExJsonSchema.Validator.Not do

defp do_validate(root, not_schema, data) do
case Validator.valid_fragment?(root, not_schema, data) do
true -> [%Error{error: %Error.Not{}}]
true -> [%Error{error: %Error.Not{}, fragment: not_schema}]
false -> []
end
end
Expand Down
10 changes: 8 additions & 2 deletions lib/ex_json_schema/validator/one_of.ex
Original file line number Diff line number Diff line change
Expand Up @@ -42,12 +42,18 @@ defmodule ExJsonSchema.Validator.OneOf do
error: %Error.OneOf{
valid_indices: [],
invalid: errors |> Enum.reverse() |> Validator.map_to_invalid_errors()
}
},
fragment: one_of
}
]

_ ->
[%Error{error: %Error.OneOf{valid_indices: Enum.reverse(valid_indices), invalid: []}}]
[
%Error{
error: %Error.OneOf{valid_indices: Enum.reverse(valid_indices), invalid: []},
fragment: one_of
}
]
end
end
end
2 changes: 1 addition & 1 deletion lib/ex_json_schema/validator/pattern.ex
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ defmodule ExJsonSchema.Validator.Pattern do
if matches? do
[]
else
[%Error{error: %Error.Pattern{expected: pattern}}]
[%Error{error: %Error.Pattern{expected: pattern}, fragment: pattern}]
end
end

Expand Down
2 changes: 1 addition & 1 deletion lib/ex_json_schema/validator/properties.ex
Original file line number Diff line number Diff line change
Expand Up @@ -68,7 +68,7 @@ defmodule ExJsonSchema.Validator.Properties do

defp validate_additional_properties(_, false, properties, path) when map_size(properties) > 0 do
Enum.map(properties, fn {name, _} ->
%Error{error: %Error.AdditionalProperties{}, path: path <> "/#{name}"}
%Error{error: %Error.AdditionalProperties{}, fragment: false, path: path <> "/#{name}"}
end)
end

Expand Down
2 changes: 1 addition & 1 deletion lib/ex_json_schema/validator/property_names.ex
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@ defmodule ExJsonSchema.Validator.PropertyNames do
if map_size(invalid) == 0 do
[]
else
[%Error{error: %Error.PropertyNames{invalid: invalid}}]
[%Error{error: %Error.PropertyNames{invalid: invalid}, fragment: property_names}]
end
end

Expand Down
2 changes: 1 addition & 1 deletion lib/ex_json_schema/validator/required.ex
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ defmodule ExJsonSchema.Validator.Required do
defp do_validate(required, data = %{}) do
case Enum.filter(List.wrap(required), &(!Map.has_key?(data, &1))) do
[] -> []
missing -> [%Error{error: %Error.Required{missing: missing}}]
missing -> [%Error{error: %Error.Required{missing: missing}, fragment: required}]
end
end

Expand Down
Loading

0 comments on commit a1afc40

Please sign in to comment.