Question

I'm using the Erlang web framework :cowboy in Elixir, And I got an error in :cowboy_http_req.reply, here is my code:

mix.exs is:

defmodule Example.Mixfile do
  use Mix.Project

  def project do
    [ app: :example,
      version: "0.0.1",
      deps: deps ]
  end

  # Configuration for the OTP application
  def application do
    [
      # you should start :inets and :crypto first, or it will not start cowboy
      applications: [:inets, :crypto],
      mod: {Example, []}
    ]
  end

  # Returns the list of dependencies in the format:
  # { :foobar, "0.1", git: "https://github.com/elixir-lang/foobar.git" }
  defp deps do
    [
      { :cowboy, github: "extend/cowboy", tag: "0.9.0" },
      # { :lager, github: "basho/lager" }
    ]
  end
end

lib/example.ex is

defmodule Example do use Application.Behaviour

  def start(_type, _args) do
    deps_started

    dispatch = :cowboy_router.compile([
      {:_, [
          {"/objects/[...]", Example.Object, []}
      ]}
    ])

    :cowboy.start_http(:http, 100, [ip: {127,0,0,1}, port: 9080], [env: [dispatch: dispatch]])

    ExampleSup.start_link
  end

  defp deps_started do
    deps = [:ranch, :cowlib, :cowboy]
    Enum.all? deps, &ensure_started/1
  end

  defp ensure_started(app) do
    case :application.start(app) do
      :ok ->
        true
      {:error, {:already_started, _app}} ->
        true
      {:error, {:not_started, dep}} ->
        true = ensure_started(dep)
        ensure_started(app)
      error ->
        IO.puts "Couldn't start #{inspect app}: #{inspect error}"
        error
    end
  end
end

and my lib/example/object.ex is:

defmodule Example.Object do
  @behaviour :cowboy_http_handler

  def init(_type, req, _opts) do
    {:ok, req, :undefine}
  end

  def handle(req, state) do
    {ok, req} = :cowboy_http_req.reply(200, [], "hello world", req)
    {:ok, req, state}
  end

  def terminate(_reason, _request, _state), do: :ok
end

I use mix to manage the reps, and I start the cowboy server with idx -S mix, then I send a http stream use curl:

curl -i http://127.0.0.1:9080/objects/index.html 

and the server got error with error report:

=ERROR REPORT==== 28-Feb-2014::18:03:36 ===
Error in process <0.201.0> with exit value: {[{reason,undef},{mfa {'Elixir.Example.Object',handle,2}},{stacktrace,[{cowboy_http_req,reply,[200,[],<<11 bytes>>,{http_req,#Port<0.4438>,ranch_tcp,keepalive,<0.201.0>,<<3 bytes>>,'HTTP/1.1',{{127,0,0,1},58008},<<9 bytes>>,undefined,9080,<<14 bytes>>,[<<5 bytes>>],<<0 bytes>>,undefined,[],[{<<10 bytes>>,<<11 bytes>>},{<<4 bytes>>,<<14 bytes>>},{<<6 bytes>>,<<3 bytes>>}],[],undefined,[],waiting,undefined...

and the curl client got 500 Internal Server Error.

Could someone help me to finger out what's the matter? Thanks very much.

Was it helpful?

Solution

The error message is broken in three parts:

  • reason: undef
  • mfa: {'Elixir.Example.Object',handle,2}
  • stacktrace: [{cowboy_http_req,reply,[200,[],<<11 bytes>>,...]}, ...]

In a poor way it is saying that you got undef error (which means undefined function) in the function handle/2 in the Example.Object module. And the error has the stacktrace of calling cowboy_http_req.reply/4. My hunch would be that cowboy_http_req does not exist and you should call cowboy_req instead.

I would also suggest for you to use plug, although we don't currently have a tool for nicely showing errors, it is coming soon™. We are also shipping a logger with Elixir soon, which should help with some messages.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top