Skip to main content

AI-powered Selenium to Playwright migration tool

Project description

QAMigrate

AI-powered test framework migration

PyPI version Python 3.11+ License: MIT

A QATonic Innovations product.


QAMigrate converts test suites between frameworks automatically. It parses your code with Tree-sitter, generates equivalent code with Claude, and produces a full migration report with per-file diffs, confidence scores, and estimated time savings.

Today: Selenium Java -> Playwright Java Next: Cypress -> Playwright, TestNG -> JUnit 5, RestAssured -> Karate, and more.

Why QAMigrate

You don't just get generated code. You get evidence:

  • Per-file diffs -- every pattern we touched, why, and side-by-side before/after
  • Confidence score -- how sure we are about each file, 0 to 100
  • Batch report -- HTML, JSON, and Markdown; share with your team
  • Time-saved estimate -- how many hours of manual work you avoided
  • Dry-run mode -- preview what would change without calling the LLM

What it does

Give it a Selenium file:

// Selenium
@FindBy(id = "username")
private WebElement usernameInput;

public void login(String user, String pass) {
    usernameInput.clear();
    usernameInput.sendKeys(user);
    passwordInput.sendKeys(pass);
    wait.until(ExpectedConditions.elementToBeClickable(loginButton));
    loginButton.click();
}

Get Playwright back:

// Playwright (generated by QAMigrate)
private final Locator usernameInput;

public LoginPage(Page page) {
    this.usernameInput = page.locator("#username");
}

public void login(String user, String pass) {
    usernameInput.fill(user);
    passwordInput.fill(pass);
    loginButton.click(); // Playwright auto-waits
}

Supported patterns (Selenium -> Playwright Java)

  • @FindBy annotations (id, css, xpath, className, name, linkText)
  • PageFactory.initElements removal
  • WebDriverWait / ExpectedConditions removal (Playwright auto-waits)
  • sendKeys -> fill, clear removal, click direct conversion
  • Actions (hover, drag) -> Playwright equivalents
  • Select dropdowns -> selectOption
  • JavascriptExecutor -> page.evaluate()
  • Alert / iframe handling
  • File uploads -> setInputFiles
  • TestNG -> JUnit 5 lifecycle (@BeforeMethod -> @BeforeEach, etc.)
  • @DataProvider -> @MethodSource
  • Assert.assertEquals / assertTrue -> Playwright assertions
  • ChromeDriver setup -> Playwright.create() + browser.newContext()
  • Base class inheritance preservation

Quick start

Prerequisites

  • Python 3.11+
  • Java 17+ (for compilation validation; optional — see compiler.skip)
  • Anthropic API key

Install

pip install qamigrate

Configure

echo "ANTHROPIC_API_KEY=sk-ant-your-key" > .env

Migrate

# Dry-run: see what would happen without calling the LLM
qamigrate migrate --all --project ./my-selenium-project --dry-run

# Migrate a single file
qamigrate migrate src/test/java/LoginPage.java --project ./my-selenium-project

# Migrate everything with a full migration report
qamigrate migrate --all --project ./my-selenium-project --report ./qamigrate-report

Output goes to playwright/ subdirectories next to each original file. If you use --report <dir>, you get report.html, report.json, and report.md.

Example report summary

QAMigrate - Migrating 7 file(s)

-> [1/7] BaseTest.java
   OK src/.../playwright/BaseTest.java (14.1s, 75% confidence)
-> [2/7] LoginPage.java
   OK src/.../playwright/LoginPage.java (17.2s, 75% confidence)
...

Files             7 / 7
Patterns handled  149
Avg confidence    75%
Time              105.3s
Est. hours saved  ~37.2

Report written:
  HTML:     ./qamigrate-report/report.html
  JSON:     ./qamigrate-report/report.json
  Markdown: ./qamigrate-report/report.md

CLI commands

Command Description
qamigrate init Initialize QAMigrate in a project
qamigrate scan Analyze codebase, detect patterns, show complexity
qamigrate migrate Convert files to the target framework

Common flags for migrate:

  • <file> — migrate a single file
  • --all, -a — migrate all Java files under src/test or src/
  • --dry-run — analyze only, no LLM calls, no writes
  • --report <dir> — write HTML + JSON + Markdown report
  • --project, -p <path> — project root (default: current dir)

How it works

Scanner (Tree-sitter)     Deterministic AST parsing, pattern detection
       |
Coder (Claude API)        Generates Playwright Java via structured output
       |
Compiler (javac)          Validates generated code compiles
       |
Fixer (rules + Claude)    Fixes compilation errors, retries up to 3x
       |
Report                    Records everything that happened

Plain Python — no LangChain, no graph framework, no agents-of-agents. Each step is a clean module you can read in 5 minutes.

Configuration

Optional qamigrate.yaml in your project root:

pipeline:
  max_retries: 3

coder:
  model: "claude-sonnet-4-20250514"
  max_tokens: 8192

compiler:
  build_tool: "maven"    # or "gradle"
  java_version: "17"
  skip: false            # set true when Playwright JARs aren't on classpath

scanner:
  exclude_patterns:
    - "**/target/**"
    - "**/build/**"
    - "**/playwright/**"

You can also use environment variables with the QAMIGRATE_ prefix:

export QAMIGRATE_COMPILER__SKIP=true       # skip compilation check
export QAMIGRATE_PIPELINE__MAX_RETRIES=5   # more retries

Python API

from qamigrate.agents.pipeline import run_migration
from qamigrate.core.config import QAMigrateConfig
from qamigrate.core.report import MigrationReport

config = QAMigrateConfig()
report = MigrationReport()

result = run_migration(
    file_path=Path("src/test/java/LoginPage.java"),
    project_path=Path("."),
    config=config,
)

if result.record:
    report.add(result.record)

report.finish()
report.write_html(Path("./report.html"))

Development

pip install -e ".[dev]"
pytest tests -v
ruff check src tests

License

MIT — see LICENSE.

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

qamigrate-0.2.1.tar.gz (66.4 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

qamigrate-0.2.1-py3-none-any.whl (49.4 kB view details)

Uploaded Python 3

File details

Details for the file qamigrate-0.2.1.tar.gz.

File metadata

  • Download URL: qamigrate-0.2.1.tar.gz
  • Upload date:
  • Size: 66.4 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.13.11

File hashes

Hashes for qamigrate-0.2.1.tar.gz
Algorithm Hash digest
SHA256 7116312cdc43b863f4bd6ea8fc5ac5dae54bf15ecea554865d1b4d531fae2c14
MD5 94dc669c613ad78076266bdd3743db49
BLAKE2b-256 0e3854adadb7fb36e7b7ba547911bac4954e9f5569a56c68defabfba6c7e5f1c

See more details on using hashes here.

File details

Details for the file qamigrate-0.2.1-py3-none-any.whl.

File metadata

  • Download URL: qamigrate-0.2.1-py3-none-any.whl
  • Upload date:
  • Size: 49.4 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.13.11

File hashes

Hashes for qamigrate-0.2.1-py3-none-any.whl
Algorithm Hash digest
SHA256 0ab982c2475d8e4d2208e8842a90c1e2adf373fd3fee1108ca50f6ece6d6a6fc
MD5 10dc1d07d4e4d8ffb034df4cbc17b23c
BLAKE2b-256 3da7f8d133ed8ab3dac78113f6409765e6b6a6097aa5c6c85edc70f65bb72254

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page