diff --git a/app/components/button_component.rb b/app/components/button_component.rb index 28615b1ac92..29bca1161a5 100644 --- a/app/components/button_component.rb +++ b/app/components/button_component.rb @@ -1,10 +1,21 @@ # frozen_string_literal: true class ButtonComponent < BaseComponent - attr_reader :action, :icon, :big, :wide, :full_width, :outline, :unstyled, :danger, :tag_options + attr_reader :url, + :method, + :icon, + :big, + :wide, + :full_width, + :outline, + :unstyled, + :danger, + :tag_options def initialize( - action: ->(**tag_options, &block) { button_tag(**tag_options, &block) }, + action: nil, + url: nil, + method: nil, icon: nil, big: false, wide: false, @@ -15,6 +26,8 @@ def initialize( **tag_options ) @action = action + @url = url + @method = method @icon = icon @big = big @wide = wide @@ -53,4 +66,18 @@ def content original_content end end + + def action + @action ||= begin + if url + if method && method != :get + ->(**tag_options, &block) { button_to(url, method:, **tag_options, &block) } + else + ->(**tag_options, &block) { link_to(url, **tag_options, &block) } + end + else + ->(**tag_options, &block) { button_tag(**tag_options, &block) } + end + end + end end diff --git a/app/views/accounts/_pii.html.erb b/app/views/accounts/_pii.html.erb index c4597b8ebaa..8decfe81eb5 100644 --- a/app/views/accounts/_pii.html.erb +++ b/app/views/accounts/_pii.html.erb @@ -5,9 +5,7 @@
<%= t('idv.cancel.description.hybrid') %>
<% c.with_action_button( - action: ->(**tag_options, &block) do - button_to(idv_cancel_path(step: params[:step], location: 'cancel'), **tag_options, &block) - end, + url: idv_cancel_path(step: params[:step], location: 'cancel'), method: :delete, ).with_content(t('forms.buttons.cancel')) %> <% c.with_action_button( - action: ->(**tag_options, &block) do - button_to(idv_cancel_path(step: params[:step]), **tag_options, &block) - end, + url: idv_cancel_path(step: params[:step]), method: :put, outline: true, ).with_content(t('links.go_back')) %> @@ -28,9 +24,7 @@<%= t('forms.backup_code_regenerate.caution') %>
-- <%= t('forms.backup_code_regenerate.caution') %> -
+ <%= render ButtonComponent.new( + url: backup_code_setup_path, + big: true, + wide: true, + class: 'margin-top-3 margin-bottom-2', + ).with_content(t('account.index.backup_code_confirm_regenerate')) %> -<%= form_tag(backup_code_setup_path, method: :get, class: 'margin-top-5') do %> - <%= button_tag t('account.index.backup_code_confirm_regenerate'), type: 'submit', - class: 'usa-button usa-button--big usa-button--wide margin-bottom-2' %> + <%= render ButtonComponent.new( + url: account_path, + big: true, + wide: true, + outline: true, + ).with_content(t('links.cancel')) %> <% end %> - -<%= link_to t('links.cancel'), account_path, - class: 'usa-button usa-button--big usa-button--wide usa-button--outline' %> diff --git a/app/views/users/piv_cac/edit.html.erb b/app/views/users/piv_cac/edit.html.erb index 7995216d56c..a4a48700f53 100644 --- a/app/views/users/piv_cac/edit.html.erb +++ b/app/views/users/piv_cac/edit.html.erb @@ -21,19 +21,13 @@ <% end %> <%= render ButtonComponent.new( - action: ->(**tag_options, &block) do - button_to( - piv_cac_path(id: @form.configuration.id), - form: { aria: { label: @presenter.delete_button_label } }, - **tag_options, - &block - ) - end, + url: piv_cac_path(id: @form.configuration.id), method: :delete, + form: { aria: { label: @presenter.delete_button_label } }, big: true, wide: true, danger: true, class: 'display-block margin-top-2', ).with_content(@presenter.delete_button_label) %> -<%= render 'shared/cancel', link: account_path %> \ No newline at end of file +<%= render 'shared/cancel', link: account_path %> diff --git a/app/views/users/webauthn/edit.html.erb b/app/views/users/webauthn/edit.html.erb index 5dc61948680..f57ad50edc9 100644 --- a/app/views/users/webauthn/edit.html.erb +++ b/app/views/users/webauthn/edit.html.erb @@ -19,15 +19,9 @@ <% end %> <%= render ButtonComponent.new( - action: ->(**tag_options, &block) do - button_to( - webauthn_path(id: @form.configuration.id), - form: { aria: { label: @presenter.delete_button_label } }, - **tag_options, - &block - ) - end, + url: webauthn_path(id: @form.configuration.id), method: :delete, + form: { aria: { label: @presenter.delete_button_label } }, big: true, wide: true, danger: true, diff --git a/config/brakeman.ignore b/config/brakeman.ignore index 07cc533c85e..031a569d24c 100644 --- a/config/brakeman.ignore +++ b/config/brakeman.ignore @@ -3,19 +3,19 @@ { "warning_type": "Dynamic Render Path", "warning_code": 15, - "fingerprint": "406a2c5ea3d852268958d2db11c146841491b6e87cee9c583dd35f5f41898fb7", + "fingerprint": "0550ef2573eae747e7e4bb6f31851ed77713409b74f7abe48c15a6a82801babb", "check_name": "Render", "message": "Render path contains parameter value", "file": "app/views/idv/cancellations/new.html.erb", - "line": 43, + "line": 31, "link": "https://brakemanscanner.org/docs/warning_types/dynamic_render_path/", - "code": "render(action => ButtonComponent.new(:action => (lambda do\n button_to(idv_cancel_path(:step => params[:step]), { **tag_options }, &block)\n end), :method => :put, :big => true, :wide => true, :outline => true, :form => ({ :\"aria-label\" => t(\"idv.cancel.actions.keep_going\") })).with_content(t(\"idv.cancel.actions.keep_going\")), {})", + "code": "render(action => ButtonComponent.new(:url => idv_session_path(:step => params[:step]), :method => :delete, :big => true, :wide => true, :form => ({ :\"aria-label\" => t(\"idv.cancel.actions.start_over\") })).with_content(t(\"idv.cancel.actions.start_over\")), {})", "render_path": [ { "type": "controller", "class": "Idv::CancellationsController", "method": "new", - "line": 13, + "line": 16, "file": "app/controllers/idv/cancellations_controller.rb", "rendered": { "name": "idv/cancellations/new", @@ -37,19 +37,19 @@ { "warning_type": "Dynamic Render Path", "warning_code": 15, - "fingerprint": "8b51f403181f74421f5681ada1096371e1f55fb03d0127db01b5e5da7dda3c51", + "fingerprint": "278d16995e8a645908c9a043314cfeebd8cb094bce766ad5101c62ff08853de6", "check_name": "Render", "message": "Render path contains parameter value", "file": "app/views/idv/cancellations/new.html.erb", - "line": 32, + "line": 60, "link": "https://brakemanscanner.org/docs/warning_types/dynamic_render_path/", - "code": "render(action => ButtonComponent.new(:action => (lambda do\n button_to(idv_session_path(:step => params[:step]), { **tag_options }, &block)\n end), :method => :delete, :big => true, :wide => true, :form => ({ :\"aria-label\" => t(\"idv.cancel.actions.start_over\") })).with_content(t(\"idv.cancel.actions.start_over\")), {})", + "code": "render(action => SpinnerButtonComponent.new(:url => idv_cancel_path(:step => params[:step], :location => \"cancel\"), :method => :delete, :big => true, :wide => true, :outline => true, :form => ({ :\"aria-label\" => CancellationsPresenter.new(:sp_name => decorated_sp_session.sp_name, :url_options => url_options).exit_action_text, :data => ({ :form_steps_wait => \"\" }) })).with_content(CancellationsPresenter.new(:sp_name => decorated_sp_session.sp_name, :url_options => url_options).exit_action_text), {})", "render_path": [ { "type": "controller", "class": "Idv::CancellationsController", "method": "new", - "line": 13, + "line": 16, "file": "app/controllers/idv/cancellations_controller.rb", "rendered": { "name": "idv/cancellations/new", @@ -71,19 +71,19 @@ { "warning_type": "Dynamic Render Path", "warning_code": 15, - "fingerprint": "f7d01c6318e6ce369f9fe9bf59b6a3a323034b4b826e2a52a9a87b581d468598", + "fingerprint": "341d99a0fdaf75dff50ea66c9da1b973cb36fc1aac2221480deff6e30d11540a", "check_name": "Render", "message": "Render path contains parameter value", "file": "app/views/idv/cancellations/new.html.erb", - "line": 65, + "line": 40, "link": "https://brakemanscanner.org/docs/warning_types/dynamic_render_path/", - "code": "render(action => SpinnerButtonComponent.new(:action => (lambda do\n button_to(idv_cancel_path(:step => params[:step], :location => \"cancel\"), { **tag_options }, &block)\n end), :method => :delete, :big => true, :wide => true, :outline => true, :form => ({ :\"aria-label\" => CancellationsPresenter.new(:sp_name => decorated_sp_session.sp_name, :url_options => url_options).exit_action_text, :data => ({ :form_steps_wait => \"\" }) })).with_content(CancellationsPresenter.new(:sp_name => decorated_sp_session.sp_name, :url_options => url_options).exit_action_text), {})", + "code": "render(action => ButtonComponent.new(:url => idv_cancel_path(:step => params[:step]), :method => :put, :big => true, :wide => true, :outline => true, :form => ({ :\"aria-label\" => t(\"idv.cancel.actions.keep_going\") })).with_content(t(\"idv.cancel.actions.keep_going\")), {})", "render_path": [ { "type": "controller", "class": "Idv::CancellationsController", "method": "new", - "line": 13, + "line": 16, "file": "app/controllers/idv/cancellations_controller.rb", "rendered": { "name": "idv/cancellations/new", @@ -103,6 +103,6 @@ "note": "" } ], - "updated": "2023-11-02 09:34:28 -0400", - "brakeman_version": "6.0.1" + "updated": "2024-04-19 08:20:16 -0400", + "brakeman_version": "6.1.0" } diff --git a/spec/components/button_component_spec.rb b/spec/components/button_component_spec.rb index f448f220ce9..57bfc72d25a 100644 --- a/spec/components/button_component_spec.rb +++ b/spec/components/button_component_spec.rb @@ -131,4 +131,33 @@ ) end end + + context 'with url' do + let(:url) { '/' } + let(:options) { { url: } } + + it 'renders link to url' do + expect(rendered).to have_link(content, href: url) + end + + context 'with method' do + let(:method) { :put } + let(:options) { super().merge(method:) } + + it 'renders button to url' do + expect(rendered).to have_selector("form[action='#{url}']") + expect(rendered).to have_selector("input[name='_method'][value='#{method}']", visible: :all) + expect(rendered).to have_selector("button[type='submit']") + expect(rendered).to have_text(content) + end + + context 'with get method' do + let(:method) { :get } + + it 'renders link to url' do + expect(rendered).to have_link(content, href: url) + end + end + end + end end diff --git a/spec/views/users/backup_code_setup/edit.html.erb_spec.rb b/spec/views/users/backup_code_setup/edit.html.erb_spec.rb new file mode 100644 index 00000000000..dee4a74f66c --- /dev/null +++ b/spec/views/users/backup_code_setup/edit.html.erb_spec.rb @@ -0,0 +1,16 @@ +require 'rails_helper' + +RSpec.describe 'users/backup_code_setup/edit.html.erb' do + subject(:rendered) { render } + + it 'has a link to confirm and proceed to setup' do + expect(rendered).to have_link( + t('account.index.backup_code_confirm_regenerate'), + href: backup_code_setup_path, + ) + end + + it 'has a link to cancel and return to account page' do + expect(rendered).to have_link(t('links.cancel'), href: account_path) + end +end