【问题标题】:Phoenix Channel - Erlang KeyError when connectingPhoenix Channel - 连接时出现 Erlang KeyError
【发布时间】:2015-12-30 09:48:11
【问题描述】:

我正在阅读《Programming Phoenix》一书,在尝试连接到经过身份验证的频道时遇到了服务器错误。错误是:

[error] Process #PID<0.1000.0> raised an exception ** (ErlangError) erlang error: [reason: %KeyError{key: :user_id, term: %{current_user: %Rumbl.User{__meta__: #Ecto.Schema.Metadata<:loaded>, annotations: #Ecto.Association.NotLoaded<association :annotations is not loaded>, id: 6, inserted_at: #Ecto.DateTime<2015-12-14T17:57:37Z>, name: "Joe", password: nil, password_hash: "$2b$12$TkUgAyJvSroft6KNhs8ECukFkrREZ/jS2xZUTLdp3oQuV.px22WrS", updated_at: #Ecto.DateTime<2015-12-14T17:57:37Z>, username: "joe", videos: #Ecto.Association.NotLoaded<association :videos is not loaded>}}}, mfa: {Phoenix.Endpoint.CowboyWebSocket, :init, 3}, stacktrace: [{Rumbl.UserSocket, :id, 1, [file: 'web/channels/user_socket.ex', line: 46]}, {Phoenix.Socket.Transport, :connect_vsn, 6, [file: 'lib/phoenix/socket/transport.ex', line: 154]}, {Phoenix.Transports.WebSocket, :init, 2, [file: 'lib/phoenix/transports/websocket.ex', line: 73]}, {Phoenix.Endpoint.CowboyWebSocket, :init, 3, [file: 'lib/phoenix/endpoint/cowboy_websocket.ex', line: 11]}, {:cowboy_handler, :handler_init, 4, [file: 'src/cowboy_handler.erl', line: 64]}, {:cowboy_protocol, :execute, 4, [file: 'src/cowboy_protocol.erl', line: 442]}], req: [socket: #Port<0.60203>, transport: :ranch_tcp, connection: :keepalive, pid: #PID<0.1000.0>, method: "GET", version: :"HTTP/1.1", peer: {{127, 0, 0, 1}, 49668}, host: "localhost", host_info: :undefined, port: 4000, path: "/socket/websocket", path_info: :undefined, qs: "token=g3QAAAACZAAEZGF0YWEGZAAGc2lnbmVkbgYA57J57lEB--NwLr3U3AgY8nAsNdr7Uya86zUrE%3D&vsn=1.0.0", qs_vals: :undefined, bindings: [], headers: [{"host", "localhost:4000"}, {"connection", "Upgrade"}, {"pragma", "no-cache"}, {"cache-control", "no-cache"}, {"upgrade", "websocket"}, {"origin", "http://localhost:4000"}, {"sec-websocket-version", "13"}, {"user-agent", "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_11_2) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/47.0.2526.106 Safari/537.36"}, {"accept-encoding", "gzip, deflate, sdch"}, {"accept-language", "en-US,en;q=0.8"}, {"cookie", "SnapABugHistory=1#; _ga=GA1.1.577046204.1438865191; access_token=f4070d3a1906ebff569d311aa0ddd842c8ef30ee; user-hash=d569532a977f78e1d96d5bab3412a265; SnapABugVisit=86#1449075542; _rumbl_key=g3QAAAACbQAAAAtfY3NyZl90b2tlbm0AAAAYRUoxM1A2NnNNelRoSkR1TGxjaWM2UT09bQAAAAd1c2VyX2lkYQY=--P7j+4zmpEx4KRG4Eq5xZXruIM0Y="}, {"sec-websocket-key", "XjCnurWNHP47g1gcmQN5LA=="}, {"sec-websocket-extensions", "permessage-deflate; client_max_window_bits"}], p_headers: [{"connection", ["upgrade"]}], cookies: :undefined, meta: [], body_state: :waiting, buffer: "", multipart: :undefined, resp_compress: false, resp_state: :waiting, resp_headers: [], resp_body: "", onresponse: :undefined], opts: {Phoenix.Transports.WebSocket, {Rumbl.Endpoint, Rumbl.UserSocket, :websocket}}] (cowboy) src/cowboy_protocol.erl:442: :cowboy_protocol.execute/4 [error] Ranch protocol #PID<0.1000.0> (:cowboy_protocol) of listener Rumbl.Endpoint.HTTP terminated ** (exit) an exception was raised: ** (ErlangError) erlang error: [reason: %KeyError{key: :user_id, term: %{current_user: %Rumbl.User{__meta__: #Ecto.Schema.Metadata<:loaded>, annotations: #Ecto.Association.NotLoaded<association :annotations is not loaded>, id: 6, inserted_at: #Ecto.DateTime<2015-12-14T17:57:37Z>, name: "Joe", password: nil, password_hash: "$2b$12$TkUgAyJvSroft6KNhs8ECukFkrREZ/jS2xZUTLdp3oQuV.px22WrS", updated_at: #Ecto.DateTime<2015-12-14T17:57:37Z>, username: "joe", videos: #Ecto.Association.NotLoaded<association :videos is not loaded>}}}, mfa: {Phoenix.Endpoint.CowboyWebSocket, :init, 3}, stacktrace: [{Rumbl.UserSocket, :id, 1, [file: 'web/channels/user_socket.ex', line: 46]}, {Phoenix.Socket.Transport, :connect_vsn, 6, [file: 'lib/phoenix/socket/transport.ex', line: 154]}, {Phoenix.Transports.WebSocket, :init, 2, [file: 'lib/phoenix/transports/websocket.ex', line: 73]}, {Phoenix.Endpoint.CowboyWebSocket, :init, 3, [file: 'lib/phoenix/endpoint/cowboy_websocket.ex', line: 11]}, {:cowboy_handler, :handler_init, 4, [file: 'src/cowboy_handler.erl', line: 64]}, {:cowboy_protocol, :execute, 4, [file: 'src/cowboy_protocol.erl', line: 442]}], req: [socket: #Port<0.60203>, transport: :ranch_tcp, connection: :keepalive, pid: #PID<0.1000.0>, method: "GET", version: :"HTTP/1.1", peer: {{127, 0, 0, 1}, 49668}, host: "localhost", host_info: :undefined, port: 4000, path: "/socket/websocket", path_info: :undefined, qs: "token=g3QAAAACZAAEZGF0YWEGZAAGc2lnbmVkbgYA57J57lEB--NwLr3U3AgY8nAsNdr7Uya86zUrE%3D&vsn=1.0.0", qs_vals: :undefined, bindings: [], headers: [{"host", "localhost:4000"}, {"connection", "Upgrade"}, {"pragma", "no-cache"}, {"cache-control", "no-cache"}, {"upgrade", "websocket"}, {"origin", "http://localhost:4000"}, {"sec-websocket-version", "13"}, {"user-agent", "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_11_2) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/47.0.2526.106 Safari/537.36"}, {"accept-encoding", "gzip, deflate, sdch"}, {"accept-language", "en-US,en;q=0.8"}, {"cookie", "SnapABugHistory=1#; _ga=GA1.1.577046204.1438865191; access_token=f4070d3a1906ebff569d311aa0ddd842c8ef30ee; user-hash=d569532a977f78e1d96d5bab3412a265; SnapABugVisit=86#1449075542; _rumbl_key=g3QAAAACbQAAAAtfY3NyZl90b2tlbm0AAAAYRUoxM1A2NnNNelRoSkR1TGxjaWM2UT09bQAAAAd1c2VyX2lkYQY=--P7j+4zmpEx4KRG4Eq5xZXruIM0Y="}, {"sec-websocket-key", "XjCnurWNHP47g1gcmQN5LA=="}, {"sec-websocket-extensions", "permessage-deflate; client_max_window_bits"}], p_headers: [{"connection", ["upgrade"]}], cookies: :undefined, meta: [], body_state: :waiting, buffer: "", multipart: :undefined, resp_compress: false, resp_state: :waiting, resp_headers: [], resp_body: "", onresponse: :undefined], opts: {Phoenix.Transports.WebSocket, {Rumbl.Endpoint, Rumbl.UserSocket, :websocket}}] (cowboy) src/cowboy_protocol.erl:442: :cowboy_protocol.execute/4

user_socket.ex 的第 46 行是:

def id(socket), do: "users_socket:#{socket.assigns.user_id}"

我在这里缺少什么?谢谢!

【问题讨论】:

  • 哎呀,这个错误信息看起来一点也不友好。你能告诉我你的 Phoenix 和 Elixir 版本吗?
  • @JoséValim,下面的答案回答了我的问题。不幸的是,我已经升级到最新的 elixir 和 phoenix,所以我不记得哪个确切版本产生了这个错误。我认为是长生不老药 1.1 和凤凰 1.0。
  • 别担心,无论如何我都能解决这个问题 :)

标签: elixir phoenix-framework


【解决方案1】:

这已被报告为勘误表here,所以我相信它会在本书的最终修订版中得到修复。要解决此问题,请更改:

def id(socket), do: "users_socket:#{socket.assigns.user_id}"

到:

def id(socket), do: "users_socket:#{socket.assigns.current_user.id}"

为什么会出现此错误

UserSocketconnect/2 中,如果用户通过了身份验证,则您将current_user 分配给套接字中的user,而不是user_id

{:ok, assign(socket, :current_user, user)}

所以socket 没有user_id 键。当您调用映射中不存在的键时会引发KeyError 错误:

【讨论】:

    猜你喜欢
    • 2016-03-18
    • 2019-07-19
    • 2021-10-30
    • 2012-01-01
    • 2020-11-04
    • 1970-01-01
    • 2017-10-07
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多