diff --git a/.github/workflows/auto-assign.yml b/.github/workflows/auto-assign.yml index 241789b6..6abbeb67 100644 --- a/.github/workflows/auto-assign.yml +++ b/.github/workflows/auto-assign.yml @@ -12,7 +12,7 @@ jobs: pull-requests: write steps: - name: 'Auto-assign issue' - uses: pozil/auto-assign-issue@07fe6dc0e9771842b428f5739098d6140734e226 # v4 + uses: pozil/auto-assign-issue@af6beea6bdf1e8eb373f061c5bc168681fc6d011 # v4.0.1 with: repo-token: ${{ secrets.GITHUB_TOKEN }} assignees: "pboling" diff --git a/.github/workflows/coverage.yml b/.github/workflows/coverage.yml index b91cecbe..56123c34 100644 --- a/.github/workflows/coverage.yml +++ b/.github/workflows/coverage.yml @@ -59,7 +59,7 @@ jobs: persist-credentials: false - name: Setup Ruby & RubyGems - uses: ruby/setup-ruby@afeafc3d1ab54a631816aba4c914a0081c12ff2f # v1.310.0 + uses: ruby/setup-ruby@89f90524b88a01fe6e0b732220432cc6142926af # v1.313.0 with: ruby-version: "${{ matrix.ruby }}" rubygems: "${{ matrix.rubygems }}" diff --git a/.github/workflows/current.yml b/.github/workflows/current.yml index 63ef7da5..ed700f12 100644 --- a/.github/workflows/current.yml +++ b/.github/workflows/current.yml @@ -50,7 +50,7 @@ jobs: persist-credentials: false - name: Setup Ruby & RubyGems - uses: ruby/setup-ruby@afeafc3d1ab54a631816aba4c914a0081c12ff2f # v1.310.0 + uses: ruby/setup-ruby@89f90524b88a01fe6e0b732220432cc6142926af # v1.313.0 with: ruby-version: ${{ matrix.ruby }} rubygems: ${{ matrix.rubygems }} diff --git a/.github/workflows/dep-heads.yml b/.github/workflows/dep-heads.yml index 7d5794f0..a6e9d872 100644 --- a/.github/workflows/dep-heads.yml +++ b/.github/workflows/dep-heads.yml @@ -56,7 +56,7 @@ jobs: # jruby-10.0 (targets Ruby 3.4 compatibility) - ruby: "jruby" appraisal: "dep-heads" - exec_cmd: "kettle-test" + exec_cmd: "rspec" rubygems: default bundler: default experimental: true @@ -70,7 +70,7 @@ jobs: - name: Setup Ruby & RubyGems if: ${{ !env.ACT || (! startsWith(matrix.ruby, 'jruby') && !startsWith(matrix.ruby, 'truffleruby')) }} - uses: ruby/setup-ruby@afeafc3d1ab54a631816aba4c914a0081c12ff2f # v1.310.0 + uses: ruby/setup-ruby@89f90524b88a01fe6e0b732220432cc6142926af # v1.313.0 with: ruby-version: ${{ matrix.ruby }} rubygems: ${{ matrix.rubygems }} @@ -93,4 +93,5 @@ jobs: - name: Tests for ${{ matrix.ruby }} via ${{ matrix.exec_cmd }} if: ${{ !env.ACT || (! startsWith(matrix.ruby, 'jruby') && !startsWith(matrix.ruby, 'truffleruby')) }} + timeout-minutes: 15 run: bundle exec appraisal ${{ matrix.appraisal }} bundle exec ${{ matrix.exec_cmd }} diff --git a/.github/workflows/heads.yml b/.github/workflows/heads.yml index e2dde5ca..a1b068d2 100644 --- a/.github/workflows/heads.yml +++ b/.github/workflows/heads.yml @@ -55,7 +55,7 @@ jobs: # jruby-head - ruby: "jruby-head" appraisal: "head" - exec_cmd: "kettle-test" + exec_cmd: "rspec" rubygems: default bundler: default @@ -68,7 +68,7 @@ jobs: - name: Setup Ruby & RubyGems if: ${{ !env.ACT || (! startsWith(matrix.ruby, 'jruby') && !startsWith(matrix.ruby, 'truffleruby')) }} - uses: ruby/setup-ruby@afeafc3d1ab54a631816aba4c914a0081c12ff2f # v1.310.0 + uses: ruby/setup-ruby@89f90524b88a01fe6e0b732220432cc6142926af # v1.313.0 with: ruby-version: ${{ matrix.ruby }} rubygems: ${{ matrix.rubygems }} @@ -91,4 +91,5 @@ jobs: - name: Tests for ${{ matrix.ruby }} via ${{ matrix.exec_cmd }} if: ${{ !env.ACT || (! startsWith(matrix.ruby, 'jruby') && !startsWith(matrix.ruby, 'truffleruby')) }} + timeout-minutes: 15 run: bundle exec appraisal ${{ matrix.appraisal }} bundle exec ${{ matrix.exec_cmd }} diff --git a/.github/workflows/jruby-9.2.yml b/.github/workflows/jruby-9.2.yml index 103b87e7..f2bd29fb 100644 --- a/.github/workflows/jruby-9.2.yml +++ b/.github/workflows/jruby-9.2.yml @@ -52,7 +52,7 @@ jobs: - name: Setup Ruby & RubyGems if: ${{ !env.ACT }} - uses: ruby/setup-ruby@afeafc3d1ab54a631816aba4c914a0081c12ff2f # v1.310.0 + uses: ruby/setup-ruby@89f90524b88a01fe6e0b732220432cc6142926af # v1.313.0 with: ruby-version: ${{ matrix.ruby }} rubygems: ${{ matrix.rubygems }} diff --git a/.github/workflows/jruby-9.3.yml b/.github/workflows/jruby-9.3.yml index 02c1b668..aa558429 100644 --- a/.github/workflows/jruby-9.3.yml +++ b/.github/workflows/jruby-9.3.yml @@ -52,7 +52,7 @@ jobs: - name: Setup Ruby & RubyGems if: ${{ !env.ACT }} - uses: ruby/setup-ruby@afeafc3d1ab54a631816aba4c914a0081c12ff2f # v1.310.0 + uses: ruby/setup-ruby@89f90524b88a01fe6e0b732220432cc6142926af # v1.313.0 with: ruby-version: ${{ matrix.ruby }} rubygems: ${{ matrix.rubygems }} diff --git a/.github/workflows/jruby-9.4.yml b/.github/workflows/jruby-9.4.yml index 43a72fad..3589cc1a 100644 --- a/.github/workflows/jruby-9.4.yml +++ b/.github/workflows/jruby-9.4.yml @@ -52,7 +52,7 @@ jobs: - name: Setup Ruby & RubyGems if: ${{ !env.ACT }} - uses: ruby/setup-ruby@afeafc3d1ab54a631816aba4c914a0081c12ff2f # v1.310.0 + uses: ruby/setup-ruby@89f90524b88a01fe6e0b732220432cc6142926af # v1.313.0 with: ruby-version: ${{ matrix.ruby }} rubygems: ${{ matrix.rubygems }} diff --git a/.github/workflows/jruby.yml b/.github/workflows/jruby.yml index f5f984bd..ed77b563 100644 --- a/.github/workflows/jruby.yml +++ b/.github/workflows/jruby.yml @@ -39,7 +39,7 @@ jobs: # jruby-10.0 (targets Ruby 3.4 compatibility) - ruby: "jruby" appraisal: "current" - exec_cmd: "kettle-test" + exec_cmd: "rspec" rubygems: default bundler: default experimental: true @@ -53,7 +53,7 @@ jobs: - name: Setup Ruby & RubyGems if: ${{ !env.ACT }} - uses: ruby/setup-ruby@afeafc3d1ab54a631816aba4c914a0081c12ff2f # v1.310.0 + uses: ruby/setup-ruby@89f90524b88a01fe6e0b732220432cc6142926af # v1.313.0 with: ruby-version: ${{ matrix.ruby }} rubygems: ${{ matrix.rubygems }} @@ -76,4 +76,5 @@ jobs: - name: Tests for ${{ matrix.ruby }} via ${{ matrix.exec_cmd }} if: ${{ !env.ACT }} + timeout-minutes: 15 run: bundle exec appraisal ${{ matrix.appraisal }} bundle exec ${{ matrix.exec_cmd }} diff --git a/.github/workflows/locked_deps.yml b/.github/workflows/locked_deps.yml index 7b10e7f4..d04da3c8 100644 --- a/.github/workflows/locked_deps.yml +++ b/.github/workflows/locked_deps.yml @@ -76,7 +76,7 @@ jobs: persist-credentials: false - name: Setup Ruby & RubyGems - uses: ruby/setup-ruby@afeafc3d1ab54a631816aba4c914a0081c12ff2f # v1.310.0 + uses: ruby/setup-ruby@89f90524b88a01fe6e0b732220432cc6142926af # v1.313.0 with: ruby-version: ${{ matrix.ruby }} rubygems: ${{ matrix.rubygems }} diff --git a/.github/workflows/macos.yml b/.github/workflows/macos.yml index ec574332..212bf21e 100644 --- a/.github/workflows/macos.yml +++ b/.github/workflows/macos.yml @@ -58,7 +58,7 @@ jobs: # jruby-10.0 (targets Ruby 3.4 compatibility) - ruby: "jruby" appraisal: "current" - exec_cmd: "kettle-test" + exec_cmd: "rspec" gemfile: "Appraisal.root" rubygems: default bundler: default @@ -73,7 +73,7 @@ jobs: uses: actions/checkout@df4cb1c069e1874edd31b4311f1884172cec0e10 # v6.0.3 - name: Setup Ruby & RubyGems - uses: ruby/setup-ruby@afeafc3d1ab54a631816aba4c914a0081c12ff2f # v1.310.0 + uses: ruby/setup-ruby@89f90524b88a01fe6e0b732220432cc6142926af # v1.313.0 with: ruby-version: ${{ matrix.ruby }} rubygems: ${{ matrix.rubygems }} @@ -88,4 +88,5 @@ jobs: - name: Appraisal for ${{ matrix.ruby }}@${{ matrix.appraisal }} run: bundle exec appraisal ${{ matrix.appraisal }} bundle - name: Tests for ${{ matrix.ruby }}@${{ matrix.appraisal }} via ${{ matrix.exec_cmd }} + timeout-minutes: 15 run: bundle exec appraisal ${{ matrix.appraisal }} bundle exec ${{ matrix.exec_cmd }} diff --git a/.github/workflows/opencollective.yml b/.github/workflows/opencollective.yml index 715bef3b..04cb6652 100644 --- a/.github/workflows/opencollective.yml +++ b/.github/workflows/opencollective.yml @@ -20,7 +20,7 @@ jobs: with: persist-credentials: false - name: Setup Ruby & RubyGems - uses: ruby/setup-ruby@afeafc3d1ab54a631816aba4c914a0081c12ff2f # v1.310.0 + uses: ruby/setup-ruby@89f90524b88a01fe6e0b732220432cc6142926af # v1.313.0 with: ruby-version: ruby rubygems: default diff --git a/.github/workflows/ruby-2.4.yml b/.github/workflows/ruby-2.4.yml index b660d363..d3b06c41 100644 --- a/.github/workflows/ruby-2.4.yml +++ b/.github/workflows/ruby-2.4.yml @@ -47,7 +47,7 @@ jobs: persist-credentials: false - name: Setup Ruby & RubyGems - uses: ruby/setup-ruby@afeafc3d1ab54a631816aba4c914a0081c12ff2f # v1.310.0 + uses: ruby/setup-ruby@89f90524b88a01fe6e0b732220432cc6142926af # v1.313.0 with: ruby-version: ${{ matrix.ruby }} rubygems: ${{ matrix.rubygems }} diff --git a/.github/workflows/ruby-2.5.yml b/.github/workflows/ruby-2.5.yml index 3c91bb91..daeece01 100644 --- a/.github/workflows/ruby-2.5.yml +++ b/.github/workflows/ruby-2.5.yml @@ -47,7 +47,7 @@ jobs: persist-credentials: false - name: Setup Ruby & RubyGems - uses: ruby/setup-ruby@afeafc3d1ab54a631816aba4c914a0081c12ff2f # v1.310.0 + uses: ruby/setup-ruby@89f90524b88a01fe6e0b732220432cc6142926af # v1.313.0 with: ruby-version: ${{ matrix.ruby }} rubygems: ${{ matrix.rubygems }} diff --git a/.github/workflows/ruby-2.6.yml b/.github/workflows/ruby-2.6.yml index 15624427..7245863e 100644 --- a/.github/workflows/ruby-2.6.yml +++ b/.github/workflows/ruby-2.6.yml @@ -47,7 +47,7 @@ jobs: persist-credentials: false - name: Setup Ruby & RubyGems - uses: ruby/setup-ruby@afeafc3d1ab54a631816aba4c914a0081c12ff2f # v1.310.0 + uses: ruby/setup-ruby@89f90524b88a01fe6e0b732220432cc6142926af # v1.313.0 with: ruby-version: ${{ matrix.ruby }} rubygems: ${{ matrix.rubygems }} diff --git a/.github/workflows/ruby-2.7.yml b/.github/workflows/ruby-2.7.yml index e8d164cd..44f3e01c 100644 --- a/.github/workflows/ruby-2.7.yml +++ b/.github/workflows/ruby-2.7.yml @@ -47,7 +47,7 @@ jobs: persist-credentials: false - name: Setup Ruby & RubyGems - uses: ruby/setup-ruby@afeafc3d1ab54a631816aba4c914a0081c12ff2f # v1.310.0 + uses: ruby/setup-ruby@89f90524b88a01fe6e0b732220432cc6142926af # v1.313.0 with: ruby-version: ${{ matrix.ruby }} rubygems: ${{ matrix.rubygems }} diff --git a/.github/workflows/ruby-3.0.yml b/.github/workflows/ruby-3.0.yml index a077d1f1..2922d218 100644 --- a/.github/workflows/ruby-3.0.yml +++ b/.github/workflows/ruby-3.0.yml @@ -50,7 +50,7 @@ jobs: persist-credentials: false - name: Setup Ruby & RubyGems - uses: ruby/setup-ruby@afeafc3d1ab54a631816aba4c914a0081c12ff2f # v1.310.0 + uses: ruby/setup-ruby@89f90524b88a01fe6e0b732220432cc6142926af # v1.313.0 with: ruby-version: ${{ matrix.ruby }} rubygems: ${{ matrix.rubygems }} diff --git a/.github/workflows/ruby-3.1.yml b/.github/workflows/ruby-3.1.yml index 3e0bb584..3cb82991 100644 --- a/.github/workflows/ruby-3.1.yml +++ b/.github/workflows/ruby-3.1.yml @@ -50,7 +50,7 @@ jobs: persist-credentials: false - name: Setup Ruby & RubyGems - uses: ruby/setup-ruby@afeafc3d1ab54a631816aba4c914a0081c12ff2f # v1.310.0 + uses: ruby/setup-ruby@89f90524b88a01fe6e0b732220432cc6142926af # v1.313.0 with: ruby-version: ${{ matrix.ruby }} rubygems: ${{ matrix.rubygems }} diff --git a/.github/workflows/ruby-3.2.yml b/.github/workflows/ruby-3.2.yml index a5a1ecab..f7753e8e 100644 --- a/.github/workflows/ruby-3.2.yml +++ b/.github/workflows/ruby-3.2.yml @@ -47,7 +47,7 @@ jobs: persist-credentials: false - name: Setup Ruby & RubyGems - uses: ruby/setup-ruby@afeafc3d1ab54a631816aba4c914a0081c12ff2f # v1.310.0 + uses: ruby/setup-ruby@89f90524b88a01fe6e0b732220432cc6142926af # v1.313.0 with: ruby-version: ${{ matrix.ruby }} rubygems: ${{ matrix.rubygems }} diff --git a/.github/workflows/ruby-3.3.yml b/.github/workflows/ruby-3.3.yml index 0f9f737e..c7ad4981 100644 --- a/.github/workflows/ruby-3.3.yml +++ b/.github/workflows/ruby-3.3.yml @@ -47,7 +47,7 @@ jobs: persist-credentials: false - name: Setup Ruby & RubyGems - uses: ruby/setup-ruby@afeafc3d1ab54a631816aba4c914a0081c12ff2f # v1.310.0 + uses: ruby/setup-ruby@89f90524b88a01fe6e0b732220432cc6142926af # v1.313.0 with: ruby-version: ${{ matrix.ruby }} rubygems: ${{ matrix.rubygems }} diff --git a/.github/workflows/ruby-3.4.yml b/.github/workflows/ruby-3.4.yml index aac2cd69..7d6c7055 100644 --- a/.github/workflows/ruby-3.4.yml +++ b/.github/workflows/ruby-3.4.yml @@ -47,7 +47,7 @@ jobs: persist-credentials: false - name: Setup Ruby & RubyGems - uses: ruby/setup-ruby@afeafc3d1ab54a631816aba4c914a0081c12ff2f # v1.310.0 + uses: ruby/setup-ruby@89f90524b88a01fe6e0b732220432cc6142926af # v1.313.0 with: ruby-version: ${{ matrix.ruby }} rubygems: ${{ matrix.rubygems }} diff --git a/.github/workflows/style.yml b/.github/workflows/style.yml index 8a72d428..49e0e1fd 100644 --- a/.github/workflows/style.yml +++ b/.github/workflows/style.yml @@ -47,7 +47,7 @@ jobs: persist-credentials: false - name: Setup Ruby & RubyGems - uses: ruby/setup-ruby@afeafc3d1ab54a631816aba4c914a0081c12ff2f # v1.310.0 + uses: ruby/setup-ruby@89f90524b88a01fe6e0b732220432cc6142926af # v1.313.0 with: ruby-version: ${{ matrix.ruby }} rubygems: ${{ matrix.rubygems }} @@ -70,5 +70,7 @@ jobs: - name: Run ${{ matrix.appraisal }} checks via ${{ matrix.exec_cmd }} run: bundle exec appraisal ${{ matrix.appraisal }} bundle exec ${{ matrix.exec_cmd }} - - name: Validate RBS Types - run: bundle exec appraisal ${{ matrix.appraisal }} rbs validate + - name: Validate RBS Environment + run: >- + bundle exec appraisal ${{ matrix.appraisal }} bundle exec ruby -rrbs -rpathname -e + 'loader = RBS::EnvironmentLoader.new; loader.add(path: Pathname("sig")); RBS::Environment.from_loader(loader).resolve_type_names' diff --git a/.github/workflows/templating.yml b/.github/workflows/templating.yml index 4366dcb0..bb61f6cd 100644 --- a/.github/workflows/templating.yml +++ b/.github/workflows/templating.yml @@ -54,7 +54,7 @@ jobs: uses: kettle-rb/ts-grammar-action@4b0c04d11ed5b85c67c0c60c6ecb590e81748ccb # v1.0.1 - name: Setup Ruby & RubyGems - uses: ruby/setup-ruby@afeafc3d1ab54a631816aba4c914a0081c12ff2f # v1.310.0 + uses: ruby/setup-ruby@89f90524b88a01fe6e0b732220432cc6142926af # v1.313.0 with: ruby-version: ${{ matrix.ruby }} rubygems: ${{ matrix.rubygems }} diff --git a/.github/workflows/truffle.yml b/.github/workflows/truffle.yml index 7452d3c3..86f9a15e 100644 --- a/.github/workflows/truffle.yml +++ b/.github/workflows/truffle.yml @@ -53,7 +53,7 @@ jobs: - name: Setup Ruby & RubyGems if: ${{ !env.ACT }} - uses: ruby/setup-ruby@afeafc3d1ab54a631816aba4c914a0081c12ff2f # v1.310.0 + uses: ruby/setup-ruby@89f90524b88a01fe6e0b732220432cc6142926af # v1.313.0 with: ruby-version: ${{ matrix.ruby }} rubygems: ${{ matrix.rubygems }} diff --git a/.github/workflows/truffleruby-22.3.yml b/.github/workflows/truffleruby-22.3.yml index 721c0004..8ed856b5 100644 --- a/.github/workflows/truffleruby-22.3.yml +++ b/.github/workflows/truffleruby-22.3.yml @@ -32,7 +32,7 @@ jobs: runs-on: ubuntu-22.04 continue-on-error: ${{ matrix.experimental || endsWith(matrix.ruby, 'head') }} env: # $BUNDLE_GEMFILE must be set at job level, so it is set for all steps - BUNDLE_GEMFILE: ${{ github.workspace }}/Appraisal.root.gemfile + BUNDLE_GEMFILE: ${{ github.workspace }}/gemfiles/ruby_3_0.gemfile strategy: matrix: include: @@ -54,27 +54,18 @@ jobs: - name: Setup Ruby & RubyGems if: ${{ !env.ACT }} - uses: ruby/setup-ruby@afeafc3d1ab54a631816aba4c914a0081c12ff2f # v1.310.0 + uses: ruby/setup-ruby@89f90524b88a01fe6e0b732220432cc6142926af # v1.313.0 with: ruby-version: ${{ matrix.ruby }} rubygems: ${{ matrix.rubygems }} bundler: ${{ matrix.bundler }} - bundler-cache: true + bundler-cache: false - - name: "[Attempt 1] Appraisal for ${{ matrix.ruby }}@${{ matrix.appraisal }}" - id: bundleAppraisalAttempt1 + - name: Bundle install if: ${{ !env.ACT }} - run: bundle exec appraisal ${{ matrix.appraisal }} install - # Continue to the next step on failure - continue-on-error: true - - # Effectively an automatic retry of the previous step. - - name: "[Attempt 2] Appraisal for ${{ matrix.ruby }}@${{ matrix.appraisal }}" - id: bundleAppraisalAttempt2 - # If bundleAppraisalAttempt1 failed, try again here; Otherwise skip. - if: ${{ steps.bundleAppraisalAttempt1.outcome == 'failure' && !env.ACT }} - run: bundle exec appraisal ${{ matrix.appraisal }} install + run: bundle install --jobs 4 - name: Tests for ${{ matrix.ruby }} via ${{ matrix.exec_cmd }} if: ${{ !env.ACT }} - run: bundle exec appraisal ${{ matrix.appraisal }} bundle exec ${{ matrix.exec_cmd }} + run: bundle exec ${{ matrix.exec_cmd }} + continue-on-error: ${{ matrix.experimental }} diff --git a/.github/workflows/truffleruby-23.0.yml b/.github/workflows/truffleruby-23.0.yml index acbb8e44..e9a3d415 100644 --- a/.github/workflows/truffleruby-23.0.yml +++ b/.github/workflows/truffleruby-23.0.yml @@ -32,7 +32,7 @@ jobs: runs-on: ubuntu-22.04 continue-on-error: ${{ matrix.experimental || endsWith(matrix.ruby, 'head') }} env: # $BUNDLE_GEMFILE must be set at job level, so it is set for all steps - BUNDLE_GEMFILE: ${{ github.workspace }}/Appraisal.root.gemfile + BUNDLE_GEMFILE: ${{ github.workspace }}/gemfiles/ruby_3_0.gemfile strategy: matrix: include: @@ -54,27 +54,18 @@ jobs: - name: Setup Ruby & RubyGems if: ${{ !env.ACT }} - uses: ruby/setup-ruby@afeafc3d1ab54a631816aba4c914a0081c12ff2f # v1.310.0 + uses: ruby/setup-ruby@89f90524b88a01fe6e0b732220432cc6142926af # v1.313.0 with: ruby-version: ${{ matrix.ruby }} rubygems: ${{ matrix.rubygems }} bundler: ${{ matrix.bundler }} - bundler-cache: true + bundler-cache: false - - name: "[Attempt 1] Appraisal for ${{ matrix.ruby }}@${{ matrix.appraisal }}" - id: bundleAppraisalAttempt1 + - name: Bundle install if: ${{ !env.ACT }} - run: bundle exec appraisal ${{ matrix.appraisal }} install - # Continue to the next step on failure - continue-on-error: true - - # Effectively an automatic retry of the previous step. - - name: "[Attempt 2] Appraisal for ${{ matrix.ruby }}@${{ matrix.appraisal }}" - id: bundleAppraisalAttempt2 - # If bundleAppraisalAttempt1 failed, try again here; Otherwise skip. - if: ${{ steps.bundleAppraisalAttempt1.outcome == 'failure' && !env.ACT }} - run: bundle exec appraisal ${{ matrix.appraisal }} install + run: bundle install --jobs 4 - name: Tests for ${{ matrix.ruby }} via ${{ matrix.exec_cmd }} if: ${{ !env.ACT }} - run: bundle exec appraisal ${{ matrix.appraisal }} bundle exec ${{ matrix.exec_cmd }} + run: bundle exec ${{ matrix.exec_cmd }} + continue-on-error: ${{ matrix.experimental }} diff --git a/.github/workflows/truffleruby-23.1.yml b/.github/workflows/truffleruby-23.1.yml index 03193a9f..ef51dc02 100644 --- a/.github/workflows/truffleruby-23.1.yml +++ b/.github/workflows/truffleruby-23.1.yml @@ -54,7 +54,7 @@ jobs: - name: Setup Ruby & RubyGems if: ${{ !env.ACT }} - uses: ruby/setup-ruby@afeafc3d1ab54a631816aba4c914a0081c12ff2f # v1.310.0 + uses: ruby/setup-ruby@89f90524b88a01fe6e0b732220432cc6142926af # v1.313.0 with: ruby-version: ${{ matrix.ruby }} rubygems: ${{ matrix.rubygems }} diff --git a/.github/workflows/truffleruby-24.2.yml b/.github/workflows/truffleruby-24.2.yml index 4a973a0b..a6d0372a 100644 --- a/.github/workflows/truffleruby-24.2.yml +++ b/.github/workflows/truffleruby-24.2.yml @@ -53,7 +53,7 @@ jobs: - name: Setup Ruby & RubyGems if: ${{ !env.ACT }} - uses: ruby/setup-ruby@afeafc3d1ab54a631816aba4c914a0081c12ff2f # v1.310.0 + uses: ruby/setup-ruby@89f90524b88a01fe6e0b732220432cc6142926af # v1.313.0 with: ruby-version: ${{ matrix.ruby }} rubygems: ${{ matrix.rubygems }} diff --git a/.github/workflows/truffleruby-25.0.yml b/.github/workflows/truffleruby-25.0.yml index c4d3c9ac..7a0069d9 100644 --- a/.github/workflows/truffleruby-25.0.yml +++ b/.github/workflows/truffleruby-25.0.yml @@ -53,7 +53,7 @@ jobs: - name: Setup Ruby & RubyGems if: ${{ !env.ACT }} - uses: ruby/setup-ruby@afeafc3d1ab54a631816aba4c914a0081c12ff2f # v1.310.0 + uses: ruby/setup-ruby@89f90524b88a01fe6e0b732220432cc6142926af # v1.313.0 with: ruby-version: ${{ matrix.ruby }} rubygems: ${{ matrix.rubygems }} diff --git a/.github/workflows/unlocked_deps.yml b/.github/workflows/unlocked_deps.yml index 4c0dc17b..61ece8e8 100644 --- a/.github/workflows/unlocked_deps.yml +++ b/.github/workflows/unlocked_deps.yml @@ -70,7 +70,7 @@ jobs: uses: kettle-rb/ts-grammar-action@4b0c04d11ed5b85c67c0c60c6ecb590e81748ccb # v1.0.1 - name: Setup Ruby & RubyGems - uses: ruby/setup-ruby@afeafc3d1ab54a631816aba4c914a0081c12ff2f # v1.310.0 + uses: ruby/setup-ruby@89f90524b88a01fe6e0b732220432cc6142926af # v1.313.0 with: ruby-version: ${{ matrix.ruby }} rubygems: ${{ matrix.rubygems }} diff --git a/.github/workflows/windows.yml b/.github/workflows/windows.yml index e0b1883f..7da47132 100644 --- a/.github/workflows/windows.yml +++ b/.github/workflows/windows.yml @@ -55,7 +55,7 @@ jobs: uses: actions/checkout@df4cb1c069e1874edd31b4311f1884172cec0e10 # v6.0.3 - name: Setup Ruby & RubyGems - uses: ruby/setup-ruby@afeafc3d1ab54a631816aba4c914a0081c12ff2f # v1.310.0 + uses: ruby/setup-ruby@89f90524b88a01fe6e0b732220432cc6142926af # v1.313.0 with: ruby-version: ${{ matrix.ruby }} rubygems: ${{ matrix.rubygems }} diff --git a/.kettle-drift.lock b/.kettle-drift.lock index 08601589..066e0da1 100644 --- a/.kettle-drift.lock +++ b/.kettle-drift.lock @@ -21,8 +21,36 @@ { "file": "CHANGELOG.md", "lines": [ - 439, - 615 + 477, + 653 + ] + } + ], + "- OAuth2::AccessToken\n- OAuth2::Client": [ + { + "file": "REEK", + "lines": [ + 25, + 87, + 91 + ] + } + ], + "- OAuth2::Client#protocol_relative_redirect_location\n- OAuth2::Client#resolve_redirect_location": [ + { + "file": "REEK", + "lines": [ + 66, + 118 + ] + } + ], + "- OAuth2::Client#resolve_redirect_location\n- OAuth2::Error#error_message": [ + { + "file": "REEK", + "lines": [ + 67, + 119 ] } ], @@ -64,6 +92,19 @@ ] } ], + "exclude:\n- OAuth2::AccessToken": [ + { + "file": "REEK", + "lines": [ + 24, + 43, + 52, + 73, + 86, + 90 + ] + } + ], "exec_cmd: \"kettle-test\"\nrubygems: default": [ { "file": ".github/workflows/dep-heads.yml", diff --git a/.reek.yml b/.reek.yml new file mode 100644 index 00000000..eaf86d90 --- /dev/null +++ b/.reek.yml @@ -0,0 +1,122 @@ +--- +# Reek policy for oauth2. +# +# The remaining exclusions are intentional compatibility constraints: this gem +# preserves long-standing public API methods, OAuth2 domain names, strategy +# signatures, and test fixture shapes that would be riskier to rename or remove +# than to document here. +detectors: + Attribute: + exclude: + - OAuth2::AccessToken#options + - OAuth2::AccessToken#refresh_token + - OAuth2::AccessToken#response + - OAuth2::Client#connection + - OAuth2::Client#options + - OAuth2::Response#options + BooleanParameter: + exclude: + - OAuth2::Response#initialize + ClassVariable: + exclude: + - OAuth2::Response + DataClump: + exclude: + - OAuth2::AccessToken + - OAuth2::Client + DuplicateMethodCall: + exclude: + - OAuth2::Client#execute_request + - OAuth2::Client#sanitize_redirect_options + FeatureEnvy: + exclude: + - OAuth2::Authenticator#apply_basic_auth + - OAuth2::Client#build_access_token + - OAuth2::Client#oauth_debug_logging + - OAuth2::Client#params_to_req_opts + - OAuth2::Client#parse_snaky_params_headers + - OAuth2::Client#resolve_redirect_location + - OAuth2::Strategy::Assertion#build_assertion + - OAuth2::Strategy::AuthCode#assert_valid_params + - OAuth2::Strategy::Implicit#assert_valid_params + InstanceVariableAssumption: + exclude: + - OAuth2::AccessToken + - OAuth2::Response + - OAuth2::Strategy::Assertion + - OAuth2::Strategy::AuthCode + - OAuth2::Strategy::ClientCredentials + - OAuth2::Strategy::Implicit + - OAuth2::Strategy::Password + IrresponsibleModule: + exclude: + - OAuth2::AccessToken + - OAuth2::ConnectionError + - OAuth2::TimeoutError + - OAuth2::Strategy::Base + - XmledString + LongParameterList: + exclude: + - OAuth2::Strategy::Assertion#get_token + - OAuth2::Strategy::Password#get_token + ManualDispatch: + exclude: + - OAuth2::AccessToken#configure_authentication! + - OAuth2::Client#build_access_token + - OAuth2::Client#protocol_relative_redirect_location + - OAuth2::Client#resolve_redirect_location + - OAuth2::Error#error_message + - OAuth2::Error#initialize + - OAuth2::Response#parsed + - OAuth2::Response#parser + MissingSafeMethod: + exclude: + - OAuth2::AccessToken + NilCheck: + exclude: + - OAuth2::AccessToken#initialize + - OAuth2::AccessToken#revoke + - OAuth2::Authenticator#apply_client_id + - OAuth2::Authenticator#apply_params_auth + SubclassedFromCoreClass: + exclude: + - StirredHash + - XmledString + TooManyInstanceVariables: + exclude: + - OAuth2::AccessToken + - OAuth2::Client + TooManyMethods: + exclude: + - OAuth2::AccessToken + - OAuth2::Client + TooManyStatements: + exclude: + - initialize + - OAuth2::AccessToken#configure_authentication! + - OAuth2::AccessToken#from_hash + - OAuth2::AccessToken#refresh + - OAuth2::AccessToken#revoke + - OAuth2::Client#connection + - OAuth2::Client#execute_request + - OAuth2::Client#get_token + - OAuth2::Client#params_to_req_opts + - OAuth2::Client#parse_response + - OAuth2::Client#parse_snaky_params_headers + - OAuth2::Client#request + - OAuth2::Client#sanitize_redirect_options + - OAuth2::Error#error_message + - OAuth2::Response#parsed + UncommunicativeModuleName: + exclude: + - OAuth2 + UtilityFunction: + exclude: + - OAuth2::AccessToken#convert_expires_at + - OAuth2::Client#authorization_header? + - OAuth2::Client#cross_origin_redirect? + - OAuth2::Client#protocol_relative_redirect_location + - OAuth2::Client#resolve_redirect_location + - OAuth2::Error#error_message + - OAuth2::Strategy::Assertion#build_request + - stubbed_client diff --git a/Appraisal.root.gemfile b/Appraisal.root.gemfile index fa38c44c..3f2a279e 100644 --- a/Appraisal.root.gemfile +++ b/Appraisal.root.gemfile @@ -15,12 +15,12 @@ source "https://gem.coop" gemspec -if Gem::Version.new(RUBY_VERSION) >= Gem::Version.new("3.2") - if respond_to?(:generator_only) - generator_only do - eval_gemfile "gemfiles/modular/style.gemfile" - end - else - eval_gemfile "gemfiles/modular/style.gemfile" +if respond_to?(:generator_only) + generator_only do + eval_gemfile "gemfiles/modular/json/truffleruby_22_3.gemfile" + eval_gemfile "gemfiles/modular/json/truffleruby_23_0.gemfile" end +else + eval_gemfile "gemfiles/modular/json/truffleruby_22_3.gemfile" + eval_gemfile "gemfiles/modular/json/truffleruby_23_0.gemfile" end diff --git a/Appraisals b/Appraisals index f8ccebf0..e393328a 100644 --- a/Appraisals +++ b/Appraisals @@ -52,8 +52,6 @@ appraise "unlocked_deps" do end appraise "head" do - eval_gemfile "modular/x_std_libs.gemfile" - gem "benchmark", "~> 0.4", ">= 0.4.1" eval_gemfile "modular/runtime_heads.gemfile" end diff --git a/CHANGELOG.md b/CHANGELOG.md index 8e45bfb1..8173e938 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -28,8 +28,29 @@ Please file a bug if you notice a violation of semantic versioning. ### Fixed +- Fixed head appraisal dependency conflicts and Ruby 2.4 protocol-relative redirect handling by @pboling + ### Security +## [2.0.23] - 2026-06-12 + +- TAG: [v2.0.23][2.0.23t] +- COVERAGE: 100.00% -- 552/552 lines in 15 files +- BRANCH COVERAGE: 98.90% -- 180/182 branches in 15 files +- 88.35% documented + +### Changed + +- Upgraded to snaky_hash v2.0.6 by @pboling +- Refreshed generated GHA workflow action SHA pins by @pboling + +### Fixed + +- Addressed Reek code-quality checks with targeted cleanup and documented compatibility exclusions by @pboling +- Fixed deprecation warning from MultiXML by @robzolkos + +[gh!733]: https://github.com/ruby-oauth/oauth2/pull/733 + ## [2.0.22] - 2026-06-07 - TAG: [v2.0.22][2.0.22t] @@ -45,7 +66,9 @@ Please file a bug if you notice a violation of semantic versioning. ### Security -- [GHSA-pp92-crg2-gfv9] Prevent protocol-relative redirect `Location` values from changing request authority, and strip `Authorization` headers from cross-origin redirects. +- [GHSA-pp92-crg2-gfv9][GHSA-pp92-crg2-gfv9] Prevent protocol-relative redirect `Location` values from changing request authority, and strip `Authorization` headers from cross-origin redirects by @tonghuaroot and @pboling + +[GHSA-pp92-crg2-gfv9]: https://github.com/ruby-oauth/oauth2/security/advisories/GHSA-pp92-crg2-gfv9 ## [2.0.21] - 2026-06-06 @@ -863,7 +886,9 @@ Please file a bug if you notice a violation of semantic versioning. [gemfiles/readme]: gemfiles/README.md -[Unreleased]: https://github.com/ruby-oauth/oauth2/compare/v2.0.22...HEAD +[Unreleased]: https://github.com/ruby-oauth/oauth2/compare/v2.0.23...HEAD +[2.0.23]: https://github.com/ruby-oauth/oauth2/compare/v2.0.22...v2.0.23 +[2.0.23t]: https://github.com/ruby-oauth/oauth2/releases/tag/v2.0.23 [2.0.22]: https://github.com/ruby-oauth/oauth2/compare/v2.0.21...v2.0.22 [2.0.22t]: https://github.com/ruby-oauth/oauth2/releases/tag/v2.0.22 [2.0.21]: https://github.com/ruby-oauth/oauth2/compare/v2.0.20...v2.0.21 diff --git a/Gemfile b/Gemfile index 2a682bb4..db4af510 100644 --- a/Gemfile +++ b/Gemfile @@ -19,7 +19,7 @@ git_source(:gitlab) { |repo_name| "https://gitlab.com/#{repo_name}" } gemspec # Local workspace dependency wiring for *_local.gemfile overrides -gem "nomono", "~> 1.0", ">= 1.0.2", require: false # ruby >= 2.2 +gem "nomono", "~> 1.0", ">= 1.0.3", require: false # ruby >= 2.2 # Templating (env-switched: SMORG_RB_DEV=/path/to/structuredmerge/ruby/gems for local paths) eval_gemfile "gemfiles/modular/templating.gemfile" if ENV.fetch("K_JEM_TEMPLATING", "false").casecmp("true").zero? diff --git a/Gemfile.lock b/Gemfile.lock index 7845978e..ed56ed74 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -1,14 +1,14 @@ PATH remote: . specs: - oauth2 (2.0.22) + oauth2 (2.0.23) auth-sanitizer (~> 0.2, >= 0.2.1) faraday (>= 0.17.3, < 4.0) jwt (>= 1.0, < 4.0) logger (~> 1.2) multi_xml (~> 0.5) rack (>= 1.2, < 4) - snaky_hash (~> 2.0, >= 2.0.5) + snaky_hash (~> 2.0, >= 2.0.6) version_gem (~> 1.1, >= 1.1.11) GEM @@ -17,11 +17,10 @@ GEM addressable (2.9.0) public_suffix (>= 2.0.2, < 8.0) ansi (1.6.0) - appraisal2 (3.1.1) + appraisal2 (3.1.2) bundler (>= 1.17.3) rake (>= 10) thor (>= 0.14) - version_gem (~> 1.1, >= 1.1.10) appraisal2-rubocop (0.2.0) appraisal2 (>= 3.1.1) rubocop (>= 1.0) @@ -36,6 +35,7 @@ GEM bundler-audit (0.9.3) bundler (>= 1.2.0) thor (~> 1.0) + cgi (0.5.1) cmdparse (3.0.7) concurrent-ruby (1.3.6) date (3.5.1) @@ -90,7 +90,7 @@ GEM version_gem (~> 1.1, >= 1.1.9) hashie (5.1.0) logger - hexapdf (1.8.0) + hexapdf (1.9.1) cmdparse (~> 3.0, >= 3.0.3) geom2d (~> 0.4, >= 0.4.1) openssl (>= 2.2.1) @@ -101,13 +101,13 @@ GEM prism (>= 1.3.0) rdoc (>= 4.0.0) reline (>= 0.4.2) - json (2.19.8) + json (2.19.9) jwt (3.2.0) base64 - kettle-dev (2.1.1) - kettle-test (~> 2.0, >= 2.0.2) + kettle-dev (2.2.5) + kettle-test (~> 2.0, >= 2.0.4) version_gem (~> 1.1, >= 1.1.11) - kettle-soup-cover (2.0.1) + kettle-soup-cover (2.0.2) simplecov (~> 0.22, >= 0.22.0) simplecov-cobertura (~> 3.1, >= 3.1.0) simplecov-console (~> 0.9, >= 0.9.5) @@ -115,8 +115,8 @@ GEM simplecov-lcov (~> 0.9, >= 0.9.0) simplecov-rcov (~> 0.3, >= 0.3.7) simplecov_json_formatter (~> 0.1, >= 0.1.4) - version_gem (~> 1.1, >= 1.1.9) - kettle-test (2.0.3) + version_gem (~> 1.1, >= 1.1.11) + kettle-test (2.0.5) appraisal2 (~> 3.0, >= 3.0.6) backports (~> 3.0) rspec (~> 3.0) @@ -126,8 +126,8 @@ GEM rspec_junit_formatter (~> 0.6) silent_stream (~> 1.0, >= 1.0.12) timecop-rspec (~> 1.0, >= 1.0.3) - turbo_tests2 (~> 3.1, >= 3.1.1) - version_gem (~> 1.1, >= 1.1.9) + turbo_tests2 (~> 3.1, >= 3.1.2) + version_gem (~> 1.1, >= 1.1.11) kramdown (2.5.2) rexml (>= 3.4.4) kramdown-parser-gfm (1.1.0) @@ -140,7 +140,7 @@ GEM mutex_m (0.3.0) net-http (0.9.1) uri (>= 0.11.1) - nkf (0.2.0) + nkf (0.3.0) nokogiri (1.19.3-aarch64-linux-gnu) racc (~> 1.4) nokogiri (1.19.3-aarch64-linux-musl) @@ -155,8 +155,8 @@ GEM racc (~> 1.4) nokogiri (1.19.3-x86_64-linux-musl) racc (~> 1.4) - nomono (1.0.2) - version_gem (~> 1.1, >= 1.1.9) + nomono (1.0.3) + version_gem (~> 1.1, >= 1.1.11) openssl (4.0.2) ostruct (0.6.3) parallel (1.28.0) @@ -219,11 +219,11 @@ GEM rspec-support (3.13.7) rspec_junit_formatter (0.6.0) rspec-core (>= 2, < 4, != 2.12.0) - rubocop (1.84.2) + rubocop (1.87.0) json (~> 2.3) language_server-protocol (~> 3.17.0.2) lint_roller (~> 1.1.0) - parallel (~> 1.10) + parallel (>= 1.10) parser (>= 3.3.0.2) rainbow (>= 2.2.2, < 4.0) regexp_parser (>= 2.9.3, < 3.0) @@ -241,7 +241,8 @@ GEM rubocop-factory_bot (2.28.0) lint_roller (~> 1.1) rubocop (~> 1.72, >= 1.72.1) - rubocop-gradual (0.3.6) + rubocop-gradual (0.4.0) + benchmark diff-lcs (>= 1.2.0, < 2.0) diffy (~> 3.0) parallel (~> 1.10) @@ -263,6 +264,10 @@ GEM rubocop-md (2.0.4) lint_roller (~> 1.1) rubocop (>= 1.72.1) + rubocop-minitest (0.39.1) + lint_roller (~> 1.1) + rubocop (>= 1.75.0, < 2.0) + rubocop-ast (>= 1.38.0, < 2.0) rubocop-on-rbs (2.0.0) lint_roller (~> 1.1) rbs (~> 4.0) @@ -278,9 +283,10 @@ GEM rubocop-rake (0.7.1) lint_roller (~> 1.1) rubocop (>= 1.72.1) - rubocop-rspec (3.9.0) + rubocop-rspec (3.10.2) lint_roller (~> 1.1) - rubocop (~> 1.81) + regexp_parser (>= 2.0) + rubocop (~> 1.86, >= 1.86.2) rubocop-rspec-extra (0.3.0) lint_roller (~> 1.1) rubocop (>= 1.72.1, < 2.0) @@ -309,7 +315,7 @@ GEM docile (~> 1.1) simplecov-html (~> 0.11) simplecov_json_formatter (~> 0.1) - simplecov-cobertura (3.1.0) + simplecov-cobertura (3.2.0) rexml simplecov (~> 0.19) simplecov-console (0.9.5) @@ -321,13 +327,13 @@ GEM simplecov-rcov (0.3.7) simplecov (>= 0.4.1) simplecov_json_formatter (0.1.4) - snaky_hash (2.0.5) + snaky_hash (2.0.6) hashie (>= 0.1.0, < 6) version_gem (>= 1.1.8, < 3) - standard (1.54.0) + standard (1.55.0) language_server-protocol (~> 3.17.0.2) lint_roller (~> 1.0) - rubocop (~> 1.84.0) + rubocop (~> 1.87.0) standard-custom (~> 1.0.0) standard-performance (~> 1.8) standard-custom (1.0.2) @@ -342,11 +348,11 @@ GEM rubocop-factory_bot (~> 2.27) rubocop-rspec (~> 3.9) rubocop-rspec_rails (~> 2.31) - standard-rubocop-lts (2.0.4) + standard-rubocop-lts (2.0.5) standard (~> 1.54, >= 1.54.0) standard-custom (~> 1.0, >= 1.0.2) standard-performance (~> 1.9, >= 1.9.0) - version_gem (~> 1.1, >= 1.1.9) + version_gem (~> 1.1, >= 1.1.11) stone_checksums (1.0.3) version_gem (~> 1.1, >= 1.1.9) stringio (3.2.0) @@ -360,24 +366,25 @@ GEM rspec (~> 3.0) timecop (>= 0.7, < 1) tsort (0.2.0) - turbo_tests2 (3.1.1) + turbo_tests2 (3.1.2) parallel_tests (>= 3.3.0, < 6) rspec (>= 3.10) - version_gem (~> 1.1, >= 1.1.9) + version_gem (~> 1.1, >= 1.1.11) unicode-display_width (3.2.0) unicode-emoji (~> 4.1) unicode-emoji (4.2.0) uri (1.1.1) version_gem (1.1.11) + webrick (1.9.2) yaml-converter (0.2.0) hexapdf (>= 1.8, < 2) kramdown (>= 2.4, < 3) kramdown-parser-gfm (~> 1.1) version_gem (~> 1.1, >= 1.1.9) yard (0.9.44) - yard-fence (0.9.2) + yard-fence (0.9.3) rdoc (>= 6.11, < 8) - version_gem (~> 1.1, >= 1.1.9) + version_gem (~> 1.1, >= 1.1.11) yard (~> 0.9, >= 0.9.37) yard-junk (0.1.0) benchmark @@ -406,24 +413,25 @@ PLATFORMS DEPENDENCIES addressable (~> 2.8, >= 2.8.7, >= 2.8, < 3) - appraisal2 (~> 3.1, >= 3.1.1) + appraisal2 (~> 3.1, >= 3.1.2) appraisal2-rubocop (~> 0.2, >= 0.2.0) backports (~> 3.25, >= 3.25.1) benchmark (~> 0.5, >= 0.5.0) bundler-audit (~> 0.9.3) + cgi (~> 0.5) debug (>= 1.1) erb (~> 6.0, >= 6.0.4) gem_bench (~> 2.0, >= 2.0.5) gitmoji-regex (~> 2.0, >= 2.0.1) irb (~> 1.17) - kettle-dev (~> 2.1, >= 2.1.1) - kettle-soup-cover (~> 2.0, >= 2.0.1) - kettle-test (~> 2.0, >= 2.0.3) + kettle-dev (~> 2.2, >= 2.2.5) + kettle-soup-cover (~> 2.0, >= 2.0.2) + kettle-test (~> 2.0, >= 2.0.5) kramdown (~> 2.5, >= 2.5.1) kramdown-parser-gfm (~> 1.1) mutex_m (~> 0.2) nkf (~> 0.2) - nomono (~> 1.0, >= 1.0.2) + nomono (~> 1.0, >= 1.0.3) oauth2! rake (~> 13.0) rbs (>= 3.0) @@ -431,8 +439,10 @@ DEPENDENCIES reek (~> 6.5, >= 6.5.0) require_bench (~> 1.0, >= 1.0.4) rexml (~> 3.2, >= 3.2.5) + rubocop-gradual (~> 0.4, >= 0.4.0) rubocop-lts (~> 8.3, >= 8.3.0) rubocop-lts-rspec (~> 1.0, >= 1.0.3) + rubocop-minitest (~> 0.38, >= 0.38.1) rubocop-on-rbs (~> 2.0, >= 2.0.0) rubocop-packaging (~> 0.6, >= 0.6.0) rubocop-ruby2_2 (~> 3.0, >= 3.0.2) @@ -440,10 +450,11 @@ DEPENDENCIES standard (~> 1.54, >= 1.54.0) stone_checksums (~> 1.0, >= 1.0.3) stringio (>= 3.0) - turbo_tests2 (~> 3.1, >= 3.1.1) + turbo_tests2 (~> 3.1, >= 3.1.2) + webrick (~> 1.9) yaml-converter (~> 0.1) yard (~> 0.9, >= 0.9.44) - yard-fence (~> 0.9, >= 0.9.2) + yard-fence (~> 0.9, >= 0.9.3) yard-junk (~> 0.1, >= 0.1.0) yard-relative_markdown_links (~> 0.6) yard-timekeeper (~> 0.2, >= 0.2.1) @@ -452,7 +463,7 @@ DEPENDENCIES CHECKSUMS addressable (2.9.0) sha256=7fdf6ac3660f7f4e867a0838be3f6cf722ace541dd97767fa42bc6cfa980c7af ansi (1.6.0) sha256=ac9ea0c0ea8d32fb4e271348e609963ac78882f34b73836c2a02b3622e666658 - appraisal2 (3.1.1) sha256=920bc89c5530e4356cf18606ceb9036a55e49ee57ba1eb6ea6d41b302ce14044 + appraisal2 (3.1.2) sha256=33a1f8c1e2808aa33a24b4c73d1f20c9571b5a34541d66d04d5e744b5906437a appraisal2-rubocop (0.2.0) sha256=c3353136ad1e32e9084c6ede76997510b3b77cf7d2fe19ab4c54a3f5e16cb9c9 ast (2.4.3) sha256=954615157c1d6a382bc27d690d973195e79db7f55e9765ac7c481c60bdb4d383 auth-sanitizer (0.2.1) sha256=917dcf01f7589b06c26726afe90568cf2fb29d37a1f94facfc664f11967cc577 @@ -462,6 +473,7 @@ CHECKSUMS bigdecimal (4.1.2) sha256=53d217666027eab4280346fba98e7d5b66baaae1b9c3c1c0ffe89d48188a3fbd bundler (4.0.13) sha256=19f08be7f27022cf0b89f27da0b044ae075e8270a9ef44ad248a932614e1ca3b bundler-audit (0.9.3) sha256=81c8766c71e47d0d28a0f98c7eed028539f21a6ea3cd8f685eb6f42333c9b4e9 + cgi (0.5.1) sha256=e93fcafc69b8a934fe1e6146121fa35430efa8b4a4047c4893764067036f18e9 cmdparse (3.0.7) sha256=f7c5cace10bec6abf853370ae095e4b97a84ed9d847b3fb38f41cc4fbc950739 concurrent-ruby (1.3.6) sha256=6b56837e1e7e5292f9864f34b69c5a2cbc75c0cf5338f1ce9903d10fa762d5ab date (3.5.1) sha256=750d06384d7b9c15d562c76291407d89e368dda4d4fff957eb94962d325a0dc0 @@ -484,14 +496,14 @@ CHECKSUMS geom2d (0.4.1) sha256=ea0998ea90c4f2752e24fe13d85a4f89bee689d151316140ebcc6369bf634ed9 gitmoji-regex (2.0.1) sha256=a0afe78c4a2cb4590068c3007a1172ac3f12a73fb289bbc8c7a73c759cf8a2f5 hashie (5.1.0) sha256=c266471896f323c446ea8207f8ffac985d2718df0a0ba98651a3057096ca3870 - hexapdf (1.8.0) sha256=3437154213be17a3d0422bdb26638b739da20fce98db1cc3554b0a675eb50437 + hexapdf (1.9.1) sha256=2d1f6a3622e6bc2a70a707d4c3f3fa44f5552ecd9d899f6283abb07398a84884 io-console (0.8.2) sha256=d6e3ae7a7cc7574f4b8893b4fca2162e57a825b223a177b7afa236c5ef9814cc irb (1.18.0) sha256=de9454a0703a54704b9811a5ef31a60c86949fbf4013fcf244fabc7c775248e3 - json (2.19.8) sha256=6354310fd76ef69b87d5bd1f38b40d730613baf90b6803d2d0a48f618d32dfaa + json (2.19.9) sha256=9b9025b7cdddafa38d316eca0b2358488e42d417045c1b90d216a9fefe46b79a jwt (3.2.0) sha256=5419b1fe37b1da0982bd07051f573a8b8789ab724c2aa7e785e4784a3ed217d7 - kettle-dev (2.1.1) sha256=29d68657fa7bc4b42fe2f669c9d82de764180d843f234cf1f5e8493fcefc8543 - kettle-soup-cover (2.0.1) sha256=58417b5d4fc6a631c09cd78a5128b388d9a18c143b8553df2ee8dedbc8a314d7 - kettle-test (2.0.3) sha256=db616394605eaab0f6369b03476d854e66c5d4d9c7a798975837a43685c2a293 + kettle-dev (2.2.5) sha256=c8e553e326f5f72b00b1dd811a00465422c75232c9d7eec72da9a9c5bd1379c5 + kettle-soup-cover (2.0.2) sha256=e400380e165cc880fb0c83f05b2836d815c414b4c707e9c93d5b91979ab12ab4 + kettle-test (2.0.5) sha256=98fd96f03c4470cd2cb0b1cef339455064d8a68bc180f70864d85fd74f41d978 kramdown (2.5.2) sha256=1ba542204c66b6f9111ff00dcc26075b95b220b07f2905d8261740c82f7f02fa kramdown-parser-gfm (1.1.0) sha256=fb39745516427d2988543bf01fc4cf0ab1149476382393e0e9c48592f6581729 language_server-protocol (3.17.0.5) sha256=fd1e39a51a28bf3eec959379985a72e296e9f9acfce46f6a79d31ca8760803cc @@ -500,7 +512,7 @@ CHECKSUMS multi_xml (0.9.1) sha256=7ce766b59c17241ed62976caeae1fae9b2431b263398c35396239a68c4a64e57 mutex_m (0.3.0) sha256=cfcb04ac16b69c4813777022fdceda24e9f798e48092a2b817eb4c0a782b0751 net-http (0.9.1) sha256=25ba0b67c63e89df626ed8fac771d0ad24ad151a858af2cc8e6a716ca4336996 - nkf (0.2.0) sha256=fbc151bda025451f627fafdfcb3f4f13d0b22ae11f58c6d3a2939c76c5f5f126 + nkf (0.3.0) sha256=357a8dbeba38b727b75930f665146546076a394a1c243faf634ff176e3588895 nokogiri (1.19.3-aarch64-linux-gnu) sha256=46b89e5d7b9e844c2ee360794240c6ea2a4e6fa0c5892a4ed487db621224b639 nokogiri (1.19.3-aarch64-linux-musl) sha256=8392dfdcd21be7a94dbbe9ccc138dea01b97b24cb2dc02a114ca98bfb1d9a0b7 nokogiri (1.19.3-arm-linux-gnu) sha256=3919d5ffc334ad778a4a9eb88fda7dcb8b1fb58c8a52ac640c6dcd2f038e774f @@ -508,8 +520,8 @@ CHECKSUMS nokogiri (1.19.3-arm64-darwin) sha256=71b9bd424b1b7abc18b05052a1a3cfd3627abdca62be280854cc411791357e42 nokogiri (1.19.3-x86_64-linux-gnu) sha256=2f5078620fe12e83669b5b17311b32532a8153d02eee7ad06948b926d6080976 nokogiri (1.19.3-x86_64-linux-musl) sha256=248c906d2166eca5efb56d52fdee5f9a1f51d69a72e2b64fdac647b4ce39ea3f - nomono (1.0.2) sha256=49236d39350a66f28ed3f51ec2d94afb8278667576e37ed9763a591e15b65f80 - oauth2 (2.0.22) + nomono (1.0.3) sha256=8a64c6d26e2500097b4fa94eeea5bab717e7b01785853c4e60fe07b0529c8d99 + oauth2 (2.0.23) openssl (4.0.2) sha256=1037ad2868ae58df9ad917891c0c0f9815a1172f6846d4bcdd508e4c2ee747c2 ostruct (0.6.3) sha256=95a2ed4a4bd1d190784e666b47b2d3f078e4a9efda2fccf18f84ddc6538ed912 parallel (1.28.0) sha256=33e6de1484baf2524792d178b0913fc8eb94c628d6cfe45599ad4458c638c970 @@ -540,20 +552,21 @@ CHECKSUMS rspec-stubbed_env (1.0.4) sha256=647886e16338bc4028fd18dde07944c945f773cc65afaa258930196da780e70f rspec-support (3.13.7) sha256=0640e5570872aafefd79867901deeeeb40b0c9875a36b983d85f54fb7381c47c rspec_junit_formatter (0.6.0) sha256=40dde674e6ae4e6cc0ff560da25497677e34fefd2338cc467a8972f602b62b15 - rubocop (1.84.2) sha256=5692cea54168f3dc8cb79a6fe95c5424b7ea893c707ad7a4307b0585e88dbf5f + rubocop (1.87.0) sha256=b9d9ddf55116a513f8ef2c7ae660662d8b49301f118d3f0df61865b33a5c188d rubocop-ast (1.49.1) sha256=4412f3ee70f6fe4546cc489548e0f6fcf76cafcfa80fa03af67098ffed755035 rubocop-capybara (2.23.0) sha256=f9ea1ba3a7561ee8e88cf76fc378ce517ce5327155f305ee7b5c2500e5aee357 rubocop-env (0.1.0) sha256=5ab9a259e71822bf514c8e900a9b68cc2f74ccc87d5493efcd03213f3068e718 rubocop-factory_bot (2.28.0) sha256=4b17fc02124444173317e131759d195b0d762844a71a29fe8139c1105d92f0cb - rubocop-gradual (0.3.6) sha256=d70505a81b63f95ff7d987afe66adf559c53708e4abf06328f6e6026b6571993 + rubocop-gradual (0.4.0) sha256=9c7e584e6fef6c2539266a193a4572c970c22f99046fd6b0305bdde6228f96ad rubocop-lts (8.3.0) sha256=c48b226deda2ac3b3e0b256d035d18ce2d049a67f9c007b389858a32966f9b40 rubocop-lts-rspec (1.0.3) sha256=4ced2fdb793c1eea69f935374ef520558c4a2b82154af95efd1dc8888e27b29c rubocop-md (2.0.4) sha256=0d076b6b5e99dea2ddc928c4bd702497decb9a8400da7808091e02ebcafcfb93 + rubocop-minitest (0.39.1) sha256=998398d6da4026d297f0f9bf709a1eac5f2b6947c24431f94af08138510cf7ed rubocop-on-rbs (2.0.0) sha256=ce74d1b3d5daead19f4b611623656c185821dfc9aed9c7079bb1e5d7d7c464be rubocop-packaging (0.6.0) sha256=fb92bd0fb48e6f8cdb1648d2249b0cd51c2497dcc87340132d22f01edbf558a7 rubocop-performance (1.26.1) sha256=cd19b936ff196df85829d264b522fd4f98b6c89ad271fa52744a8c11b8f71834 rubocop-rake (0.7.1) sha256=3797f2b6810c3e9df7376c26d5f44f3475eda59eb1adc38e6f62ecf027cbae4d - rubocop-rspec (3.9.0) sha256=8fa70a3619408237d789aeecfb9beef40576acc855173e60939d63332fdb55e2 + rubocop-rspec (3.10.2) sha256=0b3e2ecc592cd10ecbf0095bb58d1e357905276e069643523cc19eb7495f65e2 rubocop-rspec-extra (0.3.0) sha256=ee4b6484d0332a0d23c4a465eeb607e41888eb3d4ed479f850b9f5212514f787 rubocop-rspec_rails (2.32.0) sha256=4a0d641c72f6ebb957534f539d9d0a62c47abd8ce0d0aeee1ef4701e892a9100 rubocop-ruby2_2 (3.0.2) sha256=17b343e195fea52be4a645997f9c6498211f7a4bde9ea416a8f8991970bf4a4c @@ -563,18 +576,18 @@ CHECKSUMS ruby_version (1.0.3) sha256=5930f9950746b7e6c973184398ee364ee7440b170fef7922b9f5cdf317f1ccb5 silent_stream (1.0.12) sha256=377c43aa10033fe90c33b39ea8cd97d79f2d1c4856df598efc56f3091f3ae782 simplecov (0.22.0) sha256=fe2622c7834ff23b98066bb0a854284b2729a569ac659f82621fc22ef36213a5 - simplecov-cobertura (3.1.0) sha256=6d7f38aa32c965ca2174b2e5bd88cb17138eaf629518854976ac50e628925dc5 + simplecov-cobertura (3.2.0) sha256=70d702658677fcb20e5aceb6915ccf8bc62ff2ccd38b62b3ad5c9db5c0888740 simplecov-console (0.9.5) sha256=b1108bcfff5f210143e2b8301698c367b01586f20d25a73e95475a5df6fc6ff6 simplecov-html (0.13.2) sha256=bd0b8e54e7c2d7685927e8d6286466359b6f16b18cb0df47b508e8d73c777246 simplecov-lcov (0.9.0) sha256=7a77a31e200a595ed4b0249493056efd0c920601f53d2ef135ca34ee796346cd simplecov-rcov (0.3.7) sha256=372f50bf6df6b6350b7d0c840f2f8bdabe021861a43c26877b747c9ac96139fc simplecov_json_formatter (0.1.4) sha256=529418fbe8de1713ac2b2d612aa3daa56d316975d307244399fa4838c601b428 - snaky_hash (2.0.5) sha256=70e74137d6738aef067950a3bb9a4d2655778be4bc9725efc36e7607feb22cdd - standard (1.54.0) sha256=7a4b08f83d9893083c8f03bc486f0feeb6a84d48233b40829c03ef4767ea0100 + snaky_hash (2.0.6) sha256=3663cae48cdef582b517025cf8a39d8789996eaf0b4ed89e2f0624836505654a + standard (1.55.0) sha256=8a8f2c3e681a4db3aafde1b301561b0f3d7c5f06c160167cb744a4d7baf0426e standard-custom (1.0.2) sha256=424adc84179a074f1a2a309bb9cf7cd6bfdb2b6541f20c6bf9436c0ba22a652b standard-performance (1.9.0) sha256=49483d31be448292951d80e5e67cdcb576c2502103c7b40aec6f1b6e9c88e3f2 standard-rspec (0.5.0) sha256=64d396524a65af47f5331b423d8cdd313e0267401647bb7892489ca89dad2973 - standard-rubocop-lts (2.0.4) sha256=42fff6c4f1284bb6064cc620fce104233313693ace49c30454868f98341ead07 + standard-rubocop-lts (2.0.5) sha256=a379da7bcbe78bfd35e331e1ae0f2a656ded14ee1f5419a3a5284342d14923dc stone_checksums (1.0.3) sha256=1d7ee38b7c766c523cbf12ab886ffbae519a2c48288f9d8ecc7ca0deed0701fe stringio (3.2.0) sha256=c37cb2e58b4ffbd33fe5cd948c05934af997b36e0b6ca6fdf43afa234cf222e1 strscan (3.1.8) sha256=aae2db611a225559f21ffbb71765c9a4e60fd262534a9ea84f4f11c7f32f679e @@ -583,14 +596,15 @@ CHECKSUMS timecop (0.9.11) sha256=41284dc6e5041f2184f781ace766f942108c842f8d8c1386a26e6343decc7542 timecop-rspec (1.0.3) sha256=005f14841bb606dcaefb060e321b5388e2e59537742bee8b3a9a9a40e598fab9 tsort (0.2.0) sha256=9650a793f6859a43b6641671278f79cfead60ac714148aabe4e3f0060480089f - turbo_tests2 (3.1.1) sha256=5b4b03d626f3e5757ef3c450710c9a71f9886f3f421a719e14008ebc1d6b5aa3 + turbo_tests2 (3.1.2) sha256=3b3958be15b5f9d434bb62fba358c59ffa576b263af8d69826ad8ab9e969a22f unicode-display_width (3.2.0) sha256=0cdd96b5681a5949cdbc2c55e7b420facae74c4aaf9a9815eee1087cb1853c42 unicode-emoji (4.2.0) sha256=519e69150f75652e40bf736106cfbc8f0f73aa3fb6a65afe62fefa7f80b0f80f uri (1.1.1) sha256=379fa58d27ffb1387eaada68c749d1426738bd0f654d812fcc07e7568f5c57c6 version_gem (1.1.11) sha256=695df6464862b3dc976b4f6e0e089062517c8137ecd31078d8c378347f959c97 + webrick (1.9.2) sha256=beb4a15fc474defed24a3bda4ffd88a490d517c9e4e6118c3edce59e45864131 yaml-converter (0.2.0) sha256=0602148de1664ab701c7938a036987576c55e87fb6d4b3cb0fff19c4f7a91386 yard (0.9.44) sha256=eb087e9b631ccd887b049f303d489963945452d5e2a7eb49a5a74a7cf6887f28 - yard-fence (0.9.2) sha256=9c74b9986777145b93cb3e1fcb842fffec365a1ff9d5dd2ddc6391fc95a68ac8 + yard-fence (0.9.3) sha256=fe8e8eb07245024ff33b20f5ae90d565ebe8116919734d7c5e7fef5d8b165394 yard-junk (0.1.0) sha256=e85fe2ec1afa47313decd333447b53458cb1ed49b510b70015fdc3041a94bcdd yard-relative_markdown_links (0.6.0) sha256=3e5ffa85cbad9bac70bee5421774b190fb25d3bdf489323a5b3534f647d1a70e yard-timekeeper (0.2.1) sha256=561bb43fd7afccefd8d09cef000d3f1e7b3b25614cb5027f35a22218141ace70 diff --git a/LICENSE.md b/LICENSE.md index fb90c108..67fba766 100644 --- a/LICENSE.md +++ b/LICENSE.md @@ -107,4 +107,5 @@ Choose the option that best fits your use case: - Copyright (c) 2025 Sasa Rosic - Copyright (c) 2026 Jonathan Grinstead - Copyright (c) 2026 kain +- Copyright (c) 2026 Rob Zolkos - Copyright (c) 2026 StepSecurity Bot diff --git a/README.md b/README.md index 82fc3677..33c35ee4 100644 --- a/README.md +++ b/README.md @@ -871,6 +871,7 @@ See [LICENSE.md][📄license] for the official copyright notice. - Copyright (c) 2025 Sasa Rosic - Copyright (c) 2026 Jonathan Grinstead - Copyright (c) 2026 kain +- Copyright (c) 2026 Rob Zolkos - Copyright (c) 2026 StepSecurity Bot @@ -1086,7 +1087,7 @@ Thanks for RTFM. ☺️ [📌gitmoji]: https://gitmoji.dev [📌gitmoji-img]: https://img.shields.io/badge/gitmoji_commits-%20%F0%9F%98%9C%20%F0%9F%98%8D-34495e.svg?style=flat-square [🧮kloc]: https://www.youtube.com/watch?v=dQw4w9WgXcQ -[🧮kloc-img]: https://img.shields.io/badge/KLOC-0.542-FFDD67.svg?style=for-the-badge&logo=YouTube&logoColor=blue +[🧮kloc-img]: https://img.shields.io/badge/KLOC-0.552-FFDD67.svg?style=for-the-badge&logo=YouTube&logoColor=blue [🔐security]: https://github.com/ruby-oauth/oauth2/blob/main/SECURITY.md [🔐security-img]: https://img.shields.io/badge/security-policy-259D6C.svg?style=flat [📄copyright-notice-explainer]: https://opensource.stackexchange.com/questions/5778/why-do-licenses-such-as-the-mit-license-specify-a-single-year @@ -1114,7 +1115,7 @@ Thanks for RTFM. ☺️ | Package | oauth2 | | Description | 🔐 A Ruby wrapper for the OAuth 2.0 Authorization Framework, including the OAuth 2.1 draft spec, and OpenID Connect (OIDC) | | Homepage | https://github.com/ruby-oauth/oauth2 | -| Source | https://github.com/ruby-oauth/oauth2/tree/v2.0.21 | +| Source | https://github.com/ruby-oauth/oauth2/tree/v2.0.23 | | License | `MIT` | | Funding | https://github.com/sponsors/pboling, https://issuehunt.io/u/pboling, https://ko-fi.com/pboling, https://liberapay.com/pboling/donate, https://opencollective.com/ruby-oauth, https://patreon.com/galtzo, https://polar.sh/pboling, https://thanks.dev/u/gh/pboling, https://tidelift.com/funding/github/rubygems/oauth2, https://www.buymeacoffee.com/pboling | diff --git a/Rakefile b/Rakefile index 1131b77b..0916ee93 100644 --- a/Rakefile +++ b/Rakefile @@ -6,7 +6,7 @@ # kettle-jem will then preserve content between those markers across template runs. # kettle-jem:unfreeze -# oauth2 Rakefile v7.0.0 - 2026-06-06 +# oauth2 Rakefile v7.0.0 - 2026-06-13 # Ruby 2.3 (Safe Navigation) or higher required # # See LICENSE.md for license information. diff --git a/bin/kettle-bump b/bin/kettle-bump new file mode 100755 index 00000000..708c1f9e --- /dev/null +++ b/bin/kettle-bump @@ -0,0 +1,16 @@ +#!/usr/bin/env ruby +# frozen_string_literal: true + +# +# This file was generated by Bundler. +# +# The application 'kettle-bump' is installed as part of a gem, and +# this file is here to facilitate running it. +# + +ENV["BUNDLE_GEMFILE"] ||= File.expand_path("../Gemfile", __dir__) + +require "rubygems" +require "bundler/setup" + +load Gem.bin_path("kettle-dev", "kettle-bump") diff --git a/bin/kettle-gha-sha-pins b/bin/kettle-gha-sha-pins new file mode 100755 index 00000000..13b554c9 --- /dev/null +++ b/bin/kettle-gha-sha-pins @@ -0,0 +1,16 @@ +#!/usr/bin/env ruby +# frozen_string_literal: true + +# +# This file was generated by Bundler. +# +# The application 'kettle-gha-sha-pins' is installed as part of a gem, and +# this file is here to facilitate running it. +# + +ENV["BUNDLE_GEMFILE"] ||= File.expand_path("../Gemfile", __dir__) + +require "rubygems" +require "bundler/setup" + +load Gem.bin_path("kettle-dev", "kettle-gha-sha-pins") diff --git a/bin/yardoc b/bin/yardoc new file mode 100755 index 00000000..5ed01e71 --- /dev/null +++ b/bin/yardoc @@ -0,0 +1,16 @@ +#!/usr/bin/env ruby +# frozen_string_literal: true + +# +# This file was generated by Bundler. +# +# The application 'yardoc' is installed as part of a gem, and +# this file is here to facilitate running it. +# + +ENV["BUNDLE_GEMFILE"] ||= File.expand_path("../Gemfile", __dir__) + +require "rubygems" +require "bundler/setup" + +load Gem.bin_path("yard", "yardoc") diff --git a/bin/yri b/bin/yri new file mode 100755 index 00000000..80fa3d7a --- /dev/null +++ b/bin/yri @@ -0,0 +1,16 @@ +#!/usr/bin/env ruby +# frozen_string_literal: true + +# +# This file was generated by Bundler. +# +# The application 'yri' is installed as part of a gem, and +# this file is here to facilitate running it. +# + +ENV["BUNDLE_GEMFILE"] ||= File.expand_path("../Gemfile", __dir__) + +require "rubygems" +require "bundler/setup" + +load Gem.bin_path("yard", "yri") diff --git a/docs/OAuth2/AccessToken.html b/docs/OAuth2/AccessToken.html index 83879152..b395c32f 100644 --- a/docs/OAuth2/AccessToken.html +++ b/docs/OAuth2/AccessToken.html @@ -1047,11 +1047,6 @@

Verb-dependent Hash mode

 
 
-145
-146
-147
-148
-149
 150
 151
 152
@@ -1080,10 +1075,15 @@ 

Verb-dependent Hash mode

175 176 177 -178
+178 +179 +180 +181 +182 +183 -
# File 'lib/oauth2/access_token.rb', line 145
+      
# File 'lib/oauth2/access_token.rb', line 150
 
 def initialize(client, token, opts = {})
   @client = client
@@ -1757,13 +1757,7 @@ 

Examples:

71 72 73 -74 -75 -76 -77 -78 -79 -80
+74
# File 'lib/oauth2/access_token.rb', line 57
@@ -1782,13 +1776,7 @@ 

Examples:

end # :nocov: # TODO: Get rid of this branching logic when dropping Hashie < v3.2 - token = if !defined?(Hashie::VERSION) # i.e. <= "1.1.0"; the first Hashie to ship with a VERSION constant - warn("snaky_hash and oauth2 will drop support for Hashie v0 in the next major version. Please upgrade to a modern Hashie.") - # There is a bug in Hashie v0, which is accounts for. - fresh.delete(t_key) || fresh[t_key] || "" - else - fresh.delete(t_key) || "" - end + token = extract_token_value(fresh, t_key) # :nocov: new(client, token, fresh) end
@@ -1873,12 +1861,12 @@

 
 
-87
-88
-89
+81 +82 +83 -
# File 'lib/oauth2/access_token.rb', line 87
+      
# File 'lib/oauth2/access_token.rb', line 81
 
 def from_kvform(client, kvform)
   from_hash(client, Rack::Utils.parse_query(kvform))
@@ -1938,12 +1926,12 @@ 

 
 
-183
-184
-185
+188 +189 +190

-
# File 'lib/oauth2/access_token.rb', line 183
+      
# File 'lib/oauth2/access_token.rb', line 188
 
 def [](key)
   @params[key]
@@ -1985,12 +1973,12 @@ 

 
 
-365
-366
-367
+370 +371 +372

-
# File 'lib/oauth2/access_token.rb', line 365
+      
# File 'lib/oauth2/access_token.rb', line 370
 
 def delete(path, opts = {}, &block)
   request(:delete, path, opts, &block)
@@ -2042,12 +2030,12 @@ 

 
 
-197
-198
-199
+202 +203 +204

-
# File 'lib/oauth2/access_token.rb', line 197
+      
# File 'lib/oauth2/access_token.rb', line 202
 
 def expired?
   expires? && (expires_at <= Time.now.to_i)
@@ -2095,12 +2083,12 @@ 

 
 
-190
-191
-192
+195 +196 +197

-
# File 'lib/oauth2/access_token.rb', line 190
+      
# File 'lib/oauth2/access_token.rb', line 195
 
 def expires?
   !!@expires_at
@@ -2142,12 +2130,12 @@ 

 
 
-337
-338
-339
+342 +343 +344

-
# File 'lib/oauth2/access_token.rb', line 337
+      
# File 'lib/oauth2/access_token.rb', line 342
 
 def get(path, opts = {}, &block)
   request(:get, path, opts, &block)
@@ -2182,12 +2170,12 @@ 

 
 
-370
-371
-372
+375 +376 +377

-
# File 'lib/oauth2/access_token.rb', line 370
+      
# File 'lib/oauth2/access_token.rb', line 375
 
 def headers
   {"Authorization" => options[:header_format] % token}
@@ -2229,12 +2217,12 @@ 

 
 
-358
-359
-360
+363 +364 +365

-
# File 'lib/oauth2/access_token.rb', line 358
+      
# File 'lib/oauth2/access_token.rb', line 363
 
 def patch(path, opts = {}, &block)
   request(:patch, path, opts, &block)
@@ -2276,12 +2264,12 @@ 

 
 
-344
-345
-346
+349 +350 +351

-
# File 'lib/oauth2/access_token.rb', line 344
+      
# File 'lib/oauth2/access_token.rb', line 349
 
 def post(path, opts = {}, &block)
   request(:post, path, opts, &block)
@@ -2323,12 +2311,12 @@ 

 
 
-351
-352
-353
+356 +357 +358

-
# File 'lib/oauth2/access_token.rb', line 351
+      
# File 'lib/oauth2/access_token.rb', line 356
 
 def put(path, opts = {}, &block)
   request(:put, path, opts, &block)
@@ -2478,11 +2466,6 @@ 

 
 
-212
-213
-214
-215
-216
 217
 218
 219
@@ -2491,10 +2474,15 @@ 

222 223 224 -225

+225 +226 +227 +228 +229 +230

-
# File 'lib/oauth2/access_token.rb', line 212
+      
# File 'lib/oauth2/access_token.rb', line 217
 
 def refresh(params = {}, access_token_opts = {}, &block)
   raise OAuth2::Error.new({error: "A refresh_token is not available"}) unless refresh_token
@@ -2700,13 +2688,13 @@ 

 
 
-329
-330
-331
-332
+334 +335 +336 +337

-
# File 'lib/oauth2/access_token.rb', line 329
+      
# File 'lib/oauth2/access_token.rb', line 334
 
 def request(verb, path, opts = {}, &block)
   configure_authentication!(opts, verb)
@@ -2914,11 +2902,6 @@ 

 
 
-261
-262
-263
-264
-265
 266
 267
 268
@@ -2938,10 +2921,15 @@ 

282 283 284 -285

+285 +286 +287 +288 +289 +290

-
# File 'lib/oauth2/access_token.rb', line 261
+      
# File 'lib/oauth2/access_token.rb', line 266
 
 def revoke(params = {}, &block)
   token_type_hint_orig = params.delete(:token_type_hint)
@@ -3022,11 +3010,6 @@ 

 
 
-295
-296
-297
-298
-299
 300
 301
 302
@@ -3039,10 +3022,15 @@ 

309 310 311 -312

+312 +313 +314 +315 +316 +317

-
# File 'lib/oauth2/access_token.rb', line 295
+      
# File 'lib/oauth2/access_token.rb', line 300
 
 def to_hash
   hsh = {
@@ -3057,8 +3045,8 @@ 

# TODO: Switch when dropping Ruby < 2.5 support # params.transform_keys(&:to_sym) # Ruby 2.5 only # Old Ruby transform_keys alternative: - sheesh = @params.each_with_object({}) { |(k, v), memo| - memo[k.to_sym] = v + sheesh = @params.each_with_object({}) { |(key, value), memo| + memo[key.to_sym] = value } sheesh.merge(hsh) end

@@ -3072,9 +3060,9 @@

diff --git a/docs/OAuth2/Client.html b/docs/OAuth2/Client.html index 2fd967aa..28ddbeb8 100644 --- a/docs/OAuth2/Client.html +++ b/docs/OAuth2/Client.html @@ -1027,7 +1027,8 @@

93 94 95 -96 +96 +97
# File 'lib/oauth2/client.rb', line 85
@@ -1036,8 +1037,9 @@ 

@connection ||= Faraday.new(site, options[:connection_opts]) do |builder| oauth_debug_logging(builder) - if options[:connection_build] - options[:connection_build].call(builder) + connection_build = options[:connection_build] + if connection_build + connection_build.call(builder) else builder.request(:url_encoded) # form-encode POST params builder.adapter(Faraday.default_adapter) # make requests with Net::HTTP @@ -1278,12 +1280,12 @@

 
 
-315
 316
-317
+317 +318

-
# File 'lib/oauth2/client.rb', line 315
+      
# File 'lib/oauth2/client.rb', line 316
 
 def assertion
   @assertion ||= OAuth2::Strategy::Assertion.new(self)
@@ -1325,12 +1327,12 @@ 

 
 
-281
 282
-283
+283 +284

-
# File 'lib/oauth2/client.rb', line 281
+      
# File 'lib/oauth2/client.rb', line 282
 
 def auth_code
   @auth_code ||= OAuth2::Strategy::AuthCode.new(self)
@@ -1403,13 +1405,13 @@ 

 
 
-102
 103
 104
-105
+105 +106

-
# File 'lib/oauth2/client.rb', line 102
+      
# File 'lib/oauth2/client.rb', line 103
 
 def authorize_url(params = {})
   params = (params || {}).merge(redirection_params)
@@ -1452,12 +1454,12 @@ 

 
 
-302
 303
-304
+304 +305

-
# File 'lib/oauth2/client.rb', line 302
+      
# File 'lib/oauth2/client.rb', line 303
 
 def client_credentials
   @client_credentials ||= OAuth2::Strategy::ClientCredentials.new(self)
@@ -1624,7 +1626,6 @@ 

Examples:

 
 
-209
 210
 211
 212
@@ -1638,10 +1639,11 @@ 

Examples:

220 221 222 -223
+223 +224
-
# File 'lib/oauth2/client.rb', line 209
+      
# File 'lib/oauth2/client.rb', line 210
 
 def get_token(params, access_token_opts = {}, extract_access_token = nil, &block)
   warn("OAuth2::Client#get_token argument `extract_access_token` will be removed in oauth2 v3. Refactor to use `access_token_class` on #initialize.") if extract_access_token
@@ -1705,15 +1707,15 @@ 

 
 
-271
 272
 273
 274
 275
-276
+276 +277

-
# File 'lib/oauth2/client.rb', line 271
+      
# File 'lib/oauth2/client.rb', line 272
 
 def http_method
   http_meth = options[:token_method].to_sym
@@ -1758,12 +1760,12 @@ 

 
 
-288
 289
-290
+290 +291

-
# File 'lib/oauth2/client.rb', line 288
+      
# File 'lib/oauth2/client.rb', line 289
 
 def implicit
   @implicit ||= OAuth2::Strategy::Implicit.new(self)
@@ -1805,12 +1807,12 @@ 

 
 
-295
 296
-297
+297 +298

-
# File 'lib/oauth2/client.rb', line 295
+      
# File 'lib/oauth2/client.rb', line 296
 
 def password
   @password ||= OAuth2::Strategy::Password.new(self)
@@ -1887,20 +1889,22 @@ 

 
 
-340
 341
 342
 343
 344
 345
-346
+346 +347 +348

-
# File 'lib/oauth2/client.rb', line 340
+      
# File 'lib/oauth2/client.rb', line 341
 
 def redirection_params
-  if options[:redirect_uri]
-    {"redirect_uri" => options[:redirect_uri]}
+  redirect_uri = options[:redirect_uri]
+  if redirect_uri
+    {"redirect_uri" => redirect_uri}
   else
     {}
   end
@@ -2140,7 +2144,6 @@ 

 
 
-146
 147
 148
 149
@@ -2177,10 +2180,11 @@ 

180 181 182 -183

+183 +184

-
# File 'lib/oauth2/client.rb', line 146
+      
# File 'lib/oauth2/client.rb', line 147
 
 def request(verb, url, req_opts = {}, &block)
   response = execute_request(verb, url, req_opts, &block)
@@ -2188,9 +2192,9 @@ 

case status when 301, 302, 303, 307 - req_opts[:redirect_count] ||= 0 - req_opts[:redirect_count] += 1 - return response if req_opts[:redirect_count] > options[:max_redirects] + redirect_count = req_opts.fetch(:redirect_count, 0) + 1 + req_opts[:redirect_count] = redirect_count + return response if redirect_count > options[:max_redirects] if status == 303 verb = :get @@ -2464,7 +2468,6 @@

 
 
-258
 259
 260
 261
@@ -2472,10 +2475,11 @@ 

263 264 265 -266

+266 +267

-
# File 'lib/oauth2/client.rb', line 258
+      
# File 'lib/oauth2/client.rb', line 259
 
 def revoke_token(token, token_type_hint = nil, params = {}, &block)
   params[:token_method] ||= :post_with_query_string
@@ -2554,12 +2558,12 @@ 

 
 
-119
 120
-121
+121 +122

-
# File 'lib/oauth2/client.rb', line 119
+      
# File 'lib/oauth2/client.rb', line 120
 
 def revoke_url(params = nil)
   connection.build_url(options[:revoke_url], params).to_s
@@ -2632,12 +2636,12 @@ 

 
 
-111
 112
-113
+113 +114

-
# File 'lib/oauth2/client.rb', line 111
+      
# File 'lib/oauth2/client.rb', line 112
 
 def token_url(params = nil)
   connection.build_url(options[:token_url], params).to_s
@@ -2652,7 +2656,7 @@ 

diff --git a/docs/OAuth2/Error.html b/docs/OAuth2/Error.html index 02044040..4df86d73 100644 --- a/docs/OAuth2/Error.html +++ b/docs/OAuth2/Error.html @@ -346,7 +346,8 @@

35 36 37 -38

+38 +39
# File 'lib/oauth2/error.rb', line 18
@@ -356,9 +357,10 @@ 

@code = nil @description = nil if response.respond_to?(:parsed) - if response.parsed.is_a?(Hash) - @code = response.parsed["error"] - @description = response.parsed["error_description"] + parsed_response = response.parsed + if parsed_response.is_a?(Hash) + @code = parsed_response["error"] + @description = parsed_response["error_description"] end elsif response.is_a?(Hash) @code = response["error"] @@ -780,9 +782,9 @@

diff --git a/docs/OAuth2/Response.html b/docs/OAuth2/Response.html index d75e0526..4e5acd68 100644 --- a/docs/OAuth2/Response.html +++ b/docs/OAuth2/Response.html @@ -1207,19 +1207,21 @@

 
 
-134
 135
 136
 137
-138
+138 +139 +140

-
# File 'lib/oauth2/response.rb', line 134
+      
# File 'lib/oauth2/response.rb', line 135
 
 def content_type
-  return unless response.headers
+  response_headers = response.headers
+  return unless response_headers
 
-  ((response.headers.values_at("content-type", "Content-Type").compact.first || "").split(";").first || "").strip.downcase
+  ((response_headers.values_at("content-type", "Content-Type").compact.first || "").split(";").first || "").strip.downcase
 end
@@ -1389,7 +1391,8 @@

126 127 128 -129

+129 +130
# File 'lib/oauth2/response.rb', line 108
@@ -1397,15 +1400,16 @@ 

def parsed return @parsed if defined?(@parsed) + response_parser = parser @parsed = - if parser.respond_to?(:call) - case parser.arity + if response_parser.respond_to?(:call) + case response_parser.arity when 0 - parser.call + response_parser.call when 1 - parser.call(body) + response_parser.call(body) else - parser.call(body, response) + response_parser.call(body, response) end end @@ -1514,8 +1518,6 @@

 
 
-154
-155
 156
 157
 158
@@ -1525,19 +1527,23 @@ 

162 163 164 -165

+165 +166 +167 +168

-
# File 'lib/oauth2/response.rb', line 154
+      
# File 'lib/oauth2/response.rb', line 156
 
 def parser
   return @parser if defined?(@parser)
 
+  parse_option = options[:parse]
   @parser =
-    if options[:parse].respond_to?(:call)
-      options[:parse]
-    elsif options[:parse]
-      @@parsers[options[:parse].to_sym]
+    if parse_option.respond_to?(:call)
+      parse_option
+    elsif parse_option
+      @@parsers[parse_option.to_sym]
     end
 
   @parser ||= @@parsers[@@content_types[content_type]]
@@ -1624,9 +1630,9 @@ 

diff --git a/docs/OAuth2/Version.html b/docs/OAuth2/Version.html index e1f3a84f..346905bd 100644 --- a/docs/OAuth2/Version.html +++ b/docs/OAuth2/Version.html @@ -98,7 +98,7 @@

VERSION =
-
"2.0.22"
+
"2.0.23"
@@ -114,7 +114,7 @@

diff --git a/docs/file.CHANGELOG.html b/docs/file.CHANGELOG.html index 45343000..65c739e3 100644 --- a/docs/file.CHANGELOG.html +++ b/docs/file.CHANGELOG.html @@ -70,7 +70,7 @@ and yes, platform and engine support are part of the public API.
Please file a bug if you notice a violation of semantic versioning.

-

Unreleased

+

Unreleased

Added

@@ -82,8 +82,37 @@

Removed

Fixed

+
    +
  • Fixed head appraisal dependency conflicts and Ruby 2.4 protocol-relative redirect handling by @pboling
  • +
+

Security

+

+2.0.23 - 2026-06-12

+ +
    +
  • TAG: v2.0.23 +
  • +
  • COVERAGE: 100.00% – 552/552 lines in 15 files
  • +
  • BRANCH COVERAGE: 98.90% – 180/182 branches in 15 files
  • +
  • 88.35% documented
  • +
+ +

Changed

+ +
    +
  • Upgraded to snaky_hash v2.0.6 by @pboling
  • +
  • Refreshed generated GHA workflow action SHA pins by @pboling
  • +
+ +

Fixed

+ +
    +
  • Addressed Reek code-quality checks with targeted cleanup and documented compatibility exclusions by @pboling
  • +
  • Fixed deprecation warning from MultiXML by @robzolkos
  • +
+

2.0.22 - 2026-06-07

@@ -95,7 +124,7 @@

  • 88.35% documented
  • -

    Changed

    +

    Changed

    • Raised generated development tooling floors to kettle-dev >= 2.1.1 and
      @@ -106,7 +135,8 @@

      Changed

      Security

        -
      • [GHSA-pp92-crg2-gfv9] Prevent protocol-relative redirect Location values from changing request authority, and strip Authorization headers from cross-origin redirects.
      • +
      • +GHSA-pp92-crg2-gfv9 Prevent protocol-relative redirect Location values from changing request authority, and strip Authorization headers from cross-origin redirects by @tonghuaroot and @pboling

      @@ -133,7 +163,7 @@

      Added

      so generated Appraisal gemfiles are normalized during generation - by @pboling
    -

    Changed

    +

    Changed

    • Raised generated version_gem dependency floor to version_gem >= 1.1.10 - by @pboling
    • @@ -160,7 +190,7 @@

      Removed

      coverage is already handled by the standard Ruby 2.4 workflow - by @pboling
    -

    Fixed

    +

    Fixed

    • Updated CI workflow maintenance: QLTY uploads now use OIDC and harden-runner
      @@ -199,13 +229,13 @@

      Added

    • OAuth2::VERSION (Traditional Constant Location) - by @pboling
    -

    Changed

    +

    Changed

    • auth-sanitizer v0.1.3 - by @pboling
    -

    Fixed

    +

    Fixed

    • @@ -234,7 +264,7 @@

      Added

      gh!707 Add OAuth2.config[:filtered_debug_keys] to configure which key names have their values redacted from debug logging output by @pboling
    -

    Changed

    +

    Changed

    • @@ -282,7 +312,7 @@

      Added

      gh!687- Add Threat Model by @pboling
    -

    Changed

    +

    Changed

    • @@ -294,7 +324,7 @@

      Changed

    -

    Fixed

    +

    Fixed

    • @@ -356,7 +386,7 @@

      Added

      gh!676, gh!679 - Apache SkyWalking Eyes dependency license check by @pboling
    -

    Changed

    +

    Changed

    • @@ -396,14 +426,14 @@

      Added

    -

    Changed

    +

    Changed

    • gh!669 - Upgrade to kettle-dev v1.1.9 by @pboling
    -

    Fixed

    +

    Fixed

    • Remove accidentally duplicated lines, and fix typos in CHANGELOG.md
    • @@ -482,7 +512,7 @@

      Added

    • Documentation: Added docs/OIDC.md with OIDC 1.0 overview, example, and references
    -

    Changed

    +

    Changed

    • Upgrade Code of Conduct to Contributor Covenant 2.1 by @pboling
    • @@ -490,7 +520,7 @@

      Changed

      gh!660 - Shrink post-install message by 4 lines by @pboling
    -

    Fixed

    +

    Fixed

    • @@ -526,13 +556,13 @@

      Added

    • Documentation site @ https://oauth2.galtzo.com now complete
    -

    Changed

    +

    Changed

    • Updates to gemspec (email, funding url, post install message)
    -

    Fixed

    +

    Fixed

    • Documentation Typos by @pboling
    • @@ -579,7 +609,7 @@

      Added

    -

    Changed

    +

    Changed

    • @@ -591,7 +621,7 @@

      Changed

    • Updated spec.homepage_uri in gemspec to GitHub Pages YARD documentation site (@pboling)
    -

    Fixed

    +

    Fixed

    • @@ -656,7 +686,7 @@

      Added

      !648 - Improved documentation (@pboling)
    -

    Changed

    +

    Changed

    • Default value of OAuth2.config.silence_extra_tokens_warning was false, now true (@pboling)
    • @@ -673,7 +703,7 @@

      Changed

      !647 - Errors raised by OAuth2::AccessToken are now always OAuth2::Error and have better metadata (@pboling)
    -

    Fixed

    +

    Fixed

    • @@ -720,7 +750,7 @@

      Added

    • More specs (@pboling)
    -

    Changed

    +

    Changed

    • Complete migration to main branch as default (@pboling)
    • @@ -735,7 +765,7 @@

    -

    Changed

    +

    Changed

    • @@ -765,7 +795,7 @@

      Added

      !629 - Allow POST of JSON to get token (@pboling, @terracatta)
    -

    Fixed

    +

    Fixed

    • @@ -786,7 +816,7 @@

    -

    Fixed

    +

    Fixed

    • @@ -801,7 +831,7 @@

    -

    Fixed

    +

    Fixed

    • @@ -831,7 +861,7 @@

    -

    Fixed

    +

    Fixed

    • @@ -855,7 +885,7 @@

      Added

      !612 - Add snaky: false option to skip conversion to OAuth2::SnakyHash (default: true) (@pboling)
    -

    Fixed

    +

    Fixed

    • @@ -872,7 +902,7 @@

    -

    Fixed

    +

    Fixed

    • @@ -963,7 +993,7 @@

      Added

      !581 - Documentation: of breaking changes (@pboling)
    -

    Changed

    +

    Changed

    • @@ -998,7 +1028,7 @@

      Changed

      !591 - DEPRECATION: OAuth2::Client - :extract_access_token option is deprecated
    -

    Fixed

    +

    Fixed

    • @@ -1312,7 +1342,7 @@

      Added

    • Add an implementation of the MAC token spec.
    -

    Fixed

    +

    Fixed

    • Fix Base64.strict_encode64 incompatibility with Ruby 1.8.7.
    • @@ -1326,7 +1356,7 @@

    -

    Changed

    +

    Changed

    • @@ -1496,7 +1526,7 @@

      diff --git a/docs/file.LICENSE.html b/docs/file.LICENSE.html index 7294d976..3d45ae69 100644 --- a/docs/file.LICENSE.html +++ b/docs/file.LICENSE.html @@ -171,12 +171,13 @@

    • Copyright (c) 2025 Sasa Rosic
    • Copyright (c) 2026 Jonathan Grinstead
    • Copyright (c) 2026 kain
    • +
    • Copyright (c) 2026 Rob Zolkos
    • Copyright (c) 2026 StepSecurity Bot
    diff --git a/docs/file.README.html b/docs/file.README.html index 60aadeef..0f9408d1 100644 --- a/docs/file.README.html +++ b/docs/file.README.html @@ -317,7 +317,7 @@

    💡 Info you can shake a stick at

    Source -Source on GitLab.com Source on CodeBerg.org Source on Github.com The best SHA: dQw4w9WgXcQ! +Source on GitLab.com Source on CodeBerg.org Source on Github.com The best SHA: dQw4w9WgXcQ! @@ -1192,6 +1192,7 @@
  • Copyright (c) 2025 Sasa Rosic
  • Copyright (c) 2026 Jonathan Grinstead
  • Copyright (c) 2026 kain
  • +
  • Copyright (c) 2026 Rob Zolkos
  • Copyright (c) 2026 StepSecurity Bot
  • @@ -1226,14 +1227,14 @@

    Please give the project a star ⭐ ♥ | Package | oauth2 |
    | Description | 🔐 A Ruby wrapper for the OAuth 2.0 Authorization Framework, including the OAuth 2.1 draft spec, and OpenID Connect (OIDC) |
    | Homepage | https://github.com/ruby-oauth/oauth2 |
    -| Source | https://github.com/ruby-oauth/oauth2/tree/v2.0.21 |
    +| Source | https://github.com/ruby-oauth/oauth2/tree/v2.0.23 |
    | License | MIT |
    | Funding | https://github.com/sponsors/pboling, https://issuehunt.io/u/pboling, https://ko-fi.com/pboling, https://liberapay.com/pboling/donate, https://opencollective.com/ruby-oauth, https://patreon.com/galtzo, https://polar.sh/pboling, https://thanks.dev/u/gh/pboling, https://tidelift.com/funding/github/rubygems/oauth2, https://www.buymeacoffee.com/pboling |

    diff --git a/docs/index.html b/docs/index.html index 2ae79369..909a4ecf 100644 --- a/docs/index.html +++ b/docs/index.html @@ -317,7 +317,7 @@

    💡 Info you can shake a stick at

    Source -Source on GitLab.com Source on CodeBerg.org Source on Github.com The best SHA: dQw4w9WgXcQ! +Source on GitLab.com Source on CodeBerg.org Source on Github.com The best SHA: dQw4w9WgXcQ! @@ -1192,6 +1192,7 @@
  • Copyright (c) 2025 Sasa Rosic
  • Copyright (c) 2026 Jonathan Grinstead
  • Copyright (c) 2026 kain
  • +
  • Copyright (c) 2026 Rob Zolkos
  • Copyright (c) 2026 StepSecurity Bot
  • @@ -1226,14 +1227,14 @@

    Please give the project a star ⭐ ♥ | Package | oauth2 |
    | Description | 🔐 A Ruby wrapper for the OAuth 2.0 Authorization Framework, including the OAuth 2.1 draft spec, and OpenID Connect (OIDC) |
    | Homepage | https://github.com/ruby-oauth/oauth2 |
    -| Source | https://github.com/ruby-oauth/oauth2/tree/v2.0.21 |
    +| Source | https://github.com/ruby-oauth/oauth2/tree/v2.0.23 |
    | License | MIT |
    | Funding | https://github.com/sponsors/pboling, https://issuehunt.io/u/pboling, https://ko-fi.com/pboling, https://liberapay.com/pboling/donate, https://opencollective.com/ruby-oauth, https://patreon.com/galtzo, https://polar.sh/pboling, https://thanks.dev/u/gh/pboling, https://tidelift.com/funding/github/rubygems/oauth2, https://www.buymeacoffee.com/pboling |

    diff --git a/gemfiles/head.gemfile b/gemfiles/head.gemfile index 642d6d57..ceecfc2b 100644 --- a/gemfiles/head.gemfile +++ b/gemfiles/head.gemfile @@ -2,10 +2,6 @@ source "https://gem.coop" -gem "benchmark", "~> 0.4", ">= 0.4.1" - gemspec path: "../" -eval_gemfile("modular/x_std_libs.gemfile") - eval_gemfile("modular/runtime_heads.gemfile") diff --git a/gemfiles/modular/cgi/r4/v0.5.gemfile b/gemfiles/modular/cgi/r4/v0.5.gemfile new file mode 100644 index 00000000..19ed967c --- /dev/null +++ b/gemfiles/modular/cgi/r4/v0.5.gemfile @@ -0,0 +1 @@ +gem "cgi", "~> 0.5" diff --git a/gemfiles/modular/cgi/vHEAD.gemfile b/gemfiles/modular/cgi/vHEAD.gemfile new file mode 100644 index 00000000..ef8b816c --- /dev/null +++ b/gemfiles/modular/cgi/vHEAD.gemfile @@ -0,0 +1 @@ +gem "cgi", ">= 0.5" diff --git a/gemfiles/modular/coverage.gemfile b/gemfiles/modular/coverage.gemfile index 369f65d0..ce882e12 100644 --- a/gemfiles/modular/coverage.gemfile +++ b/gemfiles/modular/coverage.gemfile @@ -7,7 +7,7 @@ if ENV.fetch("KETTLE_RB_DEV", "false").casecmp("false").zero? # Coverage (remote/released) platform :mri do - gem "kettle-soup-cover", "~> 2.0", ">= 2.0.1", require: false + gem "kettle-soup-cover", "~> 2.0", ">= 2.0.2", require: false end else eval_gemfile "coverage_local.gemfile" diff --git a/gemfiles/modular/documentation.gemfile b/gemfiles/modular/documentation.gemfile index d851a58f..b1775cb7 100644 --- a/gemfiles/modular/documentation.gemfile +++ b/gemfiles/modular/documentation.gemfile @@ -15,7 +15,7 @@ gem "yard-junk", "~> 0.1", ">= 0.1.0", require: false # Ruby >= 3.1 gem "yard-relative_markdown_links", "~> 0.6", require: false if ENV.fetch("GALTZO_FLOSS_DEV", "false").casecmp("false").zero? - gem "yard-fence", "~> 0.9", ">= 0.9.2", require: false # Ruby >= 3.2 + gem "yard-fence", "~> 0.9", ">= 0.9.3", require: false # Ruby >= 3.2 gem "yard-timekeeper", "~> 0.2", ">= 0.2.1", require: false gem "yard-yaml", "~> 0.2", ">= 0.2.0", require: false else diff --git a/gemfiles/modular/multi_xml_v0_7.gemfile b/gemfiles/modular/multi_xml_v0_7.gemfile index b56c3f01..166b53f9 100644 --- a/gemfiles/modular/multi_xml_v0_7.gemfile +++ b/gemfiles/modular/multi_xml_v0_7.gemfile @@ -2,5 +2,6 @@ # Ruby >= 2.5 # We will test it against Ruby 2.5, 2.6, 2.7, 3.0, 3.1, 3.2, 3.3, 3.4. +# multi_xml 0.8.x has parser compatibility issues on TruffleRuby 23.1; # multi_xml 0.9.x uses Fiber.[], which is unavailable on TruffleRuby 24.2. -gem "multi_xml", "~> 0.7", ">= 0.7.2", "< 0.9" +gem "multi_xml", "~> 0.7", ">= 0.7.2", "< 0.8" diff --git a/gemfiles/modular/style.gemfile b/gemfiles/modular/style.gemfile index 11ffb230..04375f91 100644 --- a/gemfiles/modular/style.gemfile +++ b/gemfiles/modular/style.gemfile @@ -13,6 +13,8 @@ gem "reek", "~> 6.5", ">= 6.5.0" platform :mri do gem "appraisal2-rubocop", "~> 0.2", ">= 0.2.0", require: false + gem "rubocop-gradual", "~> 0.4", ">= 0.4.0" + gem "rubocop-minitest", "~> 0.38", ">= 0.38.1" gem "rubocop-on-rbs", "~> 2.0", ">= 2.0.0" # ruby >= 3.2.0 # gem "rubocop", "~> 1.73", ">= 1.73.2" # constrained by standard gem "rubocop-packaging", "~> 0.6", ">= 0.6.0" diff --git a/gemfiles/modular/templating.gemfile b/gemfiles/modular/templating.gemfile index cf1708d7..4094629c 100644 --- a/gemfiles/modular/templating.gemfile +++ b/gemfiles/modular/templating.gemfile @@ -10,7 +10,7 @@ end if kettle_remote # Template/plugin checks for released installs. - gem "kettle-drift", "~> 1.0", ">= 1.0.1", require: false + gem "kettle-drift", "~> 1.0", ">= 1.0.3", require: false end # Set SMORG_RB_DEV=/path/to/structuredmerge/ruby/gems for local development with path-based dependencies. diff --git a/gemfiles/modular/webrick/r4/v1.9.gemfile b/gemfiles/modular/webrick/r4/v1.9.gemfile new file mode 100644 index 00000000..eaab4a47 --- /dev/null +++ b/gemfiles/modular/webrick/r4/v1.9.gemfile @@ -0,0 +1 @@ +gem "webrick", "~> 1.9" diff --git a/gemfiles/modular/webrick/vHEAD.gemfile b/gemfiles/modular/webrick/vHEAD.gemfile new file mode 100644 index 00000000..8a789b63 --- /dev/null +++ b/gemfiles/modular/webrick/vHEAD.gemfile @@ -0,0 +1 @@ +gem "webrick", ">= 1.9" diff --git a/gemfiles/modular/x_std_libs/r4/libs.gemfile b/gemfiles/modular/x_std_libs/r4/libs.gemfile index 21f7e99a..eb557424 100644 --- a/gemfiles/modular/x_std_libs/r4/libs.gemfile +++ b/gemfiles/modular/x_std_libs/r4/libs.gemfile @@ -2,3 +2,5 @@ eval_gemfile "../../erb/r4/v5.0.gemfile" eval_gemfile "../../mutex_m/r4/v0.3.gemfile" eval_gemfile "../../stringio/r4/v3.0.gemfile" eval_gemfile "../../benchmark/r4/v0.5.gemfile" +eval_gemfile "../../cgi/r4/v0.5.gemfile" +eval_gemfile "../../webrick/r4/v1.9.gemfile" diff --git a/gemfiles/modular/x_std_libs/vHEAD.gemfile b/gemfiles/modular/x_std_libs/vHEAD.gemfile index b38c6fa7..d4d5b16c 100644 --- a/gemfiles/modular/x_std_libs/vHEAD.gemfile +++ b/gemfiles/modular/x_std_libs/vHEAD.gemfile @@ -2,3 +2,5 @@ eval_gemfile "../erb/vHEAD.gemfile" eval_gemfile "../mutex_m/vHEAD.gemfile" eval_gemfile "../stringio/vHEAD.gemfile" eval_gemfile "../benchmark/vHEAD.gemfile" +eval_gemfile "../cgi/vHEAD.gemfile" +eval_gemfile "../webrick/vHEAD.gemfile" diff --git a/lib/oauth2/access_token.rb b/lib/oauth2/access_token.rb index 6f028945..8e1f7302 100644 --- a/lib/oauth2/access_token.rb +++ b/lib/oauth2/access_token.rb @@ -68,13 +68,7 @@ def from_hash(client, hash) end # :nocov: # TODO: Get rid of this branching logic when dropping Hashie < v3.2 - token = if !defined?(Hashie::VERSION) # i.e. <= "1.1.0"; the first Hashie to ship with a VERSION constant - warn("snaky_hash and oauth2 will drop support for Hashie v0 in the next major version. Please upgrade to a modern Hashie.") - # There is a bug in Hashie v0, which is accounts for. - fresh.delete(t_key) || fresh[t_key] || "" - else - fresh.delete(t_key) || "" - end + token = extract_token_value(fresh, t_key) # :nocov: new(client, token, fresh) end @@ -108,6 +102,17 @@ def no_tokens_warning(hash, key) You may need to set `snaky: false`. See inline documentation for more info. ]) end + + # :nocov: + def extract_token_value(fresh, key) + token_value = fresh.delete(key) + return token_value || "" if defined?(Hashie::VERSION) + + warn("snaky_hash and oauth2 will drop support for Hashie v0 in the next major version. Please upgrade to a modern Hashie.") + # There is a bug in Hashie v0, which this accounts for. + token_value || fresh[key] || "" + end + # :nocov: end # Initialize an AccessToken @@ -305,8 +310,8 @@ def to_hash # TODO: Switch when dropping Ruby < 2.5 support # params.transform_keys(&:to_sym) # Ruby 2.5 only # Old Ruby transform_keys alternative: - sheesh = @params.each_with_object({}) { |(k, v), memo| - memo[k.to_sym] = v + sheesh = @params.each_with_object({}) { |(key, value), memo| + memo[key.to_sym] = value } sheesh.merge(hsh) end @@ -375,6 +380,7 @@ def headers def configure_authentication!(opts, verb) mode_opt = options[:mode] + param_name = options[:param_name] mode = if mode_opt.respond_to?(:call) mode_opt.call(verb) @@ -388,19 +394,19 @@ def configure_authentication!(opts, verb) case mode when :header - opts[:headers] ||= {} - opts[:headers].merge!(headers) + request_headers = opts[:headers] ||= {} + request_headers.merge!(headers) when :query # OAuth 2.1 note: Bearer tokens in the query string are omitted from the spec due to security risks. # Prefer the default :header mode whenever possible. - opts[:params] ||= {} - opts[:params][options[:param_name]] = token + request_params = opts[:params] ||= {} + request_params[param_name] = token when :body - opts[:body] ||= {} - if opts[:body].is_a?(Hash) - opts[:body][options[:param_name]] = token + request_body = opts[:body] ||= {} + if request_body.is_a?(Hash) + request_body[param_name] = token else - opts[:body] += "&#{options[:param_name]}=#{token}" + opts[:body] = "#{request_body}&#{param_name}=#{token}" end # @todo support for multi-part (file uploads) else diff --git a/lib/oauth2/client.rb b/lib/oauth2/client.rb index d1676f78..9008d6c7 100644 --- a/lib/oauth2/client.rb +++ b/lib/oauth2/client.rb @@ -86,8 +86,9 @@ def connection @connection ||= Faraday.new(site, options[:connection_opts]) do |builder| oauth_debug_logging(builder) - if options[:connection_build] - options[:connection_build].call(builder) + connection_build = options[:connection_build] + if connection_build + connection_build.call(builder) else builder.request(:url_encoded) # form-encode POST params builder.adapter(Faraday.default_adapter) # make requests with Net::HTTP @@ -149,9 +150,9 @@ def request(verb, url, req_opts = {}, &block) case status when 301, 302, 303, 307 - req_opts[:redirect_count] ||= 0 - req_opts[:redirect_count] += 1 - return response if req_opts[:redirect_count] > options[:max_redirects] + redirect_count = (req_opts[:redirect_count] || 0).to_i + 1 + req_opts[:redirect_count] = redirect_count + return response if redirect_count > options[:max_redirects] if status == 303 verb = :get @@ -338,8 +339,9 @@ def assertion # # @return [Hash] the params to add to a request or URL def redirection_params - if options[:redirect_uri] - {"redirect_uri" => options[:redirect_uri]} + redirect_uri = options[:redirect_uri] + if redirect_uri + {"redirect_uri" => redirect_uri} else {} end @@ -446,7 +448,7 @@ def execute_request(verb, url, opts = {}) url = connection.build_url(url).to_s # See: Hash#partition https://bugs.ruby-lang.org/issues/16252 req_opts, oauth_opts = opts. - partition { |k, _v| RESERVED_REQ_KEYS.include?(k.to_s) }. + partition { |key, _value| RESERVED_REQ_KEYS.include?(key.to_s) }. map(&:to_h) begin @@ -454,10 +456,10 @@ def execute_request(verb, url, opts = {}) req.params.update(req_opts[:params]) if req_opts[:params] yield(req) if block_given? end - rescue Faraday::ConnectionFailed => e - raise ConnectionError, e - rescue Faraday::TimeoutError => e - raise TimeoutError, e + rescue Faraday::ConnectionFailed => exception + raise ConnectionError, exception + rescue Faraday::TimeoutError => exception + raise TimeoutError, exception end parse = oauth_opts.key?(:parse) ? oauth_opts.delete(:parse) : Response::DEFAULT_OPTIONS[:parse] @@ -467,29 +469,42 @@ def execute_request(verb, url, opts = {}) end def resolve_redirect_location(current_location, location) - safe_location = - if location.respond_to?(:start_with?) && location.start_with?("//") - "./#{location}" - else - location - end + return protocol_relative_redirect_location(current_location, location) if location.respond_to?(:start_with?) && location.start_with?("//") - current_location.merge(safe_location) + current_location.merge(location) + end + + def protocol_relative_redirect_location(current_location, location) + protocol_relative_location = URI.parse(location) + authority = +"" + authority << "#{protocol_relative_location.userinfo}@" if protocol_relative_location.userinfo + authority << protocol_relative_location.host.to_s + authority << ":#{protocol_relative_location.port}" if protocol_relative_location.port + + current_location.dup.tap do |safe_location| + safe_location.path = "///#{authority}#{protocol_relative_location.path}" + safe_location.query = protocol_relative_location.query if safe_location.respond_to?(:query=) + safe_location.fragment = protocol_relative_location.fragment if safe_location.respond_to?(:fragment=) + end end def sanitize_redirect_options(req_opts, current_location, next_location) return req_opts unless cross_origin_redirect?(current_location, next_location) headers = req_opts[:headers] - return req_opts unless headers && headers.any? { |key, _value| key.to_s.casecmp("Authorization").zero? } + return req_opts unless headers && headers.any? { |key, _value| authorization_header?(key) } safe_opts = req_opts.dup safe_headers = headers.dup - safe_headers.delete_if { |key, _value| key.to_s.casecmp("Authorization").zero? } + safe_headers.delete_if { |key, _value| authorization_header?(key) } safe_opts[:headers] = safe_headers safe_opts end + def authorization_header?(key) + key.to_s.casecmp("Authorization").zero? + end + def cross_origin_redirect?(current_location, next_location) current_location.scheme != next_location.scheme || current_location.host != next_location.host || @@ -595,12 +610,13 @@ def build_access_token_legacy(response, access_token_opts, extract_access_token) def oauth_debug_logging(builder) if OAuth2::OAUTH_DEBUG + config = OAuth2.config builder.response( :logger, OAuth2::AUTH_SANITIZER::SanitizedLogger.new( options[:logger], - filtered_keys: OAuth2.config[:filtered_debug_keys], - label: OAuth2.config[:filtered_label] + filtered_keys: config[:filtered_debug_keys], + label: config[:filtered_label] ), bodies: true ) diff --git a/lib/oauth2/error.rb b/lib/oauth2/error.rb index 550d4727..a72f72e8 100644 --- a/lib/oauth2/error.rb +++ b/lib/oauth2/error.rb @@ -20,9 +20,10 @@ def initialize(response) @code = nil @description = nil if response.respond_to?(:parsed) - if response.parsed.is_a?(Hash) - @code = response.parsed["error"] - @description = response.parsed["error_description"] + parsed_response = response.parsed + if parsed_response.is_a?(Hash) + @code = parsed_response["error"] + @description = parsed_response["error_description"] end elsif response.is_a?(Hash) @code = response["error"] @@ -46,11 +47,12 @@ def initialize(response) # @return [String] Message suitable for StandardError def error_message(response_body, opts = {}) lines = [] + error_description = opts[:error_description] - lines << opts[:error_description] if opts[:error_description] + lines << error_description if error_description - error_string = if response_body.respond_to?(:encode) && opts[:error_description].respond_to?(:encoding) - script_encoding = opts[:error_description].encoding + error_string = if response_body.respond_to?(:encode) && error_description.respond_to?(:encoding) + script_encoding = error_description.encoding response_body.encode(script_encoding, invalid: :replace, undef: :replace) else response_body diff --git a/lib/oauth2/response.rb b/lib/oauth2/response.rb index 31edd09f..5c0b0170 100644 --- a/lib/oauth2/response.rb +++ b/lib/oauth2/response.rb @@ -1,6 +1,7 @@ # frozen_string_literal: true require "json" +require "set" require "multi_xml" require "rack" @@ -108,15 +109,16 @@ def body def parsed return @parsed if defined?(@parsed) + response_parser = parser @parsed = - if parser.respond_to?(:call) - case parser.arity + if response_parser.respond_to?(:call) + case response_parser.arity when 0 - parser.call + response_parser.call when 1 - parser.call(body) + response_parser.call(body) else - parser.call(body, response) + response_parser.call(body, response) end end @@ -132,9 +134,10 @@ def parsed # # @return [String, nil] The content type or nil if headers are not present def content_type - return unless response.headers + response_headers = response.headers + return unless response_headers - ((response.headers.values_at("content-type", "Content-Type").compact.first || "").split(";").first || "").strip.downcase + ((response_headers.values_at("content-type", "Content-Type").compact.first || "").split(";").first || "").strip.downcase end # Determines the parser to be used for the response body @@ -154,11 +157,12 @@ def content_type def parser return @parser if defined?(@parser) + parse_option = options[:parse] @parser = - if options[:parse].respond_to?(:call) - options[:parse] - elsif options[:parse] - @@parsers[options[:parse].to_sym] + if parse_option.respond_to?(:call) + parse_option + elsif parse_option + @@parsers[parse_option.to_sym] end @parser ||= @@parsers[@@content_types[content_type]] diff --git a/lib/oauth2/version.rb b/lib/oauth2/version.rb index ec8b4092..00585bd0 100644 --- a/lib/oauth2/version.rb +++ b/lib/oauth2/version.rb @@ -2,7 +2,7 @@ module OAuth2 module Version - VERSION = "2.0.22" + VERSION = "2.0.23" end VERSION = Version::VERSION # Traditional Constant Location end diff --git a/oauth2.gemspec b/oauth2.gemspec index 55bb15fc..21be1249 100644 --- a/oauth2.gemspec +++ b/oauth2.gemspec @@ -20,8 +20,8 @@ gem_version = Gem::Specification.new do |spec| spec.name = "oauth2" spec.version = gem_version - spec.authors = ["Peter Boling", "Erik Michaels-Ober", "Michael Bleigh"] - spec.email = ["floss@galtzo.com", "oauth-ruby@googlegroups.com"] + spec.authors = ["Peter H. Boling"] + spec.email = ["floss@galtzo.com"] spec.summary = "🔐 OAuth 2.0, 2.1 & OIDC Core Ruby implementation" spec.description = "🔐 A Ruby wrapper for the OAuth 2.0 Authorization Framework, including the OAuth 2.1 draft spec, and OpenID Connect (OIDC)" @@ -112,7 +112,7 @@ Gem::Specification.new do |spec| spec.add_dependency("logger", "~> 1.2") # ruby >= 0 spec.add_dependency("multi_xml", "~> 0.5") # ruby >= 0 spec.add_dependency("rack", [">= 1.2", "< 4"]) # ruby >= 0 - spec.add_dependency("snaky_hash", "~> 2.0", ">= 2.0.5") # ruby >= 2.2.0 + spec.add_dependency("snaky_hash", "~> 2.0", ">= 2.0.6") # ruby >= 2.2.0 spec.add_dependency("version_gem", "~> 1.1", ">= 1.1.11") # ruby >= 2.2.0 # NOTE: It is preferable to list development dependencies in the gemspec due to increased @@ -129,7 +129,7 @@ Gem::Specification.new do |spec| # and preferably a modular one (see gemfiles/modular/*.gemfile). # Dev, Test, & Release Tasks - spec.add_development_dependency("kettle-dev", "~> 2.1", ">= 2.1.1") # ruby >= 2.4 + spec.add_development_dependency("kettle-dev", "~> 2.2", ">= 2.2.5") # ruby >= 2.4 # Security spec.add_development_dependency("bundler-audit", "~> 0.9.3") # ruby >= 2.0.0 @@ -141,9 +141,9 @@ Gem::Specification.new do |spec| spec.add_development_dependency("require_bench", "~> 1.0", ">= 1.0.4") # ruby >= 2.2.0 # Testing - spec.add_development_dependency("appraisal2", "~> 3.1", ">= 3.1.1") # ruby >= 1.8.7, for testing against multiple versions of dependencies - spec.add_development_dependency("kettle-test", "~> 2.0", ">= 2.0.3") # ruby >= 2.4 - spec.add_development_dependency("turbo_tests2", "~> 3.1", ">= 3.1.1") # ruby >= 2.4.0, default kettle-test runner + spec.add_development_dependency("appraisal2", "~> 3.1", ">= 3.1.2") # ruby >= 1.8.7, for testing against multiple versions of dependencies + spec.add_development_dependency("kettle-test", "~> 2.0", ">= 2.0.5") # ruby >= 2.4 + spec.add_development_dependency("turbo_tests2", "~> 3.1", ">= 3.1.2") # ruby >= 2.4.0, default kettle-test runner # Releasing spec.add_development_dependency("ruby-progressbar", "~> 1.13") # ruby >= 0 diff --git a/spec/config/multi_xml.rb b/spec/config/multi_xml.rb index 00b240bc..1e7fc42b 100644 --- a/spec/config/multi_xml.rb +++ b/spec/config/multi_xml.rb @@ -1,5 +1,6 @@ # frozen_string_literal: true +require "set" require "multi_xml" (defined?(MultiXML) ? MultiXML : MultiXml).parser = :rexml diff --git a/spec/oauth2/access_token_spec.rb b/spec/oauth2/access_token_spec.rb index aaac469d..8348592f 100644 --- a/spec/oauth2/access_token_spec.rb +++ b/spec/oauth2/access_token_spec.rb @@ -295,10 +295,11 @@ end def assert_initialized_token(target) + target_params = target.params expect(target.token).to eq(token) expect(target).to be_expires - expect(target.params.keys).to include("foo") - expect(target.params["foo"]).to eq("bar") + expect(target_params.keys).to include("foo") + expect(target_params["foo"]).to eq("bar") end it "initializes with a Hash" do diff --git a/spec/oauth2/client_spec.rb b/spec/oauth2/client_spec.rb index f5d089aa..f1654779 100644 --- a/spec/oauth2/client_spec.rb +++ b/spec/oauth2/client_spec.rb @@ -547,6 +547,50 @@ expect(response.response.env.url.to_s).to eq("https://api.example.com///attacker.example/leak") end + it "preserves query and fragment components in protocol-relative redirect locations" do + client = described_class.new("abc", "def", site: "https://api.example.com") do |builder| + builder.adapter :test do |stub| + stub.get("/protocol_relative_redirect_with_components") do |_env| + [302, {"Content-Type" => "text/plain", "location" => "//attacker.example/leak_with_components?x=1#frag"}, ""] + end + stub.get("///attacker.example/leak_with_components") do |env| + [200, {}, JSON.dump(url: env[:url].to_s)] + end + end + end + + response = client.request(:get, "/protocol_relative_redirect_with_components") + body = JSON.parse(response.body) + + expect(body["url"]).to eq("https://api.example.com///attacker.example/leak_with_components?x=1") + expect(response.response.env.url.to_s).to eq("https://api.example.com///attacker.example/leak_with_components?x=1") + end + + it "retains protocol-relative redirect fragments on the resolved URI" do + current_location = URI("https://api.example.com/start") + full_location = subject.send(:resolve_redirect_location, current_location, "//attacker.example/leak?x=1#frag") + + expect(full_location.to_s).to eq("https://api.example.com///attacker.example/leak?x=1#frag") + end + + it "preserves userinfo and port in protocol-relative redirect authorities" do + client = described_class.new("abc", "def", site: "https://api.example.com") do |builder| + builder.adapter :test do |stub| + stub.get("/protocol_relative_redirect_with_authority") do |_env| + [302, {"Content-Type" => "text/plain", "location" => "//user:pass@attacker.example:8080/leak"}, ""] + end + stub.get("///user:pass@attacker.example:8080/leak") do |env| + [200, {}, JSON.dump(url: env[:url].to_s)] + end + end + end + + response = client.request(:get, "/protocol_relative_redirect_with_authority") + body = JSON.parse(response.body) + + expect(body["url"]).to eq("https://api.example.com///user:pass@attacker.example:8080/leak") + end + it "removes Authorization headers from cross-origin redirects" do response = subject.request(:get, "/absolute_cross_origin_redirect", headers: {"Authorization" => "Bearer secret", "X-Marker" => "kept"}) body = JSON.parse(response.body) @@ -567,6 +611,21 @@ expect(response.response.env.url.to_s).to eq("https://attacker.example/leak") end + it "preserves the header object type when sanitizing cross-origin redirects" do + headers = Faraday::Utils::Headers.new + headers["Authorization"] = "Bearer secret" + headers["X-Marker"] = "kept" + current_location = URI("https://api.example.com/start") + next_location = URI("https://attacker.example/leak") + + safe_opts = subject.send(:sanitize_redirect_options, {headers: headers}, current_location, next_location) + + expect(safe_opts[:headers]).to be_a(Faraday::Utils::Headers) + expect(safe_opts[:headers]["Authorization"]).to be_nil + expect(safe_opts[:headers]["X-Marker"]).to eq("kept") + expect(headers["Authorization"]).to eq("Bearer secret") + end + it "follows cross-origin redirects when there are no credential headers to remove" do response = subject.request(:get, "/absolute_cross_origin_redirect") body = JSON.parse(response.body) @@ -615,6 +674,12 @@ subject.options[:max_redirects] = max_redirects end + it "tolerates nil redirect counts" do + response = subject.request(:get, "/redirect", redirect_count: nil) + expect(response.status).to eq(200) + expect(response.response.env.url.to_s).to eq("https://api.example.com/success") + end + it "returns if raise_errors is false" do subject.options[:raise_errors] = false response = subject.request(:get, "/unauthorized") @@ -1140,7 +1205,7 @@ let(:body) { "BLOOP" } it "raises error" do - block_is_expected { get_token }.to raise_error(JSON::ParserError, /unexpected.*'BLOOP'/) + block_is_expected { get_token }.to raise_error(JSON::ParserError) end context "when extract_access_token raises an exception" do @@ -1292,7 +1357,7 @@ def contains_token?(hash) before do custom_class = Class.new do - def initialize(client, hash) + def initialize(_client, _hash) end class << self