From 0a3f1852c6e0e403271cdf24980497428ed3a2b6 Mon Sep 17 00:00:00 2001 From: Penar Musaraj <pmusaraj@gmail.com> Date: Sun, 3 Sep 2023 22:07:20 -0400 Subject: [PATCH] DEV: Add system test for user security keys (#23372) --- .../app/templates/preferences/security.hbs | 5 ++- spec/support/system_helpers.rb | 5 +-- spec/system/custom_sidebar_sections_spec.rb | 1 - .../page_objects/components/user_menu.rb | 19 ++++++++ .../pages/user_preferences_security.rb | 19 ++++++++ .../user_preferences_interface_spec.rb | 0 .../user_preferences_navigation_spec.rb | 0 .../user_preferences_security_spec.rb | 45 +++++++++++++++++++ 8 files changed, 88 insertions(+), 6 deletions(-) create mode 100644 spec/system/page_objects/pages/user_preferences_security.rb rename spec/system/{ => user_page}/user_preferences_interface_spec.rb (100%) rename spec/system/{ => user_page}/user_preferences_navigation_spec.rb (100%) create mode 100644 spec/system/user_page/user_preferences_security_spec.rb diff --git a/app/assets/javascripts/discourse/app/templates/preferences/security.hbs b/app/assets/javascripts/discourse/app/templates/preferences/security.hbs index 41fe1a92bbe..8803ac7d9ce 100644 --- a/app/assets/javascripts/discourse/app/templates/preferences/security.hbs +++ b/app/assets/javascripts/discourse/app/templates/preferences/security.hbs @@ -27,7 +27,10 @@ {{/unless}} <div class="controls pref-second-factor"> {{#if this.isCurrentUser}} - <LinkTo @route="preferences.second-factor" class="btn btn-default"> + <LinkTo + @route="preferences.second-factor" + class="btn btn-default btn-second-factor" + > {{d-icon "lock"}} <span>{{i18n "user.second_factor.enable"}}</span> </LinkTo> diff --git a/spec/support/system_helpers.rb b/spec/support/system_helpers.rb index 08e7d571e8c..95e0a65ea38 100644 --- a/spec/support/system_helpers.rb +++ b/spec/support/system_helpers.rb @@ -22,12 +22,9 @@ module SystemHelpers expect(page).to have_content("Signed in to #{user.encoded_username} successfully") end - def sign_out - delete File.join(GlobalSetting.relative_url_root || "", "/session") - end - def setup_system_test SiteSetting.login_required = false + SiteSetting.has_login_hint = false SiteSetting.content_security_policy = false SiteSetting.force_hostname = Capybara.server_host SiteSetting.port = Capybara.server_port diff --git a/spec/system/custom_sidebar_sections_spec.rb b/spec/system/custom_sidebar_sections_spec.rb index b55fa7460b7..bf09c1a3cf6 100644 --- a/spec/system/custom_sidebar_sections_spec.rb +++ b/spec/system/custom_sidebar_sections_spec.rb @@ -109,7 +109,6 @@ describe "Custom sidebar sections", type: :system do section_modal.save expect(sidebar).to have_section("My section") - take_screenshot expect(sidebar).to have_section_link("Faq", target: "_blank") end diff --git a/spec/system/page_objects/components/user_menu.rb b/spec/system/page_objects/components/user_menu.rb index 7edfebda1b5..2b72dfc4069 100644 --- a/spec/system/page_objects/components/user_menu.rb +++ b/spec/system/page_objects/components/user_menu.rb @@ -15,6 +15,25 @@ module PageObjects self end + def click_profile_tab + click_link("user-menu-button-profile") + has_css?("#quick-access-profile") + self + end + + def click_logout_button + find("#quick-access-profile .logout .btn").click + has_css?(".d-header .login-button") + self + end + + def sign_out + open + click_profile_tab + click_logout_button + self + end + def has_group_mentioned_notification?(topic, user_that_mentioned_group, group_mentioned) expect(find("#quick-access-replies .group-mentioned").text).to eq( "#{user_that_mentioned_group.username} @#{group_mentioned.name} #{topic.title}", diff --git a/spec/system/page_objects/pages/user_preferences_security.rb b/spec/system/page_objects/pages/user_preferences_security.rb new file mode 100644 index 00000000000..8b50bc1d999 --- /dev/null +++ b/spec/system/page_objects/pages/user_preferences_security.rb @@ -0,0 +1,19 @@ +# frozen_string_literal: true + +module PageObjects + module Pages + class UserPreferencesSecurity < PageObjects::Pages::Base + def visit(user) + page.visit("/u/#{user.username}/preferences/security") + self + end + + def visit_second_factor(password) + click_link(class: "btn-second-factor") + + find(".second-factor input#password").fill_in(with: password) + find(".second-factor .btn-primary").click + end + end + end +end diff --git a/spec/system/user_preferences_interface_spec.rb b/spec/system/user_page/user_preferences_interface_spec.rb similarity index 100% rename from spec/system/user_preferences_interface_spec.rb rename to spec/system/user_page/user_preferences_interface_spec.rb diff --git a/spec/system/user_preferences_navigation_spec.rb b/spec/system/user_page/user_preferences_navigation_spec.rb similarity index 100% rename from spec/system/user_preferences_navigation_spec.rb rename to spec/system/user_page/user_preferences_navigation_spec.rb diff --git a/spec/system/user_page/user_preferences_security_spec.rb b/spec/system/user_page/user_preferences_security_spec.rb new file mode 100644 index 00000000000..3f691416015 --- /dev/null +++ b/spec/system/user_page/user_preferences_security_spec.rb @@ -0,0 +1,45 @@ +# frozen_string_literal: true + +describe "User preferences for Security", type: :system do + fab!(:password) { "kungfukenny" } + fab!(:email) { "email@user.com" } + fab!(:user) { Fabricate(:user, email: email, password: password) } + let(:user_preferences_security_page) { PageObjects::Pages::UserPreferencesSecurity.new } + let(:user_menu) { PageObjects::Components::UserMenu.new } + + before do + user.activate + sign_in(user) + end + + describe "Security keys" do + it "adds a 2F security key and logs in with it" do + # simulate browser credential authorization + options = ::Selenium::WebDriver::VirtualAuthenticatorOptions.new + page.driver.browser.add_virtual_authenticator(options) + + user_preferences_security_page.visit(user) + user_preferences_security_page.visit_second_factor(password) + + find(".security-key .new-security-key").click + expect(user_preferences_security_page).to have_css("input#security-key-name") + + find(".modal-body input#security-key-name").fill_in(with: "First Key") + find(".add-security-key").click + + expect(user_preferences_security_page).to have_css(".security-key .second-factor-item") + + user_menu.sign_out + + # login flow + find(".d-header .login-button").click + find("input#login-account-name").fill_in(with: user.username) + find("input#login-account-password").fill_in(with: password) + + find(".modal-footer .btn-primary").click + find("#security-key .btn-primary").click + + expect(page).to have_css(".header-dropdown-toggle.current-user") + end + end +end