如何在elixir中验证url?

时间:2016-08-19 14:18:51

标签: elixir

我想验证uris:

http://vk.com
http://semantic-ui.com/collections/menu.html
https://translate.yandex.ru/?text=poll&lang=en-ru

而不是

www.vk.com
abdeeej
http://vk

但是没有找到任何本机代码包的实现。

我该怎么做?

2 个答案:

答案 0 :(得分:3)

根据规范,所有这些都是技术上有效的网址,因此URI.parse/1会为所有人返回%URI{}结构,但是如果您要拒绝没有scheme的网址和host,你可以这样做:

valid? = fn url ->
  uri = URI.parse(url)
  uri.scheme != nil && uri.host =~ "."
end

测试:

urls = [
  "http://vk.com",
  "http://semantic-ui.com/collections/menu.html",
  "https://translate.yandex.ru/?text=poll&lang=en-ru",
  "www.vk.com",
  "abdeeej",
  "http://vk"
]

urls |> Enum.map(valid?) |> IO.inspect

输出:

[true, true, true, false, false, false]

答案 1 :(得分:0)

此解决方案更完整:

  def validate_url(changeset, field, opts \\ []) do
    validate_change(changeset, field, fn _, value ->
      case URI.parse(value) do
        val(%URI{scheme: nil}) ->
          "is missing a scheme (e.g. https)"

        %URI{host: nil} ->
          "is missing a host"

        %URI{host: host} ->
          case :inet.gethostbyname(Kernel.to_charlist(host)) do
            {:ok, _} -> nil
            {:error, _} -> "invalid host"
          end
      end
      |> case do
        error when is_binary(error) -> [{field, Keyword.get(opts, :message, error)}]
        _ -> []
      end
    end)
  end

https://gist.github.com/atomkirk/74b39b5b09c7d0f21763dd55b877f998铺入