ReactでPlaywrightでテストを書いてみる

Windows環境でReact Playwrightという環境でテスト書いてみる
参考
https://zenn.dev/azukiazusa/articles/playwright-component-testing


とりあえずTypeScriptでcreate-react-app
```
npx create-react-app sample-react-playwright --template typescript
```
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/653035/63581b38-2d04-e41b-56a3-0d02fd317eea.png)

```
npm init playwright@latest -- --ct
```

proceed でy選択
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/653035/f928f96b-8679-f78e-5aa8-8e5b195b64a7.png)

reactかvueかsvlteの選択をせまられるのでreact選択
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/653035/8bebbf6b-0cb8-ff79-15ff-d2056635395a.png)

以下が作成された
```
├── playwright
│   ├── index.html
│   └── index.ts
├── playwright-ct.config.ts
```
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/653035/720af2e0-176a-d2e9-cea7-8a553cc190a4.png)

簡単なソースを用意　以下はボタン押すとカウンターが増えるサンプル
```Counter.tsx
import React, { useState } from "react";
import "./Counter.css";

const Counter: React.FC = () => {
  const [count, setCount] = useState(0);

  return (
    <div>
      <p className="hidden md-block">You clicked {count} times</p>
      <p className="md-hidden">{count}</p>
      <button>Click me</button> 
    </div>
  );
};

export default Counter;
```

テストファイルをsrc直下に配置。以下のように記述する

```Counter.spec.tsx
import { test, expect } from "@playwright/experimental-ct-react"; // ①
import Counter from "./Counter";

test("increments the counter", async ({ mount }) => {
  const component = await mount(<Counter />); // ②

  const button = component.locator('role=button[name="Click me"]'); // ③
  await button.click();

  const paragraph = component.locator("role=paragraph"); // ④
  expect(await paragraph.textContent()).toBe("You clicked 1 times");
});
```

コンポーネントをmountで定義し、
locatorで要素の取得している。
取得した要素(ボタン)をclickし、
paragrphロールを要素取得し、
expectするというもの。

```Counter.css
.hidden {
  display: none;
}

@media (min-width: 768px) {
  .md-hidden {
    display: none;
  }
  .md-block {
    display: block;
  }
}
```

元のsrc/inde.tsxの呼び出しをAppからCounterに変更
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/653035/b53636ff-866b-6395-495b-950c8435d71f.png)

ファイル作成結果
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/653035/c257defb-453a-4ecb-b322-148054a68e05.png)

実行してみる（このテストは失敗する予定）
```
npm run test-ct
```
失敗
clickが実行されていないとのこと
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/653035/495162d1-0546-8722-70b0-b359c1abf398.png)

別ターミナルで以下を実行し、レポート見れるようにしておく
```
npx playwright show-report
```
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/653035/40d93178-798d-a1d1-0305-0bd18373072e.png)

エラーレポートが見れる

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/653035/c606b43d-de0d-94be-0023-11a673fc7ea8.png)

以下は詳細
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/653035/5b23bf12-c0b1-892b-1063-324773f9d3e4.png)

テストが成功するように以下のように編集
```Counter.tsx
- <button>Click me</button>
+ <button onClick={() => setCount((prev) => prev + 1)}>Click me</button>
```

もう1回実行
```
npm run test-ct
```
パスできている
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/653035/64234c04-9a2b-4a24-c376-9761f06d7e8b.png)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/653035/1812fa9a-d46a-3666-1553-964e0cab5e74.png)


テストごとにViewportを変更できるみたい
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/653035/e5657649-c1f7-3e8c-03aa-5a495c366983.png)


あとブラウザ表示もできる。
playwright-ct.config.tsのuseに　headless=False　を追加

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/653035/c387016a-2a8f-f4e5-88a1-0a126bf5fa91.png)

ブラウザすぐ閉じてしまうので、
sleep替わりに以下いれておく。
```
await new Promise(resolve => setTimeout(resolve, 5000))
```
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/653035/2acedb93-17e2-bcc4-181d-8e6d7e922ae2.png)

実行するとエラーになってしまっていた。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/653035/681f9a78-b685-869d-0362-e44b9bbdf404.png)

ブラウザを見ると画面サイズの関係か表示がうまく You clicked 1 times が表示できず、1 だけになっている。
ブラウザ見れるとパッとわかってよいですね。
shapshotも取れると思うので今度試してみよ。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/653035/41e3dfd3-e6b1-0011-3e84-b3172fec9411.png)

テストを通すためにViewportのサイズを変更してみる。
width 320 -> 1000

再実行＞上手く表示され、テストもOKになった。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/653035/60d50b8f-689d-bdcb-f5c5-9f1eaab32b52.png)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/653035/2dc1d3f7-dde4-898b-55e1-cb44f333ba83.png)

使いやすくてよいですね。これからちょこちょこ使ってこー。