diff --git a/cypress/e2e/common/ui/kebab.ts b/cypress/e2e/common/ui/kebab.ts index c324fdf01..69ace054e 100644 --- a/cypress/e2e/common/ui/kebab.ts +++ b/cypress/e2e/common/ui/kebab.ts @@ -11,3 +11,10 @@ Then("I should see {string} kebab menu expanded", (kebab: string) => { Then("I should see {string} kebab menu collapsed", (kebab: string) => { cy.dataCy(kebab).should("have.attr", "aria-expanded", "false"); }); + +Then( + "I should see the {string} kebab menu item is disabled", + (item: string) => { + cy.dataCy(item).find("button").should("be.disabled"); + } +); diff --git a/cypress/e2e/common/ui/select.ts b/cypress/e2e/common/ui/select.ts index d5fca43f9..541bce574 100644 --- a/cypress/e2e/common/ui/select.ts +++ b/cypress/e2e/common/ui/select.ts @@ -17,7 +17,10 @@ Then( export const selectOption = (option: string, selector: string) => { cy.dataCy(selector + "-toggle").click(); cy.dataCy(selector + "-toggle").should("have.attr", "aria-expanded", "true"); - cy.dataCy(selector + "-" + option).click(); + cy.dataCy(selector + "-" + option) + .find("button") + .should("be.visible") + .click(); }; export const isOptionSelected = (option: string, selector: string) => { diff --git a/cypress/e2e/otp_tokens/otp_token_management.ts b/cypress/e2e/otp_tokens/otp_token_management.ts new file mode 100644 index 000000000..c1cc600a2 --- /dev/null +++ b/cypress/e2e/otp_tokens/otp_token_management.ts @@ -0,0 +1,62 @@ +import { Given } from "@badeball/cypress-cucumber-preprocessor"; +import { IPA_PREFIX } from "../../support/utils"; + +Given( + "OTP token {string} exists for user {string} with type {string} and description {string}", + (tokenId: string, owner: string, type: string, description: string) => { + cy.ipa({ + command: "otptoken-add", + name: tokenId, + specificOptions: `--owner="${owner}" --desc="${description}" --type=${type}`, + }); + } +); + +Given( + "an OTP token exists for user {string} with type {string} and description {string}", + (owner: string, type: string, description: string) => { + cy.exec( + `${IPA_PREFIX} otptoken-add --owner="${owner}" --desc="${description}" --type=${type}` + ); + } +); + +Given("I delete OTP token {string}", (tokenId: string) => { + cy.ipa({ + command: "otptoken-del", + name: tokenId, + }); +}); + +Given("I delete OTP token with description {string}", (description: string) => { + cy.exec(`${IPA_PREFIX} otptoken-find --desc="${description}" --raw`, { + failOnNonZeroExit: false, + }).then((result) => { + const match = result.stdout.match(/ipatokenuniqueid:\s*(\S+)/); + if (match) { + cy.ipa({ + command: "otptoken-del", + name: match[1], + }); + } + }); +}); + +Given("OTP token {string} is disabled", (tokenId: string) => { + cy.ipa({ + command: "otptoken-mod", + name: tokenId, + specificOptions: "--disabled=TRUE", + }); +}); + +Given( + "user {string} is manager of OTP token {string}", + (userName: string, tokenId: string) => { + cy.ipa({ + command: "otptoken-add-managedby", + name: tokenId, + specificOptions: `--users="${userName}"`, + }); + } +); diff --git a/cypress/e2e/otp_tokens/otp_tokens.feature b/cypress/e2e/otp_tokens/otp_tokens.feature new file mode 100644 index 000000000..dbc2e6653 --- /dev/null +++ b/cypress/e2e/otp_tokens/otp_tokens.feature @@ -0,0 +1,177 @@ +Feature: OTP tokens manipulation + Create, search, enable, disable and delete OTP tokens + + @seed + Scenario: Prep: Create user for TOTP test + Given User "otpuser" "OTP" "User" exists and is using password "Secret123" + + @test + Scenario: Add a new TOTP token with owner + Given I am logged in as admin + And I am on "otp-tokens" page + + When I click on the "otp-tokens-button-add" button + Then I should see "add-otp-token-modal" modal + And I should see the "modal-radio-totp" radio button is selected + + When I type in the "modal-textbox-description" textbox text "totp_token" + Then I should see "totp_token" in the "modal-textbox-description" textbox + + When I select "otpuser" option in the "modal-select-owner" selector + Then I should see "otpuser" option in the "modal-select-owner" selector + + When I click on the "modal-button-add" button + Then I should not see "add-otp-token-modal" modal + And I should see "configure-your-token-modal" modal + + When I click on the "modal-button-ok" button + Then I should not see "configure-your-token-modal" modal + And I should see "totp_token" entry in the data table with ID "otp-tokens-table" + + @cleanup + Scenario: Cleanup: Delete test data after TOTP test + Given I delete OTP token with description "totp_token" + And I delete user "otpuser" + + @seed + Scenario: Prep: Create user for HOTP test + Given User "otpuser" "OTP" "User" exists and is using password "Secret123" + + @test + Scenario: Add a new HOTP token with owner + Given I am logged in as admin + And I am on "otp-tokens" page + + When I click on the "otp-tokens-button-add" button + Then I should see "add-otp-token-modal" modal + + When I click on the "modal-radio-hotp" radio button + Then I should see the "modal-radio-hotp" radio button is selected + And I should see the "modal-radio-totp" radio button is not selected + + When I type in the "modal-textbox-description" textbox text "hotp_token" + Then I should see "hotp_token" in the "modal-textbox-description" textbox + + When I select "otpuser" option in the "modal-select-owner" selector + Then I should see "otpuser" option in the "modal-select-owner" selector + + When I click on the "modal-button-add" button + Then I should not see "add-otp-token-modal" modal + And I should see "configure-your-token-modal" modal + + When I click on the "modal-button-ok" button + Then I should not see "configure-your-token-modal" modal + And I should see "hotp_token" entry in the data table with ID "otp-tokens-table" + + @cleanup + Scenario: Cleanup: Delete test data after HOTP test + Given I delete OTP token with description "hotp_token" + And I delete user "otpuser" + + @seed + Scenario: Prep: Create user and token for search test + Given User "otpuser" "OTP" "User" exists and is using password "Secret123" + And an OTP token exists for user "otpuser" with type "totp" and description "search_token" + + @test + Scenario: TOTP is the default token type + Given I am logged in as admin + And I am on "otp-tokens" page + + When I click on the "otp-tokens-button-add" button + Then I should see "add-otp-token-modal" modal + And I should see the "modal-radio-totp" radio button is selected + And I should see the "modal-radio-hotp" radio button is not selected + + When I click on the "modal-button-cancel" button + Then I should not see "add-otp-token-modal" modal + + @cleanup + Scenario: Cleanup: Delete search test data + Given I delete OTP token with description "search_token" + And I delete user "otpuser" + + @seed + Scenario: Prep: Create user and token for disable test + Given User "otpuser" "OTP" "User" exists and is using password "Secret123" + And an OTP token exists for user "otpuser" with type "totp" and description "disable_token" + + @test + Scenario: Disable an OTP token + Given I am logged in as admin + And I am on "otp-tokens" page + + When I search for "otpuser" in the data table + Then I should see "otpuser" entry in the data table with ID "otp-tokens-table" + + When I select "otpuser" entry in the data table with ID "otp-tokens-table" + Then I should see "otpuser" entry selected in the data table with ID "otp-tokens-table" + + When I click on the "otp-tokens-button-disable" button + Then I should see "enable-disable-otp-tokens-modal" modal + + When I click on the "modal-button-ok" button + Then I should not see "enable-disable-otp-tokens-modal" modal + And I should see "success" alert + + @cleanup + Scenario: Cleanup: Delete disable test data + Given I delete OTP token with description "disable_token" + And I delete user "otpuser" + + @seed + Scenario: Seed: Create user and disabled token for enable test + Given User "otpuser" "OTP" "User" exists and is using password "Secret123" + And OTP token "enable_token" exists for user "otpuser" with type "totp" and description "enable_token" + And OTP token "enable_token" is disabled + + @test + Scenario: Enable a disabled OTP token + Given I am logged in as admin + And I am on "otp-tokens" page + + When I search for "otpuser" in the data table + Then I should see "otpuser" entry in the data table with ID "otp-tokens-table" + + When I select "otpuser" entry in the data table with ID "otp-tokens-table" + Then I should see "otpuser" entry selected in the data table with ID "otp-tokens-table" + + When I click on the "otp-tokens-button-enable" button + Then I should see "enable-disable-otp-tokens-modal" modal + + When I click on the "modal-button-ok" button + Then I should not see "enable-disable-otp-tokens-modal" modal + And I should see "success" alert + + @cleanup + Scenario: Cleanup: Delete enable test data + Given I delete OTP token "enable_token" + And I delete user "otpuser" + + @seed + Scenario: Seed: Create user and OTP token for delete test + Given User "otpuser" "OTP" "User" exists and is using password "Secret123" + And an OTP token exists for user "otpuser" with type "totp" and description "delete_token" + + @test + Scenario: Delete an OTP token + Given I am logged in as admin + And I am on "otp-tokens" page + + When I search for "otpuser" in the data table + Then I should see "otpuser" entry in the data table with ID "otp-tokens-table" + + When I select "otpuser" entry in the data table with ID "otp-tokens-table" + Then I should see "otpuser" entry selected in the data table with ID "otp-tokens-table" + + When I click on the "otp-tokens-button-delete" button + Then I should see "delete-otp-tokens-modal" modal + + When I click on the "modal-button-ok" button + Then I should see "remove-otp-tokens-success" alert + And I should not see "delete-otp-tokens-modal" modal + + @cleanup + Scenario: Cleanup: Delete 'delete_token' test data + Given I delete OTP token with description "delete_token" + And I delete user "otpuser" diff --git a/cypress/e2e/otp_tokens/otp_tokens_managedby.feature b/cypress/e2e/otp_tokens/otp_tokens_managedby.feature new file mode 100644 index 000000000..a0ce1b943 --- /dev/null +++ b/cypress/e2e/otp_tokens/otp_tokens_managedby.feature @@ -0,0 +1,72 @@ +Feature: OTP tokens - Is managed by page + Manage OTP token managers (users) + + @seed + Scenario: Prep: Create users and OTP token for add manager test + Given User "otpmgdbyuser" "OTPManaged" "User" exists and is using password "Secret123" + And User "otpmanager" "OTP" "Manager" exists and is using password "Secret123" + And OTP token "managedby_token" exists for user "otpmgdbyuser" with type "totp" and description "managedby_token" + + @test + Scenario: Add a user manager to OTP token + Given I am logged in as admin + And I am on "otp-tokens/managedby_token" page + + When I click on the "otp-tokens-tab-managedby" tab + Then I should see "otp-tokens-tab-managedby" tab selected + + When I click on the "member-of-button-add" button + Then I should see "member-of-add-modal" modal + And I should see "item-otpmanager" dual list item on the left + + When I click on "item-otpmanager" dual list item + Then I should see "item-otpmanager" dual list item selected + When I click on the "dual-list-add-selected" button + Then I should see "item-otpmanager" dual list item on the right + + When I click on the "modal-button-add" button + Then I should not see "member-of-add-modal" modal + And I should see "add-managedby-success" alert + + When I search for "otpmanager" in the members table + Then I should see "otpmanager" entry in the data table + + @cleanup + Scenario: Cleanup: Delete add manager test data + Given I delete OTP token "managedby_token" + And I delete user "otpmgdbyuser" + And I delete user "otpmanager" + + @seed + Scenario: Prep: Create users, OTP token, and manager for remove test + Given User "otpmgdbyuser" "OTPManaged" "User" exists and is using password "Secret123" + And User "otpmanager" "OTP" "Manager" exists and is using password "Secret123" + And OTP token "managedby_token" exists for user "otpmgdbyuser" with type "totp" and description "managedby_token" + And user "otpmanager" is manager of OTP token "managedby_token" + + @test + Scenario: Remove a user manager from OTP token + Given I am logged in as admin + And I am on "otp-tokens/managedby_token" page + + When I click on the "otp-tokens-tab-managedby" tab + Then I should see "otp-tokens-tab-managedby" tab selected + + When I select entry "otpmanager" in the members table + Then I should see "otpmanager" entry selected in the data table + + When I click on the "member-of-button-delete" button + Then I should see "member-of-delete-modal" modal + + When I click on the "modal-button-delete" button + Then I should not see "member-of-delete-modal" modal + And I should see "remove-managedby-success" alert + + When I search for "otpmanager" in the members table + Then I should not see "otpmanager" entry in the data table + + @cleanup + Scenario: Cleanup: Delete remove manager test data + Given I delete OTP token "managedby_token" + And I delete user "otpmgdbyuser" + And I delete user "otpmanager" diff --git a/cypress/e2e/otp_tokens/otp_tokens_settings.feature b/cypress/e2e/otp_tokens/otp_tokens_settings.feature new file mode 100644 index 000000000..cc9dc238f --- /dev/null +++ b/cypress/e2e/otp_tokens/otp_tokens_settings.feature @@ -0,0 +1,153 @@ +Feature: OTP tokens - Settings page + Modify OTP token settings + + @seed + Scenario: Prep: Create user and OTP token for set description test + Given User "otpsettingsuser" "OTP" "Settings" exists and is using password "Secret123" + And OTP token "settings_token" exists for user "otpsettingsuser" with type "totp" and description "settings_token" + + @test + Scenario: Set Description field + Given I am logged in as admin + And I am on "otp-tokens/settings_token" page + + When I type in the "otp-tokens-tab-settings-textbox-description" textbox text "Updated description" + Then I should see "Updated description" in the "otp-tokens-tab-settings-textbox-description" textbox + And I should see the "otp-tokens-tab-settings-button-save" button is enabled + And I should see the "otp-tokens-tab-settings-button-revert" button is enabled + + When I click on the "otp-tokens-tab-settings-button-save" button + Then I should see "success" alert + + @cleanup + Scenario: Cleanup: Delete set description test data + Given I delete OTP token "settings_token" + And I delete user "otpsettingsuser" + + @seed + Scenario: Prep: Create user and OTP token for set vendor test + Given User "otpsettingsuser" "OTP" "Settings" exists and is using password "Secret123" + And OTP token "settings_token" exists for user "otpsettingsuser" with type "totp" and description "settings_token" + + @test + Scenario: Set Vendor field + Given I am logged in as admin + And I am on "otp-tokens/settings_token" page + + When I type in the "otp-tokens-tab-settings-textbox-ipatokenvendor" textbox text "TestVendor" + Then I should see "TestVendor" in the "otp-tokens-tab-settings-textbox-ipatokenvendor" textbox + And I should see the "otp-tokens-tab-settings-button-save" button is enabled + + When I click on the "otp-tokens-tab-settings-button-save" button + Then I should see "success" alert + + @cleanup + Scenario: Cleanup: Delete set vendor test data + Given I delete OTP token "settings_token" + And I delete user "otpsettingsuser" + + @seed + Scenario: Prep: Create user and OTP token for revert test + Given User "otpsettingsuser" "OTP" "Settings" exists and is using password "Secret123" + And OTP token "settings_token" exists for user "otpsettingsuser" with type "totp" and description "settings_token" + + @test + Scenario: Revert changes + Given I am logged in as admin + And I am on "otp-tokens/settings_token" page + + When I type in the "otp-tokens-tab-settings-textbox-description" textbox text "Reverted description" + Then I should see "Reverted description" in the "otp-tokens-tab-settings-textbox-description" textbox + And I should see the "otp-tokens-tab-settings-button-revert" button is enabled + + When I click on the "otp-tokens-tab-settings-button-revert" button + Then I should see "revert-success" alert + And I should see the "otp-tokens-tab-settings-button-save" button is disabled + And I should see the "otp-tokens-tab-settings-button-revert" button is disabled + + @cleanup + Scenario: Cleanup: Delete revert test data + Given I delete OTP token "settings_token" + And I delete user "otpsettingsuser" + + @seed + Scenario: Prep: Create user and OTP token for disable test + Given User "otpsettingsuser" "OTP" "Settings" exists and is using password "Secret123" + And OTP token "settings_token" exists for user "otpsettingsuser" with type "totp" and description "settings_token" + + @test + Scenario: Disable token from settings kebab + Given I am logged in as admin + And I am on "otp-tokens/settings_token" page + + When I click on the "otp-tokens-tab-settings-kebab" kebab menu + Then I should see "otp-tokens-tab-settings-kebab" kebab menu expanded + + When I click on the "otp-tokens-tab-settings-kebab-disable" button + Then I should see "enable-disable-otp-tokens-modal" modal + + When I click on the "modal-button-ok" button + Then I should not see "enable-disable-otp-tokens-modal" modal + And I should see "success" alert + + When I click on the "otp-tokens-tab-settings-kebab" kebab menu + Then I should see "otp-tokens-tab-settings-kebab" kebab menu expanded + And I should see the "otp-tokens-tab-settings-kebab-disable" kebab menu item is disabled + + @cleanup + Scenario: Cleanup: Delete disable test data + Given I delete OTP token "settings_token" + And I delete user "otpsettingsuser" + + @seed + Scenario: Prep: Create user and disabled OTP token for enable test + Given User "otpsettingsuser" "OTP" "Settings" exists and is using password "Secret123" + And OTP token "settings_token" exists for user "otpsettingsuser" with type "totp" and description "settings_token" + And OTP token "settings_token" is disabled + + @test + Scenario: Enable token from settings kebab + Given I am logged in as admin + And I am on "otp-tokens/settings_token" page + + When I click on the "otp-tokens-tab-settings-kebab" kebab menu + Then I should see "otp-tokens-tab-settings-kebab" kebab menu expanded + + When I click on the "otp-tokens-tab-settings-kebab-enable" button + Then I should see "enable-disable-otp-tokens-modal" modal + + When I click on the "modal-button-ok" button + Then I should not see "enable-disable-otp-tokens-modal" modal + And I should see "success" alert + + When I click on the "otp-tokens-tab-settings-kebab" kebab menu + Then I should see "otp-tokens-tab-settings-kebab" kebab menu expanded + And I should see the "otp-tokens-tab-settings-kebab-enable" kebab menu item is disabled + + @cleanup + Scenario: Cleanup: Delete enable test data + Given I delete OTP token "settings_token" + And I delete user "otpsettingsuser" + + @seed + Scenario: Prep: Create user and OTP token for delete test + Given User "otpsettingsuser" "OTP" "Settings" exists and is using password "Secret123" + And OTP token "settings_token" exists for user "otpsettingsuser" with type "totp" and description "settings_token" + + @test + Scenario: Delete token from settings kebab + Given I am logged in as admin + And I am on "otp-tokens/settings_token" page + + When I click on the "otp-tokens-tab-settings-kebab" kebab menu + Then I should see "otp-tokens-tab-settings-kebab" kebab menu expanded + + When I click on the "otp-tokens-tab-settings-kebab-delete" button + Then I should see "delete-otp-tokens-modal" modal + + When I click on the "modal-button-ok" button + Then I should see "remove-otp-tokens-success" alert + + @cleanup + Scenario: Cleanup: Delete remaining test data + Given I delete user "otpsettingsuser" diff --git a/cypress/support/commands.ts b/cypress/support/commands.ts index d6ac84b90..51ffb1bfa 100644 --- a/cypress/support/commands.ts +++ b/cypress/support/commands.ts @@ -50,6 +50,7 @@ Cypress.Commands.add( command, name, specificOptions, + options, }: IpaCommandParams): Cypress.Chainable => { const safeName = name.replace(/"/g, '\\"'); let ipaCmd = `${IPA_PREFIX} ${command} "${safeName}"`; @@ -57,6 +58,6 @@ Cypress.Commands.add( ipaCmd = `${IPA_PREFIX} ${command} "${safeName}" ${specificOptions}`; } - return cy.exec(ipaCmd); + return cy.exec(ipaCmd, options); } ); diff --git a/src/pages/OtpTokens/OtpTokensSettings.tsx b/src/pages/OtpTokens/OtpTokensSettings.tsx index 34e35899a..d99c77b71 100644 --- a/src/pages/OtpTokens/OtpTokensSettings.tsx +++ b/src/pages/OtpTokens/OtpTokensSettings.tsx @@ -324,7 +324,6 @@ const OtpTokensSettings = (props: OtpTokensSettingsProps) => { @@ -338,12 +337,7 @@ const OtpTokensSettings = (props: OtpTokensSettingsProps) => { metadata={props.metadata} /> - + { @@ -372,7 +365,6 @@ const OtpTokensSettings = (props: OtpTokensSettingsProps) => { @@ -391,7 +383,6 @@ const OtpTokensSettings = (props: OtpTokensSettingsProps) => { @@ -407,7 +398,6 @@ const OtpTokensSettings = (props: OtpTokensSettingsProps) => { @@ -425,7 +415,6 @@ const OtpTokensSettings = (props: OtpTokensSettingsProps) => { @@ -442,7 +431,6 @@ const OtpTokensSettings = (props: OtpTokensSettingsProps) => { @@ -459,7 +447,6 @@ const OtpTokensSettings = (props: OtpTokensSettingsProps) => { @@ -476,7 +463,6 @@ const OtpTokensSettings = (props: OtpTokensSettingsProps) => { @@ -493,7 +479,6 @@ const OtpTokensSettings = (props: OtpTokensSettingsProps) => { @@ -509,7 +494,6 @@ const OtpTokensSettings = (props: OtpTokensSettingsProps) => { @@ -525,7 +509,6 @@ const OtpTokensSettings = (props: OtpTokensSettingsProps) => {