Slide 1

Slide 1 text

C#でのPlaywrightを使っ たE2Eテストの実際 株式会社SAKURUG プロダクトDiv 草場 友光 .NETラボ勉強会2024年2月

Slide 2

Slide 2 text

自己紹介 • 普段は主にシステムをAzureにモダナ イズする仕事をしています。 • コミュニティ活動を通じて知識をアッ プデートしています。 • 2022/08-2024 Microsoft MVP (Developer Technologies) • tomo_kusaba

Slide 3

Slide 3 text

宣伝 【VISION】ひとの可能性を開花させる企業であり続ける VISIONに共感できる仲間募集中。

Slide 4

Slide 4 text

注意 • 個人の見解・解釈が多分に入っています。 • 見解の相違・事実誤認などありましたらご指摘ください。 • #dotnetlabでtweetすると左側に表示されます

Slide 5

Slide 5 text

今日の目的 • ソフトウェアにおいてテストは重要です。 • 今日はユーザーから見たふるまいのテストをするE2Eテストのな かでもC#でのPlaywrightを使ったテストの実際を見ていきま しょう! • Playwrightを使う上でフロントエンド側での実際と、C#での Playwrightのテストの実情を知っていきましょう。

Slide 6

Slide 6 text

Playwrightとは • Chromium、WebKit、Firefoxなどに対応したヘッドレステスト がWindows、Linux、macOSでローカルまたはCIでテストがで きる。 • NUnitまたはMSTestを基底クラスとしたものが用意されてい る。 • 本セッションではNUnitを基底クラスとしたPlaywrightで話を 進めていきます。

Slide 7

Slide 7 text

Playwrightの導入方法 • NUnitのテンプレートでプロジェクトを作成します。 • 次のパッケージをNugetします。またはNUnit Playwright TestProjectでプロジェクトを作成。パッケージを最新にする。 Microsoft.Playwright.NUnit • プロジェクトをビルドします。 • NUnitのプロジェクトのディレクトリで以下のPowerShellを実 行します。 pwsh bin/Debug/netX/playwright.ps1 install netXの部分はnet8.0など実際のフォルダ名(.NETのバージョン)に置き換 えます。

Slide 8

Slide 8 text

システム要件 • .NET Standard 2.0(.NET 8推奨) • Windows10以降、Windows Server2016以降またはWSL • MacOS12、MacOS13、MacOS14 • Debian11、debian12、Ubuntu20.04、Ubuntu22.04

Slide 9

Slide 9 text

テストの同時実行 • Playwrightにおけるテストの並列実行は 「ParallelScope.Self」のみがサポートされている。 • 1つのテストクラスで(明示的にインスタンス化しなければ)1つの 仮想的なブラウザを使用することが想定しているのでメソッド単 位で同時実行することはできない。 • PralleScope.Selfはテスト自体を他のテストと並行して実行す ることができる。

Slide 10

Slide 10 text

テストの基底クラス テスト 説明 PageTest 独自のBrowserContextで作成されたWebページの新しいコピーを取得しま す。このクラスを拡張することは完全に機能するPlaywrightテストを記述する最 も簡単な方法です。(推奨) 各テストファイルのContextOptionをoverrideしてコンテキストオプションを 制御することができます。 ContextTest 各テストはBrowserContextの新しいコピーを取得します。このテストは複数の タブが必要な複数ページのシナリオをテストする簡単な方法です。 BrowserTest 各テストはブラウザーを取得して好きなだけコンテキストを作成できます。 PlaywrightTest 各テストに、Playwrightオブジェクトが与えられ、テストは必要なだけのブラウザ を開始及び停止できます。

Slide 11

Slide 11 text

ロケーター • ページ上の要素を見つける方法を表す。 ロケーター 説明 GetbyRole() アクセシビリティ属性で検索します GetbyText() テキストコンテンツで検索します GetbyLabel() ラベルのテキストでフォームコントロールを検索します。 GetbyPlaceholder() プレースホルダーで入力を検索します。 GetbyAltText() 代替テキストで要素を見つけます。 GetbyTitle() title属性で要素を検索します。 GetbyTestId() data-testidに基づいて要素を検索します。(推奨)

Slide 12

Slide 12 text

TestId • 最も確実なロケーターの方法。 • あらかじめ、テストしたい箇所にdata-testidを埋め込んでおく。

Slide 13

Slide 13 text

カスタムテストID属性 • data-testid以外でもあらかじめテストに設定することで他の属 性をテストIDとして使えるようにする機能。 • これにより新たにdata-pwがテストIDとして使用できるように なりました。

Slide 14

Slide 14 text

アサーション • ロケーターのあとに続いてアサートを行う。 • ロケーターで指定した要素がどのような状態になっているかどう かのチェックを行う。

Slide 15

Slide 15 text

主なアサーション アサート 説明 ToBeChackedAsync() チェックボックスがオンになっている。 ToBeDesabledAsync() 要素が無効になっている。 ToBeEditableAsync() 要素が編集可能である。 ToBeEnabledAsync() 要素が有効である。 ToBeVisibleAsync() 要素が表示されている。 ToBeHiddenAsync() 要素が表示されていない。 ToBeContainTextAsync() 要素にテキストが含まれている。 ToHaveAttirbuteAsync() 要素にDOM属性がある。 ToHaveClassAsync() 要素にクラスプロパティがある。 ToHaveIdAsync() 要素にIDがある。 ToHaveCSSAsync() 要素にCSSプロパティがある。

Slide 16

Slide 16 text

主なアサーション アサート 説明 ToHaveTextAsync() 要素がテキストと一致する。 ToHaveValueAsync() 入力に値がある。 ToHaveValuesAsync() 選択にオプションが選択されている。 ToHaveTitleAsync() ページにタイトルがある。 ToHaveURLAsync() ページにURLがある。 ToBeOKAsync() 応答のステータスはOKです。

Slide 17

Slide 17 text

アクション • ロケーターの後に続いてアクションを行う。 • ユーザーに代わりテキスト入力、ラジオボタン、チェックボックスな どの選択、マウスクリック、文字、キーの入力、ファイルアップロー ド、ファイルダウンロードができます。

Slide 18

Slide 18 text

自動待機 • アクションを実行する前に実行可能性チェックを実行して、期待通 りに動くかどうかを確認します。 • 関連するすべてのチェックに合格するまで一定時間自動待機しま す。

Slide 19

Slide 19 text

モックAPI • HTTPとHTTPSのネットワークトラフィックをモック及び変更するためのAPI • ページが行うすべての要求はモックできる。 • データベースの状態を抜きにしてUIをテストしたいときに有効 // Intercept the route to the fruit API await page.RouteAsync("*/**/api/v1/fruits", async route => { var json = new[] { new { name = "Strawberry", id = 21 } }; // fulfill the route with the mock data await route.FulfillAsync(new() { Json = json }); }); // Go to the page await page.GotoAsync("https://demo.playwright.dev/api-mocking"); // Assert that the Strawberry fruit is visible await Expect(page.GetByTextAsync("Strawberry")).ToBeVisibleAsync();

Slide 20

Slide 20 text

スクリーンショット • Playwrightは基本ヘッドレスで動作するのでテストの様子が見 えない。 • 証跡を残したい・どのような状態になっているのかをみたいなど の要求をかなえるためスクリーンショットを適宜撮ることを推奨し ます。 await Page.ScreenshotAsync(new() { Path = "screenshot.png", });

Slide 21

Slide 21 text

ビデオ • テストの全体を動画で録画しておきたいという要求があります。 Playwrightではビデオ録画の機能があります。 var context = await browser.NewContextAsync(new() { RecordVideoDir = "videos/" }); // Make sure to close, so that videos are saved. await context.CloseAsync();

Slide 22

Slide 22 text

トレースビューア • トレースビューアはテストを記録しておきテストで失敗したとき何 が起きたかデバッグするための優れた方法です。

Slide 23

Slide 23 text

GitHub Actions ワークフロー • ユースケースとして、GitHubにプッシュ→アプリケーションビル ド→UnitTest→デプロイ→E2Eテストというフローがある。 E2Eテストのところに着目したワークフローとしては以下の通り name: Playwright Tests on: deployment_status: jobs: test: timeout-minutes: 60 runs-on: ubuntu-latest if: github.event.deployment_status.state == 'success' steps: - uses: actions/checkout@v3 - name: Setup dotnet uses: actions/setup-dotnet@v3 with: dotnet-version: 8.0.x - run: dotnet build - name: Ensure browsers are installed run: pwsh bin/Debug/net8.0/playwright.ps1 install --with-deps - name: Run tests run: dotnet test env: # This might depend on your test-runner PLAYWRIGHT_TEST_BASE_URL: ${{ github.event.deployment_status.target_url }}

Slide 24

Slide 24 text

Playwright Testing • 構成で「PLAYWRIGHT_SERVICE_URL」にエンドポイント • 構成で「PLAYWRIGHT_SERVICE_ACCESS_TOKEN」にアク セストークン • 以上2つを設定することで動く。

Slide 25

Slide 25 text

Playwright Testing(GitHub Actions Ubuntu-latest) • 構成にさえ渡せばよいので例えば。。。 PLAYWRIGHT_SERVICE_URL=${{ secrets.PLAYWRIGHT_SERVICE_URL }} PLAYWRIGHT_SERVICE_ACCESS_TOKEN=${{ secrets.PLAYWRIGHT_SERVICE_ACC ESS_TOKEN }} dotnet test --no-restore

Slide 26

Slide 26 text

で、何をテストしますか??問題。 • ユースケース① ユーザーからみたUIの反応が壊れてないかテストしたい。 • ブラウザーのアップデートによってUIが壊れてないか? • ユースケース② インフラの変更・障害を検知テストしたい。 • アプリケーションの動作に影響を及ぼすようなインフラの変更・障害 などもE2Eテストで検出できるのでは? 例)初期表示時にデータベースをSELECTしてるがデータベース接続 に失敗してコンテンツが全く表示されていなかった。 →データベースの接続確認は正常性チェックでもするべきだがより実 際的なアプリケーションの応答としてのテスト。

Slide 27

Slide 27 text

参考文献 • Playwright for .NET Docs https://playwright.dev/dotnet/docs/intro • Scale Playwright .NET tests with Microsoft Playwright Testing https://github.com/microsoft/playwright-testing- service/blob/main/samples/.NET/NUnit/README.m d

Slide 28

Slide 28 text

おしまい おしまい