Skip to content

Migrate epub viewer TOC tests from vue test utils to Vue testing library#14542

Open
curiouscoder-cmd wants to merge 2 commits intolearningequality:developfrom
curiouscoder-cmd:epub-vtl-migration
Open

Migrate epub viewer TOC tests from vue test utils to Vue testing library#14542
curiouscoder-cmd wants to merge 2 commits intolearningequality:developfrom
curiouscoder-cmd:epub-vtl-migration

Conversation

@curiouscoder-cmd
Copy link
Copy Markdown
Contributor

@curiouscoder-cmd curiouscoder-cmd commented Apr 6, 2026

Summary

  • Description of the change: Migrated the Vue test suites for the epub viewer's table of contents capability (TocButton.spec.js, TableOfContentsSection.spec.js, and TableOfContentsSectionSideBar.spec.js) from @vue/test-utils to Vue Testing Library (@testing-library/vue). Refactored queries to test purely from a user's perspective, avoiding tight coupling to component internals.
  • Manual verification steps performed: Executed pnpm run test-jest -- --testPathPattern epub_viewer to ensure all 47 test cases in the epub_viewer suite passed successfully. Verified that NO residual @vue/test-utils imports remain in the targeted files.
  • Screenshots / Recordings: N/A (Purely a testing refactor, no UI logic modified).

References

Resolves #14189

Reviewer guidance

  • How to test:
    Reviewers can fetch this branch locally and run pnpm run test-jest -- --testPathPattern epub_viewer to verify the tests pass organically. All tests follow standard user-experience workflows (e.g. fireEvent.click).
  • Implementation Notes (Risk/Context):
    There are no risky changes to core UI routing. However, while converting the test suite, I intentionally prioritized screen.getByText queries for the navigation sections over getByRole('button'). This was done purposefully to gracefully handle KButton (when rendered as a basic link) internally lacking an explicit role="button". This strategy strictly mirrors the current preferred VTL patterns established in the reference file packages/kolibri-common/components/userAccounts/__tests__/GenderSelect.spec.js.

AI usage

I used Gemini to help structure this PR description, and help to fix the linting error and
brainstormed the @testing-library/vue refactoring approach with Gemini,I reviewed the generated test files to verify the queries correctly addressed KButton accessibility limitations and ran the full testing suite to ensure backward compatibility.

@github-actions github-actions bot added DEV: renderers HTML5 apps, videos, exercises, etc. DEV: frontend SIZE: medium labels Apr 6, 2026
@learning-equality-bot
Copy link
Copy Markdown

👋 Hi @curiouscoder-cmd, thanks for contributing!

For the review process to begin, please verify that the following is satisfied:

  • Contribution is aligned with our contributing guidelines

  • Pull request description has correctly filled AI usage section & follows our AI guidance:

    AI guidance

    State explicitly whether you didn't use or used AI & how.

    If you used it, ensure that the PR is aligned with Using AI as well as our DEEP framework. DEEP asks you:

    • Disclose — Be open about when you've used AI for support.
    • Engage critically — Question what is generated. Review code for correctness and unnecessary complexity.
    • Edit — Review and refine AI output. Remove unnecessary code and verify it still works after your edits.
    • Process sharing — Explain how you used the AI so others can learn.

    Examples of good disclosures:

    "I used Claude Code to implement the component, prompting it to follow the pattern in ComponentX. I reviewed the generated code, removed unnecessary error handling, and verified the tests pass."

    "I brainstormed the approach with Gemini, then had it write failing tests for the feature. After reviewing the tests, I used Claude Code to generate the implementation. I refactored the output to reduce verbosity and ran the full test suite."

Also check that issue requirements are satisfied & you ran pre-commit locally.

Pull requests that don't follow the guidelines will be closed.

Reviewer assignment can take up to 2 weeks.

@github-actions
Copy link
Copy Markdown
Contributor

github-actions bot commented Apr 6, 2026

@curiouscoder-cmd
Copy link
Copy Markdown
Contributor Author

curiouscoder-cmd commented Apr 6, 2026

Hello mentors, pls review the PR whenever you get time
And let me know if it satisfies all the requirements. Thanks.

@akolson akolson requested a review from rtibblesbot April 6, 2026 18:18
@learning-equality-bot
Copy link
Copy Markdown

📢✨ Before we assign a reviewer, we'll turn on @rtibblesbot to pre-review. Its comments are generated by an LLM, and should be evaluated accordingly.

Copy link
Copy Markdown
Contributor

@rtibblesbot rtibblesbot left a comment

Choose a reason for hiding this comment

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

Good migration — all three files use VTL correctly and CI is green.

No UI files changed; Phase 3 skipped.

Suggestions (non-blocking):

  • TocButton.spec.js line 12: getByRole('button') passes but doesn't verify the accessible name (see inline comment)
  • TableOfContentsSection.spec.js lines 61/66: container.firstElementChild usage (see inline comment)

Praise:

  • The sectionWithEmptyLabel test cleanly covers the href-as-fallback edge case
  • Correct choice of getByText for KButton elements — the source confirms appearance="basic-link" renders as <a> without href, which has no implicit ARIA role, making getByRole inapplicable here

@rtibblesbot's comments are generated by an LLM, and should be evaluated accordingly

How was this generated?

Reviewed the pull request diff checking for:

  • Correctness: bugs, edge cases, undocumented behavior, resource leaks, hardcoded values
  • Design: unnecessary complexity, naming, readability, comment accuracy, redundant state
  • Architecture: duplicated concerns, minimal interfaces, composition over inheritance
  • Testing: behavior-based assertions, mocks only at hard boundaries, accurate coverage
  • Completeness: missing dependencies, unupdated usages, i18n, accessibility, security
  • Principles: DRY (same reason to change), SRP, Rule of Three (no premature abstraction)
  • Checked CI status and linked issue acceptance criteria
  • For UI changes: inspected screenshots for layout, visual completeness, and consistency

expect(wrapper.exists()).toBe(true);
it('renders the table of contents button', () => {
renderComponent();
expect(screen.getByRole('button')).toBeInTheDocument();
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

suggestion: getByRole('button') finds the button but doesn't verify its accessible name. Since KIconButton receives ariaLabel="Toggle table of contents", adding { name: /toggle table of contents/i } would also assert that the label is wired up correctly — catching regressions if the $tr key or prop binding changes.

expect(wrapper.findComponent({ name: 'KButton' }).text()).toBe(sectionWithEmptyLabel.href);
it('applies the appropriate top-level styling class for root level sections', () => {
const { container } = renderComponent({ section, depth: 0 });
expect(container.firstElementChild).toHaveClass('toc-list-item-top-level');
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

suggestion: container.firstElementChild couples the test to the rendered DOM structure and is generally discouraged by Testing Library. Acceptable here because there's no accessible attribute that reflects the depth === 0 state, but worth noting. If TableOfContentsSection ever gains an aria-level or similar attribute, switching to that would make the test more resilient.

@rtibbles rtibbles self-assigned this Apr 7, 2026
Copy link
Copy Markdown
Contributor

@rtibblesbot rtibblesbot left a comment

Choose a reason for hiding this comment

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

Both prior suggestions addressed cleanly.

CI passing. No UI files changed — Phase 3 skipped.

Prior findings

Resolved:

  • getByRole('button') name filter missing (suggestion) — { name: /toggle table of contents/i } added at both query sites in TocButton.spec.js
  • container.firstElementChild DOM coupling (suggestion) — replaced with getByText().closest('li') in TableOfContentsSection.spec.js

2/2 prior findings resolved.

New findings: none.


@rtibblesbot's comments are generated by an LLM, and should be evaluated accordingly

How was this generated?

Compared the current PR state against findings from a prior review:

  • Retrieved prior bot reviews deterministically via the GitHub API
  • Classified each prior finding as RESOLVED, UNADDRESSED, ACKNOWLEDGED, or CONTESTED
  • Only raised NEW findings for newly introduced code
  • Reviewed the pull request diff checking for correctness, design, architecture, testing, completeness, and adherence to DRY/SRP principles
  • Checked CI status and linked issue acceptance criteria

expect(wrapper.exists()).toBe(true);
it('renders the table of contents button', () => {
renderComponent();
expect(screen.getByRole('button', { name: /toggle table of contents/i })).toBeInTheDocument();
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

praise: Good fix — both query sites updated consistently, and the name filter now also acts as a regression guard for the $tr binding.

@curiouscoder-cmd
Copy link
Copy Markdown
Contributor Author

curiouscoder-cmd commented Apr 9, 2026

I made the suggested changes. All prior findings are resolved now.
@rtibbles can you review it when you get time ? If there are any further changes needed to be made.

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

Labels

DEV: frontend DEV: renderers HTML5 apps, videos, exercises, etc. SIZE: medium

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Convert epub viewer table of contents unit tests to Vue Testing Library

3 participants