diff --git a/README.md b/README.md index 18187a98..787fa0fb 100644 --- a/README.md +++ b/README.md @@ -204,6 +204,9 @@ Details: - [ ] Per-module or even per-spec settings to turn on/off, configure formatter, etc. ### Changelog +- 0.10.2 - + - Fixes: + - Fixes issue where FixedMaps would accept maps any maps (even those missing the required keys) sometimes. (c.f. #74) - 0.10.1 - - Fixes: - Swaps `Murmur` out for Erlang's builtin `:erlang.phash2/2` to generate data for function-types, allowing the removal of the optional dependency on the `:murmur` library. diff --git a/lib/type_check/builtin/fixed_map.ex b/lib/type_check/builtin/fixed_map.ex index 68e57dcc..df5d898b 100644 --- a/lib/type_check/builtin/fixed_map.ex +++ b/lib/type_check/builtin/fixed_map.ex @@ -27,8 +27,8 @@ defmodule TypeCheck.Builtin.FixedMap do def to_check(s, param) do res = quote generated: true, location: :keep do - with :ok <- unquote(map_check(param, s)), - :ok <- unquote(build_keys_presence_ast(s, param)), + with {:ok, _, _} <- unquote(map_check(param, s)), + {:ok, _, _} <- unquote(build_keys_presence_ast(s, param)), {:ok, bindings3, altered_param} <- unquote(build_keypairs_checks_ast(s.keypairs, param, s)) do {:ok, bindings3, altered_param} end @@ -61,7 +61,7 @@ defmodule TypeCheck.Builtin.FixedMap do case unquote(required_keys) -- actual_keys do [] -> - :ok + {:ok, [], unquote(param)} missing_keys -> {:error, diff --git a/mix.exs b/mix.exs index d3ce11e3..476af047 100644 --- a/mix.exs +++ b/mix.exs @@ -6,7 +6,7 @@ defmodule TypeCheck.MixProject do def project do [ app: :type_check, - version: "0.10.1", + version: "0.10.2", elixir: "~> 1.9", start_permanent: Mix.env() == :prod, deps: deps(), diff --git a/test/type_check/builtin/fixed_map_test.exs b/test/type_check/builtin/fixed_map_test.exs new file mode 100644 index 00000000..7e425ab8 --- /dev/null +++ b/test/type_check/builtin/fixed_map_test.exs @@ -0,0 +1,25 @@ +defmodule TypeCheck.Builtin.FixedMapTest do + use ExUnit.Case, async: true + use TypeCheck + + defmodule UnrelatedStruct do + defstruct [] + end + + # Regression test for issue #74 + test "Date.t() only accepts valid dates" do + fun = &TypeCheck.conforms(&1, Date.t()) + + + assert {:ok, _} = fun.(Date.utc_today()) + + assert {:error, _} = fun.(DateTime.utc_now()) + assert {:error, _} = fun.(%{}) + assert {:error, _} = fun.(%UnrelatedStruct{}) + + assert {:error, _} = fun.([]) + assert {:error, _} = fun.(6) + assert {:error, _} = fun.("some string") + end + +end