Logging unhandled errors in Elixir Phoenix

I am new to Elixir/Phoenix. I am finding in hard to get in to the following topics.

  1. How to catch the unhandled error’s and write to the log in production mode for debugging purposes?
    In dev mode phoenix gives a nice error page when unhandled exception occurs. Now in production mode if I need to catch that and write it in file then how to do that?

  2. whats the recommended way to to log in production? Incase of application crash etc…

I referred an open source project https://github.com/thechangelog/changelog.com to check how they handled it. They use https://github.com/ForzaElixir/rollbax which is paid one.

Could someone please guide me on this?

Thanks.

1 Like

@shanmugharajk You don’t really need to do anything. If you’re running it on a bare linux box then run it inside Systemd and then the logs are just like any other log. If you’re running it inside a docker based system then the logs it emits can be handled like any other docker log.

1 Like

Thanks @benwilson512. I still didn’t start the deployment part or have any experience. I am totally new to API development too. That’s why I am bit confused.

Actually if something goes wrong I am getting a 500 Internal server error and the page explains stack trace and details which helps to debug.

In productions the same error

02:44:51.089 [error] #PID<0.856.0> running EposWeb.Endpoint (connection #PID<0.855.0>, stream id 1) terminated
Server: localhost:4000 (http)
Request: PUT /api/v1/sale/1549228052779/cart/A3
** (exit) an exception was raised:
    ** (KeyError) key :product_id not found in: %{"created_by" => "shan", "discount" => 440, "product_id" => "A3", "qty" => 10, "transaction_details_id" => "1549228052779", "transaction_id" => "1549228052779", "updated_by" => "shan"}
        (epos) lib/epos/sales/sales.ex:135: Epos.Sales.update_bill_total_in_cart/1
        (epos) lib/epos/sales/sales.ex:90: Epos.Sales.do_update_cart/1
        (epos) lib/epos/sales/sales.ex:16: anonymous fn/1 in Epos.Sales.update_cart/1
        (ecto_sql) lib/ecto/adapters/sql.ex:814: anonymous fn/3 in Ecto.Adapters.SQL.checkout_or_transaction/4
        (db_connection) lib/db_connection.ex:1349: DBConnection.run_transaction/4
        (epos) lib/epos_web/controllers/sales_controller.ex:28: EposWeb.SalesController.update_cart/2
        (epos) lib/epos_web/controllers/sales_controller.ex:1: EposWeb.SalesController.action/2
        (epos) lib/epos_web/controllers/sales_controller.ex:1: EposWeb.SalesController.phoenix_controller_pipeline/2

is coming in console. These errors if I want to write it somewhere with some id for debugging how to achieve this? Or this will be generated as docker log if I use docker? Sorry for the dumb question again.

will this work?

use Plug.ErrorHandler and

def handle_errors(conn, %{kind: _kind, reason: _reason, stack: _stack}) do
   # Log here or send to log server etc..
end

The production output is providing the same information. You don’t want to put that on the screen because it could leak sensitive information to website users.

Normally people have their logs routes to some log management service which can alert you of errors. Some website hosting companies also provide features like this.

1 Like

Are you familiar with how this is handled in other languages? No problem if not, being new is great! All I’m noting is that there’s nothing really different about handling this question with Elixir than Ruby

1 Like

Unfortunately no :cry: I am not so familiar. I have written C# API sometime back where i put all the controller code in try catch and log it there. I think this seems like the fundamental I will dig more in this aspect.

Right, I mean the short version is, your application code shouldn’t be concerned with logging things. The language runtime already handles logging errors. All you need to do when deploying the application is ensure that its logs are directed towards a useful location for being looked at and automatic alerting.

2 Likes

When deploy to production, the log level is info. The server log doesn’t show stack trace.

request_id=FbOsGwm8fuH_Cq0AAABR [info] Converted error MyXQL.Error to 500 response

After investigating, I found the schema field name is different from column name.