Skip to content

Add e2e test for sorting #2883

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 5 commits into
base: main
Choose a base branch
from
Open

Add e2e test for sorting #2883

wants to merge 5 commits into from

Conversation

hashicc
Copy link
Collaborator

@hashicc hashicc commented Jun 11, 2025

Description

This pr adds a e2e test for the sorting capability in our tables. The roles resource was chosen because it has support for custom sorting and regular attribute sorting.

🎟️ Jira ticket

Checklist

- [ ] I have added before and after screenshots for UI changes
- [ ] I have added JSON response output for API changes
- [ ] I have added steps to reproduce and test for bug fixes in the description

  • I have commented on my code, particularly in hard-to-understand areas
  • My changes generate no new warnings
  • I have added tests that prove my fix is effective or that my feature works

Copy link

vercel bot commented Jun 11, 2025

The latest updates on your projects. Learn more about Vercel for Git β†—οΈŽ

Name Status Preview Comments Updated (UTC)
boundary-ui βœ… Ready (Inspect) Visit Preview πŸ’¬ Add feedback Jun 18, 2025 2:20am
boundary-ui-desktop βœ… Ready (Inspect) Visit Preview πŸ’¬ Add feedback Jun 18, 2025 2:20am

@hashicc hashicc force-pushed the e2e-test-sorting branch from 7757281 to bdda7c4 Compare June 11, 2025 20:24
@hashicc hashicc force-pushed the e2e-test-sorting branch from 7db8aa1 to 3763bcc Compare June 11, 2025 20:48
@hashicc hashicc force-pushed the e2e-test-sorting branch from 3763bcc to a5702a9 Compare June 12, 2025 16:06
@hashicc hashicc force-pushed the e2e-test-sorting branch from a5702a9 to 234fb89 Compare June 12, 2025 16:37
@hashicc hashicc marked this pull request as ready for review June 12, 2025 18:06
@hashicc hashicc requested a review from a team as a code owner June 12, 2025 18:06
@hashicc hashicc force-pushed the e2e-test-sorting branch from 234fb89 to 396cc20 Compare June 12, 2025 18:06

test('Sorting works', { tag: ['@ce', '@aws', '@docker'] }, async ({ page }) => {
const rolesPage = new RolesPage(page);
rolesPage.goToRolesPage({ scope: org.id });
Copy link
Collaborator

Choose a reason for hiding this comment

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

When running the tests locally, it got stuck at this line. Is the function goToRolesPage supposed to be defined in pages/roles.js?

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

Yes, sorry about that. This time it should really work

image

@@ -249,6 +250,8 @@ After all the steps pass, you should see a `Enos operations finished!`.
### Test names and tagging
For admin tests, it's important to tag the test with the correct tags to denote which enos scenario is supported by the test. The test tags should have at least specifying the edition (`@ce`, `@ent`) and at least one specifying the enos test infrastructure (`@aws`, or `@docker`).

The `@ent` and `@ce` tags should be added to *all* and *any* test cases that are supported by the respective editions. If a test case can be ran in both editions it should have both tags.
Copy link
Collaborator Author

Choose a reason for hiding this comment

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

I think everyone else understood this. Hopefully this helps future me

const rolesPage = new RolesPage(page);
rolesPage.goToRolesPage({ scope: org.id });

const table = page.locator('table');
Copy link
Collaborator

Choose a reason for hiding this comment

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

Is it possible to update some of these locators to use the recommended locator methods (https://playwright.dev/docs/locators)?

Suggested change
const table = page.locator('table');
const table = page.getByRole('table');

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

Updated the locators, the only ones I kept as selectors were for tbody since aria doesn't have a role for the rowgroup belonging to the body separately from the rowgroup belonging to thead. I felt like tbody was better than getByRole('rowgroup').nth(2) since knowing the 2nd rowgroup is the thead is less obvious.

It seems like the w3c is aware of this limitation in the current spec:

This role does not differentiate between types of row groups (e.g., thead vs. tbody), but an issue has been raised for WAI-ARIA 2.0.

And there's an open issue around the usefulness of rowgroup in practice

Copy link
Collaborator

Choose a reason for hiding this comment

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

Would something like this work?

const rowCount = await page
            .getByRole('table')
            .getByRole('row')
            .filter({ hasNot: page.getByRole('columnheader') })
            .count();

Copy link
Collaborator

Choose a reason for hiding this comment

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

I also generally do it this way in desktop when counting table rows

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

That works great

Comment on lines 27 to 30
const columnHeadersOrder = {
name: 0,
id: 2,
};
Copy link
Collaborator

Choose a reason for hiding this comment

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

In some other tests, I had the test find the index of the column based on the name. I don't really have a strong opinion and not sure which approach is preferred, but I wanted to just share.

     let headersCount = await page
        .getByRole('table')
        .getByRole('columnheader')
        .count();
      let fullNameIndex;
      let emailIndex;
      for (let i = 0; i < headersCount; i++) {
        const header = await page
          .getByRole('table')
          .getByRole('columnheader')
          .nth(i)
          .innerText();
        if (header == 'Full Name') {
          fullNameIndex = i;
        } else if (header == 'Email') {
          emailIndex = i;
        }
      }

Copy link
Collaborator

Choose a reason for hiding this comment

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

None blocking comment: for learning purposes, I found interesting how to select columns for e2e tests.
I checked both ways, and I do not have a strong opinion either. But I will aim for consistency within.

I do think the suggested way by moduli, seems more semantic, since we pass the column name and the code does the rest. Chad's we pass the index, therefore the user needs to know the index beforehand (not a big deal), but "less computation cost" if that makes any sense.

I think the semantic way seems more resilient, in case we add a column or change the table, the test will need no changes.

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

This is definitely more flexible if the column headers ever change. I kept what I had, but after seeing this I did add an assertion to check that the column header labels matched

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

I commented before reading your comment @calcaide. Check my most recent push. I think what I was missing was asserting the label which then brings these two implementations much closer together with the main difference being a static assertion vs dynamic references

Copy link
Collaborator

Choose a reason for hiding this comment

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

Yeah I saw it, I think it was like seconds of difference lol all good πŸ˜‰

calcaide
calcaide previously approved these changes Jun 17, 2025
Copy link
Collaborator

@calcaide calcaide left a comment

Choose a reason for hiding this comment

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

I left a none blocking comment, mostly for learning purposes.

Run the sorting.spec isolated test successfully!! looks awesome, full coverage of the sorting together with the unit tests.

Thank you for the work πŸ’ͺ πŸ™Œ πŸš€


const roleNamesToCreate = ['Alpha', 'Beta', 'Delta', 'Gamma', 'Zeta'];

export const columnHeaderSortButton = (tableLocator, nth) =>
Copy link
Collaborator

Choose a reason for hiding this comment

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

I haven't ran these yet so I might just be missing something but is there a reason we can't just do something like getByRole('columnheader', { name }).getByRole('button') instead of using indices?

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

Yup, that works! Updated

Comment on lines 22 to 24
expect(
tableLocator.locator(`thead`).getByRole('columnheader').nth(nth),
).toHaveAttribute('aria-sort', 'ascending');
Copy link
Collaborator

Choose a reason for hiding this comment

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

Same here, any reason we couldn't have just grabbed by name directly?

Suggested change
expect(
tableLocator.locator(`thead`).getByRole('columnheader').nth(nth),
).toHaveAttribute('aria-sort', 'ascending');
expect(
getByRole('columnheader', { name })).toHaveAttribute('aria-sort', 'ascending');

const rolesPage = new RolesPage(page);
rolesPage.goToRolesPage({ scope: org.id });

const table = page.locator('table');
Copy link
Collaborator

Choose a reason for hiding this comment

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

I also generally do it this way in desktop when counting table rows

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

5 participants