defmodule Couch.Session do
  @moduledoc """
  CouchDB session helpers.
  """

  defstruct [:cookie, :error]

  def new(cookie, error \\ "") do
    %Couch.Session{cookie: cookie, error: error}
  end

  def logout(sess) do
    headers = [
      "Content-Type": "application/x-www-form-urlencoded",
      "X-CouchDB-WWW-Authenticate": "Cookie",
      Cookie: sess.cookie
    ]

    Couch.delete!("/_session", headers: headers)
  end

  def info(sess) do
    headers = [
      "Content-Type": "application/x-www-form-urlencoded",
      "X-CouchDB-WWW-Authenticate": "Cookie",
      Cookie: sess.cookie
    ]

    Couch.get("/_session", headers: headers).body
  end

  def get(sess, url, opts \\ []), do: go(sess, :get, url, opts)
  def get!(sess, url, opts \\ []), do: go!(sess, :get, url, opts)
  def put(sess, url, opts \\ []), do: go(sess, :put, url, opts)
  def put!(sess, url, opts \\ []), do: go!(sess, :put, url, opts)
  def post(sess, url, opts \\ []), do: go(sess, :post, url, opts)
  def post!(sess, url, opts \\ []), do: go!(sess, :post, url, opts)
  def delete(sess, url, opts \\ []), do: go(sess, :delete, url, opts)
  def delete!(sess, url, opts \\ []), do: go!(sess, :delete, url, opts)

  # Skipping head/patch/options for YAGNI. Feel free to add
  # if the need arises.
  def go(%Couch.Session{} = sess, method, url, opts) do
    parse_response = Keyword.get(opts, :parse_response, true)
    opts = opts
           |> Keyword.merge(cookie: sess.cookie)
           |> Keyword.delete(:parse_response)
    if parse_response do
      Couch.request(method, url, opts)
    else
      Rawresp.request(method, url, opts)
    end
  end

  def go!(%Couch.Session{} = sess, method, url, opts) do
    parse_response = Keyword.get(opts, :parse_response, true)
    opts = opts
           |> Keyword.merge(cookie: sess.cookie)
           |> Keyword.delete(:parse_response)
    if parse_response do
      Couch.request!(method, url, opts)
    else
      Rawresp.request!(method, url, opts)
    end
  end
end

defmodule Couch do
  use HTTPotion.Base

  @moduledoc """
  CouchDB library to power test suite.
  """

  # These constants are supplied to the underlying HTTP client and control
  # how long we will wait before timing out a test. The inactivity timeout
  # specifically fires during an active HTTP response and defaults to 10_000
  # if not specified. We're defining it to a different value than the
  # request_timeout largely just so we know which timeout fired.
  @request_timeout 60_000
  @inactivity_timeout 55_000

  def process_url("http://" <> _ = url) do
    url
  end

  def process_url(url) do
    base_url = System.get_env("EX_COUCH_URL") || "http://127.0.0.1:15984"
    base_url <> url
  end

  def process_request_headers(headers, _body, options) do
    headers = Keyword.put(headers, :"User-Agent", "couch-potion")

    headers =
      if headers[:"Content-Type"] do
        headers
      else
        Keyword.put(headers, :"Content-Type", "application/json")
      end

    case Keyword.get(options, :cookie) do
      nil ->
        headers

      cookie ->
        Keyword.put(headers, :Cookie, cookie)
    end
  end

  def process_options(options) do
    options
     |> set_auth_options()
     |> set_inactivity_timeout()
     |> set_request_timeout()
  end

  def process_request_body(body) do
    if is_map(body) do
      :jiffy.encode(body, [:use_nil])
    else
      body
    end
  end

  def process_response_body(_headers, body) when body == [] do
    ""
  end

  def process_response_body(headers, body) do
    content_type = headers[:"Content-Type"]

    if !!content_type and String.match?(content_type, ~r/application\/json/) do
      body |> IO.iodata_to_binary() |> :jiffy.decode([:return_maps, :use_nil])
    else
      process_response_body(body)
    end
  end

  def set_auth_options(options) do
    cond do
      Keyword.get(options, :no_auth, false) ->
        options
      Keyword.get(options, :cookie) == nil ->
        headers = Keyword.get(options, :headers, [])
        if headers[:basic_auth] != nil or headers[:authorization] != nil
          or List.keymember?(headers, :"X-Auth-CouchDB-UserName", 0) do
          options
        else
          username = System.get_env("EX_USERNAME") || "adm"
          password = System.get_env("EX_PASSWORD") || "pass"
          Keyword.put(options, :basic_auth, {username, password})
        end
      true ->
        options
    end
  end

  def set_inactivity_timeout(options) do
    Keyword.update(
      options,
      :ibrowse,
      [{:inactivity_timeout, @inactivity_timeout}],
      fn ibrowse ->
        Keyword.put_new(ibrowse, :inactivity_timeout, @inactivity_timeout)
      end
    )
  end

  def set_request_timeout(options) do
    timeout = Application.get_env(:httpotion, :default_timeout, @request_timeout)
    Keyword.put_new(options, :timeout, timeout)
  end

  def login(userinfo) do
    [user, pass] = String.split(userinfo, ":", parts: 2)
    login(user, pass)
  end

  def login(user, pass, expect \\ :success) do
    resp = Couch.post("/_session", body: %{:username => user, :password => pass})

    if expect == :success do
      true = resp.body["ok"]
      cookie = resp.headers[:"set-cookie"]
      [token | _] = String.split(cookie, ";")
      %Couch.Session{cookie: token}
    else
      true = Map.has_key?(resp.body, "error")
      %Couch.Session{error: resp.body["error"]}
    end
  end
end
