Playwright چیست؟ آموزش تست End-to-End با TypeScript از نصب تا Trace
در این آموزش Playwright را برای TypeScript نصب میکنید، یک تست واقعی ورود مینویسید، Locator و Assertion پایدار میسازید و شکست تست را با Trace و گزارش HTML بررسی میکنید.
تست دستی یک مسیر خرید یا ورود شاید بار اول چند دقیقه طول بکشد؛ اما با هر تغییر رابط، مرورگر و Pull Request تکرار آن پرهزینه و مستعد فراموشی میشود. Playwright تعامل واقعی کاربر با برنامه وب را در مرورگر اجرا میکند و نتیجه را با Assertionهای قابل انتظار میسنجد.
در این راهنما یک تست End-to-End کوچک اما واقعی میسازیم: نصب پروژه TypeScript، تعریف تنظیمات پایه، نوشتن سناریوی ورود، انتخاب Elementها با Locator معنایی و تحلیل شکست با Trace و گزارش HTML. هدف صرفاً سبزشدن تست نیست؛ میخواهیم تستی بسازیم که قابل خواندن، قابل تکرار و در برابر تغییرهای بیربط UI مقاوم باشد.
Playwright چیست و چه اجزایی دارد؟
Playwright Test یک Framework تست End-to-End برای برنامههای مدرن وب است. Test Runner، Assertion، Isolation، Parallel Execution، Reporter و ابزارهای Debug در یک بسته قرار دارند. تستها میتوانند روی Chromium، Firefox و WebKit در ویندوز، لینوکس و macOS اجرا شوند.
هر تست یک Browser Context جدا میگیرد؛ این Context مانند Profile تازه مرورگر است. Cookie و Storage تست قبلی به تست بعدی نشت نمیکند، مگر اینکه آگاهانه State احراز هویت را ذخیره و استفاده کنید. این Isolation پایه مهمی برای جلوگیری از تستهای وابسته به ترتیب اجراست.
چه چیزی را با تست E2E بسنجیم؟
- مسیرهای حیاتی مانند ورود، ثبت سفارش، پرداخت آزمایشی و بازیابی حساب
- قرارداد میان Frontend، Backend و Browser در یک سناریوی کامل
- رفتار برنامه در Chromium، Firefox و WebKit
- دسترسیپذیری پایه Elementهای تعاملی و نامهای قابل فهم
تست E2E جای Unit Test و Integration Test را نمیگیرد. تعداد محدودی مسیر حیاتی را با E2E پوشش دهید و منطق ریز را در لایههای سریعتر آزمایش کنید.
Playwright vs Selenium و Cypress؛ تفاوتها و انتخاب ابزار
| معیار | Playwright | Selenium | Cypress |
|---|---|---|---|
| مرورگرها | Chromium، Firefox و WebKit | اکوسیستم گسترده WebDriver | مرورگرهای پشتیبانیشده پروژه |
| Auto-wait | در Locator و Assertion داخلی | وابسته به API و طراحی تست | Retry داخلی فرمانها |
| Isolation | Browser Context برای هر تست | به طراحی Framework وابسته است | Isolation داخلی Runner |
| Trace | Snapshot، Network و گامهای تست | نیازمند ابزار و Integration جدا | Runner و Artifactهای اختصاصی |
| انتخاب مناسب | پروژه مدرن با Tooling یکپارچه | اکوسیستم قدیمی یا زبانهای متعدد | تیم Frontend با Workflow آن ابزار |
انتخاب فقط با جدول Feature انجام نمیشود. مهارت تیم، Browserهای هدف، محیط CI، نیاز به زبان برنامهنویسی دیگر و هزینه نگهداری تستها را بسنجید. برای پروژه تازه TypeScript، Playwright مسیر شروع یکپارچهای ارائه میدهد.
نصب Playwright در پروژه TypeScript
یک پوشه خالی بسازید و Installer رسمی را اجرا کنید. Wizard درباره TypeScript یا JavaScript، پوشه تستها، Workflow مربوط به GitHub Actions و نصب Browserها سؤال میکند. TypeScript و نصب Browserها را انتخاب کنید.
mkdir web-e2ecd web-e2enpm init playwright@latestnpx playwright --versionnpx playwright testnpx playwright show-reportPlaywright علاوه بر Package، Binary مرورگرهای سازگار را دریافت میکند. در CI لینوکس از npx playwright install --with-deps استفاده میشود تا Browser و وابستگیهای سیستم نصب شوند. Version فایل Lock را Commit کنید تا Runner تیم نسخه یکسانی بگیرد.
تنظیم baseURL، Browserها و Trace
فایل تنظیمات مرکز تصمیمهای مشترک است. URL پایه را از متغیر محیطی بخوانید و برای اجرای محلی مقدار امن پیشفرض بگذارید. Trace را روی نخستین Retry فعال کنید تا اجرای عادی Artifact سنگین نسازد، ولی شکست قابل بازسازی باشد.
import { defineConfig, devices } from '@playwright/test'; export default defineConfig({ testDir: './tests', fullyParallel: true, forbidOnly: Boolean(process.env.CI), retries: process.env.CI ? 2 : 0, reporter: 'html', use: { baseURL: process.env.BASE_URL ?? 'http://127.0.0.1:3000', trace: 'on-first-retry', screenshot: 'only-on-failure', }, projects: [ { name: 'chromium', use: { ...devices['Desktop Chrome'] } }, { name: 'firefox', use: { ...devices['Desktop Firefox'] } }, ],});قرار دادن URL، نام کاربری یا Token محرمانه در Repository ممنوع است. آدرس محیط و Secretها را در CI از متغیر امن تزریق کنید. Artifact تست نیز ممکن است Screenshot، DOM و داده فرم را در خود داشته باشد؛ دسترسی و زمان نگهداری آن را محدود کنید.
نوشتن نخستین تست ورود
فرض کنید برنامه صفحه ورود با Labelهای «ایمیل» و «رمز عبور» و Button با نام «ورود» دارد. تست باید رفتاری را توصیف کند که کاربر میبیند، نه جزئیات پیادهسازی CSS را.
import { test, expect } from '@playwright/test'; test('کاربر معتبر وارد داشبورد میشود', async ({ page }) => { await page.goto('/login'); await page.getByLabel('ایمیل').fill('student@example.test'); await page.getByLabel('رمز عبور').fill('local-test-password'); await page.getByRole('button', { name: 'ورود' }).click(); await expect(page).toHaveURL(//dashboard$/); await expect( page.getByRole('heading', { name: 'داشبورد' }) ).toBeVisible();});Credential بالا فقط برای Fixture محلی و حساب آزمایشی است. برای Staging از Secret Store استفاده کنید و هرگز حساب Production واقعی را در تست عمومی قرار ندهید. بهتر است داده تست در هر اجرا ساخته و پاکسازی منطقی شود تا تست به وضعیت قبلی وابسته نباشد.
Locator پایدار چگونه انتخاب میشود؟
Locator قلب Auto-wait و Retry در Playwright است. اولویت معمول، انتخاب بر اساس نقشی است که کاربر یا فناوری کمکی میبیند: getByRole، سپس Label، Text و در نهایت Test ID. Selectorهای طولانی CSS یا وابسته به ترتیب DOM با کوچکترین تغییر طراحی میشکنند.
| Locator | زمان استفاده | پایداری |
|---|---|---|
| getByRole | Button، Link، Heading و کنترل معنایی | زیاد و همسو با Accessibility |
| getByLabel | ورودی فرم دارای Label درست | زیاد |
| getByText | محتوای قابل مشاهده و نسبتاً یکتا | متوسط |
| getByTestId | وقتی قرارداد تست مستقل لازم است | زیاد، ولی مخصوص تست |
| CSS/XPath | آخرین راه برای ساختار فاقد معنا | معمولاً کم |
اگر getByRole Element را پیدا نمیکند، ممکن است HTML از نظر دسترسیپذیری مشکل داشته باشد. اصلاح Markup معمولاً هم تجربه کاربر و هم تست را بهتر میکند. برای یکتایی Locator از گزینه name و Scope کردن در بخش مشخص استفاده کنید.
چرا Timeout ثابت ضدالگو است؟
دستورهای انتظار ثابت مانند چند ثانیه Sleep تست را هم کند و هم شکننده میکنند. Playwright پیش از Action شرایط Actionability را بررسی میکند و Web-First Assertion تا رسیدن وضعیت مورد انتظار Retry میشود. بهجای صبر کور، همان نتیجهای را Assert کنید که اهمیت دارد.
اجرای تست، UI Mode و Codegen
npx playwright testnpx playwright test tests/login.spec.ts --project=chromiumnpx playwright test --headednpx playwright test --uinpx playwright codegen http://127.0.0.1:3000/loginnpx playwright show-reportCodegen نقطه شروع Locator و Action را سریع میکند، ولی خروجی آن را بدون بازبینی Commit نکنید. نام تست، داده مستقل، Assertion معنادار و حذف Stepهای زائد همچنان به قضاوت مهندس نیاز دارند. UI Mode برای مشاهده گامها و Debug محلی مناسب است؛ اجرای CI معمولاً Headless باقی میماند.
تحلیل شکست با Trace Viewer
Trace میتواند Timeline، Actionها، DOM Snapshot، Console، Network و Attachmentها را کنار هم نشان دهد. وقتی تست فقط در CI شکست میخورد، Trace بسیار ارزشمندتر از یک Screenshot نهایی است، چون وضعیت قبل و بعد هر گام را نمایش میدهد.
npx playwright test tests/login.spec.ts --trace onnpx playwright show-trace test-results/login-user-valid/trace.zipnpx playwright show-reportنام پوشه Result به نام تست و پروژه بستگی دارد. Trace ممکن است داده صفحه، Headerها یا ورودیها را ثبت کند؛ آن را Artifact حساس فرض کنید. Upload عمومی، نگهداری نامحدود و بازکردن Trace ناشناس روی سرویس بیرونی انتخاب مناسبی نیست.
اجرای Playwright در GitHub Actions
Workflow زیر Dependencyها را از Lock File نصب میکند، Browserها و وابستگی سیستم را میگیرد، تستها را اجرا میکند و فقط در شکست Report را برای مدت محدود نگه میدارد. برنامه مورد آزمون باید پیش از Step تست در دسترس باشد؛ میتوانید آن را با تنظیم webServer در Config یا Step جدا اجرا کنید.
name: Playwright testson: [push, pull_request]jobs: test: runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 - uses: actions/setup-node@v4 with: node-version: 24 cache: npm - run: npm ci - run: npx playwright install --with-deps - run: npm test - uses: actions/upload-artifact@v4 if: failure() with: name: playwright-report path: playwright-report/ retention-days: 7Actionها را در محیط حساس بر اساس سیاست Supply Chain سازمان به Commit SHA Pin کنید. Secret مربوط به محیط تست را فقط در Job مورد نیاز تزریق کنید و Workflow مربوط به Pull Requestهای Fork ناشناس را طوری طراحی کنید که Secret دریافت نکند.
خطاهای رایج و راه اصلاح
| نشانه | علت رایج | راه اصلاح |
|---|---|---|
| Timeout هنگام Click | Locator اشتباه یا Element غیرقابل Action | Trace، نام Accessible و Overlay را بررسی کنید |
| Strict mode violation | Locator چند Element پیدا کرده است | Role و Name یا Scope دقیقتر بدهید |
| فقط در CI شکست | Race، داده مشترک یا تفاوت محیط | Trace و Report را ببینید و Fixture را مستقل کنید |
| Browser executable missing | Binary مرورگر نصب نشده است | فرمان install --with-deps را اجرا کنید |
| تست گاهی سبز و قرمز | Sleep ثابت یا Assertion فوری | Web-First Assertion و انتظار نتیجهمحور بنویسید |
| تستها روی هم اثر دارند | داده یا State مشترک | داده یکتا و Browser Context مستقل استفاده کنید |
چکلیست تست E2E قابل اعتماد
- سناریو یک رفتار مهم کاربر را با نام روشن توصیف میکند.
- تست به ترتیب اجرای تست دیگر وابسته نیست.
- Locatorها بر Role، Label یا قرارداد Test ID استوارند.
- انتظار ثابت با Assertion نتیجهمحور جایگزین شده است.
- داده تست یکتا و قابل پاکسازی است.
- Retry برای پنهانکردن Flaky Test استفاده نمیشود.
- Trace و Screenshot فقط هنگام نیاز و با Retention محدود ذخیره میشوند.
- همان دستور CI روی محیط توسعه نیز قابل اجراست.
برای قرار دادن تستها در چرخه تحویل، شناخت Pipeline اهمیت دارد. راهنمای CI/CD با GitHub Actions مسیر مکملی است. اگر برنامه روی کلاستر اجرا میشود، آموزش Kubernetes و Minikube به درک محیط تست و انتشار کمک میکند.
سوالات متداول Playwright
Playwright چیست؟
Playwright ابزار تست End-to-End برای برنامههای وب است و اجرای تست روی Chromium، Firefox و WebKit، Assertion، Trace و ابزارهای اشکالزدایی را در یک workflow فراهم میکند.
تفاوت Playwright و Selenium چیست؟
هر دو برای خودکارسازی مرورگر استفاده میشوند. Playwright امکاناتی مانند auto-waiting، context isolation و Trace را بهصورت یکپارچه ارائه میکند؛ Selenium اکوسیستم قدیمیتر و گستردهای برای WebDriver و زبانهای مختلف دارد.
برای Locator پایدار در Playwright چه روشی بهتر است؟
Locatorهایی که بر نقش، label و رفتار قابل مشاهده کاربر تکیه میکنند معمولاً از selectorهای وابسته به ساختار CSS پایدارترند.
Trace در Playwright چه کاربردی دارد؟
Trace اطلاعات اجرای تست را برای بررسی مرحلهبهمرحله شکستها ذخیره میکند و در تشخیص خطاهای timing، navigation و تعامل با عناصر مفید است.
مسیر یادگیری مرتبط با تست Front-End
برای تقویت پایههای این مسیر، JavaScript و React را ببینید. برای اجرای تستها در محیطهای قابل تکرار نیز راهنمای Docker برای توسعهدهندگان و Kubernetes و Minikube مرتبط هستند.
جمعبندی
Playwright بیش از یک ابزار Click خودکار است: Locatorهای قابل Retry، Assertionهای Web-First، Isolation، اجرای چندمرورگری و Trace کنار هم چرخه ساخت و عیبیابی تست را کامل میکنند. کیفیت نهایی همچنان به طراحی سناریو، داده مستقل و انتخاب Locator درست وابسته است.
همین امروز یک مسیر حیاتی برنامه را با Locator معنایی تست کن، یک شکست کنترلشده بساز و علت آن را در Trace Viewer پیدا کن.