Code.require_file "../helpers/module_info.exs", __DIR__ defmodule Alchemist.API.Docl do @moduledoc false import IEx.Helpers, warn: false alias Alchemist.Helpers.ModuleInfo def request(args) do Application.put_env(:iex, :colors, [enabled: true]) args |> normalize |> process IO.puts "END-OF-DOCL" end def process([expr, modules, aliases]) do search(expr, modules, aliases) end def search(nil), do: true def search(expr) do try do Code.eval_string("h(#{expr})", [], __ENV__) rescue _e -> nil end end def search(expr, modules, []) do expr = to_string expr unless function?(expr) do search(expr) else search_with_context(modules, expr) end end def search(expr, modules, aliases) do unless function?(expr) do String.split(expr, ".") |> ModuleInfo.expand_alias(aliases) |> search else search_with_context(modules, expr) end end defp search_with_context(modules, expr) do modules ++ [Kernel, Kernel.SpecialForms] |> build_search(expr) |> search end defp build_search(modules, search) do function = Regex.replace(~r/\/[0-9]$/, search, "") function = String.to_atom(function) for module <- modules, ModuleInfo.docs?(module, function) do "#{module}.#{search}" end |> List.first end defp function?(expr) do Regex.match?(~r/^[a-z_]/, expr) end defp normalize(request) do {{expr, [ context: _, imports: imports, aliases: aliases]}, _} = Code.eval_string(request) [expr, imports, aliases] end end