Versión Faraday:
faraday (0.11.0)
faraday_middleware (0.11.0.1)
faraday_middleware-aws-signers-v4 (0.1.5)
Versión rubí:
rubí 2.3.0p0 (2015-12-25 revisión 53290) [x86_64-darwin15]
Tengo una interfaz que accede a alguna API, estaba usando una conexión de Faraday con el método de obtención y configurando un reintento, y todo funcionaba bien hasta que cambié mi método para publicar , luego el reintento dejó de funcionar. Busqué un poco en Google para entender que la publicación no es incluido en el
IDEMPOTENT_METHODS = [:delete, :get, :head, :options, :put]
referencia: https://github.com/lostisland/faraday/pull/437/files
y tengo que usar retry_if si me gustaría volver a intentar el POST pero no encontré una documentación dor retry_if .
Así que mi conexión se ve así:
def my_connection(my_api_endpoint)
Faraday.new(url: my_api_endpoint) do |faraday|
faraday.request :retry, max: 5, exceptions:
[BadRequest, NotFound, ServerError, Faraday::Error::ConnectionFailed]
faraday.response :logger
faraday.adapter Faraday.default_adapter
faraday.options[:open_timeout] = 10
end
end
y llamándolo de esta manera:
res = my_connection(my_api_endpoint).post do |req|
req.headers['Content-Type'] = 'application/json'
req.options.timeout = 25
req.body = body.to_json
end
Cualquier ayuda será muy bienvenida.
Hola @yusefu , disculpas por la falta de documentación, esto es algo que estamos tratando de abordar en v1.0.
Mientras tanto, déjame ayudarte con tu problema. Básicamente, el retry_if
es una opción que puede pasar exactamente como pasa max: 5, exceptions: [BadRequest, NotFound, ServerError, Faraday::Error::ConnectionFailed]
. La única diferencia es que retry_if
debe ser una función (ya sea lambda o proc.
Si no está familiarizado con ellos, le sugiero que vaya con un proc
, que se puede instanciar con Proc.new { ... }
o con el multilínea Proc.new do ... end
.
Entonces, si desea usar retry_if
su ejemplo sería algo como:
def my_connection(my_api_endpoint)
# This is optional, I've added the <strong i="17">@connections</strong> memoized variable to avoid
# re-creating the connection every time. Not sure it's applicable to your case
# but consider it as it might improve performances
<strong i="18">@connections</strong> ||= []
@connections[my_api_endpoint] ||= Faraday.new(url: my_api_endpoint) do |faraday|
faraday.request :retry, max: 5, exceptions:
[BadRequest, NotFound, ServerError, Faraday::Error::ConnectionFailed],
retry_if: Proc.new do |env, exception|
# your implementation goes here...
end
faraday.response :logger
faraday.adapter Faraday.default_adapter
faraday.options[:open_timeout] = 10
end
end
Sin embargo, si su único objetivo es agregar :post a la lista de métodos de reintento, también puede usar la opción methods
agregada en ese PR que vinculó:
def my_connection(my_api_endpoint)
# This is optional, I've added the <strong i="23">@connections</strong> memoized variable to avoid
# re-creating the connection every time. Not sure it's applicable to your case
# but consider it as it might improve performances
<strong i="24">@connections</strong> ||= []
@connections[my_api_endpoint] ||= Faraday.new(url: my_api_endpoint) do |faraday|
faraday.request :retry, max: 5, exceptions:
[BadRequest, NotFound, ServerError, Faraday::Error::ConnectionFailed],
methods: Faraday::Request::Retry::IDEMPOTENT_METHODS + [:post]
faraday.response :logger
faraday.adapter Faraday.default_adapter
faraday.options[:open_timeout] = 10
end
end
Por favor, avíseme si esto ayuda 😄
La instancia de conexiones dio un TypeError.
expected MyAPI::BadRequest, got #<TypeError: {:req=>{}, :res=>nil, :headers=>nil, :reason_phrase=>nil}> with backtrace:
Pero con la simple adición de publicación a IDEMPOTENT_METHODS, ahora es posible volver a intentarlo .
Muchas gracias @iMacTia 🙏 funcionó.
Gracias por los comentarios @yusefu y perdón por el TypeError.
Creo que el problema es que @connections
debe ser un hash, no una matriz, ¡mi error!
<strong i="9">@connections</strong> ||= {}
De todos modos, ¡feliz de saber que tu problema ahora está resuelto 👍!
Comentario más útil
Gracias por los comentarios @yusefu y perdón por el TypeError.
Creo que el problema es que
@connections
debe ser un hash, no una matriz, ¡mi error!De todos modos, ¡feliz de saber que tu problema ahora está resuelto 👍!