Skip to content

What is self-healing test automation?

Self-healing test automation updates a failing test's locators or steps when the interface changes, which cuts upkeep but can also hide real breakage.

Last updated , 8 min read

What is self-healing test automation?

Self-healing test automation is a test tool feature that adapts a failing test to a changed app, usually by replacing a broken locator. A test repaired this way is called a self-healing test. The repair cuts the upkeep of user interface (UI) tests, but it can also turn a real failure into a pass.

A locator is the query a test uses to find an element on a page, e.g. a button by its role and name. Each browser test framework has its own locators. A harmless change can rename or move an element, and the locator then stops matching. Fixing those locators by hand is a common cost of UI test automation.

In software testing, healing is used mostly on UI regression testing suites, which rerun the same steps after each change. The same word also names self-healing continuous integration (CI), in which an agent fixes a failed pipeline run. That sense is covered under CI failure triage.

How does self-healing test automation work?

A typical heal follows six steps:

  1. On a passing run, the tool saves details of each element the test used, e.g. its visible text.
  2. After a change, a locator matches no element, and the step fails.
  3. The tool collects candidate elements from the current page.
  4. The tool scores each candidate against the saved details, or a model ranks the candidates by the step's purpose.
  5. If the best score clears a threshold, the tool runs the step on that element. Otherwise the step fails.
  6. The tool reports the substitute locator or writes it into the test file.
How a tool heals a broken locator Step fails no element matches Find candidates on the current page Score each one against saved details Best score above threshold? Saved details from a passing run no Step fails as before yes Swap the locator the step runs if the match is wrong, the step still passes
The heal happens between a failed lookup and the next step. A wrong match passes the step too, and the heal shows only in a report or a patch.

Runtime healing swaps the locator during the run, and the test continues. The run can pass with no change to the test file, so the heal appears only in the tool's report.

Patch healing edits the test code and reruns it. Playwright's healer agent replays the failing steps, inspects the page for equivalent elements or flows, and suggests a patch, e.g. a locator update. It reruns the test until it passes or a limit ends the loop, and it marks the test skipped when it reports the feature as broken. It reads the page through browser tools of the kind Playwright MCP gives an agent.

A locator heal fixes a changed element, not a changed workflow. When a change adds a step, e.g. a confirmation page, no substitute locator makes the old steps work. An agent can rewrite the steps, but its patch is then a different test that needs review.

What is an example of a healed test?

Here is an illustrative example. Acme Co. sells furniture online. A developer asks a coding agent to "Let customers edit their delivery address during checkout." The agent's change also renames the "Save address" button to "Update address."

Acme's end-to-end test of checkout now fails at that button, because no button is named "Save address." A developer runs a healer agent on the failing test. The healer replays the steps, reads the page, and returns this patch:

-  await page.getByRole("button", { name: "Save address" }).click();
+  await page.getByRole("button", { name: "Update address" }).click();
   await expect(page.getByText("12 Elm Street")).toBeVisible();
-  await expect(page.getByTestId("cart-count")).toHaveText("2 items");
+  await expect(page.getByTestId("cart-count")).toHaveText("0 items");

The first change is a correct heal. The button still saves the address under its changed name.

The second change is not a locator fix. The address saved, but the cart emptied. After the button fix, the test failed on the cart check, and the healer changed the expected value to match the page. The healed test now passes on that bug.

A reviewer who reads the patch can reject the second change. A runtime heal would have swapped only the button's locator, so the cart check would still fail and show the bug.

This example is simplified. A real suite would check the cart in more tests, and a healer run on the suite could edit each of those checks.

What changes when a coding agent writes the code?

A coding agent can change many UI files in one task, so one change can break many locators at once. A healer then edits the tests to match the page the agent built. When that page is wrong, the healed tests follow the agent's work instead of the request.

Playwright's healer instructions tell it not to ask the user questions and to "do the most reasonable thing possible to pass the test." The same file lists fixing assertions and expected values among its edits. A coding agent asked to fix a failing check can make the same edits without a healer, by changing the test instead of the code. On a broken feature, the green run that follows is a false pass.

A practical adjustment is to let heals change how a test finds an element, never what it expects. Treat a changed assertion or expected value as a failed test until a person approves it.

When does healing hide a real bug?

A heal hides a bug when it lets a test pass on a broken feature. The common cases are these:

  • The heal changes the expected result. An edited assertion or expected value makes the test agree with the broken app, as the cart check did in the Acme example.
  • The heal picks the wrong element. A change can remove a button by mistake, and the closest match can be another button, e.g. "Save for later" in place of "Place order." The test then fails only if a later check reads the outcome.
  • The heal skips the test. A skipped test does not fail the run, so a broken feature marked skipped leaves the run green.
  • The heal leaves no trace in the code. A runtime heal changes nothing in the repository, so the diff a reviewer reads shows nothing to question.
  • The heal adds a wait. A longer timeout lets a slow page pass, so a real slowdown no longer fails the test, or fails it only now and then as a flaky test.

A check the healer cannot edit limits the damage. Keep a check of the outcome outside the UI, e.g. the order row in the database, in a file the healer may not change. A healed run that passes shows that an element matched, not that the feature works.

Stable locators also mean fewer heals. Playwright's locator guide recommends locators based on what a user sees, e.g. getByRole, and warns that CSS and XPath selectors tied to page structure can break when that structure changes.

How is a self-healing test different from a retried test?

A retry reruns a failed test without changing it, and the run passes if a later attempt passes. A heal changes the test, most often a locator, so the run that passes is not the test as written. Test retries target intermittent failures, and healing targets changed pages.

Both can turn a real failure green, by different routes. A retry hides an intermittent bug that does not return on the next attempt. A heal can hide a bug that fails every time, because the changed test no longer checks the broken behavior.

In agentic testing, an agent chooses every step. A healed test still follows its script, and a model that heals it acts only after a step fails.

FAQs

What is a locator in a UI test?

A locator in a UI test is the query that finds the element a step acts on, e.g. a button by its role and name. Locators based on what a user sees break less often than CSS or XPath selectors tied to page structure, so they need fewer heals.

Should a healed locator be committed without review?

A healed locator should get a person's review before it is committed, because the closest match on the page can be the wrong element. The reviewer checks that the substitute locator names the same control and that the patch changed no assertion or expected value.

Can self-healing handle a changed workflow?

Self-healing can repair a changed element but not a changed workflow. An added step, e.g. a confirmation page, needs an added action in the test, and no substitute locator supplies one. A test that an agent rewrites around the added step is a different test, so a person reviews it before it is committed.

What does Playwright's healer agent do?

Playwright's healer agent replays a failing test, inspects the page for equivalent elements or flows, and patches the test until it passes or a limit stops the loop. Its edits can include assertions and expected values. When the healer reports the feature as broken, it marks the test skipped.