Skip to content

Conversation

@nachandr
Copy link
Collaborator

@nachandr nachandr commented Oct 21, 2025

In 8.0.1, the 'Import' top kebab menu option on the App Inventory page was replaced by 'Import applications from CSV'. Currently, only a sub text is matched , but the not the entire text. So, I've added a new function to match the exact text and updated the test to use the new function.

Summary by CodeRabbit

  • Tests
    • Added a reusable selector-text verification utility to improve assertion clarity, accuracy, and reliability across UI checks.
    • Updated top-action menu tests to use the new verifier and explicitly check menu entries: Import, Manage application imports, Manage credentials, and Delete, improving test stability and reducing false positives.

@coderabbitai
Copy link

coderabbitai bot commented Oct 21, 2025

Walkthrough

Replaced direct text-existence checks in cypress/e2e/models/migration/applicationinventory/analysis.ts with the new helper verifySelectorText, using the shared actionMenuItem selector and values from appInventoryKebab. Added verifySelectorText(expectedText: string, selector: string, shouldExist: boolean) to cypress/utils/utils.ts (queries elements by selector, trims textContent, and asserts exact-match presence/absence). Extended appInventoryKebab in cypress/e2e/types/constants.ts with manageCredentials = "Manage credentials" and delete = "Delete". No public/exported signatures were changed.

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~20 minutes

  • cypress/e2e/models/migration/applicationinventory/analysis.ts — confirm correct kebab enum members and selector usage for each menu item.
  • cypress/utils/utils.ts — verify DOM selection, trimming, exact-match comparison, and negative assertion behavior.
  • cypress/e2e/types/constants.ts — confirm spelling/spacing of new enum entries.

Possibly related PRs

Suggested reviewers

  • sshveta
  • ibragins
  • abrugaro

Pre-merge checks and finishing touches

❌ Failed checks (1 warning)
Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 33.33% which is insufficient. The required threshold is 80.00%. You can run @coderabbitai generate docstrings to improve docstring coverage.
✅ Passed checks (2 passed)
Check name Status Explanation
Description Check ✅ Passed The PR description provides substantive, relevant information explaining the purpose and context of the changes. It clearly describes the problem (the App Inventory menu option changed from "Import" to "Import applications from CSV" in version 8.0.1, and the existing code only matched subtext rather than the full label) and the solution (a new function for exact text matching and updated tests). The description is neither off-topic nor vague. While the template includes instructions for requesting reviews from specific team members, the core descriptive content addressing what changed and why is complete and informative.
Title Check ✅ Passed The title "Add a new function to match selector text" accurately describes the primary change in the pull request. A new exported function verifySelectorText was added to cypress/utils/utils.ts that matches text content within selected elements, which directly aligns with the title. The title is specific and clear, avoiding vague language while remaining concise. While the PR also includes secondary changes (updating the test file to use the new function and adding enum members), the title appropriately focuses on the main deliverable, which is the new utility function. This is an acceptable level of specificity for a PR title, as it captures the core change without needing to enumerate every detail.
✨ Finishing touches
  • 📝 Generate docstrings
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

🧹 Nitpick comments (1)
cypress/e2e/models/migration/applicationinventory/analysis.ts (1)

27-27: LGTM with dependency on fixing matchText.

The refactor from doesExistText to matchText improves precision by using anchored regex patterns for exact text matching. The imports and usage pattern are correct—passing menu item text and RBAC rule booleans to conditionally verify presence/absence of menu items.

Note: The matchText function in utils.ts has a critical bug (unused toBePresent parameter) that must be fixed for these assertions to work correctly.

Optional: Consider using constants for all menu items for consistency:

// In constants file, add:
export const appInventoryKebab = {
    import: "Import",
    manageImports: "Manage application imports",
    manageCredentials: "Manage credentials",  // Add this
    delete: "Delete",  // Add this
};

// Then use:
matchText(appInventoryKebab.manageCredentials, rbacRules["Top action menu"]["Manage credentials"]);
matchText(appInventoryKebab.delete, rbacRules["Top action menu"]["Delete"]);

Also applies to: 40-40, 499-505

📜 Review details

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between be88656 and 4ef6972.

📒 Files selected for processing (2)
  • cypress/e2e/models/migration/applicationinventory/analysis.ts (3 hunks)
  • cypress/utils/utils.ts (1 hunks)
🧰 Additional context used
🧬 Code graph analysis (1)
cypress/e2e/models/migration/applicationinventory/analysis.ts (1)
cypress/utils/utils.ts (1)
  • matchText (1602-1604)
🪛 ast-grep (0.39.6)
cypress/utils/utils.ts

[warning] 1602-1602: Regular expression constructed from variable input detected. This can lead to Regular Expression Denial of Service (ReDoS) attacks if the variable contains malicious patterns. Use libraries like 'recheck' to validate regex safety or use static patterns.
Context: new RegExp(^${str}$)
Note: [CWE-1333] Inefficient Regular Expression Complexity [REFERENCES]
- https://owasp.org/www-community/attacks/Regular_expression_Denial_of_Service_-_ReDoS
- https://cwe.mitre.org/data/definitions/1333.html

(regexp-from-variable)

⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
  • GitHub Check: e2e-main / e2e-ui-integration-tests

Signed-off-by: Nandini Chandra <[email protected]>
@nachandr nachandr force-pushed the main_architect_test branch from 4ef6972 to a9b15c7 Compare October 22, 2025 05:59
@nachandr nachandr changed the title Add a new fn to match strings Add a new fn to match exact text Oct 22, 2025
@nachandr nachandr changed the title Add a new fn to match exact text Add a new function to match exact text Oct 22, 2025
@nachandr
Copy link
Collaborator Author

PRarchitect

@nachandr nachandr requested a review from ibragins October 22, 2025 06:05
@github-project-automation github-project-automation bot moved this to 🆕 New in Planning Oct 22, 2025
@nachandr nachandr requested a review from abrugaro October 22, 2025 14:59
Copy link
Collaborator

@ibragins ibragins left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This function can be useful, but I prefer to use old approach in this particular case

Comment on lines 499 to 505
matchText(appInventoryKebab.import, rbacRules["Top action menu"]["Import"]);
matchText(
appInventoryKebab.manageImports,
rbacRules["Top action menu"]["Manage application imports"]
);
doesExistText("Manage credentials", rbacRules["Top action menu"]["Manage credentials"]);
doesExistText("Delete", rbacRules["Top action menu"]["Delete"]);
matchText("Manage credentials", rbacRules["Top action menu"]["Manage credentials"]);
matchText("Delete", rbacRules["Top action menu"]["Delete"]);
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

In this particular case I would like to see exact match, not something matching regular expression. Even a typo can be missed in case of using REGEXP.

@sshveta
Copy link
Collaborator

sshveta commented Oct 23, 2025

Hi @nachandr If we are going to keep both methods then let's rename it to something that others can find and use .
Example : doesExactTextExist()
so that we know which of the two methods to use and add a comment on which condition this method should be used.

@ibragins
Copy link
Collaborator

Hi @nachandr If we are going to keep both methods then let's rename it to something that others can find and use . Example : doesExactTextExist() so that we know which of the two methods to use and add a comment on which condition this method should be used.

Hi @sshveta , IIUC Nandini's method is matching not the whole text, but regular expression instead. So that is OLD method should be renamed

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

📜 Review details

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between a9b15c7 and ce93709.

📒 Files selected for processing (2)
  • cypress/e2e/models/migration/applicationinventory/analysis.ts (4 hunks)
  • cypress/utils/utils.ts (1 hunks)
🚧 Files skipped from review as they are similar to previous changes (1)
  • cypress/utils/utils.ts
🧰 Additional context used
🧬 Code graph analysis (1)
cypress/e2e/models/migration/applicationinventory/analysis.ts (1)
cypress/e2e/views/common.view.ts (1)
  • actionMenuItem (58-58)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
  • GitHub Check: e2e-main / e2e-ui-integration-tests
🔇 Additional comments (1)
cypress/e2e/models/migration/applicationinventory/analysis.ts (1)

27-27: LGTM! Import changes align with exact text matching approach.

The addition of matchText, appInventoryKebab, and actionMenuItem imports supports the transition from substring to exact text matching, which addresses the issue where label changes (e.g., "Import" → "Import applications from CSV") broke existing tests.

Also applies to: 40-40, 90-90

@nachandr nachandr force-pushed the main_architect_test branch from ce93709 to f7f37dc Compare October 28, 2025 01:11
Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

♻️ Duplicate comments (1)
cypress/e2e/models/migration/applicationinventory/analysis.ts (1)

499-514: Address hardcoded "Delete" string and enum definition gap.

Line 514 uses a hardcoded "Delete" string instead of a constant from the appInventoryKebab enum. The enum in cypress/e2e/types/constants.ts (lines 248-252) currently lacks a delete property and must be extended.

Required changes:

  1. Add to appInventoryKebab enum in cypress/e2e/types/constants.ts:
 export enum appInventoryKebab {
     manageImports = "Manage application imports",
     import = "Import applications from CSV",
     managecredentials = "Manage credentials",
+    delete = "Delete",
 }
  1. Update line 514 in cypress/e2e/models/migration/applicationinventory/analysis.ts:
-            verifySelectorText("Delete", actionMenuItem, rbacRules["Top action menu"]["Delete"]);
+            verifySelectorText(kebab.delete, actionMenuItem, rbacRules["Top action menu"]["Delete"]);
  1. Optional: Add JSDoc to verifySelectorText in cypress/utils/utils.ts (line 1603) to document the exact-match behavior and clarify when to use this versus regex-based alternatives.
📜 Review details

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between ce93709 and f7f37dc.

📒 Files selected for processing (3)
  • cypress/e2e/models/migration/applicationinventory/analysis.ts (3 hunks)
  • cypress/e2e/types/constants.ts (1 hunks)
  • cypress/utils/utils.ts (1 hunks)
🚧 Files skipped from review as they are similar to previous changes (1)
  • cypress/utils/utils.ts
🧰 Additional context used
🧬 Code graph analysis (1)
cypress/e2e/models/migration/applicationinventory/analysis.ts (2)
cypress/utils/utils.ts (1)
  • verifySelectorText (1603-1619)
cypress/e2e/views/common.view.ts (1)
  • actionMenuItem (58-58)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
  • GitHub Check: e2e-main / e2e-ui-integration-tests
🔇 Additional comments (1)
cypress/e2e/models/migration/applicationinventory/analysis.ts (1)

34-34: LGTM on the new imports.

The imports for verifySelectorText, the kebab alias for appInventoryKebab, and actionMenuItem are correctly added and appropriately used in the updated validation logic.

Also applies to: 40-40, 90-90

@nachandr nachandr force-pushed the main_architect_test branch from f7f37dc to 73f0442 Compare October 28, 2025 04:49
Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 0

🧹 Nitpick comments (2)
cypress/utils/utils.ts (2)

1602-1619: Consider a more descriptive function name that indicates exact text matching.

Based on the PR discussion, reviewers suggested a clearer, more discoverable name such as doesExactTextExist() or verifyExactSelectorText() to distinguish this function from other text-matching utilities like doesExistText() which uses regex matching. The current name doesn't clearly convey that it performs exact text matching rather than substring or pattern matching.

Apply this diff to use a clearer name:

-export function verifySelectorText(
+export function verifyExactSelectorText(
     expectedText: string,
     selector: string,
     toBePresent: boolean
 ): void {
     cy.get(selector).then(($elements) => {
         const texts = Array.from($elements).map((el) => el.textContent?.trim() ?? "");
         const matched = texts.includes(expectedText);

         if (toBePresent) {
             expect(matched, `Expected one of the elements to have exact text "${expectedText}"`).to
                 .be.true;
         } else {
             expect(matched, `Expected no element to have exact text "${expectedText}"`).to.be.false;
         }
     });
 }

Don't forget to update the import and usage in cypress/e2e/models/migration/applicationinventory/analysis.ts to match the new name.

Based on learnings


1602-1619: Add documentation explaining when to use this function versus other text-matching utilities.

As noted in the PR discussion, developers need guidance on when to use this exact text matcher versus other similar functions like doesExistText() (regex-based) or validateTextPresence() (substring-based). Adding a JSDoc comment would improve discoverability and prevent confusion.

Apply this diff to add documentation:

+/**
+ * Verifies that at least one element matched by the selector contains the exact expected text.
+ * Unlike doesExistText() which uses regex matching or validateTextPresence() which checks substrings,
+ * this function performs exact text matching after trimming whitespace.
+ * 
+ * Use this when you need to verify exact menu labels, button text, or other UI strings that must match precisely.
+ * 
+ * @param expectedText - The exact text to match (after trimming)
+ * @param selector - CSS selector to find elements
+ * @param toBePresent - true to assert presence, false to assert absence
+ */
 export function verifySelectorText(
     expectedText: string,
     selector: string,
     toBePresent: boolean
 ): void {

Based on learnings

📜 Review details

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between f7f37dc and 73f0442.

📒 Files selected for processing (3)
  • cypress/e2e/models/migration/applicationinventory/analysis.ts (3 hunks)
  • cypress/e2e/types/constants.ts (1 hunks)
  • cypress/utils/utils.ts (1 hunks)
🚧 Files skipped from review as they are similar to previous changes (1)
  • cypress/e2e/models/migration/applicationinventory/analysis.ts
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
  • GitHub Check: e2e-main / e2e-ui-integration-tests
🔇 Additional comments (1)
cypress/e2e/types/constants.ts (1)

251-252: LGTM!

The enum additions follow proper naming conventions with camelCase (manageCredentials) consistent with the existing manageImports member, and both requested members (manageCredentials and delete) have been added correctly.

Comment on lines 1602 to 1620
// Function to verify if selector has exact text
export function verifySelectorText(
expectedText: string,
selector: string,
toBePresent: boolean
): void {
cy.get(selector).then(($elements) => {
const texts = Array.from($elements).map((el) => el.textContent?.trim() ?? "");
const matched = texts.includes(expectedText);

if (toBePresent) {
expect(matched, `Expected one of the elements to have exact text "${expectedText}"`).to
.be.true;
} else {
expect(matched, `Expected no element to have exact text "${expectedText}"`).to.be.false;
}
});
}

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

cy.get(selector).should(toBePresent ? "have.text" : "not.have.text", expectedText);

This is how I'd do this if you want to use selector

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is how it can work without selector, regexp is indeed required here

export function doesExistText(str: string, toBePresent: boolean): void {
  const regex = new RegExp(`^${str}$`);
  cy.contains(regex).should(toBePresent ? "exist" : "not.exist");
}

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

cy.get(selector).should(toBePresent ? "have.text" : "not.have.text", expectedText);

This is how I'd do this if you want to use selector

Thanks @ibragins .

  1. The option without the regex also works well.
  2. With this option, `cy.get(selector).should("have.text") checks the concatenated text of all matched elements, not per element.

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@nachandr definitely element by particular selector should be unique

@nachandr nachandr force-pushed the main_architect_test branch 2 times, most recently from 98cf1a4 to 9c25f3a Compare October 29, 2025 15:54
Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

🧹 Nitpick comments (1)
cypress/utils/utils.ts (1)

1608-1618: Consider using Cypress's retry-able assertions for better test stability.

The current implementation uses cy.get().then() with imperative expect(), which won't retry if elements are still loading or text is being updated. This can cause flaky tests in dynamic UIs.

Apply this diff to leverage Cypress's built-in retry-ability:

 export function verifySelectorText(
     expectedText: string,
     selector: string,
     toBePresent: boolean
 ): void {
-    cy.get(selector).then(($elements) => {
-        const texts = Array.from($elements).map((el) => el.textContent?.trim() ?? "");
-        const matched = texts.includes(expectedText);
-
-        if (toBePresent) {
-            expect(matched, `Expected one of the elements to have exact text "${expectedText}"`).to
-                .be.true;
-        } else {
-            expect(matched, `Expected no element to have exact text "${expectedText}"`).to.be.false;
-        }
-    });
+    cy.get(selector).should(($elements) => {
+        const texts = Array.from($elements).map((el) => el.textContent?.trim() ?? "");
+        const matched = texts.includes(expectedText);
+
+        if (toBePresent) {
+            expect(matched, `Expected one of the elements to have exact text "${expectedText}"`).to
+                .be.true;
+        } else {
+            expect(matched, `Expected no element to have exact text "${expectedText}"`).to.be.false;
+        }
+    });
 }

This change enables automatic retrying until the assertion passes or times out, improving reliability when dealing with asynchronously rendered content.

📜 Review details

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 98cf1a4 and 9c25f3a.

📒 Files selected for processing (3)
  • cypress/e2e/models/migration/applicationinventory/analysis.ts (3 hunks)
  • cypress/e2e/types/constants.ts (1 hunks)
  • cypress/utils/utils.ts (1 hunks)
🚧 Files skipped from review as they are similar to previous changes (1)
  • cypress/e2e/models/migration/applicationinventory/analysis.ts
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
  • GitHub Check: e2e-main / e2e-ui-integration-tests
🔇 Additional comments (1)
cypress/e2e/types/constants.ts (1)

251-252: LGTM! Naming consistency issue resolved.

The enum additions follow proper camelCase naming convention (consistent with manageImports on line 249), and adding these constants eliminates hardcoded strings in the codebase.

@nachandr nachandr force-pushed the main_architect_test branch from 9c25f3a to 6c2a5ff Compare October 29, 2025 16:12
@nachandr
Copy link
Collaborator Author

PR_1708

@nachandr nachandr requested a review from ibragins October 29, 2025 16:16
@nachandr nachandr force-pushed the main_architect_test branch from 6c2a5ff to c442029 Compare October 29, 2025 16:24
Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

📜 Review details

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 6c2a5ff and c442029.

📒 Files selected for processing (3)
  • cypress/e2e/models/migration/applicationinventory/analysis.ts (3 hunks)
  • cypress/e2e/types/constants.ts (1 hunks)
  • cypress/utils/utils.ts (1 hunks)
🚧 Files skipped from review as they are similar to previous changes (1)
  • cypress/e2e/models/migration/applicationinventory/analysis.ts
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
  • GitHub Check: e2e-main / e2e-ui-integration-tests
🔇 Additional comments (2)
cypress/utils/utils.ts (1)

1602-1610: LGTM! Well-documented function.

The JSDoc documentation clearly explains the function's purpose and distinguishes it from the existing doesExistText helper. This addresses the previous review feedback about adding documentation.

cypress/e2e/types/constants.ts (1)

251-252: LGTM! Consistent naming convention.

The new enum members follow the existing naming pattern: camelCase for multi-word actions (manageCredentials) and lowercase for single-word actions (delete). The string values correctly represent the menu labels from the App Inventory kebab menu.

Signed-off-by: Nandini Chandra <[email protected]>
@nachandr nachandr force-pushed the main_architect_test branch from c442029 to f22ebc9 Compare October 29, 2025 16:44
Copy link
Collaborator

@ibragins ibragins left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM

@nachandr nachandr changed the title Add a new function to match exact text Add a new function to match selector text Oct 29, 2025
@nachandr nachandr merged commit 9136486 into konveyor:main Oct 29, 2025
12 checks passed
@github-project-automation github-project-automation bot moved this from 🆕 New to ✅ Done in Planning Oct 29, 2025
@nachandr nachandr self-assigned this Oct 29, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

Status: ✅ Done

Development

Successfully merging this pull request may close these issues.

3 participants