I think many developers have encountered issues with broken UI layouts caused by unexpectedly long text elements on the frontend.
When text content exceeds the available space, truncation techniques like CSS's text-overflow
or JavaScript functions need to be applied.
Ensuring that these truncations work flawlessly across various scenarios requires effective testing strategies. In this article, we will delve into approaches for testing UI components that involve truncation, whether achieved through CSS (text-overflow
) or JavaScript functions.
Truncation Implemented with JavaScript
When utilizing JavaScript for truncating text, either through libraries like the popular lodash _.truncate
function or custom implementations, testing becomes relatively straightforward. We can write unit tests to cover the different scenarios we expect to encounter.
For instance, when using a custom truncation function, a simple test could involve verifying the return value:
import { truncate } from './custom-truncation.js';
it("truncates the text") {
expect(truncate("your long text", 10)).toEqual("expected")
}
In scenarios involving libraries, it might be worthwhile to test the truncation within the component itself. For instance, in a React component:
import { render, screen } from '@testing-library/react'
it('should render menu with truncated header', () => {
render(<Menu {...props} />)
const header = screen.getByRole('header')
expect(title).toHaveTextContent('This is some looong title too long...')
})
Component-level testing provides a more direct insight into how the truncation behaves in the context of your UI.
Handling Truncation through CSS
However, things become more intricate when dealing with truncation accomplished via CSS properties like text-overflow: ellipsis
. The initial instinct might be to write tests similar to those above—render the component and inspect the text content. But, unfortunately, this approach will not yield accurate results.
Due to the nature of text-overflow
truncation, the entire text remains within the HTML element, causing assertions to fail.
Link to the pen.
So, how do we effectively test CSS-based truncation?
To confirm successful truncation via text-overflow
, we can implement a simple validation technique by comparing offsetWidth
and scrollWidth
:
function isEllipsisActive(e: HTMLElement) {
return (e.offsetWidth < e.scrollWidth);
}
(For a quick refresher on offsetWidth
and scrollWidth
, refer to this explanation).
However, there's a catch. If your testing library relies on jsdom, accessing offsetWidth
and scrollWidth
directly from an element might not work due to rendering limitations. This limitation is further elaborated upon here.
Nonetheless, if you're using a library like Cypress, which performs actual rendering, you can incorporate this validation into your test:
it("should render menu with truncated header", () => {
cy.visit("your_page_url"); // Replace with the URL of the page containing the element
cy.get('[data-testid="your_element_id"]').then(($element) => {
const offsetWidth = $element[0].offsetWidth;
const scrollWidth = $element[0].scrollWidth;
expect(offsetWidth).to.be.lessThan(scrollWidth);
});
});
But what if your only option is a library that relies on jsdom, and accessing params such as offsetWidth
is not feasible?
In that case, an alternative approach involves validating the existence of specific styles applied to the HTML element:
it('should render menu with truncated header', () => {
// selection of element
// ...
expect(element).toHaveStyle('text-overflow: ellipsis');
expect(element).toHaveStyle('overflow: hidden');
expect(element).toHaveStyle('white-space: nowrap');
});
While not as robust as testing the actual rendered value, this method can still serve as a viable solution in certain scenarios.
Results
-
JavaScript Truncation:
- Write unit tests covering your truncation function
- Write component tests checking the actual text inside DOM after truncation
-
CSS Truncation:
- Verify truncation using rendering libraries like Cypress, comparing
offsetWidth
andscrollWidth
- For jsdom-based libraries ensure expected CSS properties are present
- Verify truncation using rendering libraries like Cypress, comparing
By following these steps, we can ensure consistent and reliable truncation behavior.
Top comments (0)