diff --git a/Gemfile b/Gemfile index 6879503..f406a81 100644 --- a/Gemfile +++ b/Gemfile @@ -42,6 +42,7 @@ gem "apipie-rails", "~> 1.2.0" gem 'omniauth', '>=2.0.0' gem 'omniauth-rails_csrf_protection' gem 'omniauth-tara', github: 'internetee/omniauth-tara' +gem 'i18n-tasks', '~> 1.0.12' # Use Rack CORS for handling Cross-Origin Resource Sharing (CORS), making cross-origin AJAX possible # gem 'rack-cors' diff --git a/Gemfile.lock b/Gemfile.lock index fbb34c1..9bfacc4 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -26,6 +26,14 @@ GIT logger nokogiri +GIT + remote: https://github.com/internetee/omniauth-tara.git + revision: d7babe56fe666739a0aca4bc94ddc8629641d220 + specs: + omniauth-tara (0.7.1) + omniauth (>= 1.9, < 3) + openid_connect (~> 2.2) + GEM remote: https://rubygems.org/ specs: @@ -96,19 +104,30 @@ GEM tzinfo (~> 2.0) addressable (2.8.5) public_suffix (>= 2.0.2, < 6.0) - airbrussh (1.4.1) + aes_key_wrap (1.1.0) + airbrussh (1.5.0) sshkit (>= 1.6.1, != 1.7.0) akami (1.3.1) gyoku (>= 0.4.0) nokogiri - apipie-rails (1.2.2) + apipie-rails (1.2.3) actionpack (>= 5.0) activesupport (>= 5.0) ast (2.4.2) - bcrypt (3.1.18) - bootsnap (1.16.0) + attr_required (1.0.1) + base64 (0.1.1) + bcrypt (3.1.19) + better_html (2.0.2) + actionview (>= 6.0) + activesupport (>= 6.0) + ast (~> 2.0) + erubi (~> 1.4) + parser (>= 2.4) + smart_properties + bindata (2.4.15) + bootsnap (1.17.0) msgpack (~> 1.2) - brakeman (6.0.0) + brakeman (6.0.1) builder (3.2.4) bundle-audit (0.1.0) bundler-audit @@ -116,7 +135,7 @@ GEM bundler (>= 1.2.0, < 3) thor (~> 1.0) byebug (11.1.3) - capistrano (3.17.1) + capistrano (3.18.0) airbrussh (>= 1.0.0) i18n rake (>= 10.0.0) @@ -125,32 +144,32 @@ GEM capistrano (~> 3.1) capistrano-passenger (0.2.1) capistrano (~> 3.0) - capistrano-rails (1.6.2) + capistrano-rails (1.6.3) capistrano (~> 3.1) capistrano-bundler (>= 1.1, < 3) capistrano-rbenv (2.2.0) capistrano (~> 3.1) sshkit (~> 1.3) concurrent-ruby (1.2.2) - connection_pool (2.3.0) - countries (5.3.1) + connection_pool (2.4.1) + countries (5.7.0) unaccent (~> 0.3) crack (0.4.5) rexml crass (1.0.6) - database_cleaner (2.0.1) - database_cleaner-active_record (~> 2.0.0) - database_cleaner-active_record (2.0.1) + database_cleaner (2.0.2) + database_cleaner-active_record (>= 2, < 3) + database_cleaner-active_record (2.1.0) activerecord (>= 5.a) database_cleaner-core (~> 2.0.0) database_cleaner-core (2.0.1) date (3.3.3) diff-lcs (1.5.0) docile (1.4.0) - dry-configurable (1.0.1) + dry-configurable (1.1.0) dry-core (~> 1.0, < 2) zeitwerk (~> 2.6) - dry-core (1.0.0) + dry-core (1.0.1) concurrent-ruby (~> 1.0) zeitwerk (~> 2.6) dry-inflector (1.0.0) @@ -159,19 +178,19 @@ GEM concurrent-ruby (~> 1.0) dry-core (~> 1.0, < 2) zeitwerk (~> 2.6) - dry-schema (1.13.0) + dry-schema (1.13.3) concurrent-ruby (~> 1.0) dry-configurable (~> 1.0, >= 1.0.1) dry-core (~> 1.0, < 2) dry-initializer (~> 3.0) - dry-logic (>= 1.5, < 2) + dry-logic (>= 1.4, < 2) dry-types (>= 1.7, < 2) zeitwerk (~> 2.6) - dry-types (1.7.0) + dry-types (1.7.1) concurrent-ruby (~> 1.0) - dry-core (~> 1.0, < 2) - dry-inflector (~> 1.0, < 2) - dry-logic (>= 1.4, < 2) + dry-core (~> 1.0) + dry-inflector (~> 1.0) + dry-logic (~> 1.4) zeitwerk (~> 2.6) dry-validation (1.10.0) concurrent-ruby (~> 1.0) @@ -185,21 +204,26 @@ GEM factory_bot_rails (6.2.0) factory_bot (~> 6.2.0) railties (>= 5.0.0) - faker (3.1.1) + faker (3.2.1) i18n (>= 1.8.11, < 2) - faraday (2.7.4) + faraday (2.7.11) + base64 faraday-net_http (>= 2.0, < 3.1) ruby2_keywords (>= 0.0.4) + faraday-follow_redirects (0.3.0) + faraday (>= 1, < 3) faraday-net_http (3.0.2) - ffi (1.15.5) + ffi (1.16.3) figaro (1.2.0) thor (>= 0.14.0, < 2) - globalid (1.1.0) - activesupport (>= 5.0) + globalid (1.2.1) + activesupport (>= 6.1) gyoku (1.4.0) builder (>= 2.1.2) rexml (~> 3.0) hashdiff (1.0.1) + hashie (5.0.0) + highline (2.1.0) hotwire-rails (0.1.3) rails (>= 6.0.0) stimulus-rails @@ -208,16 +232,35 @@ GEM rack i18n (1.14.1) concurrent-ruby (~> 1.0) - importmap-rails (1.1.5) + i18n-tasks (1.0.13) + activesupport (>= 4.0.2) + ast (>= 2.1.0) + better_html (>= 1.0, < 3.0) + erubi + highline (>= 2.0.0) + i18n + parser (>= 3.2.2.1) + rails-i18n + rainbow (>= 2.2.2, < 4.0) + terminal-table (>= 1.5.1) + importmap-rails (1.2.3) actionpack (>= 6.0.0) + activesupport (>= 6.0.0) railties (>= 6.0.0) json (2.6.3) - jwt (2.7.0) + json-jwt (1.16.3) + activesupport (>= 4.2) + aes_key_wrap + bindata + faraday (~> 2.0) + faraday-follow_redirects + jwt (2.7.1) + language_server-protocol (3.17.0.3) listen (3.8.0) rb-fsevent (~> 0.10, >= 0.10.3) rb-inotify (~> 0.9, >= 0.9.10) logger (1.5.3) - loofah (2.21.3) + loofah (2.21.4) crass (~> 1.0.2) nokogiri (>= 1.12.0) mail (2.8.1) @@ -228,11 +271,11 @@ GEM marcel (1.0.2) method_source (1.0.0) mini_mime (1.1.5) - minitest (5.19.0) + minitest (5.20.0) money (6.16.0) i18n (>= 0.6.4, <= 2) - msgpack (1.6.0) - net-imap (0.3.7) + msgpack (1.7.2) + net-imap (0.4.3) date net-protocol net-pop (0.1.2) @@ -243,25 +286,55 @@ GEM net-ssh (>= 2.6.5, < 8.0.0) net-smtp (0.4.0) net-protocol - net-ssh (7.0.1) + net-ssh (7.2.0) nio4r (2.5.9) nokogiri (1.15.4-x86_64-linux) racc (~> 1.4) nori (2.6.0) - pagy (6.0.1) - parallel (1.22.1) - parser (3.2.1.0) + omniauth (2.1.1) + hashie (>= 3.4.6) + rack (>= 2.2.3) + rack-protection + omniauth-rails_csrf_protection (1.0.1) + actionpack (>= 4.2) + omniauth (~> 2.0) + openid_connect (2.2.0) + activemodel + attr_required (>= 1.0.0) + faraday (~> 2.0) + faraday-follow_redirects + json-jwt (>= 1.16) + net-smtp + rack-oauth2 (~> 2.2) + swd (~> 2.0) + tzinfo + validate_email + validate_url + webfinger (~> 2.0) + pagy (6.1.0) + parallel (1.23.0) + parser (3.2.2.4) ast (~> 2.4.1) - pdfkit (0.8.7.2) - pg (1.4.5) + racc + pdfkit (0.8.7.3) + pg (1.5.4) pg_search (2.3.6) activerecord (>= 5.2) activesupport (>= 5.2) public_suffix (5.0.3) puma (6.3.1) nio4r (~> 2.0) - racc (1.7.1) + racc (1.7.2) rack (2.2.8) + rack-oauth2 (2.2.0) + activesupport + attr_required + faraday (~> 2.0) + faraday-follow_redirects + json-jwt (>= 1.11.0) + rack (>= 2.1.0) + rack-protection (3.1.0) + rack (~> 2.2, >= 2.2.4) rack-test (2.1.0) rack (>= 1.3) rails (7.0.7.2) @@ -285,6 +358,9 @@ GEM rails-html-sanitizer (1.6.0) loofah (~> 2.21) nokogiri (~> 1.14) + rails-i18n (7.0.8) + i18n (>= 0.7, < 2) + railties (>= 6.0.0, < 8) railties (7.0.7.2) actionpack (= 7.0.7.2) activesupport (= 7.0.7.2) @@ -293,50 +369,51 @@ GEM thor (~> 1.0) zeitwerk (~> 2.5) rainbow (3.1.1) - rake (13.0.6) + rake (13.1.0) rb-fsevent (0.11.2) rb-inotify (0.10.1) ffi (~> 1.0) - redis (5.0.6) - redis-client (>= 0.9.0) - redis-client (0.12.1) + redis (5.0.8) + redis-client (>= 0.17.0) + redis-client (0.18.0) connection_pool - regexp_parser (2.7.0) + regexp_parser (2.8.2) rexml (3.2.6) - rspec-core (3.12.1) + rspec-core (3.12.2) rspec-support (~> 3.12.0) - rspec-expectations (3.12.2) + rspec-expectations (3.12.3) diff-lcs (>= 1.2.0, < 2.0) rspec-support (~> 3.12.0) - rspec-mocks (3.12.3) + rspec-mocks (3.12.6) diff-lcs (>= 1.2.0, < 2.0) rspec-support (~> 3.12.0) - rspec-rails (6.0.1) + rspec-rails (6.0.3) actionpack (>= 6.1) activesupport (>= 6.1) railties (>= 6.1) - rspec-core (~> 3.11) - rspec-expectations (~> 3.11) - rspec-mocks (~> 3.11) - rspec-support (~> 3.11) - rspec-support (3.12.0) - rubocop (1.45.1) + rspec-core (~> 3.12) + rspec-expectations (~> 3.12) + rspec-mocks (~> 3.12) + rspec-support (~> 3.12) + rspec-support (3.12.1) + rubocop (1.57.2) json (~> 2.3) + language_server-protocol (>= 3.17.0) parallel (~> 1.10) - parser (>= 3.2.0.0) + parser (>= 3.2.2.4) rainbow (>= 2.2.2, < 4.0) regexp_parser (>= 1.8, < 3.0) rexml (>= 3.2.5, < 4.0) - rubocop-ast (>= 1.24.1, < 2.0) + rubocop-ast (>= 1.28.1, < 2.0) ruby-progressbar (~> 1.7) unicode-display_width (>= 2.4.0, < 3.0) - rubocop-ast (1.26.0) + rubocop-ast (1.30.0) parser (>= 3.2.1.0) - rubocop-rails (2.17.4) + rubocop-rails (2.22.1) activesupport (>= 4.2.0) rack (>= 1.1) rubocop (>= 1.33.0, < 2.0) - ruby-progressbar (1.11.0) + ruby-progressbar (1.13.0) ruby2_keywords (0.0.5) rubyzip (2.3.2) savon (2.14.0) @@ -348,7 +425,7 @@ GEM nokogiri (>= 1.8.1) nori (~> 2.4) wasabi (~> 3.4) - selenium-webdriver (4.8.0) + selenium-webdriver (4.10.0) rexml (~> 3.2, >= 3.2.5) rubyzip (>= 1.2.2, < 3.0) websocket (~> 1.0) @@ -360,24 +437,32 @@ GEM simplecov_json_formatter (0.1.4) simpleidn (0.2.1) unf (~> 0.1.4) + smart_properties (1.17.0) spring (4.1.1) - sprockets (4.2.0) + sprockets (4.2.1) concurrent-ruby (~> 1.0) rack (>= 2.2.4, < 4) sprockets-rails (3.4.2) actionpack (>= 5.2) activesupport (>= 5.2) sprockets (>= 3.0.0) - sshkit (1.21.3) + sshkit (1.21.5) net-scp (>= 1.1.2) net-ssh (>= 2.8.0) - stimulus-rails (1.2.1) + stimulus-rails (1.3.0) railties (>= 6.0.0) - strong_migrations (1.4.2) + strong_migrations (1.6.4) activerecord (>= 5.2) - thor (1.2.2) + swd (2.0.2) + activesupport (>= 3) + attr_required (>= 0.0.5) + faraday (~> 2.0) + faraday-follow_redirects + terminal-table (3.0.2) + unicode-display_width (>= 1.1.1, < 3) + thor (1.3.0) timeout (0.4.0) - turbo-rails (1.3.3) + turbo-rails (1.5.0) actionpack (>= 6.0.0) activejob (>= 6.0.0) railties (>= 6.0.0) @@ -387,25 +472,35 @@ GEM unf (0.1.4) unf_ext unf_ext (0.0.8.2) - unicode-display_width (2.4.2) + unicode-display_width (2.5.0) + validate_email (0.1.6) + activemodel (>= 3.0) + mail (>= 2.2.5) + validate_url (1.0.15) + activemodel (>= 3.0.0) + public_suffix wasabi (3.8.0) addressable httpi (~> 3.0) nokogiri (>= 1.4.2) - webdrivers (5.2.0) + webdrivers (5.3.1) nokogiri (~> 1.6) rubyzip (>= 1.3.0) - selenium-webdriver (~> 4.0) - webmock (3.18.1) + selenium-webdriver (~> 4.0, < 4.11) + webfinger (2.1.2) + activesupport + faraday (~> 2.0) + faraday-follow_redirects + webmock (3.19.1) addressable (>= 2.8.0) crack (>= 0.3.2) hashdiff (>= 0.4.0, < 2.0.0) - websocket (1.2.9) + websocket (1.2.10) websocket-driver (0.7.6) websocket-extensions (>= 0.1.0) websocket-extensions (0.1.5) wkhtmltopdf-binary (0.12.6.6) - zeitwerk (2.6.8) + zeitwerk (2.6.12) PLATFORMS x86_64-linux @@ -433,6 +528,7 @@ DEPENDENCIES faraday figaro hotwire-rails + i18n-tasks (~> 1.0.12) importmap-rails jwt lhv! @@ -441,6 +537,9 @@ DEPENDENCIES net-imap net-pop net-smtp + omniauth (>= 2.0.0) + omniauth-rails_csrf_protection + omniauth-tara! pagy (~> 6.0) pdfkit pg (~> 1.1) @@ -466,4 +565,4 @@ RUBY VERSION ruby 3.2.0p0 BUNDLED WITH - 2.4.1 + 2.4.13 diff --git a/app/controllers/auth/tara_controller.rb b/app/controllers/auth/tara_controller.rb index f6fb4ad..0b505e3 100644 --- a/app/controllers/auth/tara_controller.rb +++ b/app/controllers/auth/tara_controller.rb @@ -4,13 +4,12 @@ module Auth class TaraController < ParentController allow_unauthenticated + rescue_from NotAuthorizedError, with: :render_forbidden_error + def callback expires_now && reset_session - unless in_white_list? - flash[:alert] = I18n.t('.access_denied') - redirect_to sign_in_path, status: :see_other and return - end + raise NotAuthorizedError unless in_white_list? session[:omniauth_hash] = user_hash.delete_if { |key, _| key == 'credentials' } @user = User.from_omniauth(user_hash) diff --git a/app/controllers/concerns/authenticate.rb b/app/controllers/concerns/authenticate.rb index 440c000..c3080ba 100644 --- a/app/controllers/concerns/authenticate.rb +++ b/app/controllers/concerns/authenticate.rb @@ -69,4 +69,13 @@ def authenticate Current.user = nil Current.app_session = nil end + + def render_forbidden_error + flash[:alert] = I18n.t('.access_denied') + render 'errors/403', status: :forbidden + end end + +class NotAuthorizedError < StandardError +end + diff --git a/app/controllers/errors_controller.rb b/app/controllers/errors_controller.rb new file mode 100644 index 0000000..32c3853 --- /dev/null +++ b/app/controllers/errors_controller.rb @@ -0,0 +1,27 @@ +class ErrorsController < ParentController + allow_unauthenticated + + def show + @exception = request.env['action_dispatch.exception'] + @status_code = @exception.try(:status_code) || + ActionDispatch::ExceptionWrapper.new( + request.env, @exception + ).status_code + render view_for_code(@status_code), status: @status_code + end + + private + + def view_for_code(code) + supported_error_codes.fetch(code, '404') + end + + def supported_error_codes + { + 401 => '401', + 403 => '403', + 404 => '404', + 500 => '500' + } + end +end diff --git a/app/models/white_code.rb b/app/models/white_code.rb index 91a5b1a..336d18a 100644 --- a/app/models/white_code.rb +++ b/app/models/white_code.rb @@ -1,3 +1,3 @@ class WhiteCode < ApplicationRecord - validates :code, presence: true, uniqueness: true, length: { is: 11 } + validates :code, presence: true, length: { minimum: 10, maximum: 12 } end diff --git a/app/views/errors/403.html.erb b/app/views/errors/403.html.erb new file mode 100644 index 0000000..02424e5 --- /dev/null +++ b/app/views/errors/403.html.erb @@ -0,0 +1,3 @@ +