omniauth-jwt2 0.1.0 → 1.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- checksums.yaml.gz.sig +0 -0
- data/CHANGELOG.md +81 -0
- data/CITATION.cff +20 -0
- data/CODE_OF_CONDUCT.md +134 -0
- data/CONTRIBUTING.md +272 -0
- data/FUNDING.md +74 -0
- data/LICENSE.md +16 -0
- data/README.md +499 -58
- data/RUBOCOP.md +71 -0
- data/SECURITY.md +21 -0
- data/certs/pboling.pem +27 -0
- data/lib/omniauth/jwt/version.rb +6 -3
- data/lib/omniauth/jwt.rb +2 -1
- data/lib/omniauth/jwt2/version.rb +10 -0
- data/lib/omniauth/jwt2.rb +10 -0
- data/lib/omniauth/strategies/jwt.rb +31 -9
- data/lib/omniauth-jwt2.rb +3 -0
- data/sig/omniauth/jwt/version.rbs +8 -0
- data/sig/omniauth/jwt2/version.rbs +8 -0
- data.tar.gz.sig +1 -0
- metadata +269 -61
- metadata.gz.sig +0 -0
- data/.github/FUNDING.yml +0 -11
- data/.github/dependabot.yml +0 -2
- data/.github/workflows/ancient.yml +0 -53
- data/.github/workflows/ci.yml +0 -59
- data/.github/workflows/coverage.yml +0 -91
- data/.github/workflows/legacy.yml +0 -54
- data/.github/workflows/style.yml +0 -43
- data/.gitignore +0 -18
- data/.rspec +0 -2
- data/.rubocop.yml +0 -2
- data/.rubocop_gradual.lock +0 -39
- data/.simplecov +0 -2
- data/.tool-versions +0 -1
- data/Gemfile +0 -17
- data/Guardfile +0 -8
- data/LICENSE.txt +0 -23
- data/Rakefile +0 -23
- data/gemfiles/ancient.gemfile +0 -20
- data/gemfiles/contexts/coverage.gemfile +0 -2
- data/gemfiles/contexts/debug.gemfile +0 -6
- data/gemfiles/contexts/style.gemfile +0 -5
- data/gemfiles/contexts/testing.gemfile +0 -8
- data/gemfiles/coverage.gemfile +0 -20
- data/gemfiles/legacy.gemfile +0 -26
- data/gemfiles/style.gemfile +0 -20
- data/gemfiles/vanilla.gemfile +0 -20
- data/omniauth-jwt2.gemspec +0 -41
- data/spec/lib/omniauth/strategies/jwt_spec.rb +0 -213
- data/spec/spec_helper.rb +0 -64
- data/spec/support/hash.rb +0 -9
- data/spec/support/next_instance_of.rb +0 -43
data/.github/workflows/style.yml
DELETED
|
@@ -1,43 +0,0 @@
|
|
|
1
|
-
name: Code Style
|
|
2
|
-
|
|
3
|
-
on:
|
|
4
|
-
push:
|
|
5
|
-
branches:
|
|
6
|
-
- 'main'
|
|
7
|
-
tags:
|
|
8
|
-
- '!*' # Do not execute on tags
|
|
9
|
-
pull_request:
|
|
10
|
-
branches:
|
|
11
|
-
- '*'
|
|
12
|
-
|
|
13
|
-
jobs:
|
|
14
|
-
rubocop:
|
|
15
|
-
name: RuboCop
|
|
16
|
-
strategy:
|
|
17
|
-
fail-fast: false
|
|
18
|
-
matrix:
|
|
19
|
-
experimental: [false]
|
|
20
|
-
rubygems:
|
|
21
|
-
- latest
|
|
22
|
-
bundler:
|
|
23
|
-
- latest
|
|
24
|
-
gemfile:
|
|
25
|
-
- style
|
|
26
|
-
ruby:
|
|
27
|
-
- "3.2"
|
|
28
|
-
|
|
29
|
-
runs-on: ubuntu-latest
|
|
30
|
-
env: # $BUNDLE_GEMFILE must be set at the job level, so it is set for all steps
|
|
31
|
-
BUNDLE_GEMFILE: ${{ github.workspace }}/gemfiles/${{ matrix.gemfile }}.gemfile
|
|
32
|
-
steps:
|
|
33
|
-
- name: Checkout
|
|
34
|
-
uses: actions/checkout@v4
|
|
35
|
-
- name: Setup Ruby & Bundle
|
|
36
|
-
uses: ruby/setup-ruby@v1
|
|
37
|
-
with:
|
|
38
|
-
ruby-version: ${{ matrix.ruby }}
|
|
39
|
-
rubygems: ${{ matrix.rubygems }}
|
|
40
|
-
bundler: ${{ matrix.bundler }}
|
|
41
|
-
bundler-cache: true
|
|
42
|
-
- name: Run RuboCop Gradual
|
|
43
|
-
run: bundle exec rake rubocop_gradual:check
|
data/.gitignore
DELETED
data/.rspec
DELETED
data/.rubocop.yml
DELETED
data/.rubocop_gradual.lock
DELETED
|
@@ -1,39 +0,0 @@
|
|
|
1
|
-
{
|
|
2
|
-
"lib/omniauth/strategies/jwt.rb:543932255": [
|
|
3
|
-
[60, 9, 76, "Lint/RescueException: Avoid rescuing the `Exception` class. Perhaps you meant to rescue `StandardError`?", 967033479]
|
|
4
|
-
],
|
|
5
|
-
"omniauth-jwt2.gemspec:998952283": [
|
|
6
|
-
[18, 16, 16, "Packaging/GemspecGit: Avoid using git to produce lists of files. Downstreams often need to build your package in an environment that does not have git (on purpose). Use some pure Ruby alternative, like `Dir` or `Dir.glob`.", 1973161220]
|
|
7
|
-
],
|
|
8
|
-
"spec/lib/omniauth/strategies/jwt_spec.rb:2698313308": [
|
|
9
|
-
[3, 1, 34, "RSpec/FilePath: Spec path should end with `omni_auth/strategies/jwt*_spec.rb`.", 1935033905],
|
|
10
|
-
[3, 1, 34, "RSpec/SpecFilePathFormat: Spec path should end with `omni_auth/strategies/jwt*_spec.rb`.", 1935033905],
|
|
11
|
-
[12, 13, 25, "RSpec/DescribedClass: Use `described_class` instead of `OmniAuth::Strategies::JWT`.", 2234488924],
|
|
12
|
-
[19, 11, 15, "RSpec/ContextWording: Context description should match /^when\\b/, /^with\\b/, or /^without\\b/.", 391893083],
|
|
13
|
-
[20, 5, 42, "RSpec/MultipleExpectations: Example has too many expectations [2/1].", 4106660663],
|
|
14
|
-
[29, 11, 16, "RSpec/ContextWording: Context description should match /^when\\b/, /^with\\b/, or /^without\\b/.", 1409468707],
|
|
15
|
-
[51, 7, 51, "RSpec/MultipleExpectations: Example has too many expectations [2/1].", 4149552871],
|
|
16
|
-
[51, 7, 531, "RSpec/ExampleLength: Example has too many lines. [6/5]", 2143440997],
|
|
17
|
-
[91, 3, 3512, "RSpec/MultipleMemoizedHelpers: Example group has too many memoized helpers [10/5]", 2363831099],
|
|
18
|
-
[110, 7, 7, "RSpec/NamedSubject: Name your test subject if you need to reference it explicitly.", 1892732441],
|
|
19
|
-
[111, 7, 7, "RSpec/NamedSubject: Name your test subject if you need to reference it explicitly.", 1892732441],
|
|
20
|
-
[116, 9, 6, "RSpec/ExpectInHook: Do not use `expect` in `before` hook", 1179768986],
|
|
21
|
-
[116, 9, 20, "RSpec/StubbedMock: Prefer `allow` over `expect` when configuring a response.", 2951559342],
|
|
22
|
-
[116, 33, 7, "RSpec/MessageSpies: Prefer `have_received` for setting message expectations. Setup `rack_request` as a spy using `allow` or `instance_spy`.", 1384559950],
|
|
23
|
-
[130, 5, 56, "Performance/RedundantMerge: Use `algos[OpenSSL::PKey::EC] = %w[ES256 ES384 ES512]` instead of `algos.merge!(OpenSSL::PKey::EC => %w[ES256 ES384 ES512])`.", 2983772293],
|
|
24
|
-
[133, 9, 846, "RSpec/MultipleMemoizedHelpers: Example group has too many memoized helpers [10/5]", 3520352246],
|
|
25
|
-
[152, 22, 7, "RSpec/NamedSubject: Name your test subject if you need to reference it explicitly.", 1892732441],
|
|
26
|
-
[160, 5, 310, "RSpec/MultipleMemoizedHelpers: Example group has too many memoized helpers [10/5]", 3501674141],
|
|
27
|
-
[160, 13, 28, "RSpec/ContextWording: Context description should match /^when\\b/, /^with\\b/, or /^without\\b/.", 1877551307],
|
|
28
|
-
[170, 18, 7, "RSpec/NamedSubject: Name your test subject if you need to reference it explicitly.", 1892732441],
|
|
29
|
-
[174, 5, 515, "RSpec/MultipleMemoizedHelpers: Example group has too many memoized helpers [10/5]", 1246671601],
|
|
30
|
-
[185, 9, 7, "RSpec/NamedSubject: Name your test subject if you need to reference it explicitly.", 1892732441],
|
|
31
|
-
[189, 18, 7, "RSpec/NamedSubject: Name your test subject if you need to reference it explicitly.", 1892732441],
|
|
32
|
-
[193, 5, 537, "RSpec/MultipleMemoizedHelpers: Example group has too many memoized helpers [10/5]", 3770030886],
|
|
33
|
-
[205, 9, 7, "RSpec/NamedSubject: Name your test subject if you need to reference it explicitly.", 1892732441],
|
|
34
|
-
[209, 18, 7, "RSpec/NamedSubject: Name your test subject if you need to reference it explicitly.", 1892732441]
|
|
35
|
-
],
|
|
36
|
-
"spec/support/hash.rb:812296649": [
|
|
37
|
-
[2, 3, 110, "Style/ClassMethodsDefinitions: Use `class << self` to define a class method.", 3570181400]
|
|
38
|
-
]
|
|
39
|
-
}
|
data/.simplecov
DELETED
data/.tool-versions
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
ruby 2.3.8
|
data/Gemfile
DELETED
|
@@ -1,17 +0,0 @@
|
|
|
1
|
-
source "https://rubygems.org"
|
|
2
|
-
|
|
3
|
-
# Specify your gem's dependencies in omniauth-jwt.gemspec
|
|
4
|
-
gemspec
|
|
5
|
-
|
|
6
|
-
# Development dependencies that rely on Ruby version >=
|
|
7
|
-
# Style
|
|
8
|
-
eval_gemfile "gemfiles/contexts/style.gemfile"
|
|
9
|
-
|
|
10
|
-
# Coverage
|
|
11
|
-
eval_gemfile "gemfiles/contexts/coverage.gemfile"
|
|
12
|
-
|
|
13
|
-
# Testing
|
|
14
|
-
eval_gemfile "gemfiles/contexts/testing.gemfile"
|
|
15
|
-
|
|
16
|
-
# Debug
|
|
17
|
-
eval_gemfile "gemfiles/contexts/debug.gemfile"
|
data/Guardfile
DELETED
data/LICENSE.txt
DELETED
|
@@ -1,23 +0,0 @@
|
|
|
1
|
-
Copyright (c) 2013 Michael Bleigh
|
|
2
|
-
Copyright (c) 2023 Peter Boling of railsbling.com
|
|
3
|
-
|
|
4
|
-
MIT License
|
|
5
|
-
|
|
6
|
-
Permission is hereby granted, free of charge, to any person obtaining
|
|
7
|
-
a copy of this software and associated documentation files (the
|
|
8
|
-
"Software"), to deal in the Software without restriction, including
|
|
9
|
-
without limitation the rights to use, copy, modify, merge, publish,
|
|
10
|
-
distribute, sublicense, and/or sell copies of the Software, and to
|
|
11
|
-
permit persons to whom the Software is furnished to do so, subject to
|
|
12
|
-
the following conditions:
|
|
13
|
-
|
|
14
|
-
The above copyright notice and this permission notice shall be
|
|
15
|
-
included in all copies or substantial portions of the Software.
|
|
16
|
-
|
|
17
|
-
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
|
18
|
-
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
|
19
|
-
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
|
20
|
-
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
|
21
|
-
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
|
22
|
-
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
|
23
|
-
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
data/Rakefile
DELETED
|
@@ -1,23 +0,0 @@
|
|
|
1
|
-
require "bundler/gem_tasks"
|
|
2
|
-
|
|
3
|
-
require "rspec/core/rake_task"
|
|
4
|
-
RSpec::Core::RakeTask.new(:spec)
|
|
5
|
-
|
|
6
|
-
desc "alias test task to spec"
|
|
7
|
-
task test: :spec
|
|
8
|
-
|
|
9
|
-
begin
|
|
10
|
-
require "kettle-soup-cover"
|
|
11
|
-
Kettle::Soup::Cover.install_tasks
|
|
12
|
-
rescue LoadError
|
|
13
|
-
# NOOP
|
|
14
|
-
end
|
|
15
|
-
|
|
16
|
-
begin
|
|
17
|
-
require "rubocop/lts"
|
|
18
|
-
Rubocop::Lts.install_tasks
|
|
19
|
-
rescue LoadError
|
|
20
|
-
# NOOP
|
|
21
|
-
end
|
|
22
|
-
|
|
23
|
-
task default: :spec
|
data/gemfiles/ancient.gemfile
DELETED
|
@@ -1,20 +0,0 @@
|
|
|
1
|
-
# frozen_string_literal: true
|
|
2
|
-
|
|
3
|
-
git_source(:github) { |repo_name| "https://github.com/#{repo_name}" }
|
|
4
|
-
|
|
5
|
-
source "https://rubygems.org"
|
|
6
|
-
|
|
7
|
-
# Gemfile is only for local development.
|
|
8
|
-
# On CI we only need the gemspecs' dependencies (including development dependencies).
|
|
9
|
-
# Exceptions, if any, will be found in gemfiles/*
|
|
10
|
-
|
|
11
|
-
# Testing
|
|
12
|
-
gem "rack", "~> 2.1.4.3" # ruby 2.2.2
|
|
13
|
-
gem "json", "~> 2.5.1" # ruby 2.0
|
|
14
|
-
|
|
15
|
-
# Debugging
|
|
16
|
-
eval_gemfile "contexts/debug.gemfile"
|
|
17
|
-
|
|
18
|
-
gemspec path: "../"
|
|
19
|
-
|
|
20
|
-
gem "omniauth", "< 2"
|
|
@@ -1,8 +0,0 @@
|
|
|
1
|
-
# Testing
|
|
2
|
-
gem "ed25519", "~> 1.3" # ruby 2.4
|
|
3
|
-
gem "json", "~> 2.6", ">= 2.6.3" # ruby 2.3
|
|
4
|
-
gem "openssl", ">= 2.0" # ruby 2.3, v3.0 is >= 2.6, v3.2 is >= 2.7
|
|
5
|
-
gem "openssl-signature_algorithm", "~> 1.3" # ruby 2.4
|
|
6
|
-
gem "rack", "~> 3.0", ">= 3.0.8" # ruby 2.4
|
|
7
|
-
gem "rack-session", "~> 2.0" # ruby 2.4
|
|
8
|
-
gem "rspec-block_is_expected", "~> 1.0", ">= 1.0.5" # ruby 1.8.7
|
data/gemfiles/coverage.gemfile
DELETED
|
@@ -1,20 +0,0 @@
|
|
|
1
|
-
# frozen_string_literal: true
|
|
2
|
-
|
|
3
|
-
git_source(:github) { |repo_name| "https://github.com/#{repo_name}" }
|
|
4
|
-
|
|
5
|
-
source "https://rubygems.org"
|
|
6
|
-
|
|
7
|
-
# Gemfile is only for local development.
|
|
8
|
-
# On CI we only need the gemspecs' dependencies (including development dependencies).
|
|
9
|
-
# Exceptions, if any, will be found in gemfiles/*
|
|
10
|
-
|
|
11
|
-
# Coverage
|
|
12
|
-
eval_gemfile "contexts/coverage.gemfile"
|
|
13
|
-
|
|
14
|
-
# Testing
|
|
15
|
-
eval_gemfile "contexts/testing.gemfile"
|
|
16
|
-
|
|
17
|
-
# Debugging
|
|
18
|
-
eval_gemfile "contexts/debug.gemfile"
|
|
19
|
-
|
|
20
|
-
gemspec path: "../"
|
data/gemfiles/legacy.gemfile
DELETED
|
@@ -1,26 +0,0 @@
|
|
|
1
|
-
# frozen_string_literal: true
|
|
2
|
-
|
|
3
|
-
git_source(:github) { |repo_name| "https://github.com/#{repo_name}" }
|
|
4
|
-
|
|
5
|
-
source "https://rubygems.org"
|
|
6
|
-
|
|
7
|
-
# Gemfile is only for local development.
|
|
8
|
-
# On CI we only need the gemspecs' dependencies (including development dependencies).
|
|
9
|
-
# Exceptions, if any, will be found in gemfiles/*
|
|
10
|
-
|
|
11
|
-
# Testing
|
|
12
|
-
gem "rspec", "~> 3.12" # ruby *
|
|
13
|
-
gem "rack-test", "~> 2.1" # ruby 2.0
|
|
14
|
-
gem "rack" # ruby 2.4
|
|
15
|
-
gem "rack-session", "< 2", github: "pboling/rack-session", branch: "fix-missing-rack-session" # ruby < 2.4
|
|
16
|
-
gem "json" # ruby 2.3
|
|
17
|
-
gem "openssl" # ruby 2.3
|
|
18
|
-
gem "openssl-signature_algorithm" # ruby 2.4
|
|
19
|
-
gem "ed25519" # ruby 2.4
|
|
20
|
-
|
|
21
|
-
# Debugging
|
|
22
|
-
eval_gemfile "contexts/debug.gemfile"
|
|
23
|
-
|
|
24
|
-
gemspec path: "../"
|
|
25
|
-
|
|
26
|
-
gem "omniauth", "< 2"
|
data/gemfiles/style.gemfile
DELETED
|
@@ -1,20 +0,0 @@
|
|
|
1
|
-
# frozen_string_literal: true
|
|
2
|
-
|
|
3
|
-
git_source(:github) { |repo_name| "https://github.com/#{repo_name}" }
|
|
4
|
-
|
|
5
|
-
source "https://rubygems.org"
|
|
6
|
-
|
|
7
|
-
# Gemfile is only for local development.
|
|
8
|
-
# On CI we only need the gemspecs' dependencies (including development dependencies).
|
|
9
|
-
# Exceptions, if any, will be found in gemfiles/*
|
|
10
|
-
|
|
11
|
-
# Coverage
|
|
12
|
-
eval_gemfile "contexts/coverage.gemfile"
|
|
13
|
-
|
|
14
|
-
# Style
|
|
15
|
-
eval_gemfile "contexts/style.gemfile"
|
|
16
|
-
|
|
17
|
-
# Debugging
|
|
18
|
-
eval_gemfile "contexts/debug.gemfile"
|
|
19
|
-
|
|
20
|
-
gemspec path: "../"
|
data/gemfiles/vanilla.gemfile
DELETED
|
@@ -1,20 +0,0 @@
|
|
|
1
|
-
# frozen_string_literal: true
|
|
2
|
-
|
|
3
|
-
git_source(:github) { |repo_name| "https://github.com/#{repo_name}" }
|
|
4
|
-
|
|
5
|
-
source "https://rubygems.org"
|
|
6
|
-
|
|
7
|
-
# Gemfile is only for local development.
|
|
8
|
-
# On CI we only need the gemspecs' dependencies (including development dependencies).
|
|
9
|
-
# Exceptions, if any, will be found in gemfiles/*
|
|
10
|
-
|
|
11
|
-
# Coverage
|
|
12
|
-
eval_gemfile "contexts/coverage.gemfile"
|
|
13
|
-
|
|
14
|
-
# Testing
|
|
15
|
-
eval_gemfile "contexts/testing.gemfile"
|
|
16
|
-
|
|
17
|
-
# Debugging
|
|
18
|
-
eval_gemfile "contexts/debug.gemfile"
|
|
19
|
-
|
|
20
|
-
gemspec path: "../"
|
data/omniauth-jwt2.gemspec
DELETED
|
@@ -1,41 +0,0 @@
|
|
|
1
|
-
# Get the GEMFILE_VERSION without *require* "my_gem/version", for code coverage accuracy
|
|
2
|
-
# See: https://github.com/simplecov-ruby/simplecov/issues/557#issuecomment-825171399
|
|
3
|
-
load "lib/omniauth/jwt/version.rb"
|
|
4
|
-
gem_version = Omniauth::JWT::Version::VERSION
|
|
5
|
-
Omniauth::JWT::Version.send(:remove_const, :VERSION)
|
|
6
|
-
|
|
7
|
-
Gem::Specification.new do |spec|
|
|
8
|
-
spec.name = "omniauth-jwt2"
|
|
9
|
-
spec.version = gem_version
|
|
10
|
-
spec.authors = ["Michael Bleigh", "Robin Ward", "Peter Boling"]
|
|
11
|
-
spec.email = ["mbleigh@mbleigh.com", "robin.ward@gmail.com", "peter.boling@gmail.com"]
|
|
12
|
-
spec.description = "An OmniAuth strategy to accept JWT-based single sign-on."
|
|
13
|
-
spec.summary = "An OmniAuth strategy to accept JWT-based single sign-on."
|
|
14
|
-
spec.homepage = "http://github.com/pboling/omniauth-jwt2"
|
|
15
|
-
spec.license = "MIT"
|
|
16
|
-
spec.required_ruby_version = ">= 2.2"
|
|
17
|
-
|
|
18
|
-
spec.files = %x(git ls-files).split($/)
|
|
19
|
-
spec.executables = spec.files.grep(%r{^bin/}) { |f| File.basename(f) }
|
|
20
|
-
spec.require_paths = ["lib"]
|
|
21
|
-
|
|
22
|
-
# TODO: Since this gem supports Ruby >= 2.2 we need to ensure no gems are
|
|
23
|
-
# added here that require a newer version. Once this gem progresses to
|
|
24
|
-
# only support non-EOL Rubies, all dependencies can be listed in this
|
|
25
|
-
# gemspec, and the gemfiles/* pattern can be dispensed with.
|
|
26
|
-
spec.add_dependency("jwt", "~> 2.2", ">= 2.2.1") # ruby 2.1
|
|
27
|
-
spec.add_dependency("omniauth", ">= 1.1") # ruby 2.2
|
|
28
|
-
|
|
29
|
-
# Utilities
|
|
30
|
-
spec.add_dependency("version_gem", "~> 1.1", ">= 1.1.3") # ruby 2.2
|
|
31
|
-
spec.add_development_dependency("rake", "~> 13.0") # ruby 2.2, v13.1 is >= 2.3
|
|
32
|
-
|
|
33
|
-
# Hot reload
|
|
34
|
-
spec.add_development_dependency("guard", "~> 2.18", ">= 2.18.1") # ruby 1.9.3
|
|
35
|
-
spec.add_development_dependency("guard-rspec", "~> 4.7", ">= 4.7.3") # ruby *
|
|
36
|
-
|
|
37
|
-
# Testing
|
|
38
|
-
spec.add_development_dependency("rack-test", "~> 2.1") # ruby 2.0
|
|
39
|
-
spec.add_development_dependency("rspec", "~> 3.12") # ruby *
|
|
40
|
-
spec.add_development_dependency("rspec-pending_for", "~> 0.1") # ruby *
|
|
41
|
-
end
|
|
@@ -1,213 +0,0 @@
|
|
|
1
|
-
require "spec_helper"
|
|
2
|
-
|
|
3
|
-
describe OmniAuth::Strategies::JWT do
|
|
4
|
-
let(:response_json) { JSON.parse(last_response.body) }
|
|
5
|
-
let(:rand_secret) { SecureRandom.hex(10) }
|
|
6
|
-
let(:args) { [rand_secret, {auth_url: "http://example.com/login"}] }
|
|
7
|
-
|
|
8
|
-
let(:app) {
|
|
9
|
-
the_args = args
|
|
10
|
-
Rack::Builder.new do |b|
|
|
11
|
-
b.use Rack::Session::Cookie, secret: SecureRandom.hex(32)
|
|
12
|
-
b.use OmniAuth::Strategies::JWT, *the_args
|
|
13
|
-
b.run lambda { |env|
|
|
14
|
-
[200, {}, [(env["omniauth.auth"] || {}).to_json]]
|
|
15
|
-
}
|
|
16
|
-
end
|
|
17
|
-
}
|
|
18
|
-
|
|
19
|
-
context "request phase" do
|
|
20
|
-
it "redirects to the configured login url" do
|
|
21
|
-
# TODO: Figure out how to write this test without using the deprecated
|
|
22
|
-
# and unsafe, "get" method for the request phase.
|
|
23
|
-
get "/auth/jwt"
|
|
24
|
-
expect(last_response.status).to eq(302)
|
|
25
|
-
expect(last_response.headers["Location"]).to eq("http://example.com/login")
|
|
26
|
-
end
|
|
27
|
-
end
|
|
28
|
-
|
|
29
|
-
context "callback phase" do
|
|
30
|
-
it "decodes the response" do
|
|
31
|
-
encoded = JWT.encode({name: "Bob", email: "steve@example.com"}, rand_secret)
|
|
32
|
-
get "/auth/jwt/callback?jwt=" + encoded
|
|
33
|
-
expect(response_json["info"]["email"]).to eq("steve@example.com")
|
|
34
|
-
end
|
|
35
|
-
|
|
36
|
-
it "does not work without required fields" do
|
|
37
|
-
encoded = JWT.encode({name: "Steve"}, rand_secret)
|
|
38
|
-
get "/auth/jwt/callback?jwt=" + encoded
|
|
39
|
-
expect(last_response.status).to eq(302)
|
|
40
|
-
end
|
|
41
|
-
|
|
42
|
-
it "assigns the uid" do
|
|
43
|
-
encoded = JWT.encode({name: "Steve", email: "dude@awesome.com"}, rand_secret)
|
|
44
|
-
get "/auth/jwt/callback?jwt=" + encoded
|
|
45
|
-
expect(response_json["uid"]).to eq("dude@awesome.com")
|
|
46
|
-
end
|
|
47
|
-
|
|
48
|
-
context "with a non-default encoding algorithm" do
|
|
49
|
-
let(:args) { [rand_secret, {auth_url: "http://example.com/login", decode_options: {algorithms: ["HS512", "HS256"]}}] }
|
|
50
|
-
|
|
51
|
-
it "decodes the response with an allowed algorithm" do
|
|
52
|
-
encoded = JWT.encode({name: "Bob", email: "steve@example.com"}, rand_secret, "HS512")
|
|
53
|
-
get "/auth/jwt/callback?jwt=" + encoded
|
|
54
|
-
expect(JSON.parse(last_response.body)["info"]["email"]).to eq("steve@example.com")
|
|
55
|
-
|
|
56
|
-
encoded = JWT.encode({name: "Bob", email: "steve@example.com"}, rand_secret, "HS256")
|
|
57
|
-
get "/auth/jwt/callback?jwt=" + encoded
|
|
58
|
-
expect(JSON.parse(last_response.body)["info"]["email"]).to eq("steve@example.com")
|
|
59
|
-
end
|
|
60
|
-
|
|
61
|
-
it "fails decoding the response with a different algorithm" do
|
|
62
|
-
encoded = JWT.encode({name: "Bob", email: "steve@example.com"}, rand_secret, "HS384")
|
|
63
|
-
get "/auth/jwt/callback?jwt=" + encoded
|
|
64
|
-
expect(last_response.headers["Location"]).to include("/auth/failure")
|
|
65
|
-
end
|
|
66
|
-
end
|
|
67
|
-
|
|
68
|
-
context "with a :valid_within option set" do
|
|
69
|
-
let(:args) { [rand_secret, {auth_url: "http://example.com/login", valid_within: 300}] }
|
|
70
|
-
|
|
71
|
-
it "works if the iat key is within the time window" do
|
|
72
|
-
encoded = JWT.encode({name: "Ted", email: "ted@example.com", iat: Time.now.to_i}, rand_secret)
|
|
73
|
-
get "/auth/jwt/callback?jwt=" + encoded
|
|
74
|
-
expect(last_response.status).to eq(200)
|
|
75
|
-
end
|
|
76
|
-
|
|
77
|
-
it "does not work if the iat key is outside the time window" do
|
|
78
|
-
encoded = JWT.encode({name: "Ted", email: "ted@example.com", iat: Time.now.to_i + 500}, rand_secret)
|
|
79
|
-
get "/auth/jwt/callback?jwt=" + encoded
|
|
80
|
-
expect(last_response.status).to eq(302)
|
|
81
|
-
end
|
|
82
|
-
|
|
83
|
-
it "does not work if the iat key is missing" do
|
|
84
|
-
encoded = JWT.encode({name: "Ted", email: "ted@example.com"}, rand_secret)
|
|
85
|
-
get "/auth/jwt/callback?jwt=" + encoded
|
|
86
|
-
expect(last_response.status).to eq(302)
|
|
87
|
-
end
|
|
88
|
-
end
|
|
89
|
-
end
|
|
90
|
-
|
|
91
|
-
describe "#decoded" do
|
|
92
|
-
subject { described_class.new({}) }
|
|
93
|
-
|
|
94
|
-
let(:timestamp) { Time.now.to_i }
|
|
95
|
-
let(:claims) do
|
|
96
|
-
{
|
|
97
|
-
id: 123,
|
|
98
|
-
name: "user_example",
|
|
99
|
-
email: "user@example.com",
|
|
100
|
-
iat: timestamp,
|
|
101
|
-
}
|
|
102
|
-
end
|
|
103
|
-
|
|
104
|
-
let(:algorithm) { "HS256" }
|
|
105
|
-
let(:secret) { rand_secret }
|
|
106
|
-
let(:private_key) { secret }
|
|
107
|
-
let(:payload) { JWT.encode(claims, private_key, algorithm) }
|
|
108
|
-
|
|
109
|
-
before do
|
|
110
|
-
subject.options[:secret] = secret
|
|
111
|
-
subject.options[:algorithm] = algorithm
|
|
112
|
-
|
|
113
|
-
# We use Rack::Request instead of ActionDispatch::Request because
|
|
114
|
-
# Rack::Test::Methods enables testing of this module.
|
|
115
|
-
expect_next_instance_of(Rack::Request) do |rack_request|
|
|
116
|
-
expect(rack_request).to receive(:params).and_return("jwt" => payload)
|
|
117
|
-
end
|
|
118
|
-
end
|
|
119
|
-
|
|
120
|
-
ecdsa_named_curves = {
|
|
121
|
-
"ES256" => "prime256v1",
|
|
122
|
-
"ES384" => "secp384r1",
|
|
123
|
-
"ES512" => "secp521r1",
|
|
124
|
-
}.freeze
|
|
125
|
-
|
|
126
|
-
algos = {
|
|
127
|
-
OpenSSL::PKey::RSA => %w[RS256 RS384 RS512],
|
|
128
|
-
String => %w[HS256 HS384 HS512],
|
|
129
|
-
}
|
|
130
|
-
algos.merge!(OpenSSL::PKey::EC => %w[ES256 ES384 ES512]) unless ["2.2.10", "2.3.8"].include?(RubyVersion.to_s)
|
|
131
|
-
algos.each do |private_key_class, algorithms|
|
|
132
|
-
algorithms.each do |algorithm|
|
|
133
|
-
context "when the #{algorithm} algorithm is used" do
|
|
134
|
-
let(:algorithm) { algorithm }
|
|
135
|
-
let(:secret) do
|
|
136
|
-
# rubocop:disable Style/CaseLikeIf
|
|
137
|
-
if private_key_class == OpenSSL::PKey::RSA
|
|
138
|
-
private_key_class.generate(2048)
|
|
139
|
-
.to_pem
|
|
140
|
-
elsif private_key_class == OpenSSL::PKey::EC
|
|
141
|
-
private_key_class.generate(ecdsa_named_curves[algorithm])
|
|
142
|
-
.to_pem
|
|
143
|
-
else
|
|
144
|
-
private_key_class.new(rand_secret)
|
|
145
|
-
end
|
|
146
|
-
# rubocop:enable Style/CaseLikeIf
|
|
147
|
-
end
|
|
148
|
-
|
|
149
|
-
let(:private_key) { private_key_class ? private_key_class.new(secret) : secret }
|
|
150
|
-
|
|
151
|
-
it "decodes the user information" do
|
|
152
|
-
result = subject.decoded
|
|
153
|
-
|
|
154
|
-
expect(result).to eq(claims.stringify_keys)
|
|
155
|
-
end
|
|
156
|
-
end
|
|
157
|
-
end
|
|
158
|
-
end
|
|
159
|
-
|
|
160
|
-
context "required claims is missing" do
|
|
161
|
-
let(:claims) do
|
|
162
|
-
{
|
|
163
|
-
id: 123,
|
|
164
|
-
email: "user@example.com",
|
|
165
|
-
iat: timestamp,
|
|
166
|
-
}
|
|
167
|
-
end
|
|
168
|
-
|
|
169
|
-
it "raises error" do
|
|
170
|
-
expect { subject.decoded }.to raise_error(OmniAuth::Strategies::Jwt::ClaimInvalid)
|
|
171
|
-
end
|
|
172
|
-
end
|
|
173
|
-
|
|
174
|
-
context "when valid_within is specified but iat attribute is missing in response" do
|
|
175
|
-
let(:claims) do
|
|
176
|
-
{
|
|
177
|
-
id: 123,
|
|
178
|
-
name: "user_example",
|
|
179
|
-
email: "user@example.com",
|
|
180
|
-
}
|
|
181
|
-
end
|
|
182
|
-
|
|
183
|
-
before do
|
|
184
|
-
# Omniauth config values are always strings!
|
|
185
|
-
subject.options[:valid_within] = (60 * 60 * 24 * 2).to_s # 2 days
|
|
186
|
-
end
|
|
187
|
-
|
|
188
|
-
it "raises error" do
|
|
189
|
-
expect { subject.decoded }.to raise_error(OmniAuth::Strategies::Jwt::ClaimInvalid)
|
|
190
|
-
end
|
|
191
|
-
end
|
|
192
|
-
|
|
193
|
-
context "when timestamp claim is too skewed from present" do
|
|
194
|
-
let(:claims) do
|
|
195
|
-
{
|
|
196
|
-
id: 123,
|
|
197
|
-
name: "user_example",
|
|
198
|
-
email: "user@example.com",
|
|
199
|
-
iat: timestamp - (60 * 60 * 10), # minus ten minutes
|
|
200
|
-
}
|
|
201
|
-
end
|
|
202
|
-
|
|
203
|
-
before do
|
|
204
|
-
# Omniauth config values are always strings!
|
|
205
|
-
subject.options[:valid_within] = "2" # 2 seconds
|
|
206
|
-
end
|
|
207
|
-
|
|
208
|
-
it "raises error" do
|
|
209
|
-
expect { subject.decoded }.to raise_error(OmniAuth::Strategies::Jwt::ClaimInvalid)
|
|
210
|
-
end
|
|
211
|
-
end
|
|
212
|
-
end
|
|
213
|
-
end
|
data/spec/spec_helper.rb
DELETED
|
@@ -1,64 +0,0 @@
|
|
|
1
|
-
# Std Lib
|
|
2
|
-
require "securerandom"
|
|
3
|
-
|
|
4
|
-
# 3rd party gems
|
|
5
|
-
require "rspec/pending_for"
|
|
6
|
-
begin
|
|
7
|
-
require "rack/session"
|
|
8
|
-
rescue LoadError
|
|
9
|
-
nil # File won't exist in old rack for Ruby 2.2 & 2.3
|
|
10
|
-
end
|
|
11
|
-
require "rack/test"
|
|
12
|
-
require "json"
|
|
13
|
-
require "omniauth"
|
|
14
|
-
begin
|
|
15
|
-
require "openssl"
|
|
16
|
-
require "openssl/signature_algorithm"
|
|
17
|
-
require "ed25519"
|
|
18
|
-
rescue LoadError
|
|
19
|
-
nil # Gem doesn't exist for ancient Rubies 2.2 & 2.3
|
|
20
|
-
end
|
|
21
|
-
|
|
22
|
-
require "byebug" if ENV["DEBUG"] == "true"
|
|
23
|
-
# This does not require "simplecov",
|
|
24
|
-
# because that has a side-effect of running `.simplecov`
|
|
25
|
-
begin
|
|
26
|
-
require "kettle-soup-cover"
|
|
27
|
-
rescue LoadError
|
|
28
|
-
puts "Not analyzing test coverage"
|
|
29
|
-
end
|
|
30
|
-
|
|
31
|
-
require "support/hash"
|
|
32
|
-
require "support/next_instance_of"
|
|
33
|
-
|
|
34
|
-
OmniAuth.config.logger = Logger.new("/dev/null")
|
|
35
|
-
require "omniauth/version"
|
|
36
|
-
puts "OMNIAUTH VERSION: #{OmniAuth::VERSION}"
|
|
37
|
-
if Gem::Version.new(OmniAuth::VERSION) > Gem::Version.new("2.0")
|
|
38
|
-
OmniAuth.config.silence_get_warning = true
|
|
39
|
-
OmniAuth.config.allowed_request_methods |= [:get, :post]
|
|
40
|
-
end
|
|
41
|
-
# This file was generated by the `rspec --init` command. Conventionally, all
|
|
42
|
-
# specs live under a `spec` directory, which RSpec adds to the `$LOAD_PATH`.
|
|
43
|
-
# Require this file using `require "spec_helper"` to ensure that it is only
|
|
44
|
-
# loaded once.
|
|
45
|
-
#
|
|
46
|
-
# See http://rubydoc.info/gems/rspec-core/RSpec/Core/Configuration
|
|
47
|
-
RSpec.configure do |config|
|
|
48
|
-
config.run_all_when_everything_filtered = true
|
|
49
|
-
config.filter_run :focus
|
|
50
|
-
|
|
51
|
-
include Rack::Test::Methods
|
|
52
|
-
include NextInstanceOf
|
|
53
|
-
|
|
54
|
-
# Run specs in random order to surface order dependencies. If you find an
|
|
55
|
-
# order dependency and want to debug it, you can fix the order by providing
|
|
56
|
-
# the seed, which is printed after each run.
|
|
57
|
-
# --seed 1234
|
|
58
|
-
config.order = "random"
|
|
59
|
-
end
|
|
60
|
-
|
|
61
|
-
# Last thing before loading this library, load simplecov:
|
|
62
|
-
require "simplecov" if defined?(Kettle::Soup::Cover) && Kettle::Soup::Cover::DO_COV
|
|
63
|
-
|
|
64
|
-
require "omniauth/jwt"
|