[Proposal] Add Protocol.assert_impl?/2

25 views
Skip to first unread message

thia.md...@gmail.com

unread,
Sep 26, 2020, 6:25:19 PM9/26/20
to elixir-lang-core
Currently we have in the stdlib Protocol.assert_impl!/2 that raises an exception if the given module does not implement the protocol.

I think would be nice if we had a function with a similar behavior, used to check if the module implements a protocol, but return true or false.

The use case that I have in mind, to use this function, is when serializing values that may be structs would be useful to just add a simple if/else to check if it implements a behavior like String.Chars or Enumerable.

To implement this kind of functionality today I would need to try/rescue.

# enumerable
def serialize(data) when is_map(data) do
  data
  |> Enum.map(fn {key, value} -> {serialize_key(key), serialize(value)} end)
  |> Enum.into(%{})
rescue
  Protocol.UndefinedError -> serialize_struct(value)
end

# String.Chars
def serialize_string(%mod{} = value)
  try do
    Protocol.assert_impl!(String.Chars, mod)
    to_string(value)
  rescue
    Protocol.UndefinedError -> serialize_struct(value)
  end
end


Does it makes sense? Am I missing something? A predicate function to check if a protocol is implemented would be something acceptable in the stdlib?

Greg Vaughn

unread,
Sep 26, 2020, 7:31:18 PM9/26/20
to elixir-l...@googlegroups.com
Each protocol module has an `impl_for/1` function that returns the implementation module or nil which works in a truthy/falsey check. So for example:

iex(26)> String.Chars.impl_for("foo")
String.Chars.BitString
iex(27)> String.Chars.impl_for({:foo})
nil

More details here https://hexdocs.pm/elixir/1.10.4/Protocol.html#module-reflection

-Greg Vaughn
> --
> You received this message because you are subscribed to the Google Groups "elixir-lang-core" group.
> To unsubscribe from this group and stop receiving emails from it, send an email to elixir-lang-co...@googlegroups.com.
> To view this discussion on the web visit https://groups.google.com/d/msgid/elixir-lang-core/6830a5fa-9989-433e-a7e7-24d5537ae5f0n%40googlegroups.com.

Thiago Santos

unread,
Sep 27, 2020, 10:40:21 AM9/27/20
to elixir-l...@googlegroups.com
Thanks Greg, I was indeed missing something. The impl_for function covers all my current use cases.

Reply all
Reply to author
Forward
0 new messages