diff --git a/lib/phoenix/socket/serializers/v1_json_serializer.ex b/lib/phoenix/socket/serializers/v1_json_serializer.ex index 174f70c351..cd96fe8cc9 100644 --- a/lib/phoenix/socket/serializers/v1_json_serializer.ex +++ b/lib/phoenix/socket/serializers/v1_json_serializer.ex @@ -28,9 +28,15 @@ defmodule Phoenix.Socket.V1.JSONSerializer do @impl true def decode!(message, _opts) do - message - |> Phoenix.json_library().decode!() - |> Phoenix.Socket.Message.from_map!() + payload = Phoenix.json_library().decode!(message) + + case payload do + %{} -> + Phoenix.Socket.Message.from_map!(payload) + + other -> + raise "V1 JSON Serializer expected a map, got #{inspect(other)}" + end end defp encode_v1_fields_only(%Message{} = msg) do diff --git a/test/phoenix/socket/v1_json_serializer_test.exs b/test/phoenix/socket/v1_json_serializer_test.exs index 9e25aabaf9..7f0cfc9eb7 100644 --- a/test/phoenix/socket/v1_json_serializer_test.exs +++ b/test/phoenix/socket/v1_json_serializer_test.exs @@ -6,6 +6,7 @@ defmodule Phoenix.Socket.V1.JSONSerializerTest do # v1 responses must not contain join_ref @serializer V1.JSONSerializer @v1_msg_json "{\"event\":\"e\",\"payload\":\"m\",\"ref\":null,\"topic\":\"t\"}" + @v1_bad_json "[null,null,\"t\",\"e\",{\"m\":1}]" @v1_reply_json "{\"event\":\"phx_reply\",\"payload\":{\"response\":null,\"status\":null},\"ref\":\"null\",\"topic\":\"t\"}" @v1_fastlane_json "{\"event\":\"e\",\"payload\":\"m\",\"ref\":null,\"topic\":\"t\"}" @@ -33,7 +34,15 @@ defmodule Phoenix.Socket.V1.JSONSerializerTest do test "decode!/2 decodes `Phoenix.Socket.Message` from JSON" do assert %Message{topic: "t", event: "e", payload: "m"} == - decode!(@serializer, @v1_msg_json, opcode: :text) + decode!(@serializer, @v1_msg_json, opcode: :text) + end + + test "decode!/2 raise a PayloadFormatException if the JSON doesn't contain a map" do + assert_raise( + RuntimeError, + "V1 JSON Serializer expected a map, got [nil, nil, \"t\", \"e\", %{\"m\" => 1}]", + fn -> decode!(@serializer, @v1_bad_json, opcode: :text) end + ) end test "fastlane!/1 encodes a broadcast into a message as JSON" do