Skip to content
This repository was archived by the owner on Nov 8, 2022. It is now read-only.

refactor(editor-validator): improve schema validator code #291

Merged
merged 2 commits into from
Feb 24, 2021
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
36 changes: 36 additions & 0 deletions lib/helper/utils.ex
Original file line number Diff line number Diff line change
Expand Up @@ -246,4 +246,40 @@ defmodule Helper.Utils do
end

def str_occurence(_, _), do: "must be strings"

@spec large_than(String.t() | Integer.t(), Integer.t()) :: true | false
def large_than(value, target) when is_binary(value) and is_integer(target) do
String.length(value) >= target
end

def large_than(value, target) when is_integer(value) and is_integer(target) do
value >= target
end

@spec large_than(String.t() | Integer.t(), Integer.t(), :no_equal) :: true | false
def large_than(value, target, :no_equal) when is_binary(value) and is_integer(target) do
String.length(value) > target
end

def large_than(value, target, :no_equal) when is_integer(value) and is_integer(target) do
value > target
end

@spec less_than(String.t() | Integer.t(), Integer.t()) :: true | false
def less_than(value, target) when is_binary(value) and is_integer(target) do
String.length(value) <= target
end

def less_than(value, target) when is_integer(value) and is_integer(target) do
value <= target
end

@spec less_than(String.t() | Integer.t(), Integer.t(), :no_equal) :: true | false
def less_than(value, target, :no_equal) when is_binary(value) and is_integer(target) do
String.length(value) < target
end

def less_than(value, target, :no_equal) when is_integer(value) and is_integer(target) do
value < target
end
end
7 changes: 7 additions & 0 deletions lib/helper/validator/guards.ex
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
defmodule Helper.Validator.Guards do
@moduledoc """
general guards
"""
defguard g_pos_int(value) when is_integer(value) and value >= 0
defguard g_not_nil(value) when not is_nil(value)
end
36 changes: 15 additions & 21 deletions lib/helper/validator/schema.ex
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,13 @@ defmodule Helper.Validator.Schema do
data = %{checked: true, label: "done"}
Schema.cast(schema, data)
"""

alias Helper.Utils
import Helper.Validator.Guards, only: [g_pos_int: 1, g_not_nil: 1]

@support_min [:string, :number]

@spec cast(map, map) :: {:ok, :pass} | {:error, map}
def cast(schema, data) do
errors_info = cast_errors(schema, data)

Expand Down Expand Up @@ -62,11 +69,8 @@ defmodule Helper.Validator.Schema do
{:ok, value}

false ->
{:error,
%{
field: field,
message: "should be: #{enum |> Enum.join(" | ")}"
}}
msg = %{field: field, message: "should be: #{enum |> Enum.join(" | ")}"}
{:error, msg}
end
end

Expand All @@ -78,22 +82,11 @@ defmodule Helper.Validator.Schema do
end

# custom validate logic
defp match(field, value, :string, [{:min, min} | options])
when is_binary(value) and is_integer(min) do
case String.length(value) >= min do
true ->
match(field, value, :string, options)

false ->
error(field, value, :min, min)
end
end

defp match(field, value, :number, [{:min, min} | options])
when is_integer(value) and is_integer(min) do
case value >= min do
defp match(field, value, type, [{:min, min} | options])
when type in @support_min and g_not_nil(value) and g_pos_int(min) do
case Utils.large_than(value, min) do
true ->
match(field, value, :number, options)
match(field, value, type, options)

false ->
error(field, value, :min, min)
Expand All @@ -109,13 +102,14 @@ defmodule Helper.Validator.Schema do
defp match(field, value, :boolean, []) when is_boolean(value), do: done(field, value)
# main type end

# judge option
# error for option
defp match(field, value, type, [option]) when is_tuple(option) do
# 如果这里不判断的话会和下面的 match 冲突,是否有更好的写法?
case option_valid?(option) do
true ->
error(field, value, type)

# unknow option or option not valid
false ->
{k, v} = option
error(field, value, option: "#{to_string(k)}: #{to_string(v)}")
Expand Down
34 changes: 34 additions & 0 deletions test/helper/utils_test.exs
Original file line number Diff line number Diff line change
Expand Up @@ -128,4 +128,38 @@ defmodule GroupherServer.Test.Helper.UtilsTest do
assert 0 == Utils.str_occurence("hello world", "foo")
end
end

describe "[basic compare]" do
test "large_than work for both number and string" do
assert true == Utils.large_than(10, 9)
assert false == Utils.large_than(8, 9)

assert true == Utils.large_than("lang", 3)
assert false == Utils.large_than("ok", 3)
end

test "large_than equal case" do
assert true == Utils.large_than(9, 9)
assert false == Utils.large_than(9, 9, :no_equal)

assert true == Utils.large_than("lang", 4)
assert false == Utils.large_than("lang", 4, :no_equal)
end

test "less_than work for both number and string" do
assert false == Utils.less_than(10, 9)
assert true == Utils.less_than(8, 9)

assert false == Utils.less_than("lang", 3)
assert true == Utils.less_than("ok", 3)
end

test "less_than equal case" do
assert true == Utils.less_than(9, 9)
assert false == Utils.less_than(9, 9, :no_equal)

assert true == Utils.less_than("lang", 4)
assert false == Utils.less_than("lang", 4, :no_equal)
end
end
end
1 change: 0 additions & 1 deletion test/helper/validator/schema_test.exs
Original file line number Diff line number Diff line change
Expand Up @@ -85,7 +85,6 @@ defmodule GroupherServer.Test.Helper.Validator.Schema do
# hello world
end

@tag :wip2
test "number with wrong option" do
schema = %{"text" => [:number, required: true, min: "5"]}
data = %{"text" => 1}
Expand Down