Packages

appsignal

1.4.1
2.17.4 2.17.3 2.17.2 2.17.1 2.17.0 2.16.0 2.15.11 2.15.10 2.15.9 2.15.8 2.15.7 2.15.6 2.15.5 2.15.4 2.15.3 2.15.2 2.15.1 2.15.0 2.14.1 2.14.0 2.13.4 2.13.3 2.13.2 2.13.1 2.13.0 2.12.3 2.12.2 2.12.1 2.12.0 2.11.0 2.10.2 2.10.1 2.10.0 2.9.2 2.9.1 2.9.0 2.8.3 2.8.2 2.8.1 2.8.0 2.7.13 2.7.12 2.7.11 2.7.10 2.7.9 2.7.8 2.7.7 2.7.6 2.7.5 2.7.4 2.7.3 2.7.2 2.7.1 2.7.0 2.7.0-beta.1 2.6.1 2.6.0 2.5.3 2.5.2 2.5.1 2.5.0 2.4.3 2.4.2 2.4.1 2.4.0 2.3.1 2.3.0 2.2.19 2.2.18 2.2.17 2.2.16 2.2.15 2.2.14 2.2.13 2.2.12 retired 2.2.11 2.2.10 2.2.9 2.2.8 2.2.7 2.2.6 2.2.5 2.2.4 2.2.3 2.2.2 2.2.1 2.2.0 2.1.15 2.1.14 2.1.13 2.1.12 2.1.11 2.1.10 2.1.9 2.1.8 2.1.7 2.1.7-beta.1 2.1.6 2.1.5 2.1.4 2.1.3 2.1.2 2.1.1 2.1.0 2.0.8 2.0.7 2.0.6 2.0.6-beta.1 2.0.5 retired 2.0.4 retired 2.0.3 retired 2.0.2 retired 2.0.1 retired 2.0.0 retired 2.0.0-beta.11 2.0.0-beta.10 2.0.0-beta.9 2.0.0-beta.8 2.0.0-beta.7 2.0.0-beta.6 2.0.0-beta.5 2.0.0-beta.4 2.0.0-beta.3 2.0.0-beta.2 2.0.0-beta.1 2.0.0-alpha.7 2.0.0-alpha.6 2.0.0-alpha.5 2.0.0-alpha.4 2.0.0-alpha.3 2.0.0-alpha.2 2.0.0-alpha.1 1.13.5 1.13.4 1.13.3 1.13.2 1.13.1 1.13.0 1.13.0-beta.2 1.13.0-beta.1 1.12.1 1.12.0 1.12.0-beta.3 1.12.0-beta.2 1.12.0-beta.1 1.11.8 1.11.7 1.11.6 1.11.5 1.11.4 1.11.3 1.11.2 1.11.1 1.11.0 1.11.0-beta.1 1.10.13 1.10.12 1.10.11 1.10.10 1.10.9 1.10.8 1.10.7 1.10.6 1.10.5 1.10.4 1.10.3 1.10.2 1.10.1 1.10.0 1.9.4 1.9.3 1.9.2 1.9.1 1.9.1-beta.1 1.9.0 1.9.0-beta.1 1.9.0-alpha.1 1.8.2 1.8.1 1.8.1-beta.2 1.8.1-beta.1 1.8.0 1.7.2 1.7.1 1.7.0 1.7.0-beta.2 1.7.0-beta.1 1.7.0-alpha.4 1.7.0-alpha.3 1.7.0-alpha.2 1.7.0-alpha.1 1.6.7 1.6.6 1.6.6-beta.2 1.6.6-beta.1 1.6.5 1.6.4 1.6.3 1.6.2 1.6.1 1.6.0 1.6.0-beta.1 1.6.0-alpha.1 1.5.1 1.5.0 1.5.0-beta.2 1.5.0-beta.1 1.4.11-beta.1 1.4.10 1.4.9 1.4.8 1.4.7 1.4.6 1.4.5 1.4.4 1.4.3 1.4.2 1.4.1 1.4.0 1.4.0-alpha.1 1.3.6 1.3.6-beta.1 1.3.5 1.3.4 1.3.4-beta.1 1.3.3 1.3.2 1.3.1 1.3.0 1.3.0-beta.3 1.3.0-beta.2 1.3.0-beta.1 1.2.3 1.2.2 1.2.1 1.2.0 1.1.1 1.1.0 1.0.4 1.0.3 1.0.2 1.0.1 1.0.0 1.0.0-rc.1 0.13.0 0.12.3 0.12.2 0.12.1 0.12.0 0.11.6 0.11.5 0.11.4 0.11.3 0.11.2 0.11.1 0.11.0 0.10.0 0.9.2 0.9.1 0.9.0 0.8.0 0.7.1 0.7.0 0.6.2 0.6.1 0.6.0 0.5.0 0.4.0 0.3.0 0.2.0 0.1.0 0.0.9 0.0.8 0.0.7 0.0.6 0.0.5 0.0.4 0.0.3 0.0.2 0.0.1

Collects error and performance data from your Elixir applications and sends it to AppSignal

Current section

Files

Jump to
appsignal lib appsignal plug.ex
Raw

lib/appsignal/plug.ex

if Appsignal.plug? do
defmodule Appsignal.Plug do
@moduledoc """
Plug handler for Phoenix requests
"""
defmacro __using__(_) do
quote do
@transaction Application.get_env(:appsignal, :appsignal_transaction, Appsignal.Transaction)
def call(conn, opts) do
id = Logger.metadata()[:request_id] || @transaction.generate_id()
transaction = @transaction.start(id, :http_request)
try do
super(conn, opts)
catch
kind, error ->
Plug.ErrorHandler.__catch__(conn, kind, error, fn(conn, _exception) ->
case Appsignal.Plug.extract_error_metadata(error) do
{reason, message} ->
transaction
|> @transaction.set_error(reason, message, System.stacktrace)
|> finish_with_conn(conn)
nil -> conn
end
end)
else
conn -> finish_with_conn(transaction, conn)
end
end
defp finish_with_conn(transaction, conn) do
try_set_action(transaction, conn)
if @transaction.finish(transaction) == :sample do
@transaction.set_request_metadata(transaction, conn)
end
:ok = @transaction.complete(transaction)
conn
end
defp try_set_action(transaction, conn) do
case Appsignal.Plug.extract_action(conn) do
nil -> nil
action -> @transaction.set_action(transaction, action)
end
end
end
end
@doc """
Returns a tuple with the exception's reason and message unless the error has
a status code under 500.
"""
def extract_error_metadata(%{plug_status: status}) when status < 500 do
nil
end
def extract_error_metadata(%Plug.Conn.WrapperError{reason: reason = %{}}) do
Appsignal.ErrorHandler.extract_reason_and_message(reason, "HTTP request error")
end
def extract_error_metadata(reason) do
Appsignal.ErrorHandler.extract_reason_and_message(reason, "HTTP request error")
end
@doc false
def extract_error_metadata(reason, conn, stack) do
IO.warn "Appsignal.Plug.extract_error_metadata/3 is deprecated. Use Appsignal.Plug.extract_error_metadata/1 instead."
{reason, message} = extract_error_metadata(reason)
{reason, message, stack, conn}
end
def extract_action(%Plug.Conn{private: %{phoenix_action: action, phoenix_controller: controller}}) do
merge_action_and_controller(action, controller)
end
def extract_action(%Plug.Conn{private: %{phoenix_endpoint: _}}), do: nil
def extract_action(%Plug.Conn{method: method, request_path: path}) do
"#{method} #{path}"
end
def extract_sample_data(%Plug.Conn{params: params, host: host,
method: method, script_name: script_name, request_path: request_path,
port: port, query_string: query_string} = conn) do
%{
"params" => Appsignal.Utils.ParamsFilter.filter_values(params),
"environment" => %{
"host" => host,
"method" => method,
"script_name" => script_name,
"request_path" => request_path,
"port" => port,
"query_string" => query_string,
"request_uri" => url(conn),
"peer" => peer(conn)
} |> Map.merge(extract_request_headers(conn))
}
end
@header_keys ~w(
accept accept-charset accept-encoding accept-language cache-control
connection content-length user-agent from negotiate pragma referer range
auth-type gateway-interface path-translated remote-host remote-ident
remote-user remote-addr request-method server-name server-port
server-protocol request-uri path-info client-ip range
x-request-start x-queue-start x-queue-time x-heroku-queue-wait-time
x-application-start x-forwarded-for
)
def extract_request_headers(%Plug.Conn{req_headers: req_headers}) do
req_headers
|> Keyword.take(@header_keys)
|> Enum.map(fn({key, value}) -> {"req_headers.#{key}", value} end)
|> Enum.into(%{})
end
def extract_meta_data(%Plug.Conn{method: method, request_path: path}) do
%{"method" => method, "path" => path}
end
defp merge_action_and_controller(action, controller) when is_atom(controller) do
merge_action_and_controller(
action,
controller |> Atom.to_string |> String.trim_leading("Elixir.")
)
end
defp merge_action_and_controller(action, controller) do
"#{controller}##{action}"
end
defp url(%Plug.Conn{scheme: scheme, host: host, port: port, request_path: request_path}) do
"#{scheme}://#{host}:#{port}#{request_path}"
end
defp peer(%Plug.Conn{peer: {host, port}}) do
"#{:inet_parse.ntoa host}:#{port}"
end
end
end