Playwright + TypeScript de la zero: structură, page objects și primul test în CI

Academia Testarii 11 septembrie 2026
Înapoi la Blog

Vrei să construiești un framework de automatizare serios cu Playwright în TypeScript, dar nu știi de unde să începi? Hai pas cu pas: structură de proiect, pattern-ul page object model și primul test care rulează verde în CI. 🚀

Ai instalat Playwright, ai rulat `npx playwright test` o dată, a mers ceva, și acum te uiți la un folder gol și nu știi ce urmează. Sună familiar? Exact de acolo începem.

Nu vorbim despre un "hello world" care impresionează pe nimeni. Vorbim despre un framework pe care îl poți pune în producție, pe care colegii tăi îl pot înțelege a doua zi, și care nu se prăbușește la primul refactor de UI. Shall we?

De ce Playwright în TypeScript și nu altceva?

Selenium 4 e încă solid și are o comunitate uriașă — la DevTalks și GoTech World îl auzi menționat în aproape orice talk de automatizare. Cypress are fanii lui devotați. Dar Playwright a câștigat teren rapid din motive concrete: rulează nativ pe Chromium, Firefox și WebKit, are suport built‑in pentru multiple tabs, iframes și network interception, iar API‑ul de așteptare este inteligent by default — nu mai scrii `Thread.sleep()` și nu mai speri.

TypeScript adaugă un strat de siguranță pe care, odată ce l‑ai gustat, nu mai vrei să renunți la el. Autocompletare, erori detectate la compilare, refactoring fără frică. Dacă lucrezi într‑un proiect cu JIRA, cu zeci de test cases și cu o echipă de 3+ testeri, TypeScript nu e un moft, e o necesitate.

Structura de proiect: ordinea care salvează echipe

Un framework dezorganizat e mai periculos decât niciunul. Ajungi să ai teste duplicate, page objects contradictorii și nimeni nu știe ce rulează și ce nu. Iată o structură simplă, dar scalabilă:

```
my‑playwright‑framework/
├── tests/
│ ├── auth/
│ │ └── login.spec.ts
│ └── checkout/
│ └── checkout.spec.ts
├── pages/
│ ├── LoginPage.ts
│ └── CheckoutPage.ts
├── fixtures/
│ └── base.fixture.ts
├── utils/
│ └── api‑helper.ts
├── test‑data/
│ └── users.json
├── playwright.config.ts
└── .github/
└── workflows/
└── playwright.yml
```

Regula de bază: `tests/` conține doar ce se testează, `pages/` conține doar cum se interacționează cu UI‑ul, `utils/` conține logică reutilizabilă. Niciodată invers.

Folderul `test‑data/` pare inutil la început. Devine salvator când ai 40 de utilizatori de test pentru domenii diferite — bancar, retail, energie — și nu vrei să le bagi hardcodat în fiecare spec.

Page Object Model: patternul care face diferența dintre un test și un framework

Page Object Model (POM) nu e o idee nouă. A existat în Selenium de ani buni. Dar în Playwright cu TypeScript arată deosebit de curat.

Ideea: fiecare pagină sau componentă a aplicației are o clasă dedicată care expune metode clare. Testul nu știe că există un selector, nu știe că butonul se numește `#submit‑btn` — el știe doar că poate apela `loginPage.loginAs(user)`.

Un exemplu concret pentru o pagină de login

```typescript
// pages/LoginPage.ts
import { Page, Locator } from '@playwright/test';

export class LoginPage {
private emailInput: Locator;
private passwordInput: Locator;
private submitButton: Locator;

constructor(private page: Page) {
this.emailInput = page.getByLabel('Email');
this.passwordInput = page.getByLabel('Parola');
this.submitButton = page.getByRole('button', { name: 'Autentificare' });
}

async loginAs(email: string, password: string) {
await this.emailInput.fill(email);
await this.passwordInput.fill(password);
await this.submitButton.click();
}
}
```

Acum în test

```typescript
// tests/auth/login.spec.ts
import { test, expect } from '../fixtures/base.fixture';

test('utilizatorul valid se autentifică cu succes', async ({ loginPage }) => {
await loginPage.loginAs('user@example.com', 'parola123');
await expect(loginPage.page).toHaveURL('/dashboard');
});
```

Observi că testul e aproape lizibil și de un PM care nu știe TypeScript. Asta înseamnă un framework bun.

Fixtures: cola care ține totul împreună

Fixtures în Playwright sunt echivalentul unui `@BeforeEach` inteligent, dar mult mai flexibil. Poți injecta instanțe de page objects direct în teste, poți gestiona starea de autentificare o singură dată per sesiune și poți partaja contextul browser între teste dacă ai nevoie de performanță.

```typescript
// fixtures/base.fixture.ts
import { test as base } from '@playwright/test';
import { LoginPage } from '../pages/LoginPage';

type Fixtures = {
loginPage: LoginPage;
};

export const test = base.extend<Fixtures>({
loginPage: async ({ page }, use) => {
const loginPage = new LoginPage(page);
await page.goto('/login');
await use(loginPage);
},
});

export { expect } from '@playwright/test';
```

Simplu. Elegant. Ușor de extins când adaugi `CheckoutPage`, `DashboardPage` sau orice altă pagină.

CI cu GitHub Actions: primul test care rulează în pipeline

Un test care rulează doar local e un test care nu există. CI‑ul transformă framework‑ul dintr‑un proiect personal într‑o unealtă de echipă.

Un workflow minimal pentru GitHub Actions

```yaml
# .github/workflows/playwright.yml
name: Playwright Tests

on:
push:
branches: [main]
pull_request:
branches: [main]

jobs:
test:
runs‑on: ubuntu‑latest
steps:
- uses: actions/checkout@v4
- uses: actions/setup‑node@v4
with:
node‑version: 20
- name: Install dependencies
run: npm ci
- name: Install Playwright Browsers
run: npx playwright install --with‑deps
- name: Run Playwright Tests
run: npx playwright test
- uses: actions/upload‑artifact@v4
if: always()
with:
name: playwright‑report
path: playwright‑report/
retention‑days: 7
```

La fiecare pull request, testele rulează automat. Raportul HTML generat de Playwright — cu screenshot‑uri, video și trace — se uploadează ca artifact și poate fi descărcat direct din GitHub. Fără setup complicat, fără server dedicat pentru început.

Un mic #FunFact: Playwright trace viewer este unul dintre cele mai utile instrumente de debugging pe care le‑am văzut în ultimii ani în ecosistemul de testare. Deschizi fișierul `.zip` generat la un test eșuat și vezi pas cu pas exact ce s‑a întâmplat în browser, inclusiv network requests și DOM snapshots. Niciun alt framework nu oferă asta out‑of‑the‑box la același nivel.

Greșeli comune pe care le poți evita de la început

Nu pune logică de business în fișierele de test. Nu hardcoda URL‑uri și credențiale direct în spec‑uri — folosește variabile de environment și fișiere `.env`. Nu ignora `playwright.config.ts`: acolo configurezi base URL, timeouts, numărul de workeri pentru rulări paralele, și proiectele (Chromium, Firefox, WebKit) pe care vrei să testezi.

Și poate cel mai important: nu încerca să automatizezi tot de la bun început. Începe cu fluxurile critice — autentificare, checkout, creare cont. Adaugă treptat. Un framework de automatizare e un produs în sine, nu un sprint de o săptămână.

---

Dacă acest articol ți‑a deschis apetitul pentru automatizare serioasă, știi unde ne găsești. La Academia Testarii am format deja sute de cursanți care au trecut de la zero la primul framework funcțional, mulți dintre ei angajați imediat după curs în companii din domenii precum banking, automotive și retail. Cursurile noastre practice acoperă exact ce ai citit azi — și mult mai mult: Postman pentru API testing, integrare cu JIRA, raportare, și pregătire pentru certificarea ISTQB.

Vino pe academiatestarii.ro, uită-te la programele disponibile și fă primul pas concret spre cariera în QA pe care o vrei. Abia așteptăm să te vedem în cohortă.

#DeAziEstiTester #AcademiaTestarii #TestAutomation #ISTQB #TestareSoftware

Toate articoleleAutor: Academia Testarii