Duffel.Error exception (Duffel v0.1.0)

Copy Markdown View Source

The error every Duffel function returns when something goes wrong.

A failed call always gives you {:error, %Duffel.Error{}}, whether the API rejected the request or the request never reached it, so one clause covers both:

case Duffel.Orders.create(client, params) do
  {:ok, order} -> ...
  {:error, %Duffel.Error{type: :rate_limit_error}} -> retry_later()
  {:error, %Duffel.Error{type: :validation_error, source: source}} -> ...
  {:error, %Duffel.Error{type: :transport_error}} -> retry_later()
end

API errors

These mirror the Duffel error schema. The struct fields come from the first error in the response; the full list is under :errors, and :status holds the HTTP status. :request_id identifies the request to Duffel support, and is read from the response body, or from the x-request-id header Duffel sets on every response when the body carries no id. :type is one of :airline_error, :api_error, :authentication_error, :invalid_request_error, :invalid_state_error, :rate_limit_error or :validation_error. A type Duffel adds later reads as :unknown_error.

Transport errors

When the request could not be completed at all — connection refused, DNS failure, timeout — :type is :transport_error and :status is nil. The underlying exception, usually a Req.TransportError, is kept under :reason for when you need to tell those cases apart.

Rate limits

:rate_limit holds a Duffel.RateLimit whenever the response reported your remaining allowance, which is most useful on a :rate_limit_error:

{:error, %Duffel.Error{type: :rate_limit_error, rate_limit: rate_limit}} ->
  retry_in(rate_limit.retry_after_ms)

Unexpected responses

Duffel wraps every resource in a data envelope. A success response without one means the endpoint returned something this library does not know how to read, so :type is :unexpected_response and the body is kept under :reason.

Summary

Types

t()

@type t() :: %Duffel.Error{
  __exception__: true,
  code: String.t() | nil,
  documentation_url: String.t() | nil,
  errors: [map()],
  message: String.t() | nil,
  rate_limit: Duffel.RateLimit.t() | nil,
  reason: term(),
  request_id: String.t() | nil,
  source: map() | nil,
  status: pos_integer() | nil,
  title: String.t() | nil,
  type: atom() | nil
}