Magik.Contract (Magik v0.9.0) View Source
validate contract schema
Support validation
Type
Support built-in types;
booleaninteger,floatnumber- string or integerstringtuplemaparraylistatomfunctionkeywordstructarrayof type
Example:
Magik.Contract.validate(%{name: "Bluz"}, %{name: [type: :string]})
Magik.Contract.validate(%{id: 123}, %{name: [type: :integer]})
Magik.Contract.validate(%{id: 123}, %{name: [type: {:array, :integer}]})
Magik.Contract.validate(%{user: %User{}}, %{user: [type: User]})
Magik.Contract.validate(%{user: %User{}}, %{user: [type: {:array: User}]})Required
Magik.Contract.validate(%{name: "Bluz"}, %{name: [type: :string, required: true]})Allow nil
Magik.Contract.validate(
%{name: "Bluz", email: nil},
%{
name: [type: :string],
email: [type: string, allow_nil: false]
})Inclusion/Exclusion
Magik.Contract.validate(
%{status: "active"},
%{status: [type: :string, in: ~w(active in_active)]}
)
Magik.Contract.validate(
%{status: "active"},
%{status: [type: :string, not_in: ~w(banned locked)]}
)Format
Validate string against regex pattern
Magik.Contract.validate(
%{email: "Bluzblu@gm.com"},
%{name: [type: :string, format: ~r/.+?@.+.com/]
})Number
Validate number value
Magik.Contract.validate(
%{age: 200},
%{age: [type: :integer, number[greater_than: 0, less_than: 100]]
})Support conditions
equal_togreater_than_or_equal_to|mingreater_thanless_thanless_than_or_equal_to|max
Length
Check length of list, map, string, keyword, tuple
Supported condtions are the same with Number check
Magik.Contract.validate(
%{title: "Hello world"},
%{age: [type: :string, length: [min: 10, max: 100]]
})Custom validation function
Invoke given function to validate value. The function signature must be
func(field_name ::(String.t() | atom()), value :: any(), all_params :: map()) :: :ok | {:error, message}Magik.Contract.validate(
%{email: "blue@hmail.com"},
%{email: [type: :string, func: &validate_email/3]})
def validate_email(_name, email, _params) do
if Regex.match?(~r/[a-z0-9._%+-]+@[a-z0-9.-]+.[a-z]{2,4}$/, email) do
:ok
else
{:error, "not a valid email"}
end
endNested map
Nested map declaration is the same.
data = %{name: "Doe John", address: %{city: "HCM", street: "NVL"} }
schema = %{
name: [type: :string],
address: [type: %{
city: [type: :string],
street: [type: :string]
}]
}
Magik.Contract.validate(data, schema)Nested list
data = %{name: "Doe John", address: [%{city: "HCM", street: "NVL"}] }
address = %{ city: [type: :string], street: [type: :string] }
schema = %{
name: [type: :string],
address: [type: {:array, address}]
}
Magik.Contract.validate(data, schema)