diff --git a/lib/elixir/lib/module/types/descr.ex b/lib/elixir/lib/module/types/descr.ex index e0f4174161c..82cb8e68239 100644 --- a/lib/elixir/lib/module/types/descr.ex +++ b/lib/elixir/lib/module/types/descr.ex @@ -4149,6 +4149,10 @@ defmodule Module.Types.Descr do {required_keys, optional_keys, maybe_negated_set, required_domains, optional_domains} end + defp map_split_keys_and_domains(:term) do + map_split_keys_and_domains(unfolded_term()) + end + defp map_split_keys_and_domains(%{atom: {:union, atoms}} = key_descr) do {:sets.to_list(atoms), [], nil, to_domain_keys(key_descr), []} end diff --git a/lib/elixir/test/elixir/module/types/descr_test.exs b/lib/elixir/test/elixir/module/types/descr_test.exs index 1c73a3a8ae1..a3d13f0e73f 100644 --- a/lib/elixir/test/elixir/module/types/descr_test.exs +++ b/lib/elixir/test/elixir/module/types/descr_test.exs @@ -2971,6 +2971,13 @@ defmodule Module.Types.DescrTest do test "with projected negative maps" do assert map_get(projected_negative_map(100), atom([:k])) == {:ok, open_map()} end + + test "with term() key considers atom fields" do + map = closed_map(a: {integer(), false}) + assert map_get(map, term()) == {:ok, integer()} + assert map_get(map, term()) == map_get(map, atom()) + assert map_get(open_map(a: {integer(), false}), term()) == {:ok, term()} + end end describe "map_update" do @@ -3474,6 +3481,15 @@ defmodule Module.Types.DescrTest do assert type == term() assert equal?(descr, open_map(__struct__: {opt_negation(atom()), true})) end + + test "with term() key considers atom fields" do + {value, descr, _errors} = + map_update(closed_map(a: {integer(), false}), term(), atom([:x]), false) + + assert equal?(value, integer()) + assert subtype?(closed_map(a: {atom([:x]), false}), descr) + assert subtype?(closed_map(a: {integer(), false}), descr) + end end describe "map_put" do @@ -3781,6 +3797,12 @@ defmodule Module.Types.DescrTest do assert map_put(none(), atom([:a]), integer()) == :badmap assert map_put(a2, atom([:a]), integer()) == :badmap end + + test "with term() key considers atom fields" do + {:ok, descr} = map_put(closed_map(a: {integer(), false}), term(), pid()) + assert subtype?(closed_map(a: {pid(), false}), descr) + assert subtype?(closed_map(a: {integer(), false}), descr) + end end describe "disjoint" do