rails_base 0.51.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 +7 -0
- data/MIT-LICENSE +20 -0
- data/README.md +32 -0
- data/Rakefile +32 -0
- data/app/assets/config/rails_base/manifest.js +3 -0
- data/app/assets/images/rails_base/favicon.ico +0 -0
- data/app/assets/javascripts/rails_base/admin.js +2 -0
- data/app/assets/javascripts/rails_base/application.js +22 -0
- data/app/assets/javascripts/rails_base/cable.js +13 -0
- data/app/assets/javascripts/rails_base/mfa_auth.coffee +3 -0
- data/app/assets/javascripts/rails_base/secondary_authentication.coffee +3 -0
- data/app/assets/javascripts/rails_base/sessions.js +152 -0
- data/app/assets/javascripts/rails_base/user_settings.coffee +3 -0
- data/app/assets/stylesheets/rails_base/admin.css +4 -0
- data/app/assets/stylesheets/rails_base/application.scss +15 -0
- data/app/assets/stylesheets/rails_base/mfa_auth.scss +3 -0
- data/app/assets/stylesheets/rails_base/scaffolds.scss +84 -0
- data/app/assets/stylesheets/rails_base/secondary_authentication.scss +3 -0
- data/app/assets/stylesheets/rails_base/user_settings.scss +3 -0
- data/app/controllers/rails_base/admin_controller.rb +315 -0
- data/app/controllers/rails_base/application_controller.rb +153 -0
- data/app/controllers/rails_base/errors_controller.rb +29 -0
- data/app/controllers/rails_base/mfa_auth_controller.rb +50 -0
- data/app/controllers/rails_base/secondary_authentication_controller.rb +224 -0
- data/app/controllers/rails_base/switch_user_controller.rb +29 -0
- data/app/controllers/rails_base/user_settings_controller.rb +81 -0
- data/app/controllers/rails_base/users/passwords_controller.rb +19 -0
- data/app/controllers/rails_base/users/registrations_controller.rb +80 -0
- data/app/controllers/rails_base/users/sessions_controller.rb +108 -0
- data/app/helpers/rails_base/admin_helper.rb +107 -0
- data/app/helpers/rails_base/appearance_helper.rb +58 -0
- data/app/helpers/rails_base/application_helper.rb +26 -0
- data/app/helpers/rails_base/capture_reference_helper.rb +57 -0
- data/app/helpers/rails_base/mfa_auth_helper.rb +2 -0
- data/app/helpers/rails_base/secondary_authentication_helper.rb +2 -0
- data/app/helpers/rails_base/user_field_validators.rb +108 -0
- data/app/helpers/rails_base/user_settings_helper.rb +22 -0
- data/app/jobs/rails_base/application_job.rb +10 -0
- data/app/jobs/twilio_job.rb +9 -0
- data/app/mailers/rails_base/application_mailer.rb +9 -0
- data/app/mailers/rails_base/email_verification_mailer.rb +22 -0
- data/app/mailers/rails_base/event_mailer.rb +16 -0
- data/app/models/admin_action.rb +119 -0
- data/app/models/rails_base/application_record.rb +22 -0
- data/app/models/rails_base/user_constants.rb +28 -0
- data/app/models/secret.rb +37 -0
- data/app/models/short_lived_data.rb +132 -0
- data/app/models/user.rb +143 -0
- data/app/services/rails_base/admin_risky_mfa_send.rb +80 -0
- data/app/services/rails_base/admin_update_attribute.rb +100 -0
- data/app/services/rails_base/authentication/authenticate_user.rb +28 -0
- data/app/services/rails_base/authentication/constants.rb +60 -0
- data/app/services/rails_base/authentication/decision_twofa_type.rb +76 -0
- data/app/services/rails_base/authentication/destroy_user.rb +45 -0
- data/app/services/rails_base/authentication/mfa_set_encrypt_token.rb +32 -0
- data/app/services/rails_base/authentication/mfa_validator.rb +88 -0
- data/app/services/rails_base/authentication/modify_password.rb +67 -0
- data/app/services/rails_base/authentication/send_forgot_password.rb +26 -0
- data/app/services/rails_base/authentication/send_login_mfa_to_user.rb +77 -0
- data/app/services/rails_base/authentication/send_verification_email.rb +103 -0
- data/app/services/rails_base/authentication/session_token_verifier.rb +31 -0
- data/app/services/rails_base/authentication/single_sign_on_create.rb +44 -0
- data/app/services/rails_base/authentication/single_sign_on_send.rb +101 -0
- data/app/services/rails_base/authentication/single_sign_on_verify.rb +42 -0
- data/app/services/rails_base/authentication/sso_verify_email.rb +43 -0
- data/app/services/rails_base/authentication/update_phone_send_verification.rb +46 -0
- data/app/services/rails_base/authentication/verify_forgot_password.rb +46 -0
- data/app/services/rails_base/email_change.rb +20 -0
- data/app/services/rails_base/encryption.rb +87 -0
- data/app/services/rails_base/name_change.rb +71 -0
- data/app/services/rails_base/service_base.rb +65 -0
- data/app/services/rails_base/service_logging.rb +23 -0
- data/app/views/layouts/rails_base/application.html.erb +185 -0
- data/app/views/layouts/rails_base/mailer.html.erb +13 -0
- data/app/views/layouts/rails_base/mailer.text.erb +1 -0
- data/app/views/new.html.erb +4 -0
- data/app/views/rails_base/admin/history.html.erb +26 -0
- data/app/views/rails_base/admin/index.html.erb +149 -0
- data/app/views/rails_base/admin/show_config.html.erb +18 -0
- data/app/views/rails_base/devise/confirmations/new.html.erb +16 -0
- data/app/views/rails_base/devise/mailer/confirmation_instructions.html.erb +5 -0
- data/app/views/rails_base/devise/mailer/email_changed.html.erb +7 -0
- data/app/views/rails_base/devise/mailer/password_change.html.erb +3 -0
- data/app/views/rails_base/devise/mailer/reset_password_instructions.html.erb +8 -0
- data/app/views/rails_base/devise/mailer/unlock_instructions.html.erb +7 -0
- data/app/views/rails_base/devise/passwords/edit.html.erb +25 -0
- data/app/views/rails_base/devise/passwords/new.html.erb +27 -0
- data/app/views/rails_base/devise/registrations/edit.html.erb +43 -0
- data/app/views/rails_base/devise/registrations/new.html.erb +123 -0
- data/app/views/rails_base/devise/sessions/new.html.erb +4 -0
- data/app/views/rails_base/devise/shared/_error_messages.html.erb +15 -0
- data/app/views/rails_base/devise/shared/_links.html.erb +25 -0
- data/app/views/rails_base/devise/unlocks/new.html.erb +16 -0
- data/app/views/rails_base/email_verification_mailer/email_verification.html.erb +25 -0
- data/app/views/rails_base/email_verification_mailer/event.html.erb +20 -0
- data/app/views/rails_base/email_verification_mailer/forgot_password.html.erb +22 -0
- data/app/views/rails_base/errors/internal_error.html.erb +1 -0
- data/app/views/rails_base/errors/not_found.html.erb +1 -0
- data/app/views/rails_base/errors/unacceptable.html.erb +1 -0
- data/app/views/rails_base/event_mailer/event.html.erb +10 -0
- data/app/views/rails_base/mfa_auth/mfa_code.html.erb +10 -0
- data/app/views/rails_base/secondary_authentication/after_email_login_session_new.html.erb +3 -0
- data/app/views/rails_base/secondary_authentication/forgot_password.html.erb +9 -0
- data/app/views/rails_base/secondary_authentication/remove_me.html.erb +1 -0
- data/app/views/rails_base/secondary_authentication/static.html.erb +5 -0
- data/app/views/rails_base/shared/_admin_actions_modal.html.erb +65 -0
- data/app/views/rails_base/shared/_admin_config_class.html.erb +52 -0
- data/app/views/rails_base/shared/_admin_history.html.erb +86 -0
- data/app/views/rails_base/shared/_admin_modify_email.html.erb +78 -0
- data/app/views/rails_base/shared/_admin_modify_name.html.erb +107 -0
- data/app/views/rails_base/shared/_admin_modify_phone.html.erb +87 -0
- data/app/views/rails_base/shared/_admin_modify_text.html.erb +35 -0
- data/app/views/rails_base/shared/_admin_risky_change.html.erb +57 -0
- data/app/views/rails_base/shared/_admin_risky_mfa.html.erb +74 -0
- data/app/views/rails_base/shared/_admin_selector_dropdown.html.erb +70 -0
- data/app/views/rails_base/shared/_admin_toggle_button.html.erb +72 -0
- data/app/views/rails_base/shared/_admin_warning_alert.html.erb +7 -0
- data/app/views/rails_base/shared/_appearance_mode_selector.html.erb +183 -0
- data/app/views/rails_base/shared/_custom_form_validation_javascript.html.erb +129 -0
- data/app/views/rails_base/shared/_enable_mfa_auth_modal.html.erb +105 -0
- data/app/views/rails_base/shared/_error_pages.html.erb +123 -0
- data/app/views/rails_base/shared/_logged_in_header.html.erb +123 -0
- data/app/views/rails_base/shared/_logged_out_header.html.erb +14 -0
- data/app/views/rails_base/shared/_mfa_input_layout.html.erb +5 -0
- data/app/views/rails_base/shared/_mfa_input_layout_default.html.erb +97 -0
- data/app/views/rails_base/shared/_mfa_input_layout_fallback.html.erb +55 -0
- data/app/views/rails_base/shared/_modify_mfa_auth_modal.html.erb +20 -0
- data/app/views/rails_base/shared/_password_confirm_javascript.html.erb +71 -0
- data/app/views/rails_base/shared/_reset_password_form.html.erb +111 -0
- data/app/views/rails_base/shared/_session_create_form.html.erb +32 -0
- data/app/views/rails_base/shared/_session_timeout_modal.html.erb +76 -0
- data/app/views/rails_base/switch_user/_widget.html.erb +5 -0
- data/app/views/rails_base/user_settings/_confirm_destroy_user.html.erb +42 -0
- data/app/views/rails_base/user_settings/_destroy_user.html.erb +106 -0
- data/app/views/rails_base/user_settings/_modify_name.html.erb +71 -0
- data/app/views/rails_base/user_settings/_modify_password.html.erb +101 -0
- data/app/views/rails_base/user_settings/_modify_password_update_password.html.erb +2 -0
- data/app/views/rails_base/user_settings/index.html.erb +54 -0
- data/config/initializers/01_rails_config.rb +19 -0
- data/config/initializers/admin_action_helper.rb +88 -0
- data/config/initializers/browser.rb +4 -0
- data/config/initializers/default_logged_in_headers.rb +23 -0
- data/config/initializers/devise.rb +314 -0
- data/config/initializers/encryption.rb +2 -0
- data/config/initializers/switch_user.rb +58 -0
- data/config/initializers/switch_user_helper.rb +29 -0
- data/config/locales/devise.en.yml +65 -0
- data/config/locales/en.yml +58 -0
- data/config/routes.rb +114 -0
- data/db/migrate/20210212175453_devise_create_rails_base_users.rb +56 -0
- data/db/migrate/20210212190537_create_rails_base_short_lived_data.rb +19 -0
- data/db/migrate/20210212192645_create_rails_base_secrets.rb +11 -0
- data/db/migrate/20210406015744_create_rails_base_admin_actions.rb +17 -0
- data/db/seeds.rb +23 -0
- data/lib/link_decision_helper.rb +71 -0
- data/lib/rails_base.rb +50 -0
- data/lib/rails_base/admin/action_cache.rb +99 -0
- data/lib/rails_base/admin/action_helper.rb +134 -0
- data/lib/rails_base/admin/default_index_tile.rb +176 -0
- data/lib/rails_base/admin/index_tile.rb +186 -0
- data/lib/rails_base/config.rb +52 -0
- data/lib/rails_base/configuration/active_job.rb +38 -0
- data/lib/rails_base/configuration/admin.rb +231 -0
- data/lib/rails_base/configuration/app.rb +52 -0
- data/lib/rails_base/configuration/appearance.rb +131 -0
- data/lib/rails_base/configuration/authentication.rb +37 -0
- data/lib/rails_base/configuration/base.rb +209 -0
- data/lib/rails_base/configuration/display/background_color.rb +25 -0
- data/lib/rails_base/configuration/display/btn_danger.rb +25 -0
- data/lib/rails_base/configuration/display/btn_dark.rb +25 -0
- data/lib/rails_base/configuration/display/btn_info.rb +25 -0
- data/lib/rails_base/configuration/display/btn_light.rb +25 -0
- data/lib/rails_base/configuration/display/btn_primary.rb +25 -0
- data/lib/rails_base/configuration/display/btn_secondary.rb +25 -0
- data/lib/rails_base/configuration/display/btn_success.rb +25 -0
- data/lib/rails_base/configuration/display/btn_warning.rb +25 -0
- data/lib/rails_base/configuration/display/footer.rb +54 -0
- data/lib/rails_base/configuration/display/navbar.rb +25 -0
- data/lib/rails_base/configuration/display/table_body.rb +25 -0
- data/lib/rails_base/configuration/display/table_header.rb +25 -0
- data/lib/rails_base/configuration/display/text.rb +26 -0
- data/lib/rails_base/configuration/exceptions_app.rb +25 -0
- data/lib/rails_base/configuration/login_behavior.rb +17 -0
- data/lib/rails_base/configuration/mailer.rb +116 -0
- data/lib/rails_base/configuration/mfa.rb +84 -0
- data/lib/rails_base/configuration/owner.rb +17 -0
- data/lib/rails_base/configuration/redis.rb +29 -0
- data/lib/rails_base/configuration/user.rb +43 -0
- data/lib/rails_base/engine.rb +51 -0
- data/lib/rails_base/version.rb +10 -0
- data/lib/tasks/rails_base_tasks.rake +4 -0
- data/lib/twilio_helper.rb +26 -0
- data/lib/velocity_limiter.rb +91 -0
- metadata +619 -0
@@ -0,0 +1,123 @@
|
|
1
|
+
<nav class="navbar navbar-expand-lg navbar-light bg-light">
|
2
|
+
<a class="navbar-brand" href="#"><%= RailsBase.config.app.web_title_logged_in(current_user)%></a>
|
3
|
+
<button class="navbar-toggler" type="button" data-toggle="collapse" data-target="#navbarSupportedContent" aria-controls="navbarSupportedContent" aria-expanded="false" aria-label="Toggle navigation">
|
4
|
+
<span class="navbar-toggler-icon"></span>
|
5
|
+
</button>
|
6
|
+
|
7
|
+
<div class="collapse navbar-collapse" id="navbarSupportedContent">
|
8
|
+
<ul class="navbar-nav mr-auto">
|
9
|
+
<% Rails.application.config.n_logged_in.each_with_index do |link_helper, index| %>
|
10
|
+
<% next unless link_helper.display?(current_user) %>
|
11
|
+
<li class="nav-item <%= 'active' if index==0 %>">
|
12
|
+
<a class="nav-link" href="<%= link_helper.url %>" <%= "target='_blank'" if link_helper.blank? %> >
|
13
|
+
<%= link_helper.title %>
|
14
|
+
<% if index==0 %>
|
15
|
+
<span class="sr-only">(current)</span>
|
16
|
+
<% end %>
|
17
|
+
</a>
|
18
|
+
</li>
|
19
|
+
<% end %>
|
20
|
+
</ul>
|
21
|
+
<% if defined?(@error_page)%>
|
22
|
+
<button onclick="goBack()" class="btn btn_warning">
|
23
|
+
← Return to Previous page
|
24
|
+
</button>
|
25
|
+
<%else%>
|
26
|
+
<button type="button" class="btn btn_secondary" data-toggle="modal" data-target="#settings_modal">
|
27
|
+
My Settings
|
28
|
+
</button>
|
29
|
+
<%end%>
|
30
|
+
</div>
|
31
|
+
</nav>
|
32
|
+
|
33
|
+
<!-- Modal -->
|
34
|
+
<div class="modal fade" id="settings_modal" tabindex="-1" role="dialog" aria-labelledby="appearance_mode_selectorTitle" aria-hidden="true">
|
35
|
+
<div class="modal-dialog modal-dialog-centered" role="document">
|
36
|
+
<div class="modal-content">
|
37
|
+
<div class="modal-header">
|
38
|
+
<h5 class="modal-title" id="appearance_mode_selectorTitle">My Settings</h5>
|
39
|
+
<button type="button" class="close" data-dismiss="modal" aria-label="Close">
|
40
|
+
<span aria-hidden="true">×</span>
|
41
|
+
</button>
|
42
|
+
</div>
|
43
|
+
<div class="modal-body ">
|
44
|
+
<div class='row'>
|
45
|
+
<div class='col'>
|
46
|
+
<% if RailsBase.config.mfa.enable? %>
|
47
|
+
<% if current_user.mfa_enabled %>
|
48
|
+
<button type="button" class="btn btn-block btn_info close-me" data-toggle="modal" data-target="#modifyMfamodal">
|
49
|
+
Modify 2fa Auth
|
50
|
+
</button>
|
51
|
+
<% else %>
|
52
|
+
<button type="button" class="btn btn-block btn_info close-me" data-toggle="modal" data-target="#enableMfamodal">
|
53
|
+
Enable 2fa Auth
|
54
|
+
</button>
|
55
|
+
<% end %>
|
56
|
+
<% end %>
|
57
|
+
</div>
|
58
|
+
</div>
|
59
|
+
</br>
|
60
|
+
<div class='row'>
|
61
|
+
<div class='col'>
|
62
|
+
<a class="btn btn_info btn-block" href="<%=RailsBase.url_routes.user_settings_path%>" role="button">Modify User</a>
|
63
|
+
</div>
|
64
|
+
</div>
|
65
|
+
</br>
|
66
|
+
<div class='row'>
|
67
|
+
<div class='col'>
|
68
|
+
<%= render partial: 'rails_base/shared/appearance_mode_selector', locals: { btn: 'btn-block', display: true } %>
|
69
|
+
</div>
|
70
|
+
</div>
|
71
|
+
</br>
|
72
|
+
<div class="dropdown-divider"></div>
|
73
|
+
<div class='row'>
|
74
|
+
<div class='col'>
|
75
|
+
<%= button_to 'Logout', RailsBase.url_routes.signout_path, method: :delete, class: 'btn btn_danger btn-block' %>
|
76
|
+
</div>
|
77
|
+
</div>
|
78
|
+
</div>
|
79
|
+
</div>
|
80
|
+
</div>
|
81
|
+
</div>
|
82
|
+
|
83
|
+
<% if RailsBase.config.mfa.enable? %>
|
84
|
+
<% if current_user.mfa_enabled %>
|
85
|
+
<%= render partial: 'rails_base/shared/modify_mfa_auth_modal'%>
|
86
|
+
<% else %>
|
87
|
+
<%= render partial: 'rails_base/shared/enable_mfa_auth_modal'%>
|
88
|
+
<% end %>
|
89
|
+
<% end %>
|
90
|
+
|
91
|
+
<% if @__admin_actions_array && @__admin_actions_array.present? %>
|
92
|
+
<%= render partial: 'rails_base/shared/admin_actions_modal'%>
|
93
|
+
<% end %>
|
94
|
+
|
95
|
+
<% if session[RailsBase::Authentication::Constants::ADMIN_REMEMBER_REASON].present? %>
|
96
|
+
<div class="alert alert-warning" role="alert">
|
97
|
+
<%= render partial: 'rails_base/shared/admin_warning_alert' %>
|
98
|
+
</div>
|
99
|
+
<% end %>
|
100
|
+
|
101
|
+
<% if RailsBase.config.auth.session_timeout %>
|
102
|
+
<% show_warning = RailsBase.config.auth.session_timeout_warning %>
|
103
|
+
<% if show_warning %>
|
104
|
+
<%= render partial: 'rails_base/shared/session_timeout_modal'%>
|
105
|
+
<% end %>
|
106
|
+
<script type="text/javascript">
|
107
|
+
<%
|
108
|
+
# this is to account for the delay
|
109
|
+
timeout = RailsBase.config.auth.session_timeout
|
110
|
+
%>
|
111
|
+
sessionManager.init(<%= timeout %>, '<%= RailsBase.url_routes.heartbeat_without_auth_path %>', '<%= RailsBase.url_routes.heartbeat_with_auth_path %>' ,$('meta[name="csrf-token"]').attr('content'), <%= show_warning %>)
|
112
|
+
|
113
|
+
$('.close-me').on('click', function (e) {
|
114
|
+
$("#settings_modal").modal('hide');
|
115
|
+
})
|
116
|
+
$('#settings_modal').on('shown.bs.modal', function (e) {
|
117
|
+
$('.navbar-collapse').collapse('hide');
|
118
|
+
});
|
119
|
+
</script>
|
120
|
+
<% end%>
|
121
|
+
|
122
|
+
|
123
|
+
|
@@ -0,0 +1,14 @@
|
|
1
|
+
<nav class="navbar navbar-expand-lg navbar-light bg-light">
|
2
|
+
<a class="navbar-brand" href="#"><%= RailsBase.config.app.web_title_logged_out %></a>
|
3
|
+
<button class="navbar-toggler" type="button" data-toggle="collapse" data-target="#navbarSupportedContent" aria-controls="navbarSupportedContent" aria-expanded="false" aria-label="Toggle navigation">
|
4
|
+
<span class="navbar-toggler-icon"></span>
|
5
|
+
</button>
|
6
|
+
|
7
|
+
<div class="collapse navbar-collapse" id="navbarSupportedContent">
|
8
|
+
<div class="mr-auto">
|
9
|
+
</div>
|
10
|
+
<a class="btn btn_primary my-2 my-sm-0" href="<%=Rails.application.routes.url_helpers.new_user_registration_path%>" role="button">Sign Up</a>
|
11
|
+
</div>
|
12
|
+
</nav>
|
13
|
+
|
14
|
+
<%= render partial: 'rails_base/shared/appearance_mode_selector', locals: { btn: 'btn', display: false } %>
|
@@ -0,0 +1,5 @@
|
|
1
|
+
<% if !mfa_fallback? %>
|
2
|
+
<%= render partial: 'rails_base/shared/mfa_input_layout_fallback', locals: { url: url, size: size, masked_phone: masked_phone}%>
|
3
|
+
<% else %>
|
4
|
+
<%= render partial: 'rails_base/shared/mfa_input_layout_default', locals: { url: url, size: size, masked_phone: masked_phone}%>
|
5
|
+
<% end %>
|
@@ -0,0 +1,97 @@
|
|
1
|
+
<%= form_for :mfa, url: url do |f| %>
|
2
|
+
<div class="form-group text-center">
|
3
|
+
<div class="text-center" style="font-size: <%= size %>px">
|
4
|
+
Please enter the MFA code you received at <%= masked_phone %>
|
5
|
+
</div>
|
6
|
+
<span>
|
7
|
+
<div class style="font-size: <%= size %>px;">
|
8
|
+
<% RailsBase::Authentication::Constants::MFA_LENGTH.times do |index| %>
|
9
|
+
<%= f.text_field "#{RailsBase::Authentication::Constants::MV_BASE_NAME}#{index}", type: "tel", style: "caret-color: transparent; text-align: center;", class: "numbersOnly digit mfa-validator", size: 1, maxlength: 1, autofocus: index==0 %>
|
10
|
+
<% end %>
|
11
|
+
</div>
|
12
|
+
</span>
|
13
|
+
</div>
|
14
|
+
<div class="text-center">
|
15
|
+
<% unless defined?(disable) %>
|
16
|
+
<%= f.submit "submit", class: "submit-mfa btn btn_success", style: "width: 50%;", disabled: true %>
|
17
|
+
<%end%>
|
18
|
+
</div>
|
19
|
+
<% end %>
|
20
|
+
|
21
|
+
|
22
|
+
<script type="text/javascript">
|
23
|
+
$('.mfa-validator').keyup(function(event){
|
24
|
+
this.value = this.value.replace(/[^0-9\.]/g,'');
|
25
|
+
var valid_char = this.value != '';
|
26
|
+
if(valid_char){
|
27
|
+
var next_mfa_id = get_next_mfa($(this).attr('id'));
|
28
|
+
if(next_mfa_id==undefined){
|
29
|
+
$(this).focus();
|
30
|
+
return
|
31
|
+
}
|
32
|
+
$(`#${next_mfa_id}`).focus();
|
33
|
+
} else {
|
34
|
+
$(this).focus();
|
35
|
+
}
|
36
|
+
submit_button_prop();
|
37
|
+
})
|
38
|
+
|
39
|
+
$(".mfa-validator").click(function(event){
|
40
|
+
var next_mfa_id = $(this).attr('id');
|
41
|
+
$(`#${next_mfa_id}`).val('');
|
42
|
+
while (next_mfa_id = get_next_mfa(next_mfa_id)) {
|
43
|
+
$(`#${next_mfa_id}`).val('');
|
44
|
+
}
|
45
|
+
$('.submit-mfa').prop('disabled', true);
|
46
|
+
});
|
47
|
+
|
48
|
+
function submit_button_prop(){
|
49
|
+
var disabled = false
|
50
|
+
var inputs = $(".mfa-validator");
|
51
|
+
for(var i = 0; i < inputs.length; i++){
|
52
|
+
if($(inputs[i]).val().length==0){
|
53
|
+
disabled = true;
|
54
|
+
break;
|
55
|
+
}
|
56
|
+
}
|
57
|
+
$('.submit-mfa').prop('disabled', disabled);
|
58
|
+
}
|
59
|
+
|
60
|
+
function get_next_mfa(elem_id) {
|
61
|
+
var max_length = <%= RailsBase::Authentication::Constants::MFA_LENGTH %>;
|
62
|
+
var elem_array = elem_id.split('_');
|
63
|
+
var last_elem = elem_array.pop();
|
64
|
+
if(isNaN(last_elem)){
|
65
|
+
return undefined
|
66
|
+
}
|
67
|
+
var last_elem_as_int = parseInt(last_elem)
|
68
|
+
if(last_elem_as_int>=max_length){
|
69
|
+
return undefined
|
70
|
+
}
|
71
|
+
elem_array.push(last_elem_as_int + 1)
|
72
|
+
return elem_array.join('_')
|
73
|
+
}
|
74
|
+
|
75
|
+
function paste_mfa_input(pastedData){
|
76
|
+
var pastedDataOg = e.originalEvent.clipboardData.getData('text');
|
77
|
+
if(pastedDataOg.length != <%= RailsBase::Authentication::Constants::MFA_LENGTH %>){
|
78
|
+
return;
|
79
|
+
}
|
80
|
+
pastedData = pastedDataOg.split('');
|
81
|
+
pastedDataIsNotANumber = pastedData.every(function (pos) {
|
82
|
+
return isNaN(pos)
|
83
|
+
});
|
84
|
+
|
85
|
+
if(pastedDataIsNotANumber) {
|
86
|
+
return;
|
87
|
+
}
|
88
|
+
|
89
|
+
<% # We know pasted data is correct length %>
|
90
|
+
<% # We know pasted data is all numbers %>
|
91
|
+
<% # Paste it into the correct boxes %>
|
92
|
+
|
93
|
+
<% RailsBase::Authentication::Constants::MFA_LENGTH.times do |index| %>
|
94
|
+
$("#<%= "mfa_#{RailsBase::Authentication::Constants::MV_BASE_NAME}#{index}"%>").val(pastedData[<%= index %>])
|
95
|
+
<% end %>
|
96
|
+
}
|
97
|
+
</script>
|
@@ -0,0 +1,55 @@
|
|
1
|
+
<%= form_for :mfa, url: url, html: { class: 'mfa_submission', novalidate: true} do |f| %>
|
2
|
+
<div class="form-group text-center">
|
3
|
+
<div class="text-center" style="font-size: <%= size %>px">
|
4
|
+
Please enter the MFA code you received at <%= masked_phone %>
|
5
|
+
</div>
|
6
|
+
<div class='row justify-content-center' style="font-size: <%= size %>px;">
|
7
|
+
<div class="col-xs-2">
|
8
|
+
<%= text_field_tag 'alternate_mfa', nil, maxlength: RailsBase::Authentication::Constants::MFA_LENGTH, class: 'text-center form-control', autofocus: true, type: "tel", style: "font-size:#{size}px;" %>
|
9
|
+
<div class="invalid-feedback">
|
10
|
+
2FA code must be <%= RailsBase::Authentication::Constants::MFA_LENGTH %> numbers
|
11
|
+
</div>
|
12
|
+
</div>
|
13
|
+
</div>
|
14
|
+
<% RailsBase::Authentication::Constants::MFA_LENGTH.times do |index| %>
|
15
|
+
<%= f.hidden_field "#{RailsBase::Authentication::Constants::MV_BASE_NAME}#{index}", style: "caret-color: transparent; text-align: center;", class: "numbersOnly digit mfa-validator form-control", size: 1, maxlength: 1, autofocus: index==0 %>
|
16
|
+
<% end %>
|
17
|
+
</div>
|
18
|
+
<div class="text-center">
|
19
|
+
<%= f.submit "submit", class: "submit-mfa btn btn_success", style: "width: 50%;"%>
|
20
|
+
</div>
|
21
|
+
<% end %>
|
22
|
+
|
23
|
+
<script type="text/javascript">
|
24
|
+
$('.mfa_submission').submit(function( event ) {
|
25
|
+
console.log($('#alternate_mfa').val())
|
26
|
+
var length_match = $('#alternate_mfa').val().length === <%= RailsBase::Authentication::Constants::MFA_LENGTH %>;
|
27
|
+
var valid_data = !invalidate_data($('#alternate_mfa').val());
|
28
|
+
if (length_match && valid_data){
|
29
|
+
set_values($('#alternate_mfa').val())
|
30
|
+
return
|
31
|
+
}
|
32
|
+
|
33
|
+
event.preventDefault();
|
34
|
+
event.stopPropagation();
|
35
|
+
$('#alternate_mfa').addClass('is-invalid');
|
36
|
+
$('#alternate_mfa').val('')
|
37
|
+
$('#alternate_mfa').focus();
|
38
|
+
});
|
39
|
+
|
40
|
+
function set_values(data) {
|
41
|
+
var dataArr = data.split('')
|
42
|
+
<% RailsBase::Authentication::Constants::MFA_LENGTH.times do |index| %>
|
43
|
+
$('#<%="mfa_#{RailsBase::Authentication::Constants::MV_BASE_NAME}#{index}"%>').val(data[<%=index%>])
|
44
|
+
<% end %>
|
45
|
+
}
|
46
|
+
|
47
|
+
function invalidate_data(data) {
|
48
|
+
dataArr = data.split('');
|
49
|
+
var dataIsNotANumber = dataArr.every(function (pos) {
|
50
|
+
return isNaN(pos)
|
51
|
+
});
|
52
|
+
console.log(dataIsNotANumber)
|
53
|
+
return dataIsNotANumber
|
54
|
+
}
|
55
|
+
</script>
|
@@ -0,0 +1,20 @@
|
|
1
|
+
<% confirm = "Disabling 2fa on your account will make it more vulnerable. Are you sure you want to disable two factor authentication via SMS text?" %>
|
2
|
+
|
3
|
+
<div class="modal fade" id="modifyMfamodal" tabindex="-1" role="dialog" aria-labelledby="exampleModalLabel" aria-hidden="true">
|
4
|
+
<div class="modal-dialog modal-lg" role="document">
|
5
|
+
<div class="modal-content">
|
6
|
+
<div class="modal-header">
|
7
|
+
<h5 class="modal-title" id="exampleModalLabel">Disable MFA via SMS</h5>
|
8
|
+
<button type="button" class="close" data-dismiss="modal" aria-label="Close">
|
9
|
+
<span aria-hidden="true">×</span>
|
10
|
+
</button>
|
11
|
+
</div>
|
12
|
+
<div class="modal-body">
|
13
|
+
<%= button_to "Disable 2fa", RailsBase.url_routes.remove_phone_registration_mfa_path, data: { confirm: confirm }, method: :delete, class: "btn btn_danger btn-block" %>
|
14
|
+
</div>
|
15
|
+
<div class="modal-footer">
|
16
|
+
<button type="button" class="mr-auto btn btn_secondary" data-dismiss="modal">Close</button>
|
17
|
+
</div>
|
18
|
+
</div>
|
19
|
+
</div>
|
20
|
+
</div>
|
@@ -0,0 +1,71 @@
|
|
1
|
+
<script type="text/javascript">
|
2
|
+
function user_password_validity(){
|
3
|
+
var value = $('#<%= id_password %>').val()
|
4
|
+
if (value < <%= RailsBase::Authentication::Constants::MP_MIN_LENGTH %>){
|
5
|
+
return false
|
6
|
+
}
|
7
|
+
|
8
|
+
var numbers = value.replace(/[a-zA-Z]/g,'')
|
9
|
+
if(numbers.length < <%= RailsBase::Authentication::Constants::MP_MIN_NUMS %>){
|
10
|
+
return false
|
11
|
+
}
|
12
|
+
|
13
|
+
var chars = value.replace(/[0-9]/g,'')
|
14
|
+
if(chars.length < <%= RailsBase::Authentication::Constants::MP_MIN_ALPHA %>){
|
15
|
+
return false
|
16
|
+
}
|
17
|
+
|
18
|
+
var unknown = value.replace(/[0-9a-zA-Z]/g,'')
|
19
|
+
if(unknown.length > 0) {
|
20
|
+
return false
|
21
|
+
}
|
22
|
+
true
|
23
|
+
};
|
24
|
+
|
25
|
+
$('#<%= id_password %>').focus(function() {
|
26
|
+
if(<%= enable_submit %>){
|
27
|
+
$('.<%= submit_klass %>').prop('disabled', false);
|
28
|
+
};
|
29
|
+
$('#<%= id_password_conf %>').val('')
|
30
|
+
$('#<%= id_password_conf %>').removeClass('is-invalid')
|
31
|
+
$('#<%= id_password_conf %>').removeClass('is-valid')
|
32
|
+
$('#<%= id_password %>').removeClass('is-valid')
|
33
|
+
$('#<%= id_password %>').removeClass('is-invalid')
|
34
|
+
});
|
35
|
+
|
36
|
+
$('#<%= id_password %>').blur(function() {
|
37
|
+
if (user_password_validity() === false) {
|
38
|
+
$('#<%= id_password %>').focus();
|
39
|
+
$('#<%= id_password %>').val('');
|
40
|
+
$('#<%= id_password %>').addClass('is-invalid');
|
41
|
+
} else {
|
42
|
+
$('#<%= id_password %>').removeClass('is-invalid');
|
43
|
+
if(<%= enable_submit %>){
|
44
|
+
$('.<%= submit_klass %>').prop('disabled', false);
|
45
|
+
};
|
46
|
+
}
|
47
|
+
});
|
48
|
+
|
49
|
+
$('.<%= form_klass %>').submit(function( event ) {
|
50
|
+
if ($('#<%= id_password_conf %>').val() === $('#<%= id_password %>').val()){
|
51
|
+
return
|
52
|
+
}
|
53
|
+
|
54
|
+
event.preventDefault();
|
55
|
+
event.stopPropagation();
|
56
|
+
$('#<%= id_password_conf %>').addClass('is-invalid');
|
57
|
+
$('#<%= id_password_conf %>').val('')
|
58
|
+
$('#<%= id_password_conf %>').focus();
|
59
|
+
});
|
60
|
+
|
61
|
+
$('#<%= id_password_conf %>').keyup(function(event){
|
62
|
+
if ($('#<%= id_password_conf %>').val() === $('#<%= id_password %>').val()){
|
63
|
+
$('#<%= id_password_conf %>').addClass('is-valid');
|
64
|
+
$('#<%= id_password_conf %>').removeClass('is-invalid');
|
65
|
+
$('#<%= id_password %>').addClass('is-valid');
|
66
|
+
} else {
|
67
|
+
$('#<%= id_password_conf %>').removeClass('is-valid')
|
68
|
+
$('#<%= id_password %>').removeClass('is-valid');
|
69
|
+
}
|
70
|
+
});
|
71
|
+
</script>
|
@@ -0,0 +1,111 @@
|
|
1
|
+
<%= form_for(:user, as: :user, url: url, html: { method: :post, class: 'password-reset-needs-validation', id: 'password-reset-confirmation', novalidate: true }) do |f| %>
|
2
|
+
<div class="field form-group row">
|
3
|
+
<div class="col-md-10 offset-md-1">
|
4
|
+
<%= f.password_field :password, autofocus: true, autocomplete: "new-password", placeholder: "Password", class: 'form-control', required: true %>
|
5
|
+
<div class="invalid-feedback">
|
6
|
+
<%= RailsBase::Authentication::Constants::MP_REQ_MESSAGE %>
|
7
|
+
</div>
|
8
|
+
</div>
|
9
|
+
</div>
|
10
|
+
<div class="field form-group row">
|
11
|
+
<div class="col-md-10 offset-md-1">
|
12
|
+
<%= f.password_field :password_confirmation, autocomplete: "new-password", placeholder: "Password Confirmation", class: 'form-control', required: true %>
|
13
|
+
<div class="invalid-feedback">
|
14
|
+
Password Confirmation does not match Password
|
15
|
+
</div>
|
16
|
+
<div class="valid-feedback">
|
17
|
+
Password and Password Confirmation match!
|
18
|
+
</div>
|
19
|
+
</div>
|
20
|
+
</div>
|
21
|
+
|
22
|
+
<% if sign_in_flow %>
|
23
|
+
<div class="actions row">
|
24
|
+
<div class="col-md-10 offset-md-1 text-center">
|
25
|
+
<div class="row">
|
26
|
+
<div class="col-md-9">
|
27
|
+
<%= f.submit "Reset Password", class: "reset-password-submit btn btn_success btn-block", disabled: true %>
|
28
|
+
</div>
|
29
|
+
<div class="col-md-3">
|
30
|
+
<a class="btn btn_primary btn-block" href="<%=RailsBase.url_routes.new_user_session_path%>" role="button">Sign in</a>
|
31
|
+
</div>
|
32
|
+
</div>
|
33
|
+
</div>
|
34
|
+
</div>
|
35
|
+
<% else %>
|
36
|
+
<div class="actions row">
|
37
|
+
<div class="col-md-10 offset-md-1 text-center">
|
38
|
+
<%= f.submit "Reset Password", class: "btn btn_success btn-block" %>
|
39
|
+
</div>
|
40
|
+
</div>
|
41
|
+
<% end %>
|
42
|
+
<% end %>
|
43
|
+
|
44
|
+
|
45
|
+
<script type="text/javascript">
|
46
|
+
function user_password_validity(){
|
47
|
+
var value = $('#user_password').val()
|
48
|
+
if (value < <%= RailsBase::Authentication::Constants::MP_MIN_LENGTH %>){
|
49
|
+
return false
|
50
|
+
}
|
51
|
+
|
52
|
+
var numbers = value.replace(/[a-zA-Z]/g,'')
|
53
|
+
if(numbers.length < <%= RailsBase::Authentication::Constants::MP_MIN_NUMS %>){
|
54
|
+
return false
|
55
|
+
}
|
56
|
+
|
57
|
+
var chars = value.replace(/[0-9]/g,'')
|
58
|
+
if(chars.length < <%= RailsBase::Authentication::Constants::MP_MIN_ALPHA %>){
|
59
|
+
return false
|
60
|
+
}
|
61
|
+
|
62
|
+
var unknown = value.replace(/[0-9a-zA-Z]/g,'')
|
63
|
+
if(unknown.length > 0) {
|
64
|
+
return false
|
65
|
+
}
|
66
|
+
true
|
67
|
+
};
|
68
|
+
|
69
|
+
$('#user_password').focus(function() {
|
70
|
+
$('.reset-password-submit').prop('disabled', true);
|
71
|
+
$('#user_password_confirmation').val('')
|
72
|
+
$('#user_password_confirmation').removeClass('is-invalid')
|
73
|
+
$('#user_password_confirmation').removeClass('is-valid')
|
74
|
+
$('#user_password').removeClass('is-valid')
|
75
|
+
$('#user_password').removeClass('is-invalid')
|
76
|
+
});
|
77
|
+
|
78
|
+
$('#user_password').blur(function() {
|
79
|
+
if (user_password_validity() === false) {
|
80
|
+
$('#user_password').focus();
|
81
|
+
$('#user_password').val('');
|
82
|
+
$('#user_password').addClass('is-invalid');
|
83
|
+
} else {
|
84
|
+
$('#user_password').removeClass('is-invalid');
|
85
|
+
$('.reset-password-submit').prop('disabled', false);
|
86
|
+
}
|
87
|
+
});
|
88
|
+
|
89
|
+
$('.password-reset-needs-validation').submit(function( event ) {
|
90
|
+
if ($('#user_password_confirmation').val() === $('#user_password').val()){
|
91
|
+
return
|
92
|
+
}
|
93
|
+
|
94
|
+
event.preventDefault();
|
95
|
+
event.stopPropagation();
|
96
|
+
$('#user_password_confirmation').addClass('is-invalid');
|
97
|
+
$('#user_password_confirmation').val('')
|
98
|
+
$('#user_password_confirmation').focus();
|
99
|
+
});
|
100
|
+
|
101
|
+
$("#user_password_confirmation").keyup(function(event){
|
102
|
+
if ($('#user_password_confirmation').val() === $('#user_password').val()){
|
103
|
+
$('#user_password_confirmation').addClass('is-valid');
|
104
|
+
$('#user_password_confirmation').removeClass('is-invalid');
|
105
|
+
$('#user_password').addClass('is-valid');
|
106
|
+
} else {
|
107
|
+
$('#user_password_confirmation').removeClass('is-valid')
|
108
|
+
$('#user_password').removeClass('is-valid');
|
109
|
+
}
|
110
|
+
});
|
111
|
+
</script>
|