Gor*_*eng 5 elixir ecto phoenix-framework
当 Ecto(或 postgrex?)遇到数据库查询超时时,我想返回一个特定的错误响应(带有自定义消息的 HTTP 503)。
发生超时时,抛出的异常如下所示:
** (DBConnection.ConnectionError) tcp recv: closed
(ecto) lib/ecto/adapters/postgres/connection.ex:86: Ecto.Adapters.Postgres.Connection.prepare_execute/5
(ecto) lib/ecto/adapters/sql.ex:243: Ecto.Adapters.SQL.sql_call/6
(ecto) lib/ecto/adapters/sql.ex:431: Ecto.Adapters.SQL.execute_and_cache/7
(ecto) lib/ecto/repo/queryable.ex:130: Ecto.Repo.Queryable.execute/5
(ecto) lib/ecto/repo/queryable.ex:35: Ecto.Repo.Queryable.all/4
(stdlib) timer.erl:166: :timer.tc/1
Run Code Online (Sandbox Code Playgroud)
我为Plug.Exception
协议定义了一个实现,以便DBConnection.ConnectionError
在异常消息为 时映射到状态 503 "tcp recv: closed"
,这似乎有效。
defimpl Plug.Exception, for: DBConnection.ConnectionError do
def status(exception) do
if exception.message == "tcp recv: closed" do
503
else
500
end
end
end
Run Code Online (Sandbox Code Playgroud)
但是,我担心的是DBConnection.ConnectionError
异常以及异常"tcp recv: closed"
对我来说太普遍了,无法假设发生了数据库超时。如果关闭的连接是由其他原因引起的,例如网络故障怎么办?
是否有更具体的方法来检测何时发生数据库查询超时?
如果发生数据库连接问题时检查 DNS 解析是否正常以及网络连接是否正常,则可以使错误消息更加具体。
检查网络连接的示例:
curl --head http://ipaddress/
Run Code Online (Sandbox Code Playgroud)
或者
ping ipadress
Run Code Online (Sandbox Code Playgroud)
或者
#!/bin/bash
echo -e "GET http://stackoverflow.com HTTP/1.0\n\n" | nc stackoverflow.com 80 > /dev/null 2>&1
if [ $? -eq 0 ]; then
echo "Online"
else
echo "Offline"
fi
Run Code Online (Sandbox Code Playgroud)