aws-sigv4 1.4.0 → 1.5.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/CHANGELOG.md +10 -0
- data/VERSION +1 -1
- data/lib/aws-sigv4/signature.rb +2 -0
- data/lib/aws-sigv4/signer.rb +154 -5
- data/lib/aws-sigv4.rb +6 -0
- metadata +2 -2
    
        checksums.yaml
    CHANGED
    
    | @@ -1,7 +1,7 @@ | |
| 1 1 | 
             
            ---
         | 
| 2 2 | 
             
            SHA256:
         | 
| 3 | 
            -
              metadata.gz:  | 
| 4 | 
            -
              data.tar.gz:  | 
| 3 | 
            +
              metadata.gz: '024807372644472d420e52bd415e36b47d1ceb4eabad0d76c505e9a5b8c1bf4a'
         | 
| 4 | 
            +
              data.tar.gz: a1f7102b525847893157a95988b2252fa560443d461fd568744599563a060a10
         | 
| 5 5 | 
             
            SHA512:
         | 
| 6 | 
            -
              metadata.gz:  | 
| 7 | 
            -
              data.tar.gz:  | 
| 6 | 
            +
              metadata.gz: 1e2d0ad4e485957c009ced92febe1df4105c557a224ac9a6a93c960f46503cb8f8fde5e695afec58bcd02b8866fb5705c96e085863479115ceb193a490a55e51
         | 
| 7 | 
            +
              data.tar.gz: 7cc4b490fd35ceb5a7af7904b8f353cdb08f76da8c286a4358071136f3491bf49e4adbbe24599193da2a5dc59a0daa3ad382aa0609a8060a5f13d0ed52a48d63
         | 
    
        data/CHANGELOG.md
    CHANGED
    
    | @@ -1,6 +1,16 @@ | |
| 1 1 | 
             
            Unreleased Changes
         | 
| 2 2 | 
             
            ------------------
         | 
| 3 3 |  | 
| 4 | 
            +
            1.5.1 (2022-07-19)
         | 
| 5 | 
            +
            ------------------
         | 
| 6 | 
            +
             | 
| 7 | 
            +
            * Issue - Fix performance regression when checking if `aws-crt` is available. (#2729)
         | 
| 8 | 
            +
             | 
| 9 | 
            +
            1.5.0 (2022-04-20)
         | 
| 10 | 
            +
            ------------------
         | 
| 11 | 
            +
             | 
| 12 | 
            +
            * Feature - Use CRT based signers if `aws-crt` is available - provides support for `sigv4a`.
         | 
| 13 | 
            +
             | 
| 4 14 | 
             
            1.4.0 (2021-09-02)
         | 
| 5 15 | 
             
            ------------------
         | 
| 6 16 |  | 
    
        data/VERSION
    CHANGED
    
    | @@ -1 +1 @@ | |
| 1 | 
            -
            1. | 
| 1 | 
            +
            1.5.1
         | 
    
        data/lib/aws-sigv4/signature.rb
    CHANGED
    
    
    
        data/lib/aws-sigv4/signer.rb
    CHANGED
    
    | @@ -74,6 +74,14 @@ module Aws | |
| 74 74 | 
             
                #
         | 
| 75 75 | 
             
                class Signer
         | 
| 76 76 |  | 
| 77 | 
            +
                  @@use_crt =
         | 
| 78 | 
            +
                    begin
         | 
| 79 | 
            +
                      require 'aws-crt'
         | 
| 80 | 
            +
                      true
         | 
| 81 | 
            +
                    rescue LoadError
         | 
| 82 | 
            +
                      false
         | 
| 83 | 
            +
                    end
         | 
| 84 | 
            +
             | 
| 77 85 | 
             
                  # @overload initialize(service:, region:, access_key_id:, secret_access_key:, session_token:nil, **options)
         | 
| 78 86 | 
             
                  #   @param [String] :service The service signing name, e.g. 's3'.
         | 
| 79 87 | 
             
                  #   @param [String] :region The region name, e.g. 'us-east-1'.
         | 
| @@ -118,6 +126,18 @@ module Aws | |
| 118 126 | 
             
                  #   headers. This is required for AWS Glacier, and optional for
         | 
| 119 127 | 
             
                  #   every other AWS service as of late 2016.
         | 
| 120 128 | 
             
                  #
         | 
| 129 | 
            +
                  # @option options [Symbol] :signing_algorithm (:sigv4) The
         | 
| 130 | 
            +
                  #   algorithm to use for signing.  :sigv4a is only supported when
         | 
| 131 | 
            +
                  #   `aws-crt` is available.
         | 
| 132 | 
            +
                  #
         | 
| 133 | 
            +
                  # @option options [Boolean] :omit_session_token (false)
         | 
| 134 | 
            +
                  #   (Supported only when `aws-crt` is available) If `true`,
         | 
| 135 | 
            +
                  #   then security token is added to the final signing result,
         | 
| 136 | 
            +
                  #   but is treated as "unsigned" and does not contribute
         | 
| 137 | 
            +
                  #   to the authorization signature.
         | 
| 138 | 
            +
                  #
         | 
| 139 | 
            +
                  # @option options [Boolean] :normalize_path (true) (Supported only when `aws-crt` is available)
         | 
| 140 | 
            +
                  #   When `true`, the uri paths will be normalized when building the canonical request
         | 
| 121 141 | 
             
                  def initialize(options = {})
         | 
| 122 142 | 
             
                    @service = extract_service(options)
         | 
| 123 143 | 
             
                    @region = extract_region(options)
         | 
| @@ -126,13 +146,15 @@ module Aws | |
| 126 146 | 
             
                    @unsigned_headers << 'authorization'
         | 
| 127 147 | 
             
                    @unsigned_headers << 'x-amzn-trace-id'
         | 
| 128 148 | 
             
                    @unsigned_headers << 'expect'
         | 
| 129 | 
            -
                     | 
| 130 | 
            -
             | 
| 131 | 
            -
                     | 
| 149 | 
            +
                    @uri_escape_path = options.fetch(:uri_escape_path, true)
         | 
| 150 | 
            +
                    @apply_checksum_header = options.fetch(:apply_checksum_header, true)
         | 
| 151 | 
            +
                    @signing_algorithm = options.fetch(:signing_algorithm, :sigv4)
         | 
| 152 | 
            +
                    @normalize_path = options.fetch(:normalize_path, true)
         | 
| 153 | 
            +
                    @omit_session_token = options.fetch(:omit_session_token, false)
         | 
| 132 154 |  | 
| 133 | 
            -
                    if  | 
| 155 | 
            +
                    if @signing_algorithm == :sigv4a && !Signer.use_crt?
         | 
| 134 156 | 
             
                      raise ArgumentError, 'You are attempting to sign a' \
         | 
| 135 | 
            -
            ' request with sigv4a which requires  | 
| 157 | 
            +
            ' request with sigv4a which requires the `aws-crt` gem.'\
         | 
| 136 158 | 
             
            ' Please install the gem or add it to your gemfile.'
         | 
| 137 159 | 
             
                    end
         | 
| 138 160 | 
             
                  end
         | 
| @@ -211,6 +233,8 @@ module Aws | |
| 211 233 | 
             
                  #
         | 
| 212 234 | 
             
                  def sign_request(request)
         | 
| 213 235 |  | 
| 236 | 
            +
                    return crt_sign_request(request) if Signer.use_crt?
         | 
| 237 | 
            +
             | 
| 214 238 | 
             
                    creds = fetch_credentials
         | 
| 215 239 |  | 
| 216 240 | 
             
                    http_method = extract_http_method(request)
         | 
| @@ -289,6 +313,7 @@ module Aws | |
| 289 313 | 
             
                  #   signature value (a binary string) used at ':chunk-signature' needs to converted to
         | 
| 290 314 | 
             
                  #   hex-encoded string using #unpack
         | 
| 291 315 | 
             
                  def sign_event(prior_signature, payload, encoder)
         | 
| 316 | 
            +
                    # Note: CRT does not currently provide event stream signing, so we always use the ruby implementation.
         | 
| 292 317 | 
             
                    creds = fetch_credentials
         | 
| 293 318 | 
             
                    time = Time.now
         | 
| 294 319 | 
             
                    headers = {}
         | 
| @@ -376,6 +401,8 @@ module Aws | |
| 376 401 | 
             
                  #
         | 
| 377 402 | 
             
                  def presign_url(options)
         | 
| 378 403 |  | 
| 404 | 
            +
                    return crt_presign_url(options) if Signer.use_crt?
         | 
| 405 | 
            +
             | 
| 379 406 | 
             
                    creds = fetch_credentials
         | 
| 380 407 |  | 
| 381 408 | 
             
                    http_method = extract_http_method(options)
         | 
| @@ -693,8 +720,130 @@ module Aws | |
| 693 720 | 
             
                      !credentials.secret_access_key.empty?
         | 
| 694 721 | 
             
                  end
         | 
| 695 722 |  | 
| 723 | 
            +
                  ### CRT Code
         | 
| 724 | 
            +
             | 
| 725 | 
            +
                  # the credentials used by CRT must be a
         | 
| 726 | 
            +
                  # CRT StaticCredentialsProvider object
         | 
| 727 | 
            +
                  def crt_fetch_credentials
         | 
| 728 | 
            +
                    creds = fetch_credentials
         | 
| 729 | 
            +
                    Aws::Crt::Auth::StaticCredentialsProvider.new(
         | 
| 730 | 
            +
                      creds.access_key_id,
         | 
| 731 | 
            +
                      creds.secret_access_key,
         | 
| 732 | 
            +
                      creds.session_token
         | 
| 733 | 
            +
                    )
         | 
| 734 | 
            +
                  end
         | 
| 735 | 
            +
             | 
| 736 | 
            +
                  def crt_sign_request(request)
         | 
| 737 | 
            +
                    creds = crt_fetch_credentials
         | 
| 738 | 
            +
                    http_method = extract_http_method(request)
         | 
| 739 | 
            +
                    url = extract_url(request)
         | 
| 740 | 
            +
                    headers = downcase_headers(request[:headers])
         | 
| 741 | 
            +
             | 
| 742 | 
            +
                    datetime =
         | 
| 743 | 
            +
                      if headers.include? 'x-amz-date'
         | 
| 744 | 
            +
                        Time.parse(headers.delete('x-amz-date'))
         | 
| 745 | 
            +
                      end
         | 
| 746 | 
            +
             | 
| 747 | 
            +
                    content_sha256 = headers.delete('x-amz-content-sha256')
         | 
| 748 | 
            +
                    content_sha256 ||= sha256_hexdigest(request[:body] || '')
         | 
| 749 | 
            +
             | 
| 750 | 
            +
                    sigv4_headers = {}
         | 
| 751 | 
            +
                    sigv4_headers['host'] = headers['host'] || host(url)
         | 
| 752 | 
            +
             | 
| 753 | 
            +
                    # Modify the user-agent to add usage of crt-signer
         | 
| 754 | 
            +
                    # This should be temporary during developer preview only
         | 
| 755 | 
            +
                    if headers.include? 'user-agent'
         | 
| 756 | 
            +
                      headers['user-agent'] = "#{headers['user-agent']} crt-signer/#{@signing_algorithm}/#{Aws::Sigv4::VERSION}"
         | 
| 757 | 
            +
                      sigv4_headers['user-agent'] = headers['user-agent']
         | 
| 758 | 
            +
                    end
         | 
| 759 | 
            +
             | 
| 760 | 
            +
                    headers = headers.merge(sigv4_headers) # merge so we do not modify given headers hash
         | 
| 761 | 
            +
             | 
| 762 | 
            +
                    config = Aws::Crt::Auth::SigningConfig.new(
         | 
| 763 | 
            +
                      algorithm: @signing_algorithm,
         | 
| 764 | 
            +
                      signature_type: :http_request_headers,
         | 
| 765 | 
            +
                      region: @region,
         | 
| 766 | 
            +
                      service: @service,
         | 
| 767 | 
            +
                      date: datetime,
         | 
| 768 | 
            +
                      signed_body_value: content_sha256,
         | 
| 769 | 
            +
                      signed_body_header_type: @apply_checksum_header ?
         | 
| 770 | 
            +
                                                 :sbht_content_sha256 : :sbht_none,
         | 
| 771 | 
            +
                      credentials: creds,
         | 
| 772 | 
            +
                      unsigned_headers: @unsigned_headers,
         | 
| 773 | 
            +
                      use_double_uri_encode: @uri_escape_path,
         | 
| 774 | 
            +
                      should_normalize_uri_path: @normalize_path,
         | 
| 775 | 
            +
                      omit_session_token: @omit_session_token
         | 
| 776 | 
            +
                    )
         | 
| 777 | 
            +
                    http_request = Aws::Crt::Http::Message.new(
         | 
| 778 | 
            +
                      http_method, url.to_s, headers
         | 
| 779 | 
            +
                    )
         | 
| 780 | 
            +
                    signable = Aws::Crt::Auth::Signable.new(http_request)
         | 
| 781 | 
            +
             | 
| 782 | 
            +
                    signing_result = Aws::Crt::Auth::Signer.sign_request(config, signable)
         | 
| 783 | 
            +
             | 
| 784 | 
            +
                    Signature.new(
         | 
| 785 | 
            +
                      headers: sigv4_headers.merge(
         | 
| 786 | 
            +
                        downcase_headers(signing_result[:headers])
         | 
| 787 | 
            +
                      ),
         | 
| 788 | 
            +
                      string_to_sign: 'CRT_INTERNAL',
         | 
| 789 | 
            +
                      canonical_request: 'CRT_INTERNAL',
         | 
| 790 | 
            +
                      content_sha256: content_sha256,
         | 
| 791 | 
            +
                      extra: {config: config, signable: signable}
         | 
| 792 | 
            +
                    )
         | 
| 793 | 
            +
                  end
         | 
| 794 | 
            +
             | 
| 795 | 
            +
                  def crt_presign_url(options)
         | 
| 796 | 
            +
                    creds = crt_fetch_credentials
         | 
| 797 | 
            +
             | 
| 798 | 
            +
                    http_method = extract_http_method(options)
         | 
| 799 | 
            +
                    url = extract_url(options)
         | 
| 800 | 
            +
                    headers = downcase_headers(options[:headers])
         | 
| 801 | 
            +
                    headers['host'] ||= host(url)
         | 
| 802 | 
            +
             | 
| 803 | 
            +
                    datetime = headers.delete('x-amz-date')
         | 
| 804 | 
            +
                    datetime ||= (options[:time] || Time.now)
         | 
| 805 | 
            +
             | 
| 806 | 
            +
                    content_sha256 = headers.delete('x-amz-content-sha256')
         | 
| 807 | 
            +
                    content_sha256 ||= options[:body_digest]
         | 
| 808 | 
            +
                    content_sha256 ||= sha256_hexdigest(options[:body] || '')
         | 
| 809 | 
            +
             | 
| 810 | 
            +
                    config = Aws::Crt::Auth::SigningConfig.new(
         | 
| 811 | 
            +
                      algorithm: @signing_algorithm,
         | 
| 812 | 
            +
                      signature_type: :http_request_query_params,
         | 
| 813 | 
            +
                      region: @region,
         | 
| 814 | 
            +
                      service: @service,
         | 
| 815 | 
            +
                      date: datetime,
         | 
| 816 | 
            +
                      signed_body_value: content_sha256,
         | 
| 817 | 
            +
                      signed_body_header_type: @apply_checksum_header ?
         | 
| 818 | 
            +
                                                 :sbht_content_sha256 : :sbht_none,
         | 
| 819 | 
            +
                      credentials: creds,
         | 
| 820 | 
            +
                      unsigned_headers: @unsigned_headers,
         | 
| 821 | 
            +
                      use_double_uri_encode: @uri_escape_path,
         | 
| 822 | 
            +
                      should_normalize_uri_path: @normalize_path,
         | 
| 823 | 
            +
                      omit_session_token: @omit_session_token,
         | 
| 824 | 
            +
                      expiration_in_seconds: options.fetch(:expires_in, 900)
         | 
| 825 | 
            +
                    )
         | 
| 826 | 
            +
                    http_request = Aws::Crt::Http::Message.new(
         | 
| 827 | 
            +
                      http_method, url.to_s, headers
         | 
| 828 | 
            +
                    )
         | 
| 829 | 
            +
                    signable = Aws::Crt::Auth::Signable.new(http_request)
         | 
| 830 | 
            +
             | 
| 831 | 
            +
                    signing_result = Aws::Crt::Auth::Signer.sign_request(config, signable, http_method, url.to_s)
         | 
| 832 | 
            +
                    url = URI.parse(signing_result[:path])
         | 
| 833 | 
            +
             | 
| 834 | 
            +
                    if options[:extra] && options[:extra].is_a?(Hash)
         | 
| 835 | 
            +
                      options[:extra][:config] = config
         | 
| 836 | 
            +
                      options[:extra][:signable] = signable
         | 
| 837 | 
            +
                    end
         | 
| 838 | 
            +
                    url
         | 
| 839 | 
            +
                  end
         | 
| 840 | 
            +
             | 
| 696 841 | 
             
                  class << self
         | 
| 697 842 |  | 
| 843 | 
            +
                    def use_crt?
         | 
| 844 | 
            +
                      @@use_crt
         | 
| 845 | 
            +
                    end
         | 
| 846 | 
            +
             | 
| 698 847 | 
             
                    # @api private
         | 
| 699 848 | 
             
                    def uri_escape_path(path)
         | 
| 700 849 | 
             
                      path.gsub(/[^\/]+/) { |part| uri_escape(part) }
         | 
    
        data/lib/aws-sigv4.rb
    CHANGED
    
    | @@ -4,3 +4,9 @@ require_relative 'aws-sigv4/credentials' | |
| 4 4 | 
             
            require_relative 'aws-sigv4/errors'
         | 
| 5 5 | 
             
            require_relative 'aws-sigv4/signature'
         | 
| 6 6 | 
             
            require_relative 'aws-sigv4/signer'
         | 
| 7 | 
            +
             | 
| 8 | 
            +
            module Aws
         | 
| 9 | 
            +
              module Sigv4
         | 
| 10 | 
            +
                VERSION = File.read(File.expand_path('../VERSION', __dir__)).strip
         | 
| 11 | 
            +
              end
         | 
| 12 | 
            +
            end
         | 
    
        metadata
    CHANGED
    
    | @@ -1,14 +1,14 @@ | |
| 1 1 | 
             
            --- !ruby/object:Gem::Specification
         | 
| 2 2 | 
             
            name: aws-sigv4
         | 
| 3 3 | 
             
            version: !ruby/object:Gem::Version
         | 
| 4 | 
            -
              version: 1. | 
| 4 | 
            +
              version: 1.5.1
         | 
| 5 5 | 
             
            platform: ruby
         | 
| 6 6 | 
             
            authors:
         | 
| 7 7 | 
             
            - Amazon Web Services
         | 
| 8 8 | 
             
            autorequire: 
         | 
| 9 9 | 
             
            bindir: bin
         | 
| 10 10 | 
             
            cert_chain: []
         | 
| 11 | 
            -
            date:  | 
| 11 | 
            +
            date: 2022-07-19 00:00:00.000000000 Z
         | 
| 12 12 | 
             
            dependencies:
         | 
| 13 13 | 
             
            - !ruby/object:Gem::Dependency
         | 
| 14 14 | 
             
              name: aws-eventstream
         |