Script 'mail_helper' called by obssrc Hello community, here is the log from the commit of package rubygem-faraday for openSUSE:Factory checked in at 2023-11-14 21:43:26 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Comparing /work/SRC/openSUSE:Factory/rubygem-faraday (Old) and /work/SRC/openSUSE:Factory/.rubygem-faraday.new.17445 (New) ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Package is "rubygem-faraday" Tue Nov 14 21:43:26 2023 rev:33 rq:1123004 version:2.7.11 Changes: -------- --- /work/SRC/openSUSE:Factory/rubygem-faraday/rubygem-faraday.changes 2022-12-13 18:56:55.791671592 +0100 +++ /work/SRC/openSUSE:Factory/.rubygem-faraday.new.17445/rubygem-faraday.changes 2023-11-14 21:43:34.673831109 +0100 @@ -1,0 +2,143 @@ +Thu Nov 2 15:47:19 UTC 2023 - Dan Äermák <dan.cer...@posteo.net> + +- 2.7.11: + +## What's Changed +* Refer to correct branch [ci skip] by @olleolleolle in https://github.com/lostisland/faraday/pull/1516 +* ð New docs ð by @iMacTia in https://github.com/lostisland/faraday/pull/1517 +* Fix capitalization for Elasticsearch by @picandocodigo in https://github.com/lostisland/faraday/pull/1520 +* Fix 404 link in UPGRADING documentation by @shanempope in https://github.com/lostisland/faraday/pull/1521 +* Fix included middleware links by @edwardloveall in https://github.com/lostisland/faraday/pull/1522 +* Fix a test failure using Ruby 3.3.0dev by @koic in https://github.com/lostisland/faraday/pull/1523 +* Format code with less indent by @olleolleolle in https://github.com/lostisland/faraday/pull/1524 +* Add `base64` to runtime dependency by @koic in https://github.com/lostisland/faraday/pull/1525 +* Add option for omitting request data from Faraday exceptions by @ClaytonPassmore in https://github.com/lostisland/faraday/pull/1526 + +## New Contributors +* @picandocodigo made their first contribution in https://github.com/lostisland/faraday/pull/1520 +* @shanempope made their first contribution in https://github.com/lostisland/faraday/pull/1521 +* @edwardloveall made their first contribution in https://github.com/lostisland/faraday/pull/1522 +* @koic made their first contribution in https://github.com/lostisland/faraday/pull/1523 +* @ClaytonPassmore made their first contribution in https://github.com/lostisland/faraday/pull/1526 + +**Full Changelog**: https://github.com/lostisland/faraday/compare/v2.7.10...v2.7.11 + +2.7.10: + +## What's Changed +* Fix some logging inefficiencies by @semaperepelitsa in https://github.com/lostisland/faraday/pull/1515 + +## New Contributors +* @semaperepelitsa made their first contribution in https://github.com/lostisland/faraday/pull/1515 + +**Full Changelog**: https://github.com/lostisland/faraday/compare/v2.7.9...v2.7.10 + +2.7.9: + +## What's Changed +* Raise Error: Add Faraday::RequestTimeoutError by @tisba in https://github.com/lostisland/faraday/pull/1513 +* Include `env[:headers]` in `Stubs::NotFound` by @yykamei in https://github.com/lostisland/faraday/pull/1514 + +## New Contributors +* @tisba made their first contribution in https://github.com/lostisland/faraday/pull/1513 + +**Full Changelog**: https://github.com/lostisland/faraday/compare/v2.7.8...v2.7.9 + +2.7.8: + +## What's Changed +* Failing test: Logging headers & errors fails when ConnectionFailed is raised by @eikes in https://github.com/lostisland/faraday/pull/1512 + +## New Contributors +* @eikes made their first contribution in https://github.com/lostisland/faraday/pull/1512 + +**Full Changelog**: https://github.com/lostisland/faraday/compare/v2.7.7...v2.7.8 + +2.7.7: + +## What's Changed +* Fix implementation of Faraday::Error helpers. by @iMacTia in https://github.com/lostisland/faraday/pull/1510 + + +**Full Changelog**: https://github.com/lostisland/faraday/compare/v2.7.6...v2.7.7 + +2.7.6: + +## What's Changed +* Fix "method redefined" warnings introduced in Faraday 2.7.5 by @mattbrictson in https://github.com/lostisland/faraday/pull/1506 + + +**Full Changelog**: https://github.com/lostisland/faraday/compare/v2.7.5...v2.7.6 + +2.7.5: + +## What's Changed +* Subclass Options structs using a block by @bdewater in https://github.com/lostisland/faraday/pull/1489 +* Remove direct struct subclassing by @bdewater in https://github.com/lostisland/faraday/pull/1491 +* Fix incorrect use of logger middleware in docs by @mattbrictson in https://github.com/lostisland/faraday/pull/1497 +* Always assume the existence of `URI::Generic#find_proxy` by @yykamei in https://github.com/lostisland/faraday/pull/1502 +* Encode `false` to `"false"` in `Faraday::Request::Json` by @yykamei in https://github.com/lostisland/faraday/pull/1504 +* ProxyOptions should treat empty string as nil by @exoego in https://github.com/lostisland/faraday/pull/1493 + +## New Contributors +* @mattbrictson made their first contribution in https://github.com/lostisland/faraday/pull/1497 +* @exoego made their first contribution in https://github.com/lostisland/faraday/pull/1493 + +**Full Changelog**: https://github.com/lostisland/faraday/compare/v2.7.4...v2.7.5 + +2.7.4: + +## What's Changed +* Fix support for custom URI parsers by @iMacTia in https://github.com/lostisland/faraday/pull/1485 + + +**Full Changelog**: https://github.com/lostisland/faraday/compare/v2.7.3...v2.7.4 + +2.7.3: + +## What's Changed + +Fixes: +* Fix Style/ZeroLengthPredicate by @olleolleolle in https://github.com/lostisland/faraday/pull/1480 +* Connection#build_exclusive_url: replace simple syntax by @hyuraku in https://github.com/lostisland/faraday/pull/1481 +* Add URL to to_hash in Faraday::Response (#1474) by @aaronstillwell in https://github.com/lostisland/faraday/pull/1475 + +Misc: +* Clarify diff between connection settings `timeout` and `open_timeout` by @Yu-Chieh-Henry-Yang in https://github.com/lostisland/faraday/pull/1470 +* Adds Ruby 3.2 to the CI matrix. by @petergoldstein in https://github.com/lostisland/faraday/pull/1471 +* Fix typo in Adapters documentation by @henrialb in https://github.com/lostisland/faraday/pull/1473 +* docs: Update to 2023 by @frederikspang in https://github.com/lostisland/faraday/pull/1477 +* Update connection.rb documentation to use PUT in an example by @wlads in https://github.com/lostisland/faraday/pull/1482 + +## New Contributors +* @Yu-Chieh-Henry-Yang made their first contribution in https://github.com/lostisland/faraday/pull/1470 +* @henrialb made their first contribution in https://github.com/lostisland/faraday/pull/1473 +* @frederikspang made their first contribution in https://github.com/lostisland/faraday/pull/1477 +* @aaronstillwell made their first contribution in https://github.com/lostisland/faraday/pull/1475 +* @wlads made their first contribution in https://github.com/lostisland/faraday/pull/1482 + +**Full Changelog**: https://github.com/lostisland/faraday/compare/v2.7.2...v2.7.3 + +2.7.2: + +## What's Changed +* Replace actions/setup-ruby with ruby/setup-ruby by @kyoshidajp in https://github.com/lostisland/faraday/pull/1466 +* Enforce timeouts in Faraday's test adapter by @dpep in https://github.com/lostisland/faraday/pull/1465 +* Rename Faraday::Logger::Formatter#error to #exception by @iMacTia in https://github.com/lostisland/faraday/pull/1468 + +## ATTENTION +Rename Faraday::Logger::Formatter#error ([#1468](https://github.com/lostisland/faraday/pull/1468)) is potentially a breaking change IF you've created a custom `Faraday::Logging::Formatter` implementing the new `error` method introduced in v2.7.0. + +We've decided to rollout this change in a fix version anyway because the name of the method was potentially causing infinite loop issues, and because the feature was very recently released. + +This should not be impacting you otherwise and you can safely upgrade. + +## New Contributors +* @kyoshidajp made their first contribution in https://github.com/lostisland/faraday/pull/1466 +* @dpep made their first contribution in https://github.com/lostisland/faraday/pull/1465 + +**Full Changelog**: https://github.com/lostisland/faraday/compare/v2.7.1...v2.7.2 + + + +------------------------------------------------------------------- Old: ---- faraday-2.7.1.gem New: ---- faraday-2.7.11.gem ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Other differences: ------------------ ++++++ rubygem-faraday.spec ++++++ --- /var/tmp/diff_new_pack.zRBphX/_old 2023-11-14 21:43:35.325855245 +0100 +++ /var/tmp/diff_new_pack.zRBphX/_new 2023-11-14 21:43:35.329855393 +0100 @@ -1,7 +1,7 @@ # # spec file for package rubygem-faraday # -# Copyright (c) 2022 SUSE LLC +# Copyright (c) 2023 SUSE LLC # # All modifications and additions to the file contributed by third parties # remain the property of their copyright owners, unless otherwise agreed @@ -24,11 +24,10 @@ # Name: rubygem-faraday -Version: 2.7.1 +Version: 2.7.11 Release: 0 %define mod_name faraday %define mod_full_name %{mod_name}-%{version} -BuildRoot: %{_tmppath}/%{name}-%{version}-build BuildRequires: %{ruby >= 2.6} BuildRequires: %{rubygem gem2rpm} BuildRequires: ruby-macros >= 5 @@ -37,7 +36,6 @@ Source1: gem2rpm.yml Summary: HTTP/REST API client library License: MIT -Group: Development/Languages/Ruby %description HTTP/REST API client library. ++++++ faraday-2.7.1.gem -> faraday-2.7.11.gem ++++++ diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/LICENSE.md new/LICENSE.md --- old/LICENSE.md 2022-11-18 12:09:30.000000000 +0100 +++ new/LICENSE.md 2023-09-12 17:43:57.000000000 +0200 @@ -1,4 +1,4 @@ -Copyright (c) 2009-2022 Rick Olson, Zack Hobson +Copyright (c) 2009-2023 Rick Olson, Zack Hobson Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/README.md new/README.md --- old/README.md 2022-11-18 12:09:30.000000000 +0100 +++ new/README.md 2023-09-12 17:43:57.000000000 +0200 @@ -1,19 +1,34 @@ -# [![Faraday](./docs/assets/img/repo-card-slim.png)][website] +# [![Faraday](./docs/_media/home-logo.svg)][website] [![Gem Version](https://badge.fury.io/rb/faraday.svg)](https://rubygems.org/gems/faraday) [![GitHub Actions CI](https://github.com/lostisland/faraday/workflows/CI/badge.svg)](https://github.com/lostisland/faraday/actions?query=workflow%3ACI) [![GitHub Discussions](https://img.shields.io/github/discussions/lostisland/faraday?logo=github)](https://github.com/lostisland/faraday/discussions) - Faraday is an HTTP client library abstraction layer that provides a common interface over many adapters (such as Net::HTTP) and embraces the concept of Rack middleware when processing the request/response cycle. -You probably don't want to use Faraday directly in your project, as it will lack an actual client library to perform -requests. Instead, you probably want to have a look at [Awesome Faraday][awesome] for a list of available adapters. +Take a look at [Awesome Faraday][awesome] for a list of available adapters and middleware. + +## Why use Faraday? + +Faraday gives you the power of Rack middleware for manipulating HTTP requests and responses, +making it easier to build sophisticated API clients or web service libraries that abstract away +the details of how HTTP requests are made. + +Faraday comes with a lot of features out of the box, such as: +* Support for multiple adapters (Net::HTTP, Typhoeus, Patron, Excon, HTTPClient, and more) +* Persistent connections (keep-alive) +* Parallel requests +* Automatic response parsing (JSON, XML, YAML) +* Customization of the request/response cycle with middleware +* Support for streaming responses +* Support for uploading files +* And much more! ## Getting Started The best starting point is the [Faraday Website][website], with its introduction and explanation. -Need more details? See the [Faraday API Documentation][apidoc] to see how it works internally. + +Need more details? See the [Faraday API Documentation][apidoc] to see how it works internally, or take a look at [Advanced techniques for calling HTTP APIs in Ruby](https://mattbrictson.com/blog/advanced-http-techniques-in-ruby) blog post from [@mattbrictson](https://github.com/mattbrictson) ð ## Supported Ruby versions @@ -42,14 +57,11 @@ But before you start coding, please read our [Contributing Guide][contributing] ## Copyright -© 2009 - 2022, the [Faraday Team][faraday_team]. Website and branding design by [Elena Lo Piccolo](https://elelopic.design). -[awesome]: https://github.com/lostisland/awesome-faraday/#adapters -[website]: https://lostisland.github.io/faraday -[faraday_team]: https://lostisland.github.io/faraday/team -[contributing]: https://github.com/lostisland/faraday/blob/master/.github/CONTRIBUTING.md -[apidoc]: https://www.rubydoc.info/github/lostisland/faraday -[actions]: https://github.com/lostisland/faraday/actions -[jruby]: http://jruby.org/ -[rubinius]: http://rubini.us/ -[license]: LICENSE.md +© 2009 - 2023, the Faraday Team. Website and branding design by [Elena Lo Piccolo](https://elelopic.design). + +[awesome]: https://github.com/lostisland/awesome-faraday/#adapters +[website]: https://lostisland.github.io/faraday +[contributing]: https://github.com/lostisland/faraday/blob/main/.github/CONTRIBUTING.md +[apidoc]: https://www.rubydoc.info/github/lostisland/faraday +[actions]: https://github.com/lostisland/faraday/actions diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/Rakefile new/Rakefile --- old/Rakefile 2022-11-18 12:09:30.000000000 +0100 +++ new/Rakefile 2023-09-12 17:43:57.000000000 +0200 @@ -2,6 +2,8 @@ require 'rspec/core/rake_task' -RSpec::Core::RakeTask.new(:spec) +RSpec::Core::RakeTask.new(:spec) do |task| + task.ruby_opts = %w[-W] +end task default: :spec Binary files old/checksums.yaml.gz and new/checksums.yaml.gz differ diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/lib/faraday/adapter/test.rb new/lib/faraday/adapter/test.rb --- old/lib/faraday/adapter/test.rb 2022-11-18 12:09:30.000000000 +0100 +++ new/lib/faraday/adapter/test.rb 2023-09-12 17:43:57.000000000 +0200 @@ -1,5 +1,7 @@ # frozen_string_literal: true +require 'timeout' + module Faraday class Adapter # @example @@ -182,7 +184,7 @@ end # Stub request - class Stub < Struct.new(:host, :path, :query, :headers, :body, :strict_mode, :block) # rubocop:disable Style/StructInheritance + Stub = Struct.new(:host, :path, :query, :headers, :body, :strict_mode, :block) do # @param env [Faraday::Env] def matches?(env) request_host = env[:url].host @@ -238,7 +240,7 @@ end def body_match?(request_body) - return true if body.to_s.size.zero? + return true if body.to_s.empty? case body when Proc @@ -273,15 +275,26 @@ unless stub raise Stubs::NotFound, "no stubbed request for #{env[:method]} " \ - "#{env[:url]} #{env[:body]}" + "#{env[:url]} #{env[:body]} #{env[:headers]}" end block_arity = stub.block.arity + params = if block_arity >= 0 + [env, meta].take(block_arity) + else + [env, meta] + end + + timeout = request_timeout(:open, env[:request]) + timeout ||= request_timeout(:read, env[:request]) + status, headers, body = - if block_arity >= 0 - stub.block.call(*[env, meta].take(block_arity)) + if timeout + ::Timeout.timeout(timeout, Faraday::TimeoutError) do + stub.block.call(*params) + end else - stub.block.call(env, meta) + stub.block.call(*params) end # We need to explicitly pass `reason_phrase = nil` here to avoid keyword args conflicts. diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/lib/faraday/adapter.rb new/lib/faraday/adapter.rb --- old/lib/faraday/adapter.rb 2022-11-18 12:09:30.000000000 +0100 +++ new/lib/faraday/adapter.rb 2023-09-12 17:43:57.000000000 +0200 @@ -78,8 +78,7 @@ # @param type [Symbol] Describes which timeout setting to get: :read, # :write, or :open. # @param options [Hash] Hash containing Symbol keys like :timeout, - # :read_timeout, :write_timeout, :open_timeout, or - # :timeout + # :read_timeout, :write_timeout, or :open_timeout # # @return [Integer, nil] Timeout duration in seconds, or nil if no timeout # has been set. diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/lib/faraday/connection.rb new/lib/faraday/connection.rb --- old/lib/faraday/connection.rb 2022-11-18 12:09:30.000000000 +0100 +++ new/lib/faraday/connection.rb 2023-09-12 17:43:57.000000000 +0200 @@ -220,7 +220,7 @@ # @yield [Faraday::Request] for further request customizations # @return [Faraday::Response] def options(*args) - return @options if args.size.zero? + return @options if args.empty? url, params, headers = *args run_request(:options, url, nil, headers) do |request| @@ -261,14 +261,13 @@ # @param headers [Hash, nil] unencoded HTTP header key/value pairs. # # @example - # # TODO: Make it a PUT example - # conn.post '/items', data, content_type: 'application/json' + # conn.put '/products/123', data, content_type: 'application/json' # - # # Simple ElasticSearch indexing sample. - # conn.post '/twitter/tweet' do |req| - # req.headers[:content_type] = 'application/json' - # req.params[:routing] = 'kimchy' - # req.body = JSON.generate(user: 'kimchy', ...) + # # Star a gist. + # conn.put 'https://api.github.com/gists/GIST_ID/star' do |req| + # req.headers['Accept'] = 'application/vnd.github+json' + # req.headers['Authorization'] = 'Bearer <YOUR-TOKEN>' + # req.headers['X-GitHub-Api-Version'] = '2022-11-28' # end # # @yield [Faraday::Request] for further request customizations @@ -471,10 +470,10 @@ def build_exclusive_url(url = nil, params = nil, params_encoder = nil) url = nil if url.respond_to?(:empty?) && url.empty? base = url_prefix.dup - if url && base.path && base.path !~ %r{/$} + if url && !base.path.end_with?('/') base.path = "#{base.path}/" # ensure trailing slash end - url = url.to_s.gsub(':', '%3A') if url && URI.parse(url.to_s).opaque + url = url.to_s.gsub(':', '%3A') if URI.parse(url.to_s).opaque uri = url ? base + url : base if params uri.query = params.to_query(params_encoder || options.params_encoder) @@ -515,22 +514,17 @@ return if Faraday.ignore_env_proxy uri = nil - if URI.parse('').respond_to?(:find_proxy) - case url - when String - uri = Utils.URI(url) - uri = if uri.host.nil? - find_default_proxy - else - URI.parse("#{uri.scheme}://#{uri.host}").find_proxy - end - when URI - uri = url.find_proxy - when nil - uri = find_default_proxy - end - else - warn 'no_proxy is unsupported' if ENV['no_proxy'] || ENV['NO_PROXY'] + case url + when String + uri = Utils.URI(url) + uri = if uri.host.nil? + find_default_proxy + else + URI.parse("#{uri.scheme}://#{uri.host}").find_proxy + end + when URI + uri = url.find_proxy + when nil uri = find_default_proxy end ProxyOptions.from(uri) if uri diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/lib/faraday/error.rb new/lib/faraday/error.rb --- old/lib/faraday/error.rb 2022-11-18 12:09:30.000000000 +0100 +++ new/lib/faraday/error.rb 2023-09-12 17:43:57.000000000 +0200 @@ -29,15 +29,21 @@ end def response_status - @response[:status] if @response + return unless @response + + @response.is_a?(Faraday::Response) ? @response.status : @response[:status] end def response_headers - @response[:headers] if @response + return unless @response + + @response.is_a?(Faraday::Response) ? @response.headers : @response[:headers] end def response_body - @response[:body] if @response + return unless @response + + @response.is_a?(Faraday::Response) ? @response.body : @response[:body] end protected @@ -106,6 +112,10 @@ class ProxyAuthError < ClientError end + # Raised by Faraday::Response::RaiseError in case of a 408 response. + class RequestTimeoutError < ClientError + end + # Raised by Faraday::Response::RaiseError in case of a 409 response. class ConflictError < ClientError end diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/lib/faraday/logging/formatter.rb new/lib/faraday/logging/formatter.rb --- old/lib/faraday/logging/formatter.rb 2022-11-18 12:09:30.000000000 +0100 +++ new/lib/faraday/logging/formatter.rb 2023-09-12 17:43:57.000000000 +0200 @@ -1,6 +1,6 @@ # frozen_string_literal: true -require 'pp' # rubocop:disable Lint/RedundantRequireStatement +require 'pp' module Faraday module Logging @@ -13,40 +13,40 @@ def initialize(logger:, options:) @logger = logger - @filter = [] @options = DEFAULT_OPTIONS.merge(options) + unless %i[debug info warn error fatal].include?(@options[:log_level]) + @options[:log_level] = :info + end + @filter = [] end def_delegators :@logger, :debug, :info, :warn, :error, :fatal def request(env) - request_log = proc do + public_send(log_level, 'request') do "#{env.method.upcase} #{apply_filters(env.url.to_s)}" end - public_send(log_level, 'request', &request_log) log_headers('request', env.request_headers) if log_headers?(:request) log_body('request', env[:body]) if env[:body] && log_body?(:request) end def response(env) - status = proc { "Status #{env.status}" } - public_send(log_level, 'response', &status) + public_send(log_level, 'response') { "Status #{env.status}" } log_headers('response', env.response_headers) if log_headers?(:response) log_body('response', env[:body]) if env[:body] && log_body?(:response) end - def error(error) + def exception(exc) return unless log_errors? - error_log = proc { error.full_message } - public_send(log_level, 'error', &error_log) + public_send(log_level, 'error') { exc.full_message } - log_headers('error', error.response_headers) if error.respond_to?(:response_headers) && log_headers?(:error) - return unless error.respond_to?(:response_body) && error.response_body && log_body?(:error) + log_headers('error', exc.response_headers) if exc.respond_to?(:response_headers) && log_headers?(:error) + return unless exc.respond_to?(:response_body) && exc.response_body && log_body?(:error) - log_body('error', error.response_body) + log_body('error', exc.response_body) end def filter(filter_word, filter_replacement) @@ -56,6 +56,8 @@ private def dump_headers(headers) + return if headers.nil? + headers.map { |k, v| "#{k}: #{v.inspect}" }.join("\n") end @@ -101,21 +103,15 @@ end def log_level - unless %i[debug info warn error fatal].include?(@options[:log_level]) - return :info - end - @options[:log_level] end def log_headers(type, headers) - headers_log = proc { apply_filters(dump_headers(headers)) } - public_send(log_level, type, &headers_log) + public_send(log_level, type) { apply_filters(dump_headers(headers)) } end def log_body(type, body) - body_log = proc { apply_filters(dump_body(body)) } - public_send(log_level, type, &body_log) + public_send(log_level, type) { apply_filters(dump_body(body)) } end end end diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/lib/faraday/options/connection_options.rb new/lib/faraday/options/connection_options.rb --- old/lib/faraday/options/connection_options.rb 2022-11-18 12:09:30.000000000 +0100 +++ new/lib/faraday/options/connection_options.rb 2023-09-12 17:43:57.000000000 +0200 @@ -1,12 +1,13 @@ # frozen_string_literal: true module Faraday - # ConnectionOptions contains the configurable properties for a Faraday - # connection object. - class ConnectionOptions < Options.new(:request, :proxy, :ssl, :builder, :url, - :parallel_manager, :params, :headers, - :builder_class) - + # @!parse + # # ConnectionOptions contains the configurable properties for a Faraday + # # connection object. + # class ConnectionOptions < Options; end + ConnectionOptions = Options.new(:request, :proxy, :ssl, :builder, :url, + :parallel_manager, :params, :headers, + :builder_class) do options request: RequestOptions, ssl: SSLOptions memoized(:request) { self.class.options_for(:request).new } diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/lib/faraday/options/env.rb new/lib/faraday/options/env.rb --- old/lib/faraday/options/env.rb 2022-11-18 12:09:30.000000000 +0100 +++ new/lib/faraday/options/env.rb 2023-09-12 17:43:57.000000000 +0200 @@ -1,65 +1,70 @@ # frozen_string_literal: true module Faraday - # @!attribute method - # @return [Symbol] HTTP method (`:get`, `:post`) - # - # @!attribute body - # @return [String] The request body that will eventually be converted to a - # string. - # - # @!attribute url - # @return [URI] URI instance for the current request. - # - # @!attribute request - # @return [Hash] options for configuring the request. - # Options for configuring the request. - # - # - `:timeout` open/read timeout Integer in seconds - # - `:open_timeout` - read timeout Integer in seconds - # - `:on_data` - Proc for streaming - # - `:proxy` - Hash of proxy options - # - `:uri` - Proxy Server URI - # - `:user` - Proxy server username - # - `:password` - Proxy server password - # - # @!attribute request_headers - # @return [Hash] HTTP Headers to be sent to the server. - # - # @!attribute ssl - # @return [Hash] options for configuring SSL requests - # - # @!attribute parallel_manager - # @return [Object] sent if the connection is in parallel mode - # - # @!attribute params - # @return [Hash] - # - # @!attribute response - # @return [Response] - # - # @!attribute response_headers - # @return [Hash] HTTP headers from the server - # - # @!attribute status - # @return [Integer] HTTP response status code - # - # @!attribute reason_phrase - # @return [String] - class Env < Options.new(:method, :request_body, :url, :request, - :request_headers, :ssl, :parallel_manager, :params, - :response, :response_headers, :status, - :reason_phrase, :response_body) - - # rubocop:disable Naming/ConstantName - ContentLength = 'Content-Length' - StatusesWithoutBody = Set.new [204, 304] - SuccessfulStatuses = (200..299).freeze - # rubocop:enable Naming/ConstantName + # @!parse + # # @!attribute method + # # @return [Symbol] HTTP method (`:get`, `:post`) + # # + # # @!attribute body + # # @return [String] The request body that will eventually be converted to a + # # string. + # # + # # @!attribute url + # # @return [URI] URI instance for the current request. + # # + # # @!attribute request + # # @return [Hash] options for configuring the request. + # # Options for configuring the request. + # # + # # - `:timeout` - time limit for the entire request (Integer in + # # seconds) + # # - `:open_timeout` - time limit for just the connection phase (e.g. + # # handshake) (Integer in seconds) + # # - `:read_timeout` - time limit for the first response byte received from + # # the server (Integer in seconds) + # # - `:write_timeout` - time limit for the client to send the request to the + # # server (Integer in seconds) + # # - `:on_data` - Proc for streaming + # # - `:proxy` - Hash of proxy options + # # - `:uri` - Proxy server URI + # # - `:user` - Proxy server username + # # - `:password` - Proxy server password + # # + # # @!attribute request_headers + # # @return [Hash] HTTP Headers to be sent to the server. + # # + # # @!attribute ssl + # # @return [Hash] options for configuring SSL requests + # # + # # @!attribute parallel_manager + # # @return [Object] sent if the connection is in parallel mode + # # + # # @!attribute params + # # @return [Hash] + # # + # # @!attribute response + # # @return [Response] + # # + # # @!attribute response_headers + # # @return [Hash] HTTP headers from the server + # # + # # @!attribute status + # # @return [Integer] HTTP response status code + # # + # # @!attribute reason_phrase + # # @return [String] + # class Env < Options; end + Env = Options.new(:method, :request_body, :url, :request, + :request_headers, :ssl, :parallel_manager, :params, + :response, :response_headers, :status, + :reason_phrase, :response_body) do + const_set(:ContentLength, 'Content-Length') + const_set(:StatusesWithoutBody, Set.new([204, 304])) + const_set(:SuccessfulStatuses, (200..299).freeze) # A Set of HTTP verbs that typically send a body. If no body is set for # these requests, the Content-Length header is set to 0. - MethodsWithBodies = Set.new(Faraday::METHODS_WITH_BODY.map(&:to_sym)) + const_set(:MethodsWithBodies, Set.new(Faraday::METHODS_WITH_BODY.map(&:to_sym))) options request: RequestOptions, request_headers: Utils::Headers, response_headers: Utils::Headers @@ -120,25 +125,25 @@ # @return [Boolean] true if status is in the set of {SuccessfulStatuses}. def success? - SuccessfulStatuses.include?(status) + Env::SuccessfulStatuses.include?(status) end # @return [Boolean] true if there's no body yet, and the method is in the - # set of {MethodsWithBodies}. + # set of {Env::MethodsWithBodies}. def needs_body? - !body && MethodsWithBodies.include?(method) + !body && Env::MethodsWithBodies.include?(method) end # Sets content length to zero and the body to the empty string. def clear_body - request_headers[ContentLength] = '0' + request_headers[Env::ContentLength] = '0' self.body = +'' end # @return [Boolean] true if the status isn't in the set of - # {StatusesWithoutBody}. + # {Env::StatusesWithoutBody}. def parse_body? - !StatusesWithoutBody.include?(status) + !Env::StatusesWithoutBody.include?(status) end # @return [Boolean] true if there is a parallel_manager diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/lib/faraday/options/proxy_options.rb new/lib/faraday/options/proxy_options.rb --- old/lib/faraday/options/proxy_options.rb 2022-11-18 12:09:30.000000000 +0100 +++ new/lib/faraday/options/proxy_options.rb 2023-09-12 17:43:57.000000000 +0200 @@ -1,15 +1,19 @@ # frozen_string_literal: true module Faraday - # ProxyOptions contains the configurable properties for the proxy - # configuration used when making an HTTP request. - class ProxyOptions < Options.new(:uri, :user, :password) + # @!parse + # # ProxyOptions contains the configurable properties for the proxy + # # configuration used when making an HTTP request. + # class ProxyOptions < Options; end + ProxyOptions = Options.new(:uri, :user, :password) do extend Forwardable def_delegators :uri, :scheme, :scheme=, :host, :host=, :port, :port=, :path, :path= def self.from(value) case value + when '' + value = nil when String # URIs without a scheme should default to http (like 'example:123'). # This fixes #1282 and prevents a silent failure in some adapters. diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/lib/faraday/options/request_options.rb new/lib/faraday/options/request_options.rb --- old/lib/faraday/options/request_options.rb 2022-11-18 12:09:30.000000000 +0100 +++ new/lib/faraday/options/request_options.rb 2023-09-12 17:43:57.000000000 +0200 @@ -1,12 +1,13 @@ # frozen_string_literal: true module Faraday - # RequestOptions contains the configurable properties for a Faraday request. - class RequestOptions < Options.new(:params_encoder, :proxy, :bind, - :timeout, :open_timeout, :read_timeout, - :write_timeout, :boundary, :oauth, - :context, :on_data) - + # @!parse + # # RequestOptions contains the configurable properties for a Faraday request. + # class RequestOptions < Options; end + RequestOptions = Options.new(:params_encoder, :proxy, :bind, + :timeout, :open_timeout, :read_timeout, + :write_timeout, :boundary, :oauth, + :context, :on_data) do def []=(key, value) if key && key.to_sym == :proxy super(key, value ? ProxyOptions.from(value) : nil) diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/lib/faraday/options/ssl_options.rb new/lib/faraday/options/ssl_options.rb --- old/lib/faraday/options/ssl_options.rb 2022-11-18 12:09:30.000000000 +0100 +++ new/lib/faraday/options/ssl_options.rb 2023-09-12 17:43:57.000000000 +0200 @@ -1,56 +1,57 @@ # frozen_string_literal: true module Faraday - # SSL-related options. - # - # @!attribute verify - # @return [Boolean] whether to verify SSL certificates or not - # - # @!attribute verify_hostname - # @return [Boolean] whether to enable hostname verification on server certificates - # during the handshake or not (see https://github.com/ruby/openssl/pull/60) - # - # @!attribute ca_file - # @return [String] CA file - # - # @!attribute ca_path - # @return [String] CA path - # - # @!attribute verify_mode - # @return [Integer] Any `OpenSSL::SSL::` constant (see https://ruby-doc.org/stdlib-2.5.1/libdoc/openssl/rdoc/OpenSSL/SSL.html) - # - # @!attribute cert_store - # @return [OpenSSL::X509::Store] certificate store - # - # @!attribute client_cert - # @return [String, OpenSSL::X509::Certificate] client certificate - # - # @!attribute client_key - # @return [String, OpenSSL::PKey::RSA, OpenSSL::PKey::DSA] client key - # - # @!attribute certificate - # @return [OpenSSL::X509::Certificate] certificate (Excon only) - # - # @!attribute private_key - # @return [OpenSSL::PKey::RSA, OpenSSL::PKey::DSA] private key (Excon only) - # - # @!attribute verify_depth - # @return [Integer] maximum depth for the certificate chain verification - # - # @!attribute version - # @return [String, Symbol] SSL version (see https://ruby-doc.org/stdlib-2.5.1/libdoc/openssl/rdoc/OpenSSL/SSL/SSLContext.html#method-i-ssl_version-3D) - # - # @!attribute min_version - # @return [String, Symbol] minimum SSL version (see https://ruby-doc.org/stdlib-2.5.1/libdoc/openssl/rdoc/OpenSSL/SSL/SSLContext.html#method-i-min_version-3D) - # - # @!attribute max_version - # @return [String, Symbol] maximum SSL version (see https://ruby-doc.org/stdlib-2.5.1/libdoc/openssl/rdoc/OpenSSL/SSL/SSLContext.html#method-i-max_version-3D) - class SSLOptions < Options.new(:verify, :verify_hostname, - :ca_file, :ca_path, :verify_mode, - :cert_store, :client_cert, :client_key, - :certificate, :private_key, :verify_depth, - :version, :min_version, :max_version) - + # @!parse + # # SSL-related options. + # # + # # @!attribute verify + # # @return [Boolean] whether to verify SSL certificates or not + # # + # # @!attribute verify_hostname + # # @return [Boolean] whether to enable hostname verification on server certificates + # # during the handshake or not (see https://github.com/ruby/openssl/pull/60) + # # + # # @!attribute ca_file + # # @return [String] CA file + # # + # # @!attribute ca_path + # # @return [String] CA path + # # + # # @!attribute verify_mode + # # @return [Integer] Any `OpenSSL::SSL::` constant (see https://ruby-doc.org/stdlib-2.5.1/libdoc/openssl/rdoc/OpenSSL/SSL.html) + # # + # # @!attribute cert_store + # # @return [OpenSSL::X509::Store] certificate store + # # + # # @!attribute client_cert + # # @return [String, OpenSSL::X509::Certificate] client certificate + # # + # # @!attribute client_key + # # @return [String, OpenSSL::PKey::RSA, OpenSSL::PKey::DSA] client key + # # + # # @!attribute certificate + # # @return [OpenSSL::X509::Certificate] certificate (Excon only) + # # + # # @!attribute private_key + # # @return [OpenSSL::PKey::RSA, OpenSSL::PKey::DSA] private key (Excon only) + # # + # # @!attribute verify_depth + # # @return [Integer] maximum depth for the certificate chain verification + # # + # # @!attribute version + # # @return [String, Symbol] SSL version (see https://ruby-doc.org/stdlib-2.5.1/libdoc/openssl/rdoc/OpenSSL/SSL/SSLContext.html#method-i-ssl_version-3D) + # # + # # @!attribute min_version + # # @return [String, Symbol] minimum SSL version (see https://ruby-doc.org/stdlib-2.5.1/libdoc/openssl/rdoc/OpenSSL/SSL/SSLContext.html#method-i-min_version-3D) + # # + # # @!attribute max_version + # # @return [String, Symbol] maximum SSL version (see https://ruby-doc.org/stdlib-2.5.1/libdoc/openssl/rdoc/OpenSSL/SSL/SSLContext.html#method-i-max_version-3D) + # class SSLOptions < Options; end + SSLOptions = Options.new(:verify, :verify_hostname, + :ca_file, :ca_path, :verify_mode, + :cert_store, :client_cert, :client_key, + :certificate, :private_key, :verify_depth, + :version, :min_version, :max_version) do # @return [Boolean] true if should verify def verify? verify != false diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/lib/faraday/options.rb new/lib/faraday/options.rb --- old/lib/faraday/options.rb 2022-11-18 12:09:30.000000000 +0100 +++ new/lib/faraday/options.rb 2023-09-12 17:43:57.000000000 +0200 @@ -174,6 +174,7 @@ memoized_attributes[key.to_sym] = block class_eval <<-RUBY, __FILE__, __LINE__ + 1 + remove_method(key) if method_defined?(key, false) def #{key}() self[:#{key}]; end RUBY end diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/lib/faraday/request/instrumentation.rb new/lib/faraday/request/instrumentation.rb --- old/lib/faraday/request/instrumentation.rb 2022-11-18 12:09:30.000000000 +0100 +++ new/lib/faraday/request/instrumentation.rb 2023-09-12 17:43:57.000000000 +0200 @@ -5,12 +5,14 @@ # Middleware for instrumenting Requests. class Instrumentation < Faraday::Middleware # Options class used in Request::Instrumentation class. - class Options < Faraday::Options.new(:name, :instrumenter) + Options = Faraday::Options.new(:name, :instrumenter) do + remove_method :name # @return [String] def name self[:name] ||= 'request.faraday' end + remove_method :instrumenter # @return [Class] def instrumenter self[:instrumenter] ||= ActiveSupport::Notifications diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/lib/faraday/request/json.rb new/lib/faraday/request/json.rb --- old/lib/faraday/request/json.rb 2022-11-18 12:09:30.000000000 +0100 +++ new/lib/faraday/request/json.rb 2023-09-12 17:43:57.000000000 +0200 @@ -40,7 +40,16 @@ end def body?(env) - (body = env[:body]) && !(body.respond_to?(:to_str) && body.empty?) + body = env[:body] + case body + when true, false + true + when nil + # NOTE: nil can be converted to `"null"`, but this middleware doesn't process `nil` for the compatibility. + false + else + !(body.respond_to?(:to_str) && body.empty?) + end end def request_type(env) diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/lib/faraday/request.rb new/lib/faraday/request.rb --- old/lib/faraday/request.rb 2022-11-18 12:09:30.000000000 +0100 +++ new/lib/faraday/request.rb 2023-09-12 17:43:57.000000000 +0200 @@ -24,13 +24,14 @@ # @return [String] body # @!attribute options # @return [RequestOptions] options - # - # rubocop:disable Style/StructInheritance - class Request < Struct.new(:http_method, :path, :params, :headers, :body, :options) - # rubocop:enable Style/StructInheritance - + Request = Struct.new(:http_method, :path, :params, :headers, :body, :options) do extend MiddlewareRegistry + alias_method :member_get, :[] + private :member_get + alias_method :member_set, :[]= + private :member_set + # @param request_method [String] # @yield [request] for block customization, if block given # @yieldparam request [Request] @@ -41,6 +42,7 @@ end end + remove_method :params= # Replace params, preserving the existing hash type. # # @param hash [Hash] new params @@ -48,10 +50,11 @@ if params params.replace hash else - super + member_set(:params, hash) end end + remove_method :headers= # Replace request headers, preserving the existing hash type. # # @param hash [Hash] new headers @@ -59,7 +62,7 @@ if headers headers.replace hash else - super + member_set(:headers, hash) end end diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/lib/faraday/response/logger.rb new/lib/faraday/response/logger.rb --- old/lib/faraday/response/logger.rb 2022-11-18 12:09:30.000000000 +0100 +++ new/lib/faraday/response/logger.rb 2023-09-12 17:43:57.000000000 +0200 @@ -27,8 +27,8 @@ @formatter.response(env) end - def on_error(error) - @formatter.error(error) if @formatter.respond_to?(:error) + def on_error(exc) + @formatter.exception(exc) if @formatter.respond_to?(:exception) end end end diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/lib/faraday/response/raise_error.rb new/lib/faraday/response/raise_error.rb --- old/lib/faraday/response/raise_error.rb 2022-11-18 12:09:30.000000000 +0100 +++ new/lib/faraday/response/raise_error.rb 2023-09-12 17:43:57.000000000 +0200 @@ -24,6 +24,8 @@ # mimic the behavior that we get with proxy requests with HTTPS msg = %(407 "Proxy Authentication Required") raise Faraday::ProxyAuthError.new(msg, response_values(env)) + when 408 + raise Faraday::RequestTimeoutError, response_values(env) when 409 raise Faraday::ConflictError, response_values(env) when 422 @@ -37,11 +39,26 @@ end end + # Returns a hash of response data with the following keys: + # - status + # - headers + # - body + # - request + # + # The `request` key is omitted when the middleware is explicitly + # configured with the option `include_request: false`. def response_values(env) - { + response = { status: env.status, headers: env.response_headers, - body: env.body, + body: env.body + } + + # Include the request data by default. If the middleware was explicitly + # configured to _not_ include request data, then omit it. + return response unless options.fetch(:include_request, true) + + response.merge( request: { method: env.method, url: env.url, @@ -50,7 +67,7 @@ headers: env.request_headers, body: env.request_body } - } + ) end def query_params(env) diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/lib/faraday/response.rb new/lib/faraday/response.rb --- old/lib/faraday/response.rb 2022-11-18 12:09:30.000000000 +0100 +++ new/lib/faraday/response.rb 2023-09-12 17:43:57.000000000 +0200 @@ -61,7 +61,8 @@ def to_hash { status: env.status, body: env.body, - response_headers: env.response_headers + response_headers: env.response_headers, + url: env.url } end diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/lib/faraday/version.rb new/lib/faraday/version.rb --- old/lib/faraday/version.rb 2022-11-18 12:09:30.000000000 +0100 +++ new/lib/faraday/version.rb 2023-09-12 17:43:57.000000000 +0200 @@ -1,5 +1,5 @@ # frozen_string_literal: true module Faraday - VERSION = '2.7.1' + VERSION = '2.7.11' end diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/metadata new/metadata --- old/metadata 2022-11-18 12:09:30.000000000 +0100 +++ new/metadata 2023-09-12 17:43:57.000000000 +0200 @@ -1,7 +1,7 @@ --- !ruby/object:Gem::Specification name: faraday version: !ruby/object:Gem::Version - version: 2.7.1 + version: 2.7.11 platform: ruby authors: - "@technoweenie" @@ -10,9 +10,23 @@ autorequire: bindir: bin cert_chain: [] -date: 2022-11-18 00:00:00.000000000 Z +date: 2023-09-12 00:00:00.000000000 Z dependencies: - !ruby/object:Gem::Dependency + name: base64 + requirement: !ruby/object:Gem::Requirement + requirements: + - - ">=" + - !ruby/object:Gem::Version + version: '0' + type: :runtime + prerelease: false + version_requirements: !ruby/object:Gem::Requirement + requirements: + - - ">=" + - !ruby/object:Gem::Version + version: '0' +- !ruby/object:Gem::Dependency name: faraday-net_http requirement: !ruby/object:Gem::Requirement requirements: @@ -131,7 +145,7 @@ - MIT metadata: homepage_uri: https://lostisland.github.io/faraday - changelog_uri: https://github.com/lostisland/faraday/releases/tag/v2.7.1 + changelog_uri: https://github.com/lostisland/faraday/releases/tag/v2.7.11 source_code_uri: https://github.com/lostisland/faraday bug_tracker_uri: https://github.com/lostisland/faraday/issues post_install_message: diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/spec/faraday/adapter/test_spec.rb new/spec/faraday/adapter/test_spec.rb --- old/spec/faraday/adapter/test_spec.rb 2022-11-18 12:09:30.000000000 +0100 +++ new/spec/faraday/adapter/test_spec.rb 2023-09-12 17:43:57.000000000 +0200 @@ -410,4 +410,33 @@ end end end + + describe 'request timeout' do + subject(:request) do + connection.get('/sleep') do |req| + req.options.timeout = timeout + end + end + + before do + stubs.get('/sleep') do + sleep(0.01) + [200, {}, ''] + end + end + + context 'when request is within timeout' do + let(:timeout) { 1 } + + it { expect(request.status).to eq 200 } + end + + context 'when request is too slow' do + let(:timeout) { 0.001 } + + it 'raises an exception' do + expect { request }.to raise_error(Faraday::TimeoutError) + end + end + end end diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/spec/faraday/connection_spec.rb new/spec/faraday/connection_spec.rb --- old/spec/faraday/connection_spec.rb 2022-11-18 12:09:30.000000000 +0100 +++ new/spec/faraday/connection_spec.rb 2023-09-12 17:43:57.000000000 +0200 @@ -310,6 +310,21 @@ expect(uri.to_s).to eq('http://service.com/api/service%3Asearch?limit=400') end end + + context 'with a custom `default_uri_parser`' do + let(:url) { 'http://httpbingo.org' } + let(:parser) { Addressable::URI } + + around do |example| + with_default_uri_parser(parser) do + example.run + end + end + + it 'does not raise error' do + expect { conn.build_exclusive_url('/nigiri') }.not_to raise_error + end + end end describe '#build_url' do diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/spec/faraday/error_spec.rb new/spec/faraday/error_spec.rb --- old/spec/faraday/error_spec.rb 2022-11-18 12:09:30.000000000 +0100 +++ new/spec/faraday/error_spec.rb 2023-09-12 17:43:57.000000000 +0200 @@ -1,6 +1,6 @@ # frozen_string_literal: true -RSpec.describe Faraday::ClientError do +RSpec.describe Faraday::Error do describe '.initialize' do subject { described_class.new(exception, response) } let(:response) { nil } @@ -12,8 +12,10 @@ it { expect(subject.response).to be_nil } it { expect(subject.message).to eq(exception.message) } it { expect(subject.backtrace).to eq(exception.backtrace) } - it { expect(subject.inspect).to eq('#<Faraday::ClientError wrapped=#<RuntimeError: test>>') } + it { expect(subject.inspect).to eq('#<Faraday::Error wrapped=#<RuntimeError: test>>') } it { expect(subject.response_status).to be_nil } + it { expect(subject.response_headers).to be_nil } + it { expect(subject.response_body).to be_nil } end context 'with response hash' do @@ -22,8 +24,10 @@ it { expect(subject.wrapped_exception).to be_nil } it { expect(subject.response).to eq(exception) } it { expect(subject.message).to eq('the server responded with status 400') } - it { expect(subject.inspect).to eq('#<Faraday::ClientError response={:status=>400}>') } + it { expect(subject.inspect).to eq('#<Faraday::Error response={:status=>400}>') } it { expect(subject.response_status).to eq(400) } + it { expect(subject.response_headers).to be_nil } + it { expect(subject.response_body).to be_nil } end context 'with string' do @@ -32,8 +36,10 @@ it { expect(subject.wrapped_exception).to be_nil } it { expect(subject.response).to be_nil } it { expect(subject.message).to eq('custom message') } - it { expect(subject.inspect).to eq('#<Faraday::ClientError #<Faraday::ClientError: custom message>>') } + it { expect(subject.inspect).to eq('#<Faraday::Error #<Faraday::Error: custom message>>') } it { expect(subject.response_status).to be_nil } + it { expect(subject.response_headers).to be_nil } + it { expect(subject.response_body).to be_nil } end context 'with anything else #to_s' do @@ -42,8 +48,10 @@ it { expect(subject.wrapped_exception).to be_nil } it { expect(subject.response).to be_nil } it { expect(subject.message).to eq('["error1", "error2"]') } - it { expect(subject.inspect).to eq('#<Faraday::ClientError #<Faraday::ClientError: ["error1", "error2"]>>') } + it { expect(subject.inspect).to eq('#<Faraday::Error #<Faraday::Error: ["error1", "error2"]>>') } it { expect(subject.response_status).to be_nil } + it { expect(subject.response_headers).to be_nil } + it { expect(subject.response_body).to be_nil } end context 'with exception string and response hash' do @@ -53,8 +61,25 @@ it { expect(subject.wrapped_exception).to be_nil } it { expect(subject.response).to eq(response) } it { expect(subject.message).to eq('custom message') } - it { expect(subject.inspect).to eq('#<Faraday::ClientError response={:status=>400}>') } + it { expect(subject.inspect).to eq('#<Faraday::Error response={:status=>400}>') } it { expect(subject.response_status).to eq(400) } + it { expect(subject.response_headers).to be_nil } + it { expect(subject.response_body).to be_nil } + end + + context 'with exception and response object' do + let(:exception) { RuntimeError.new('test') } + let(:body) { { test: 'test' } } + let(:headers) { { 'Content-Type' => 'application/json' } } + let(:response) { Faraday::Response.new(status: 400, response_headers: headers, response_body: body) } + + it { expect(subject.wrapped_exception).to eq(exception) } + it { expect(subject.response).to eq(response) } + it { expect(subject.message).to eq(exception.message) } + it { expect(subject.backtrace).to eq(exception.backtrace) } + it { expect(subject.response_status).to eq(400) } + it { expect(subject.response_headers).to eq(headers) } + it { expect(subject.response_body).to eq(body) } end end end diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/spec/faraday/options/options_spec.rb new/spec/faraday/options/options_spec.rb --- old/spec/faraday/options/options_spec.rb 2022-11-18 12:09:30.000000000 +0100 +++ new/spec/faraday/options/options_spec.rb 2023-09-12 17:43:57.000000000 +0200 @@ -2,7 +2,7 @@ RSpec.describe Faraday::Options do SubOptions = Class.new(Faraday::Options.new(:sub_a, :sub_b)) - class ParentOptions < Faraday::Options.new(:a, :b, :c) + ParentOptions = Faraday::Options.new(:a, :b, :c) do options c: SubOptions end diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/spec/faraday/options/proxy_options_spec.rb new/spec/faraday/options/proxy_options_spec.rb --- old/spec/faraday/options/proxy_options_spec.rb 2022-11-18 12:09:30.000000000 +0100 +++ new/spec/faraday/options/proxy_options_spec.rb 2023-09-12 17:43:57.000000000 +0200 @@ -32,6 +32,14 @@ expect(proxy.user).to be_nil expect(proxy.password).to be_nil end + + it 'treats empty string as nil' do + proxy = nil + proxy_string = proxy.to_s # => empty string + options = Faraday::ProxyOptions.from proxy_string + expect(options).to be_a_kind_of(Faraday::ProxyOptions) + expect(options.inspect).to eq('#<Faraday::ProxyOptions (empty)>') + end end it 'allows hash access' do diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/spec/faraday/request/json_spec.rb new/spec/faraday/request/json_spec.rb --- old/spec/faraday/request/json_spec.rb 2022-11-18 12:09:30.000000000 +0100 +++ new/spec/faraday/request/json_spec.rb 2023-09-12 17:43:57.000000000 +0200 @@ -73,6 +73,30 @@ end end + context 'true body' do + let(:result) { process(true) } + + it 'encodes body' do + expect(result_body).to eq('true') + end + + it 'adds content type' do + expect(result_type).to eq('application/json') + end + end + + context 'false body' do + let(:result) { process(false) } + + it 'encodes body' do + expect(result_body).to eq('false') + end + + it 'adds content type' do + expect(result_type).to eq('application/json') + end + end + context 'object body with json type' do let(:result) { process({ a: 1 }, 'application/json; charset=utf-8') } diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/spec/faraday/response/logger_spec.rb new/spec/faraday/response/logger_spec.rb --- old/spec/faraday/response/logger_spec.rb 2022-11-18 12:09:30.000000000 +0100 +++ new/spec/faraday/response/logger_spec.rb 2023-09-12 17:43:57.000000000 +0200 @@ -25,6 +25,7 @@ stubs.get('/filtered_headers') { [200, { 'Content-Type' => 'text/html' }, 'headers response'] } stubs.get('/filtered_params') { [200, { 'Content-Type' => 'text/html' }, 'params response'] } stubs.get('/filtered_url') { [200, { 'Content-Type' => 'text/html' }, 'url response'] } + stubs.get('/connection_failed') { raise Faraday::ConnectionFailed, 'Failed to open TCP connection' } end end end @@ -68,7 +69,7 @@ context 'when no route' do it 'delegates logging to the formatter' do expect(formatter).to receive(:request).with(an_instance_of(Faraday::Env)) - expect(formatter).to receive(:error).with(an_instance_of(Faraday::Adapter::Test::Stubs::NotFound)) + expect(formatter).to receive(:exception).with(an_instance_of(Faraday::Adapter::Test::Stubs::NotFound)) expect { conn.get '/noroute' }.to raise_error(Faraday::Adapter::Test::Stubs::NotFound) end @@ -216,6 +217,15 @@ end end + context 'when logging headers and errors' do + let(:logger_options) { { headers: true, errors: true } } + + it 'logs error message' do + expect { conn.get '/connection_failed' }.to raise_error(Faraday::ConnectionFailed) + expect(string_io.string).to match(%(Failed to open TCP connection)) + end + end + context 'when using log_level' do let(:logger_options) { { bodies: true, log_level: :debug } } diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/spec/faraday/response/raise_error_spec.rb new/spec/faraday/response/raise_error_spec.rb --- old/spec/faraday/response/raise_error_spec.rb 2022-11-18 12:09:30.000000000 +0100 +++ new/spec/faraday/response/raise_error_spec.rb 2023-09-12 17:43:57.000000000 +0200 @@ -11,6 +11,7 @@ stub.get('forbidden') { [403, { 'X-Reason' => 'because' }, 'keep looking'] } stub.get('not-found') { [404, { 'X-Reason' => 'because' }, 'keep looking'] } stub.get('proxy-error') { [407, { 'X-Reason' => 'because' }, 'keep looking'] } + stub.get('request-timeout') { [408, { 'X-Reason' => 'because' }, 'keep looking'] } stub.get('conflict') { [409, { 'X-Reason' => 'because' }, 'keep looking'] } stub.get('unprocessable-entity') { [422, { 'X-Reason' => 'because' }, 'keep looking'] } stub.get('4xx') { [499, { 'X-Reason' => 'because' }, 'keep looking'] } @@ -79,6 +80,17 @@ end end + it 'raises Faraday::RequestTimeoutError for 408 responses' do + expect { conn.get('request-timeout') }.to raise_error(Faraday::RequestTimeoutError) do |ex| + expect(ex.message).to eq('the server responded with status 408') + expect(ex.response[:headers]['X-Reason']).to eq('because') + expect(ex.response[:status]).to eq(408) + expect(ex.response_status).to eq(408) + expect(ex.response_body).to eq('keep looking') + expect(ex.response_headers['X-Reason']).to eq('because') + end + end + it 'raises Faraday::ConflictError for 409 responses' do expect { conn.get('conflict') }.to raise_error(Faraday::ConflictError) do |ex| expect(ex.message).to eq('the server responded with status 409') @@ -137,7 +149,7 @@ describe 'request info' do let(:conn) do Faraday.new do |b| - b.response :raise_error + b.response :raise_error, **middleware_options b.adapter :test do |stub| stub.post(url, request_body, request_headers) do [400, { 'X-Reason' => 'because' }, 'keep looking'] @@ -145,6 +157,7 @@ end end end + let(:middleware_options) { {} } let(:request_body) { JSON.generate({ 'item' => 'sth' }) } let(:request_headers) { { 'Authorization' => 'Basic 123' } } let(:url_path) { 'request' } @@ -168,5 +181,19 @@ expect(ex.response[:request][:body]).to eq(request_body) end end + + context 'when the include_request option is set to false' do + let(:middleware_options) { { include_request: false } } + + it 'does not include request info in the exception' do + expect { perform_request }.to raise_error(Faraday::BadRequestError) do |ex| + expect(ex.response.keys).to contain_exactly( + :status, + :headers, + :body + ) + end + end + end end end diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/spec/faraday/response_spec.rb new/spec/faraday/response_spec.rb --- old/spec/faraday/response_spec.rb 2022-11-18 12:09:30.000000000 +0100 +++ new/spec/faraday/response_spec.rb 2023-09-12 17:43:57.000000000 +0200 @@ -4,7 +4,7 @@ subject { Faraday::Response.new(env) } let(:env) do - Faraday::Env.from(status: 404, body: 'yikes', + Faraday::Env.from(status: 404, body: 'yikes', url: Faraday::Utils.URI('https://lostisland.github.io/faraday'), response_headers: { 'Content-Type' => 'text/plain' }) end @@ -30,6 +30,7 @@ it { expect(hash[:status]).to eq(subject.status) } it { expect(hash[:response_headers]).to eq(subject.headers) } it { expect(hash[:body]).to eq(subject.body) } + it { expect(hash[:url]).to eq(subject.env.url) } end describe 'marshal serialization support' do @@ -45,6 +46,7 @@ it { expect(loaded.env[:body]).to eq(env[:body]) } it { expect(loaded.env[:response_headers]).to eq(env[:response_headers]) } it { expect(loaded.env[:status]).to eq(env[:status]) } + it { expect(loaded.env[:url]).to eq(env[:url]) } end describe '#on_complete' do diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/spec/faraday_spec.rb new/spec/faraday_spec.rb --- old/spec/faraday_spec.rb 2022-11-18 12:09:30.000000000 +0100 +++ new/spec/faraday_spec.rb 2023-09-12 17:43:57.000000000 +0200 @@ -18,10 +18,14 @@ end it 'uses method_missing on Faraday if there is no proxyable method' do - expect { Faraday.this_method_does_not_exist }.to raise_error( - NoMethodError, - "undefined method `this_method_does_not_exist' for Faraday:Module" - ) + expected_message = + if RUBY_VERSION >= '3.3' + "undefined method `this_method_does_not_exist' for module Faraday" + else + "undefined method `this_method_does_not_exist' for Faraday:Module" + end + + expect { Faraday.this_method_does_not_exist }.to raise_error(NoMethodError, expected_message) end it 'proxied methods can be accessed' do