Skip to content

Commit e99e5c7

Browse files
committed
Only check actual callbacks
1 parent 7fd966d commit e99e5c7

File tree

2 files changed

+19
-8
lines changed

2 files changed

+19
-8
lines changed

lib/elixir/lib/module/types.ex

Lines changed: 16 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -130,17 +130,25 @@ defmodule Module.Types do
130130

131131
defp impl_for(attrs) do
132132
case List.keyfind(attrs, :__impl__, 0) do
133-
{:__impl__, [protocol: _, for: for]} -> for
134-
_ -> nil
135-
end
136-
end
133+
{:__impl__, [protocol: protocol, for: for]} ->
134+
if Code.ensure_loaded?(protocol) and function_exported?(protocol, :behaviour_info, 1) do
135+
{for, protocol.behaviour_info(:callbacks)}
136+
else
137+
nil
138+
end
137139

138-
defp default_domain({fun, arity}, impl) when impl != nil and fun != :__impl__ and arity >= 1 do
139-
[Module.Types.Of.impl(impl) | List.duplicate(Descr.dynamic(), arity - 1)]
140+
_ ->
141+
nil
142+
end
140143
end
141144

142-
defp default_domain({_, arity}, _) do
143-
List.duplicate(Descr.dynamic(), arity)
145+
defp default_domain({_, arity} = fun_arity, impl) do
146+
with {for, callbacks} <- impl,
147+
true <- fun_arity in callbacks do
148+
[Module.Types.Of.impl(for) | List.duplicate(Descr.dynamic(), arity - 1)]
149+
else
150+
_ -> List.duplicate(Descr.dynamic(), arity)
151+
end
144152
end
145153

146154
defp undefined_function!(reason, meta, {fun, arity}, stack, env) do

lib/elixir/test/elixir/module/types/integration_test.exs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -79,6 +79,7 @@ defmodule Module.Types.IntegrationTest do
7979
Unknown
8080
] do
8181
def itself(data), do: data
82+
def this_wont_warn(:ok), do: :ok
8283
end
8384
"""
8485
}
@@ -88,6 +89,8 @@ defmodule Module.Types.IntegrationTest do
8889
assert stderr =~
8990
"you are implementing a protocol for Unknown but said module is not available"
9091

92+
refute stderr =~ "this_wont_warn"
93+
9194
itself_arg = fn mod ->
9295
{_, %{sig: {:infer, [{[value], value}]}}} =
9396
List.keyfind(read_chunk(modules[mod]).exports, {:itself, 1}, 0)

0 commit comments

Comments
 (0)