omniauth_strong_auth_oidc 0.1.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.
Files changed (29) hide show
  1. checksums.yaml +7 -0
  2. data/.gitignore +34 -0
  3. data/.rspec +3 -0
  4. data/CHANGELOG.md +6 -0
  5. data/CONTRIBUTING.md +9 -0
  6. data/Gemfile +6 -0
  7. data/LICENSE +21 -0
  8. data/README.md +313 -0
  9. data/Rakefile +12 -0
  10. data/lib/generators/omniauth_strong_auth_oidc/install_generator.rb +73 -0
  11. data/lib/generators/omniauth_strong_auth_oidc/templates/relying_party_entity_statement_controller.rb.tt +61 -0
  12. data/lib/omniauth/strategies/strong_auth_oidc.rb +210 -0
  13. data/lib/omniauth_strong_auth_oidc/entity_statement.rb +22 -0
  14. data/lib/omniauth_strong_auth_oidc/entity_statement_fetcher/base.rb +37 -0
  15. data/lib/omniauth_strong_auth_oidc/entity_statement_fetcher/federation_url_fetcher.rb +29 -0
  16. data/lib/omniauth_strong_auth_oidc/entity_statement_fetcher/file_fetcher.rb +22 -0
  17. data/lib/omniauth_strong_auth_oidc/entity_statement_fetcher.rb +9 -0
  18. data/lib/omniauth_strong_auth_oidc/jwks_cache.rb +31 -0
  19. data/lib/omniauth_strong_auth_oidc/jwks_fetcher.rb +87 -0
  20. data/lib/omniauth_strong_auth_oidc/relying_party_entity_statement_generator.rb +77 -0
  21. data/lib/omniauth_strong_auth_oidc/relying_party_jwks_generator.rb +50 -0
  22. data/lib/omniauth_strong_auth_oidc/relying_party_jwks_storage/base.rb +101 -0
  23. data/lib/omniauth_strong_auth_oidc/relying_party_jwks_storage/cache_storage.rb +235 -0
  24. data/lib/omniauth_strong_auth_oidc/relying_party_jwks_storage/env_storage.rb +112 -0
  25. data/lib/omniauth_strong_auth_oidc/relying_party_jwks_storage.rb +10 -0
  26. data/lib/omniauth_strong_auth_oidc/version.rb +3 -0
  27. data/lib/omniauth_strong_auth_oidc.rb +15 -0
  28. data/omniauth_strong_auth_oidc.gemspec +32 -0
  29. metadata +494 -0
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA256:
3
+ metadata.gz: 19c27ecbd57d5babdc8c9914923c0242e23f153c74f5401f365d532619deee73
4
+ data.tar.gz: 4f8be4e8e78f707378f1b40c09cf8890db0bb314b9ad4c78e4869f5dac872b40
5
+ SHA512:
6
+ metadata.gz: 508bb03ae1ec63d48d724889d51120895adca15f32d4b696ea42bec2eea965c5f267266b57c42b0eedfbcb2dea64ae07ac646c1bc42e91a211a76a2b72574dfd
7
+ data.tar.gz: 9be502336071893f07dbe41e97c5780347999a2b3761fe05eb639e22e811c317dadf301e70805b1a50f3a201c0ca44f4847b5833a7b22d5bad365faa3728b89f
data/.gitignore ADDED
@@ -0,0 +1,34 @@
1
+ .bundle/
2
+ /pkg/
3
+ /vendor/
4
+ .DS_Store
5
+ /.yardoc
6
+ /.cache
7
+ /coverage/
8
+ /*.gem
9
+ /.env
10
+ /.env.*
11
+ /.idea/
12
+ /.vscode/
13
+ /.rubocop-*
14
+ node_modules/
15
+ spec/.result
16
+ *.gem
17
+ *.rbc
18
+ .bundle
19
+ .config
20
+ .yardoc
21
+ Gemfile.lock
22
+ InstalledFiles
23
+ _yardoc
24
+ coverage
25
+ doc/
26
+ lib/bundler/man
27
+ pkg
28
+ rdoc
29
+ spec/reports
30
+ test/tmp
31
+ test/version_tmp
32
+ tmp
33
+ *.swp
34
+ .rspec_status
data/.rspec ADDED
@@ -0,0 +1,3 @@
1
+ --require spec_helper
2
+ --color
3
+ --format documentation
data/CHANGELOG.md ADDED
@@ -0,0 +1,6 @@
1
+ # Changelog
2
+
3
+ All notable changes to this project will be documented in this file.
4
+
5
+ ## [0.1.0] - INITIAL
6
+ - Initial release
data/CONTRIBUTING.md ADDED
@@ -0,0 +1,9 @@
1
+ # Contributing
2
+
3
+ Thanks for your interest in contributing!
4
+
5
+ - Fork the repo
6
+ - Create a feature branch
7
+ - Open a PR with a clear description
8
+
9
+ Please run the test suite and follow existing style.
data/Gemfile ADDED
@@ -0,0 +1,6 @@
1
+ # frozen_string_literal: true
2
+
3
+ source "https://rubygems.org"
4
+
5
+ # Specify your gem's dependencies in omniauth_strong_auth_oidc.gemspec
6
+ gemspec
data/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2025 Kisko Labs
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
data/README.md ADDED
@@ -0,0 +1,313 @@
1
+ # OmniAuth Strong Auth OIDC
2
+
3
+ An OmniAuth strategy for implementing strong authentication with Finnish Identification Broker Services via OpenID Connect (OIDC).
4
+
5
+ ## Overview
6
+
7
+ This gem provides an OmniAuth strategy that implements the OpenID Connect Federation protocol for strong authentication with Finnish identification providers. It supports:
8
+
9
+ - **Private Key JWT authentication** for client authentication
10
+ - **JWE (JSON Web Encryption)** for encrypted ID tokens
11
+ - **Entity Statements** for federation metadata discovery
12
+ - **Key rotation** with multiple storage backends
13
+ - **Signed authorization requests** using JWT
14
+
15
+ ## Installation
16
+
17
+ Add this line to your application's Gemfile:
18
+
19
+ ```ruby
20
+ gem 'omniauth_strong_auth_oidc'
21
+ ```
22
+
23
+ And then execute:
24
+
25
+ ```bash
26
+ bundle install
27
+ ```
28
+
29
+ ## Configuration
30
+
31
+ ### Environment Variables
32
+
33
+ Configure the following environment variables:
34
+
35
+ ```bash
36
+ # Required
37
+ OIDC_CLIENT_ID=your_client_id
38
+ OIDC_ACR_VALUES="your_acr_value1 your_acr_value2"
39
+
40
+ # Optional - For production with static keys
41
+ OIDC_SIGNING_KEY_BASE64=base64_encoded_signing_key
42
+ OIDC_ENCRYPTION_KEY_BASE64=base64_encoded_encryption_key
43
+
44
+ # Optional - For key rotation
45
+ OIDC_KEY_ROTATION_ENABLED=true
46
+
47
+ # Optional - Federation metadata URL
48
+ OAUTH_ISSUER_URL=https://your-issuer-url.com
49
+ ```
50
+
51
+ ## Usage with Devise
52
+
53
+ ### Enable OmniAuth in User Model
54
+
55
+ Add the OmniAuth provider to your User model:
56
+
57
+ ```ruby
58
+ class User < ApplicationRecord
59
+ devise :database_authenticatable, :registerable,
60
+ :recoverable, :rememberable, :validatable,
61
+ :omniauthable, omniauth_providers: [:strong_auth_oidc]
62
+ end
63
+ ```
64
+
65
+ ### Add Required Fields to User
66
+
67
+ Generate a migration to add OmniAuth fields:
68
+
69
+ ```bash
70
+ rails generate migration AddOmniauthToUsers provider:string uid:string identity_number:string
71
+ rails db:migrate
72
+ ```
73
+
74
+ ### Configure Devise Initializer
75
+
76
+ In `config/initializers/devise.rb`, configure the OmniAuth provider:
77
+
78
+ ```ruby
79
+ Devise.setup do |config|
80
+ # ... other Devise configuration ...
81
+
82
+ # Configure entity statement fetcher
83
+ provider_entity_statement_fetcher = OmniauthStrongAuthOidc::EntityStatementFetcher::FileFetcher.new(
84
+ path_to_file: Rails.root.join("config", "oidc_test_entity_statement").to_s
85
+ )
86
+
87
+ if ENV["OAUTH_ISSUER_URL"].present?
88
+ provider_entity_statement_fetcher = OmniauthStrongAuthOidc::EntityStatementFetcher::FederationUrlFetcher.new(
89
+ issuer_url: ENV.fetch("OAUTH_ISSUER_URL")
90
+ )
91
+ end
92
+
93
+ # Configure JWKS storage
94
+ if ENV['OIDC_SIGNING_KEY_BASE64'].present? && ENV['OIDC_ENCRYPTION_KEY_BASE64'].present?
95
+ relying_party_jwks_storage = OmniauthStrongAuthOidc::RelyingPartyJwksStorage::EnvStorage.new
96
+ elsif ENV['OIDC_KEY_ROTATION_ENABLED'] == 'true'
97
+ cache_store = Rails.cache
98
+ # Use in-memory store in non-production environments if cache is NullStore
99
+ # this is useful for development and testing
100
+ # Use a more robust cache store in production (e.g., Memcached, Redis)
101
+ if Rails.cache.is_a?(ActiveSupport::Cache::NullStore) && !Rails.env.production?
102
+ cache_store = ActiveSupport::Cache::MemoryStore.new
103
+ end
104
+ relying_party_jwks_storage = OmniauthStrongAuthOidc::RelyingPartyJwksStorage::CacheStorage.new(
105
+ cache_store: cache_store
106
+ )
107
+ else
108
+ raise "OIDC signing and encryption keys are not configured. Please set OIDC_SIGNING_KEY_BASE64 and OIDC_ENCRYPTION_KEY_BASE64 environment variables, or enable key rotation with OIDC_KEY_ROTATION_ENABLED."
109
+ end
110
+
111
+ OmniauthStrongAuthOidc::RelyingPartyJwksStorage::Base.instance ||= relying_party_jwks_storage
112
+
113
+ provider_jwks_fetcher = OmniauthStrongAuthOidc::JwksFetcher.new(
114
+ entity_statement_fetcher: provider_entity_statement_fetcher
115
+ )
116
+
117
+ config.omniauth :strong_auth_oidc,
118
+ client_id: ENV.fetch("OIDC_CLIENT_ID"),
119
+ relying_party_jwks_storage: relying_party_jwks_storage,
120
+ provider_jwks_loader: OmniauthStrongAuthOidc::JwksCache.new(provider_jwks_fetcher),
121
+ provider_entity_statement_fetcher: provider_entity_statement_fetcher,
122
+ authorize_params: {
123
+ acr_values: ENV.fetch("OIDC_ACR_VALUES").split(' '),
124
+ response_type: 'code',
125
+ scope: 'openid'
126
+ },
127
+ client_options: {
128
+ auth_scheme: :private_key_jwt
129
+ }
130
+ end
131
+ ```
132
+
133
+ ### Create OmniAuth Callbacks Controller
134
+
135
+ ```ruby
136
+ class Users::OmniauthCallbacksController < Devise::OmniauthCallbacksController
137
+ def strong_auth_oidc
138
+ @user = User.from_omniauth(request.env['omniauth.auth'])
139
+
140
+ if @user.persisted?
141
+ sign_in_and_redirect @user, event: :authentication
142
+ set_flash_message(:notice, :success, kind: 'Strong Auth') if is_navigational_format?
143
+ else
144
+ session['devise.strong_auth_oidc_data'] = request.env['omniauth.auth'].except(:extra)
145
+ redirect_to new_user_registration_url
146
+ end
147
+ end
148
+
149
+ def failure
150
+ redirect_to root_path, alert: "Authentication failed: #{failure_message}"
151
+ end
152
+ end
153
+ ```
154
+
155
+ ### Add Class Method to User Model
156
+
157
+ ```ruby
158
+ class User < ApplicationRecord
159
+ # ... devise configuration ...
160
+
161
+ def self.from_omniauth(auth)
162
+ where(provider: auth.provider, uid: auth.uid).first_or_create do |user|
163
+ user.email = "#{auth.uid}@strong-auth.local" # or handle email differently
164
+ user.password = Devise.friendly_token[0, 20]
165
+ user.identity_number = auth.info.identity_number
166
+ # user.first_name = auth.info.first_name
167
+ # user.last_name = auth.info.last_name
168
+ end
169
+ end
170
+ end
171
+ ```
172
+
173
+ ### Configure Routes
174
+
175
+ ```ruby
176
+ Rails.application.routes.draw do
177
+ devise_for :users, controllers: {
178
+ omniauth_callbacks: 'users/omniauth_callbacks'
179
+ }
180
+ end
181
+ ```
182
+
183
+ ### Add Login Link to View
184
+
185
+ ```erb
186
+ <%= link_to "Sign in with Finnish Strong Authentication", user_strong_auth_oidc_omniauth_authorize_path %>
187
+ ```
188
+
189
+ ## Federation Endpoints Controller
190
+
191
+ To expose the required OIDC federation endpoints (entity statement, JWKS), use the Rails generator:
192
+
193
+ ```bash
194
+ rails generate omniauth_strong_auth_oidc:install \
195
+ --redirect_uris="https://example.com/users/auth/strong_auth_oidc/callback" \
196
+ --org_name="Your Organization Name" \
197
+ --iss="https://example.com"
198
+ ```
199
+
200
+ **Generator options:**
201
+
202
+ | Option | Required | Description |
203
+ |--------|----------|-------------|
204
+ | `--redirect_uris` | Yes | Comma-separated list of OAuth callback URLs |
205
+ | `--org_name` | Yes | Your organization name for the entity statement |
206
+ | `--iss` | Yes | Issuer URL (your application's base URL) |
207
+
208
+ **Example with multiple redirect URIs:**
209
+
210
+ ```bash
211
+ rails generate omniauth_strong_auth_oidc:install \
212
+ --redirect_uris="https://example.com/users/auth/strong_auth_oidc/callback,https://staging.example.com/users/auth/strong_auth_oidc/callback" \
213
+ --org_name="Acme Corporation" \
214
+ --iss="https://example.com"
215
+ ```
216
+
217
+ This will:
218
+ 1. Create `app/controllers/relying_party_entity_statement_controller.rb`
219
+ 2. Add the following routes to `config/routes.rb`:
220
+
221
+ ```ruby
222
+ # OIDC Federation endpoints
223
+ get '/.well-known/openid-federation', to: 'relying_party_entity_statement#entity_statement', as: :openid_federation
224
+ get '/.well-known/jwks.json', to: 'relying_party_entity_statement#jwks', as: :jwks
225
+ get '/.well-known/signed-jwks.jwt', to: 'relying_party_entity_statement#signed_jwks', as: :signed_jwks
226
+ ```
227
+
228
+ The generated controller provides the following endpoints:
229
+
230
+ | Endpoint | Content-Type | Description |
231
+ |----------|--------------|-------------|
232
+ | `/.well-known/openid-federation` | `application/entity-statement+jwt` | Signed entity statement JWT |
233
+ | `/.well-known/jwks.json` | `application/json` | Public JWKS for token encryption |
234
+ | `/.well-known/signed-jwks.jwt` | `application/jwks+jwt` | Signed JWKS JWT |
235
+
236
+ **Additional environment variable required:**
237
+
238
+ ```bash
239
+ OIDC_CONFIGURATION_SIGNING_KEY_BASE64=base64_encoded_configuration_signing_key
240
+ ```
241
+
242
+ This key is used to sign the entity statement and JWKS. It should be a separate RSA key pair from the signing/encryption keys used for tokens.
243
+
244
+ ## Key Storage Options
245
+
246
+ ### Environment Storage (EnvStorage)
247
+
248
+ Store static keys in environment variables:
249
+
250
+ ```bash
251
+ OIDC_SIGNING_KEY_BASE64=<base64_encoded_private_key>
252
+ OIDC_ENCRYPTION_KEY_BASE64=<base64_encoded_private_key>
253
+ ```
254
+
255
+ ### Cache Storage (CacheStorage)
256
+
257
+ Enable automatic key rotation using Rails cache:
258
+
259
+ ```bash
260
+ OIDC_KEY_ROTATION_ENABLED=true
261
+ ```
262
+
263
+ Keys are automatically generated and rotated based on cache TTL.
264
+
265
+ ## Entity Statement Fetchers
266
+
267
+ ### File Fetcher
268
+
269
+ For testing and development, load entity statements from a local file:
270
+
271
+ ```ruby
272
+ OmniauthStrongAuthOidc::EntityStatementFetcher::FileFetcher.new(
273
+ path_to_file: Rails.root.join("config", "oidc_entity_statement.json").to_s
274
+ )
275
+ ```
276
+
277
+ ### Federation URL Fetcher
278
+
279
+ For production, fetch entity statements from the federation URL:
280
+
281
+ ```ruby
282
+ OmniauthStrongAuthOidc::EntityStatementFetcher::FederationUrlFetcher.new(
283
+ issuer_url: ENV.fetch("OAUTH_ISSUER_URL")
284
+ )
285
+ ```
286
+
287
+ ## User Attributes
288
+
289
+ The strategy returns the following user attributes:
290
+
291
+ - `uid`: Unique identifier (subject)
292
+ - `identity_number`: Finnish personal identity code (urn:oid:1.2.246.21)
293
+ - `first_name`: Given name (urn:oid:1.2.246.575.1.14)
294
+ - `last_name`: Family name (urn:oid:2.5.4.4)
295
+
296
+ Raw claims are available in `auth['extra']['raw_info']`.
297
+
298
+ ## Development
299
+
300
+ After checking out the repo, run:
301
+
302
+ ```bash
303
+ bundle install
304
+ bundle exec rspec
305
+ ```
306
+
307
+ ## Contributing
308
+
309
+ Bug reports and pull requests are welcome on GitHub at https://github.com/kiskolabs/omniauth_strong_auth_oidc.
310
+
311
+ ## License
312
+
313
+ The gem is available as open source under the terms of the [MIT License](LICENSE).
data/Rakefile ADDED
@@ -0,0 +1,12 @@
1
+ require "bundler/gem_tasks"
2
+
3
+ task default: :spec
4
+
5
+ desc "Run spec suite"
6
+ task :spec do
7
+ if File.exist?("Gemfile")
8
+ sh "bundle exec rspec"
9
+ else
10
+ sh "rspec"
11
+ end
12
+ end
@@ -0,0 +1,73 @@
1
+ # frozen_string_literal: true
2
+
3
+ if defined?(Rails::Generators::Base)
4
+ module OmniauthStrongAuthOidc
5
+ module Generators
6
+ class InstallGenerator < Rails::Generators::Base
7
+ source_root File.expand_path('templates', __dir__)
8
+
9
+ class_option :redirect_uris,
10
+ type: :string,
11
+ required: true,
12
+ desc: 'Comma-separated list of redirect URIs (e.g., "https://example.com/users/auth/strong_auth_oidc/callback")'
13
+
14
+ class_option :org_name,
15
+ type: :string,
16
+ required: true,
17
+ desc: 'Organization name for the entity statement'
18
+
19
+ class_option :iss,
20
+ type: :string,
21
+ required: true,
22
+ desc: 'Issuer URL (e.g., "https://example.com")'
23
+
24
+ desc 'Generates the RelyingPartyEntityStatementController for OIDC federation endpoints'
25
+
26
+ def create_controller
27
+ template 'relying_party_entity_statement_controller.rb.tt',
28
+ 'app/controllers/relying_party_entity_statement_controller.rb'
29
+ end
30
+
31
+ def create_routes
32
+ route_content = <<~ROUTES
33
+ # OIDC Federation endpoints
34
+ get '/.well-known/openid-federation', to: 'relying_party_entity_statement#entity_statement', as: :openid_federation
35
+ get '/.well-known/jwks.json', to: 'relying_party_entity_statement#jwks', as: :jwks
36
+ get '/.well-known/signed-jwks.jwt', to: 'relying_party_entity_statement#signed_jwks', as: :signed_jwks
37
+ ROUTES
38
+
39
+ route route_content
40
+ end
41
+
42
+ def show_post_install_message
43
+ say ''
44
+ say '============================================================', :green
45
+ say 'OmniAuth Strong Auth OIDC controller installed successfully!', :green
46
+ say '============================================================', :green
47
+ say ''
48
+ say 'Next steps:', :yellow
49
+ say '1. Review the generated controller at app/controllers/relying_party_entity_statement_controller.rb'
50
+ say '2. Ensure you have the required environment variables set:'
51
+ say ' - OIDC_CLIENT_ID'
52
+ say ' - OIDC_CONFIGURATION_SIGNING_KEY_BASE64'
53
+ say '3. Update your Devise/OmniAuth configuration'
54
+ say ''
55
+ end
56
+
57
+ private
58
+
59
+ def redirect_uris_array
60
+ options[:redirect_uris].split(',').map(&:strip)
61
+ end
62
+
63
+ def org_name
64
+ options[:org_name]
65
+ end
66
+
67
+ def iss
68
+ options[:iss]
69
+ end
70
+ end
71
+ end
72
+ end
73
+ end
@@ -0,0 +1,61 @@
1
+ # frozen_string_literal: true
2
+
3
+ # Handles OIDC federation endpoints for entity statements and JWKS
4
+ class RelyingPartyEntityStatementController < ApplicationController
5
+ # Return plain JWKS (for backward compatibility)
6
+ def jwks
7
+ jwks = OmniauthStrongAuthOidc::RelyingPartyJwksStorage::Base.instance.current_jwks.export
8
+ render json: jwks
9
+ rescue StandardError => e
10
+ Rails.logger.error "Failed to generate JWKS: #{e.message}"
11
+ render json: { error: 'Failed to generate JWKS' }, status: :internal_server_error
12
+ end
13
+
14
+ # Returns signed JWKS JWT containing the client's public keys
15
+ def signed_jwks
16
+ signed_jwks = OmniauthStrongAuthOidc::RelyingPartyJwksGenerator.new(
17
+ relying_party_jwks_storage: OmniauthStrongAuthOidc::RelyingPartyJwksStorage::Base.instance,
18
+ relying_party_configuration_jwks_storage: configuration_jwks_storage,
19
+ issuer: ENV.fetch("OIDC_CLIENT_ID")
20
+ )
21
+
22
+ render plain: signed_jwks.generate_signed, content_type: 'application/jwks+jwt'
23
+ rescue StandardError => e
24
+ Rails.logger.error "Failed to generate signed JWKS: #{e.message}"
25
+ render json: { error: 'Failed to generate signed JWKS' }, status: :internal_server_error
26
+ end
27
+
28
+ # Returns the OpenID Client Configuration including the entity statement
29
+ def entity_statement
30
+ entity_statement = OmniauthStrongAuthOidc::RelyingPartyEntityStatementGenerator.new(
31
+ iss: <%= iss.inspect %>,
32
+ org_name: <%= org_name.inspect %>,
33
+ jwks_uri: jwks_url,
34
+ signed_jwks_uri: signed_jwks_url,
35
+ redirect_uris: <%= redirect_uris_array.inspect %>,
36
+ configuration_jwks_storage: configuration_jwks_storage
37
+ )
38
+
39
+ render plain: entity_statement.generate_signed, content_type: 'application/entity-statement+jwt'
40
+ rescue StandardError => e
41
+ Rails.logger.error "Failed to generate entity statement: #{e.message}"
42
+ render json: { error: 'Failed to generate entity statement' }, status: :internal_server_error
43
+ end
44
+
45
+ private
46
+
47
+ def configuration_jwks_storage
48
+ @configuration_jwks_storage ||= OmniauthStrongAuthOidc::RelyingPartyJwksStorage::EnvStorage.new(
49
+ signing_key_env: 'OIDC_CONFIGURATION_SIGNING_KEY_BASE64',
50
+ encryption_key_env: nil
51
+ )
52
+ end
53
+
54
+ def jwks_url
55
+ url_for(action: :jwks, only_path: false)
56
+ end
57
+
58
+ def signed_jwks_url
59
+ url_for(action: :signed_jwks, only_path: false)
60
+ end
61
+ end