Agent skill
playwright-dotnet
Guide for E2E testing with Playwright for .NET using Microsoft.Playwright.MSTest.v4 integration
Install this agent skill to your Project
npx add-skill https://github.com/majiayu000/claude-skill-registry/tree/main/skills/testing/playwright-dotnet
SKILL.md
Playwright for .NET Testing
This skill provides guidance for end-to-end (E2E) testing with Playwright for .NET using Microsoft.Playwright.MSTest.v4 integration in this .NET 10 project.
Table of Contents
- Overview
- Project Setup
- Installing Browsers
- Writing Tests
- Selectors and Assertions
- Debugging Tests
- CI/CD Integration
- Troubleshooting
- Quick Reference
Overview
What is Playwright?
Playwright is a modern E2E testing framework for web applications. It supports:
- Multiple browsers: Chromium, Firefox, WebKit
- Cross-platform: Windows, Linux, macOS
- Auto-waiting: Smart waits for elements
- Powerful selectors: CSS, text, accessibility
- Reliable: Reduces flakiness
- Fast: Parallel execution
Microsoft.Playwright.MSTest.v4
This project uses the MSTest integration which provides:
PageTestbase class - one browser context per testContextTestbase class - browser context with multiple pagesBrowserTestbase class - full browser control- Built-in fixtures (Page, Context, Browser)
- Automatic cleanup
Version: 1.55.0-beta-4 (configured in Directory.Packages.props)
Project Setup
Current Playwright Projects
This repository has 2 Playwright test projects:
tests/ClaudeStack.Web.Tests.Playwright/- Tests for MVC applicationtests/ClaudeStack.API.Tests.Playwright/- Tests for API application
Project Configuration
Both projects use this configuration:
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<EnableMSTestRunner>true</EnableMSTestRunner>
<OutputType>Exe</OutputType>
</PropertyGroup>
<ItemGroup>
<PackageReference Include="Microsoft.Playwright.MSTest.v4" />
<PackageReference Include="MSTest" />
</ItemGroup>
</Project>
Key points:
- Uses Microsoft.Testing.Platform (see mstest-testing-platform skill)
- Package versions managed in Directory.Packages.props (see dotnet-centralized-packages skill)
- MSTestSettings.cs configures method-level parallelization
Creating New Playwright Project
# Step 1: Create MSTest project
dotnet new mstest -o tests/Example.NewApp.Tests.Playwright
# Step 2: Edit .csproj to add required properties
# <PropertyGroup>
# <EnableMSTestRunner>true</EnableMSTestRunner>
# <OutputType>Exe</OutputType>
# </PropertyGroup>
# Step 3: Add Playwright package reference (version in Directory.Packages.props)
# <PackageReference Include="Microsoft.Playwright.MSTest.v4" />
# <PackageReference Include="MSTest" />
# Step 4: Install browsers (see next section)
# Step 5: Add MSTestSettings.cs with parallelization
# [assembly: Parallelize(Scope = ExecutionScope.MethodLevel)]
Installing Browsers
Initial Browser Installation
After creating a Playwright project or after building, install browsers:
# Navigate to the build output directory
cd tests/ClaudeStack.Web.Tests.Playwright/bin/Debug/net10.0
# Run the Playwright PowerShell script
./playwright.ps1 install
Important: Browsers must be installed after building the project because the playwright.ps1 script is generated during build.
Installation on Different Platforms
Windows (PowerShell):
pwsh -Command "cd tests/ClaudeStack.Web.Tests.Playwright/bin/Debug/net10.0; ./playwright.ps1 install"
Linux/macOS (Bash):
pwsh tests/ClaudeStack.Web.Tests.Playwright/bin/Debug/net10.0/playwright.ps1 install
Installing Specific Browsers
# Install only Chromium
./playwright.ps1 install chromium
# Install Chromium and Firefox
./playwright.ps1 install chromium firefox
# Install with dependencies (for Linux CI)
./playwright.ps1 install --with-deps
Browser Locations
Browsers are installed in:
- Windows:
%USERPROFILE%\AppData\Local\ms-playwright - Linux:
~/.cache/ms-playwright - macOS:
~/Library/Caches/ms-playwright
Writing Tests
Basic Test Structure
All tests inherit from PageTest:
using System.Threading.Tasks;
using Microsoft.Playwright.MSTest;
using Microsoft.VisualStudio.TestTools.UnitTesting;
namespace ClaudeStack.Web.Tests.Playwright;
[TestClass]
public class HomePageTests : PageTest
{
[TestMethod]
public async Task HomePageLoadsSuccessfully()
{
await Page.GotoAsync("https://localhost:5001");
await Expect(Page).ToHaveTitleAsync("Home Page");
}
}
Key points:
- Inherit from
PageTest - Test methods are
async Task Pageproperty available automaticallyExpectfor assertions
PageTest Fixtures
PageTest provides automatic fixtures:
public class MyTests : PageTest
{
// Available properties:
// - Page: IPage (automatically created per test)
// - Context: IBrowserContext
// - Browser: IBrowser
// - Playwright: IPlaywright
}
Test Initialization
Use [TestInitialize] and [TestCleanup] as needed. Page is automatically disposed.
Selectors and Assertions
Selectors
Page.Locator("css") // CSS selector
Page.Locator("text=Get Started") // Text
Page.GetByTestId("id") // Test ID
Page.GetByRole(AriaRole.Button) // Accessibility
Page.GetByLabel("Email") // Form label
Page.Locator("div").Locator("button") // Chaining
Assertions
await Expect(Page).ToHaveTitleAsync("Title");
await Expect(element).ToBeVisibleAsync();
await Expect(element).ToHaveTextAsync("text");
await Expect(element).ToHaveAttributeAsync("href", "/about");
Actions
await element.ClickAsync();
await element.FillAsync("value");
await element.CheckAsync();
await element.SelectOptionAsync("option");
Debugging Tests
Headed Mode
$env:HEADED="1"
dotnet run --project tests/ClaudeStack.Web.Tests.Playwright
Screenshots and Tracing
// Screenshot
await Page.ScreenshotAsync(new() { Path = "screenshot.png" });
// Tracing
await Context.Tracing.StartAsync(new() { Screenshots = true, Snapshots = true });
// ... test actions ...
await Context.Tracing.StopAsync(new() { Path = "trace.zip" });
View trace: pwsh .../playwright.ps1 show-trace trace.zip
Playwright Inspector
$env:PWDEBUG="1"
dotnet run --project tests/ClaudeStack.Web.Tests.Playwright
CI/CD Integration
# Azure DevOps / GitHub Actions
- Build project: dotnet build tests/**/*.Playwright.csproj
- Install browsers: pwsh .../playwright.ps1 install --with-deps
- Run tests: dotnet run --project tests/ClaudeStack.Web.Tests.Playwright
Important: Use --with-deps flag in CI to install system dependencies (Linux).
Troubleshooting
Issue: Browsers Not Installed
Error: "Executable doesn't exist at..."
Solution: Install browsers after building:
cd tests/ClaudeStack.Web.Tests.Playwright/bin/Debug/net10.0
./playwright.ps1 install
Issue: playwright.ps1 Not Found
Cause: Project not built yet.
Solution: Build first, then install browsers:
dotnet build tests/ClaudeStack.Web.Tests.Playwright
# Then install browsers
Issue: Tests Timeout
Cause: Default timeout (30s) exceeded.
Solution: Increase timeout:
[TestMethod]
[Timeout(60000)] // 60 seconds
public async Task SlowTest()
{
// Or set per-action timeout:
await Page.GotoAsync("https://example.com", new() { Timeout = 60000 });
}
Issue: Element Not Found
Solution: Playwright auto-waits, but verify selector:
// Debug: Get all matching elements
var count = await Page.Locator("button").CountAsync();
Console.WriteLine($"Found {count} buttons");
// Use more specific selector
var button = Page.GetByRole(AriaRole.Button, new() { Name = "Submit" });
Issue: Flaky Tests
Solutions:
- Use
Expectassertions (built-in retries) - Avoid hardcoded waits
- Use
Page.WaitForLoadStateAsync(LoadState.NetworkIdle) - Make selectors more specific
Quick Reference
Base Classes
PageTest // Single page per test (most common)
ContextTest // Browser context, create own pages
BrowserTest // Full browser control
Common Patterns
// Navigation
await Page.GotoAsync("url");
// Waiting
await Page.WaitForLoadStateAsync(LoadState.NetworkIdle);
await Page.WaitForSelectorAsync("button");
// Locators
Page.Locator("css")
Page.GetByTestId("id")
Page.GetByRole(AriaRole.Button)
Page.GetByText("text")
// Assertions
await Expect(Page).ToHaveTitleAsync("title");
await Expect(element).ToBeVisibleAsync();
await Expect(element).ToHaveTextAsync("text");
// Actions
await element.ClickAsync();
await element.FillAsync("value");
await element.CheckAsync();
Running Tests
# Run all Playwright tests
dotnet run --project tests/ClaudeStack.Web.Tests.Playwright
# Headed mode
$env:HEADED="1"
dotnet run --project tests/ClaudeStack.Web.Tests.Playwright
# Debug mode
$env:PWDEBUG="1"
dotnet run --project tests/ClaudeStack.Web.Tests.Playwright
Browser Installation
cd tests/ClaudeStack.Web.Tests.Playwright/bin/Debug/net10.0
./playwright.ps1 install # All browsers
./playwright.ps1 install chromium # Chromium only
./playwright.ps1 install --with-deps # With system dependencies (Linux)
Related Skills
- mstest-testing-platform: Running Playwright tests with Microsoft.Testing.Platform
- dotnet-centralized-packages: Managing Playwright package versions
- dotnet-cli-essentials: Building and running test projects
Additional Resources
- Playwright .NET Documentation
- Microsoft.Playwright.MSTest.v4 Package
- Playwright API Reference
- Best Practices
Version Information
- Microsoft.Playwright.MSTest.v4: 1.55.0-beta-4
- Playwright Version: 1.55 (beta)
- .NET SDK: 10.0.100-rc.2.25502.107
This skill is accurate as of Playwright 1.55 beta. Some APIs may change in future versions.
Didn't find tool you were looking for?