playwright icon indicating copy to clipboard operation
playwright copied to clipboard

[Feature]: Add `value` filter method for matching input values

Open adam-mak opened this issue 6 months ago • 9 comments

🚀 Feature Request

Proposal

It would be great if there's a built-in way to filter an input by its current value attribute.

This is the way we are currently using:

page.locator("input[value='foo']");

Thank you for considering this!

Example

It would be nice if we could leverage the newer locator methods, something like:

page.getByRole(AriaRole.TEXTBOX)
    .filter(new Locator.FilterOptions().setHasValue("foo"));

Motivation

I understand that not every type of element has a value attribute, but think adding this would make our tests more declarative and expressive.

adam-mak avatar Jun 02 '25 19:06 adam-mak

What is your use case for matching on value? You specifically use textbox as your example role, but why would you want to identify a text input via its current contents? Under normal circumstances, you generally don't have a situation where you have an assortment of text fields and you know one of them has the value "foo", but you're not sure which one. Instead, you know that you expect the first one specifically to contain "foo".

We generally recommend that you narrow your selection via other Aria selectors.

agg23 avatar Jun 03 '25 12:06 agg23

I'm working with existing code that does not use unique identifiers for every input field (I know ideally something like data-testid is used instead). Our test pre fills certain inputs with a dynamic name on a certain action, and we want to check that it does that correctly.

adam-mak avatar Jun 03 '25 13:06 adam-mak

Our test pre fills certain inputs

"Certain" implies predetermined (and I would expect that's how you intend it to work). Assuming your test (or even actual) code sets input 0 to "foo" every time the test starts, why can't you use the same mechanism to choose the DOM element you're going to assert the value of?

To be clear, you'd do something like this:

// Narrow this to a single element somehow
const locator = page.locator('input');
await expect(locator).toHaveValue("foo");

agg23 avatar Jun 03 '25 13:06 agg23

The inputs are predetermined, but don't have unique identifiers. So page.locator('input') returns multiple candidates. The "unique identifier" in our case is the input value itself. I also care more about locating the element so I can fill it, or modify the input in some way, rather than asserting that it has such input value.

Again, using data-testid or some other unique identifier for each input element would be ideal, so I understand if this isn't enough of a use case to consider being added in 😅 .

adam-mak avatar Jun 05 '25 05:06 adam-mak

Can you explain in more detail how you're populating these inputs? I do not understand how you could input text and not have some identity information. Even if you just ran:

await page.keyboard.press('Tab');
await page.keyboard.insertText('Input 0');
await page.keyboard.press('Tab');
await page.keyboard.insertText('Input 1');

you'd still have an inherent ordering, and you'd know which value corresponds to which input.

agg23 avatar Jun 05 '25 12:06 agg23

For the record, this has been asked for previously: #34364, #18970, #14679, #3228. However, there was not enough interest in the feature.

dgozman avatar Jun 09 '25 10:06 dgozman

@agg23 The inputs are being populated from a backend service upon page load. Frontend frameworks such as Vue allow for dynamic text rendering for inputs without defining a unique identifier for the input itself.

adam-mak avatar Jun 10 '25 22:06 adam-mak

I also have use for this feature. I am doing visual testing. However, a textarea is populated with dynamic content (attachment IDs in markdown). I'd like to have a locator to mask this element, or to write a replacer that replaces the content of the textarea. Unfortunately, I couldn't find a convenient way to only match textareas or other input elements with specific content.

fnetX avatar Oct 02 '25 01:10 fnetX

I have a similar requirement, I would like to do

const option = myForm.getByRole("radio", { value: "specific-value" })

option values are independent from i18n - whereas the "name" is not and may vary, I don't care for my tests... I am interested only in the correctness of the option's value.

DocMoebiuz avatar Nov 26 '25 10:11 DocMoebiuz