Skip to content

Commit

Permalink
Don't crash on non-Unicode data
Browse files Browse the repository at this point in the history
This fixes an issue where ASCII data got passed through that was a
little corrupt and it triggered a crash. This bulletproofs the
flattening code against junk being logged.
  • Loading branch information
fhunleth committed Apr 4, 2024
1 parent fbca24f commit 45c729b
Show file tree
Hide file tree
Showing 2 changed files with 42 additions and 1 deletion.
18 changes: 17 additions & 1 deletion lib/ring_logger.ex
Original file line number Diff line number Diff line change
Expand Up @@ -328,6 +328,22 @@ defmodule RingLogger do
end

defp flatten({mod, msg, ts, md}) do
{mod, IO.chardata_to_string(msg), ts, md}
{mod, safe_chardata_to_string(msg), ts, md}
end

defp safe_chardata_to_string(msg) do
IO.chardata_to_string(msg)
rescue
UnicodeConversionError ->
# ASCII?
safe_iodata_to_binary(msg)
end

defp safe_iodata_to_binary(msg) do
IO.iodata_to_binary(msg)
rescue
ArgumentError ->
# Give up
inspect(msg)
end
end
25 changes: 25 additions & 0 deletions test/ring_logger_test.exs
Original file line number Diff line number Diff line change
Expand Up @@ -555,6 +555,31 @@ defmodule RingLoggerTest do
assert message =~ "[info] Cześć!"
end

test "logging corrupt data", %{io: io} do
# This is non-Unicode and shouldn't crash RingLogger. There are slightly
# different paths that are taken for iodata vs binary data, so make sure
# they behave identically.
message_string = <<227, 97, 195, 253, 123, 50, 91, 116, 114, 227, 110>>
message = [message_string]

:ok = RingLogger.attach(io: io)
Logger.debug(message_string)
assert_receive {:io, message_string_result}

Logger.debug(message)
assert_receive {:io, message_result}

assert message_result == message_string_result
assert message_result =~ "{2[tr"
end

test "logging totally wrong data doesn't crash", %{io: io} do
:ok = RingLogger.attach(io: io)
Logger.info([[{1, 2, 3}]])
assert_receive {:io, message}
assert message =~ "[info] cannot truncate chardata"
end

describe "fetching config" do
test "can retrieve config for attached client", %{io: io} do
:ok = RingLogger.attach(io: io)
Expand Down

0 comments on commit 45c729b

Please sign in to comment.