[[ðArticles]] > [[ð2022 Articles]]
![[2022-10-30.jpg|cover-picture]]
Webããã³ããšã³ãã®[[E2Eãã¹ã]]ã«æ¬ ãããªã[[Playwright]]ã«ã€ããŠã2022幎çŸåšã®ææ°æ
å ±ãèžãŸããŠæåŒãã®èšäºãæžããŠã¿ãŸããã
## ã¯ããã«
ç§ã[[Playwright]]ã®èšäºãåããŠæžããã®ã¯ããã2幎åã2020幎ã®12æã§ãã
<div class="link-card">
<div class="link-card-header">
<img src="https://avatars1.githubusercontent.com/u/9500018?s=460&v=4" class="link-card-site-icon"/>
<span class="link-card-site-name">MAMANã®ITããã°</span>
</div>
<div class="link-card-body">
<div class="link-card-content">
<div>
<p class="link-card-title">Playwrightã§e2eãã¹ããæžããŠã¿ã</p>
</div>
<div class="link-card-description">
Playwrightã䜿ã£ãŠãTogowlã®e2eãã¹ããæžããŠã¿ãŸããã
</div>
</div>
<img src="https://blog.mamansoft.net/images/cover/2020-12-20.jpg" class="link-card-image" />
</div>
<a href="https://blog.mamansoft.net/2020/12/20/playwright-realtime-e2e-web-test/"></a>
</div>
åœåã¯ä»ã»ã©ã·ã¹ãã ãæŽåãããŠãªãã[[Playwright]]ã¯ãã©ãŠã¶æäœãã¡ã€ã³ã®ä»äºã§ããããã¹ããæžãã«ã¯[[Jest]]ãšé£æºããããå¥ã®ã©ã€ãã©ãªãå¿
èŠã§ãããã€ãã®èšå®ãã¡ã€ã«ãå¿
èŠã§èŠæŠããæãåºããããŸãã
ãã®ç¹ã¯ç¿å¹Žã®2021幎ã«è§£æ¶ããããããå«ããå¥ã®[[Playwright]]èšäºãæžããŠããŸããè«žäºæ
ã«ããããã§ã¯çŽ¹ä»ã§ããŸããããããããããç¥ããã®ãã¡ã«ã芧ã«ãªã£ãŠãããããããŸããã
åœæã¯å
é²çã ã£ã[[Playwright]]ããæšä»ã§ã¯ä»äºã§æ®åããããã§ãŒãºã«å
¥ãã»ã©ç¥å床ãäžãã£ãŠããŸããããã ã[[Googleãã¬ã³ã]]ã§ã¯[[Cypress]]ã[[Selenium]]ã®æ¹ãäžã§ãã
![[Pasted image 20221030130251.png]]
äžæ¹ã[[GitHub]]ã®ã¹ã¿ãŒæ°ã¯[[Playwright]]ããããã§ãã(2022-10-30çŸåš)
| ãªããžã㪠| ã¹ã¿ãŒæ° |
| --------------------------------------------------------------- | -------- |
| [microsoft/playwright](https://github.com/microsoft/playwright) | 43.9k |
| [cypress-io/cypress](https://github.com/cypress-io/cypress) | 41.3k |
| [SeleniumHQ/selenium](https://github.com/SeleniumHQ/selenium) | 25k |
å人çã«ã¯ãéçºãã人ã§ããã°[[Playwright]]ãäžçªäœ¿ãããããšæã£ãŠããã®ã§ããã®çµæã¯çŽåŸã§ããéã«ééçºè
ã«ãšã£ãŠã[[Playwright]]ã¯æ·å±
ãé«ããšæãããããããããŸããã
ãããª[[Playwright]]ãä»äžåºŠãã£ããåŠç¿ããæå³ã§ãããã®èšäºãæžãããšã«ããŸããããªãã[[Playwright]]ã䜿ãã¹ãçç±ã®èª¬æã¯å²æããŸãã
## ãã¹ã察象ãããžã§ã¯ãã®äœæ
ãã¹ã察象ã®ç°¡åãªWebããŒãžãäœæããŸãããããäœãããã€ããã¯ãªãã®ã§ãæãã·ã³ãã«ã«æžããã§ããã[[Svelte]]ã䜿ããŸãã
```console
npm create vite@latest playwright-svelte-sample -- --template svelte-ts
cd playwright-svelte-sample
npm i
npm i --save-dev prettier-plugin-svelte prettier
```
äœèšãªãã¡ã€ã«ããããšæ°ãæ£ãã®ã§ãå¿
èŠãªãã®ä»¥å€ã¯åé€ããŸãã
```console
rm -rf public src/lib src/assets
```
æçµçã«ä»¥äžã®ãã¡ã€ã«ã ãæ®ããŸãã
```ls
ï .
âââ ï» index.html
âââ î package-lock.json
âââ î package.json
âââ ï README.md
âââ ï src
â âââ î app.css
â âââ ï
App.svelte
â âââ îš main.ts
â âââ îš vite-env.d.ts
âââ î svelte.config.js
âââ î tsconfig.json
âââ î tsconfig.node.json
âââ îš vite.config.ts
```
`App.svelte`ã以äžã®ããã«æžãæããŸãã
```html
<script lang="ts">
let count = 0;
</script>
<main>
<h1>Playwright Svelte Sample</h1>
<h2>Push "Increment/Decrement" button</h2>
<div style=" justify-content: center; gap: 10px;">
<button on:click={() => count++}>Increment</button>
<button on:click={() => count--}>Decrement</button>
</div>
<div data-test-id="counter" style="font-size: 200%; padding: 30px;">
<span>Count:</span>
<span>{count}</span>
</div>
</main>
```
ã¯ãªãã¯ãããšã«ãŠã³ããå¢ãããæžã£ããããã·ã³ãã«ãªããŒãžã§ããèµ·åããŠåäœã確èªããŸãã
```console
npm run dev
```
![[2022-10-30-13-22-12.gif]]
## [[Playwright]]ã®ã€ã³ã¹ããŒã«
å
¬åŒããã¥ã¡ã³ãããã奜ã¿ã®ã€ã³ã¹ããŒã«æ¹æ³ãéžæããŸãã
<div class="link-card">
<div class="link-card-header">
<img src="https://playwright.dev/img/playwright-logo.svg" class="link-card-site-icon"/>
<span class="link-card-site-name">playwright.dev</span>
</div>
<div class="link-card-body">
<div class="link-card-content">
<div>
<p class="link-card-title">Installation | Playwright</p>
</div>
<div class="link-card-description">
Playwright Test was created specifically to accommodate the needs of end-to-end testing. Playwright ...
</div>
</div>
<img src="https://repository-images.githubusercontent.com/221981891/8c5c6942-c91f-4df1-825f-4cf474056bd7" class="link-card-image" />
</div>
<a href="https://playwright.dev/docs/intro"></a>
</div>
ç§ã¯[[npm]]ã§ã€ã³ã¹ããŒã«ããŸãããå
ã»ã©äœæãã[[Svelte]]ãããžã§ã¯ãã®äžã§ã³ãã³ããå®è¡ããŸãã
```console
$ npm init playwright@latest
â Where to put your end-to-end tests? · tests
â Add a GitHub Actions workflow? (y/N) · false
â Install Playwright browsers (can be done manually via 'npx playwright install')? (Y/n) · true
```
[[Playwright]]ã§äœ¿ããã©ãŠã¶ãã€ã³ã¹ããŒã«ããããšãªãå Žåã¯ããããã®ããŠã³ããŒããè¡ãããããå°ãæéãããããŸãã
ã€ã³ã¹ããŒã«ãå®äºããããã¹ããå®è¡ããŠåäœç¢ºèªããŸãã
```console
$ npx playwright test
Running 3 tests using 3 workers
3 passed (6s)
To open last HTML report run:
npx playwright show-report
```
ãªããããŒãžã§ã³ã¯`1.27.1`ã§ãã
```console
$ npx playwright --version
Version 1.27.1
```
> [!info] [[VSCode]]ã§[[Playwright]]ã䜿ãæ¹æ³
>
æè¿ã¯[[VSCode]]ã§äœ¿ãã[[Playwright Test for VSCode]]ãšãã䟿å©ãªãã®ããããŸãã[[VSCode]]ã[[Playwright]]ãéçºããŠãã[[Microsoft]]ã®éçºãªã®ã§ä¿¡é Œæ§ãæ矀ã§ããã
>
> <div class="link-card"> <div class="link-card-header"> <img src="https://playwright.dev/img/playwright-logo.svg" class="link-card-site-icon"/> <span class="link-card-site-name">playwright.dev</span> </div> <div class="link-card-body"> <div class="link-card-content"> <div> <p class="link-card-title">Getting started - VS Code | Playwright</p> </div> <div class="link-card-description"> Playwright Test was created specifically to accommodate the needs of end-to-end testing. Playwright ... </div> </div> <img src="https://repository-images.githubusercontent.com/221981891/8c5c6942-c91f-4df1-825f-4cf474056bd7" class="link-card-image" /> </div> <a href="https://playwright.dev/docs/getting-started-vscode"></a></div>
>
> ãã ãç§ã®ç°å¢ ([[Windows 10]]) ã§ã¯äžéšã®æ©èœã䜿ããªãã£ããã[[CLI]]ã®æ¹ãæ©èœãè±å¯ã§å°ãããšããªããšãã£ãçç±ãããæ¬èšäºã§ã¯è§Šããªãããšã«ããŸããã
> > [!add] #2022-11-21 è¿œèš
> > [[Playwright Test for VSCode]]ã®v1.0ã«ãŠ[[Windows 10]]ã§ãäžéãæ©èœãåãããã«ãªããŸããããšãã£ã¿äžã§ã³ãŒãããããã°ã§ããã®ã§ãçšéã«ãã£ãŠäœ¿ãåããã®ãããããã§ãã
## [[Playwright]]ã®èšå®ãã¡ã€ã«
`playwright.config.ts`ãèšå®ãã¡ã€ã«ã§ãããã¹ãã«å¿
èŠãªèšå®ã®ã»ãšãã©ãããã§ã«ã¹ã¿ãã€ãºå¯èœã§ãã詳现ã¯å
¬åŒããã¥ã¡ã³ããã芧ãã ããã
<div class="link-card">
<div class="link-card-header">
<img src="https://playwright.dev/img/playwright-logo.svg" class="link-card-site-icon"/>
<span class="link-card-site-name">playwright.dev</span>
</div>
<div class="link-card-body">
<div class="link-card-content">
<div>
<p class="link-card-title">Configuration | Playwright</p>
</div>
<div class="link-card-description">
Playwright Test provides options to configure the default browser, context and page fixtures. For ex...
</div>
</div>
<img src="https://repository-images.githubusercontent.com/221981891/8c5c6942-c91f-4df1-825f-4cf474056bd7" class="link-card-image" />
</div>
<a href="https://playwright.dev/docs/test-configuration"></a>
</div>
ããšã§äœåºŠãèšå®å€æŽããããšã«ãªããŸãããã¿ã€ã ã¢ãŠã30ç§ã¯é·ãã®ã§ãããããã5ç§ã«å€æŽããŠãããŸãã
```diff
- timeout: 30 * 1000,
+ timeout: 5 * 1000,
```
ããšãæ¯å3ã€ã®ãã©ãŠã¶ã§ç¢ºèªããã®ãç¡é§ãªã®ã§[[Chromium]]以å€ãã³ã¡ã³ãã¢ãŠãããŸããå®éã®ãããã¯ãã§ãã¹ãããå Žåã¯ãå¿
èŠãªãã®ããã¹ãŠéžã³ãŸãããã
```diff
projects: [
{
name: 'chromium',
use: {
...devices['Desktop Chrome'],
},
},
- {
- name: 'firefox',
- use: {
- ...devices['Desktop Firefox'],
- },
- },
-
- {
- name: 'webkit',
- use: {
- ...devices['Desktop Safari'],
- },
- },
+ // {
+ // name: 'firefox',
+ // use: {
+ // ...devices['Desktop Firefox'],
+ // },
+ // },
+ //
+ // {
+ // name: 'webkit',
+ // use: {
+ // ...devices['Desktop Safari'],
+ // },
+ // },
```
## [[Locator]]ã§èŠçŽ ãç¹å®ãã
[[E2Eãã¹ã]]ããŒã«ãšèšãã°ãçã£å
ã«çŽ¹ä»ãããç¥èããæäœããšãã¢ãµãŒã·ã§ã³ãã ãšæããŸããããããæ¬èšäºã§ã¯å
ã«[[Locator]]ã«ã€ããŠèª¬æããŸãã
<div class="link-card">
<div class="link-card-header">
<img src="https://playwright.dev/img/playwright-logo.svg" class="link-card-site-icon"/>
<span class="link-card-site-name">playwright.dev</span>
</div>
<div class="link-card-body">
<div class="link-card-content">
<div>
<p class="link-card-title">Locators | Playwright</p>
</div>
<div class="link-card-description">
Locator]s are the central piece of Playwright's auto-waiting and retry-ability. In a nutshell, locat...
</div>
</div>
<img src="https://repository-images.githubusercontent.com/221981891/8c5c6942-c91f-4df1-825f-4cf474056bd7" class="link-card-image" />
</div>
<a href="https://playwright.dev/docs/locators"></a>
</div>
å
¬åŒããã¥ã¡ã³ãããåŒçšãã[[Locator]]ã®èª¬æã¯ä»¥äžã®éãã§ãã
> Locators are the central piece of Playwright's auto-waiting and retry-ability. In a nutshell, locators represent a way to find element(s) on the page at any moment. Locator can be created with the page.locator(selector[, options]) method.
ãã£ããèšããšãGUIäžã®ããŒã¹ãç¹å®ããæ段/æ¹æ³ã§ãããæäœãã«ãããã¢ãµãŒã·ã§ã³ãã«ããã察象ãã¯å¿
èŠã§ããããšãã°ããããã¿ã³ãã¯ãªãã¯ãããªãããââãã¿ã³ãã¯ãªãã¯ããšããã³ãŒããèšè¿°ããŸãããªã¹ãã«è¡šç€ºãããæååãã¢ãµãŒããããªãããââãªã¹ãã«xxxãšè¡šç€ºãããŠããããšã確èªããšããã³ãŒããèšè¿°ããŸããäžèšã®ãââãã¿ã³ãããââãªã¹ããã«ããããã®ã[[Locator]]ã§ãã
[[Locator]]ã¯`page.locator(ã»ã¬ã¯ã¿)`ãšãã圢ã§äœæããŸãã`App.svelte`ã®ã±ãŒã¹ã§äŸãæããŠã¿ãŸãããã
```html
<main>
<h1>Playwright Svelte Sample</h1>
<h2>Push "Increment/Decrement" button</h2>
<div style="justify-content: center; gap: 10px;">
<button on:click={() => count++}>Increment</button>
<button on:click={() => count--}>Decrement</button>
</div>
<div data-test-id="counter" style="font-size: 200%; padding: 30px;">
<span>Count:</span>
<span>{count}</span>
</div>
</main>
```
`Incrementãã¿ã³`ãš`ã«ãŠã³ã¿ãŒ`ã®[[Locator]]ã¯ä»¥äžã®ããã«è¡šçŸã§ããŸãã
![[Pasted image 20221030155444.png]]
`page.getByText(/^Increment$/)`ã¯ã`^Increment
ã®æ£èŠè¡šçŸãå«ãããã¹ãããã€èŠçŽ ããæå³ããŸããã€ãŸããã`Increment`ãšããã¹ããå®å
šäžèŽããèŠçŽ ãã®ããšãæããããã`Incrementãã¿ã³`ãšãªããŸãã
`page.locator(':right-of(:text("Count:"))')`ã¯ã`Count:`ãå«ãèŠçŽ ã®å³åŽã®èŠçŽ (è¿ãé )ããæå³ããŸããããã¯`<span>{count}</span>`ãæå³ããŸãã[[DOM]]ã®æ§é ã§ã¯ãªãã**ç»é¢äžã®èŠãç®(é
眮座æš)ããçžå¯Ÿçã«èŠçŽ ãç¹å®ã§ãã**ããã`ã«ãŠã³ã¿ãŒ`ã®ããã«ç¹å®ãé£ããèŠçŽ ã®[[Locator]]ãäœæããå Žåã«äŸ¿å©ã§ãã
## ãã¹ãäœææã«äœ¿ãå®è¡ãªãã·ã§ã³
[[Locator]]ã«ã€ããŠåŠãã ã®ã§ã`Incrementãã¿ã³`ãã¯ãªãã¯ããã³ãŒããæžããŠã[[Playwright]]ã§å®è¡ããŠã¿ãŸãããã`tests/example.spec.ts`ã以äžã®ããã«å€æŽããŸãã
```ts
import { test, expect } from "@playwright/test";
test("Test App.svelte", async ({ page }) => {
await page.goto("localhost:5173");
// Incrementãã¿ã³ã®Locatoräœæ
const incrementButton = page.getByText(/^Increment$/);
// Incrementãã¿ã³ãã¯ãªãã¯
await incrementButton.click();
// ããéããªãããã«5ç§åŸ
ã€
await page.waitForTimeout(5000);
}
```
ãã©ãŠã¶ã®æäœã¯éåæåŠçã«ãªãããã`await`ããŒã¯ãŒããå¿
é ã§ããä»ãå¿ããŠããšã©ãŒã«ã¯ãªããŸããã®ã§æ³šæããŠãã ããã(åŠçã®å®äºãåŸ
ããã«æ¬¡ã®åŠçã移ãããå Žåé€ã)
ãã¹ããå®è¡ããŠã¿ãŸãã
```console
npx playwright test
```
ããã¯æåãããšæããŸã...ããæ¬åœã«ããŸããã£ãŠããã®ãäžå®ã«ãªããŸãããããã¹ãéçºæã«äœ¿ããå®è¡ãªãã·ã§ã³ã玹ä»ããŸãã
### ãããã¬ã¹ã¢ãŒããç¡å¹ã«ããŠå®è¡
`--headed`ãªãã·ã§ã³ãæå®ããŠå®è¡ãããšããã©ãŠã¶ã®æäœãç»é¢äžã§ç¢ºèªã§ããŸãã
```console
npx playwright test --headed
```
ã¯ãªãã¯ã¯äžç¬ãªã®ã§èçŒã§ã®ç¢ºèªã¯é£ãããšæããŸã...ããã«ãŠã³ã¿ãŒã1ã«ãªãã5ç§çµã£ãŠããçµäºããããšã確èªã§ãããšæããŸãã
### ãããã°ã¢ãŒã
ãããã¬ã¹ã¢ãŒããç¡å¹ã«ããããšã§ãæäœã®æ§åã¯åãããŸãããã ããã¹ãã³ãŒããééã£ãŠããå Žåã«äœãåé¡ãªã®ãã調ã¹ãããšã¯å°é£ã§ãããã`waitForTimeout`ãé©å®å
¥ããŠã[[Chrome devtools]]ãéããŠ...ãªã©ãšãã£ãŠããŠã¯æ¥ãæ®ããŠããŸããŸãã
`--debug`ãªãã·ã§ã³ãæå®ããŠå®è¡ãããšã1è¡ããšã«ã¹ããããªãŒããŒããŠãã¹ããå®è¡ã§ããããã«ãªããŸãã
```console
npx playwright test --debug
```
èµ·åãšåæã«`--headed`ã®ãšãåæ§ããã©ãŠã¶ã衚瀺ãããŸããå ããŠã[[Playwright Inspector]]ãšåŒã°ãããŠã£ã³ããŠã衚瀺ãããŸãã[[Playwright]]çšã®ç°¡æçãª[[Chrome devtools]]ã¿ãããªãã®ã§ãã
![[Pasted image 20221030161546.png]]
1è¡ãã€ã¹ããããªãŒããŒããŠç¶æ³ã確èªã§ããããããã¹ããæåŸ
éãåäœããªãå Žåã®ãããã°ã«ãšãŠã䟿å©ã§ãã
![[Pasted image 20221030162339.png]]
ãŸããExploreã¯[[Locator]]ãååŸããããã®ã»ã¬ã¯ã¿ (`page.locator(ã»ã¬ã¯ã¿)`) ãæå®ããããšã§ã察象ãšãªãèŠçŽ ããã®å Žã§ç¢ºèªã§ããŸãã
![[Pasted image 20221030162521.png]]
äžèšã®äŸã§ã¯ã`Increment`ãå«ãŸããèŠçŽ ããååŸãããããããŒãžå
ã§2ã€ã®èŠçŽ ã[[Locator]]ã®åè£ãšãªããŸããããã©ã«ãã§ã¯[[Locator]]ã®åè£ãšãªãèŠçŽ ã2ã€ä»¥äžååšããå Žåããã¹ãã倱æããŠçµäºããŸãããªããªããããã¯æ¬æ¥ã1ã€ã®èŠçŽ ãç¹å®ãããããšãæåŸ
ããŠããããã§ããããã¯ã`Incrementãã¿ã³`ã®[[Locator]]ãäœæããéã`page.getByText("Increment")`ãšæžããªãã£ãçç±ã§ãã
ä»ã®ãªãã·ã§ã³ã¯å
¬åŒããã¥ã¡ã³ããã芧ãã ããã
<div class="link-card">
<div class="link-card-header">
<img src="https://playwright.dev/img/playwright-logo.svg" class="link-card-site-icon"/>
<span class="link-card-site-name">playwright.dev</span>
</div>
<div class="link-card-body">
<div class="link-card-content">
<div>
<p class="link-card-title">Running Tests | Playwright</p>
</div>
<div class="link-card-description">
You can run a single test, a set of tests or all tests. Tests can be run on one browser or multiple ...
</div>
</div>
<img src="https://repository-images.githubusercontent.com/221981891/8c5c6942-c91f-4df1-825f-4cf474056bd7" class="link-card-image" />
</div>
<a href="https://playwright.dev/docs/running-tests#debugging-tests"></a>
</div>
## ã¢ãµãŒã·ã§ã³ã§çµæã確èªãã
ãããŸã§ã¯ãã©ãŠã¶ã®èªåæäœã«é¢ããããšã玹ä»ããŠããŸãããããããã¯æäœçµæãæåŸ
éãããã確èªããæ¹æ³ãã¢ãµãŒã·ã§ã³ã«ã€ããŠçŽ¹ä»ããŸãã
`tests/example.spec.ts`ã以äžã®ããã«å€æŽããŸãã
```ts
import { test, expect } from "@playwright/test";
test("Test App.svelte", async ({ page }) => {
await page.goto("localhost:5173");
const incrementButton = page.getByText(/^Increment$/);
await incrementButton.click();
// ãCount:ããšããæåãå«ãèŠçŽ ããå³åŽã«ããèŠçŽ ãLocatorãšããŠååŸ
const counter = page.locator(':right-of(:text("Count:"))');
// ã«ãŠã³ã¿ãŒã®ããã¹ãã1ãšäžèŽããã確èª
await expect(counter).toHaveText("1");
}
```
`expect(counter).toHaveText("1")`ã®éšåããã€ã³ãã§ãã[[Locator]]ã瀺ãèŠçŽ ã®ããã¹ãéšåã`1`ãšäžèŽãããã確èªããŠããŸãã
![[Pasted image 20221030164048.png]]
ä»åã¯æåŸ
éããªã®ã§ããã¹ãã¯æåããŸããã¢ãµãŒã·ã§ã³ã«äœ¿ããã¡ãœããã¯æ²¢å±±ãããŸãã®ã§ã詳现ã¯å
¬åŒããã¥ã¡ã³ããã芧ãã ããã
<div class="link-card">
<div class="link-card-header">
<img src="https://playwright.dev/img/playwright-logo.svg" class="link-card-site-icon"/>
<span class="link-card-site-name">playwright.dev</span>
</div>
<div class="link-card-body">
<div class="link-card-content">
<div>
<p class="link-card-title">Assertions | Playwright</p>
</div>
<div class="link-card-description">
Playwright Test uses expect library for test assertions. This library provides a lot of matchers lik...
</div>
</div>
<img src="https://repository-images.githubusercontent.com/221981891/8c5c6942-c91f-4df1-825f-4cf474056bd7" class="link-card-image" />
</div>
<a href="https://playwright.dev/docs/test-assertions"></a>
</div>
ãŸãã`expect`ã®åã«`await`ãä»ãå¿ãããšæåŸ
éãåäœããŸããããšã©ãŒãåºãªããããããããããã€ã³ããšãªã£ãŠããŸãã詳现ã¯[[ðPlaywrightã®toHaveTextãæåŸ
éãåããªã]]ãã芧ãã ããã
<div class="link-card">
<div class="link-card-header">
<img src="https://publish-01.obsidian.md/access/35d05cd1bf5cc500e11cc8ba57daaf88/favicon-64.png" class="link-card-site-icon"/>
<span class="link-card-site-name">minerva.mamansoft.net</span>
</div>
<div class="link-card-body">
<div class="link-card-content">
<div>
<p class="link-card-title">ðPlaywrightã®toHaveTextãæåŸ
éãåããªã - Minerva</p>
</div>
<div class="link-card-description">
ðPlaywrightã®toHaveTextãæåŸ
éãåããªã - Minerva
</div>
</div>
<img src="https://publish-01.obsidian.md/access/35d05cd1bf5cc500e11cc8ba57daaf88/Notes/attachments/minerva-image.webp" class="link-card-image" />
</div>
<a
class="internal-link"
data-href="ðPlaywrightã®toHaveTextãæåŸ
éãåããªã"
></a>
</div>
## HTMLã¬ããŒãã§ãã¹ãçµæã確èªãã
ããã©ã«ãã§ã¯ã[[Playwright]]ã®ãã¹ãã倱æãããšèªåã§[[HTML]]ã¬ããŒãã衚瀺ãããŸãã
<div class="link-card">
<div class="link-card-header">
<img src="https://playwright.dev/img/playwright-logo.svg" class="link-card-site-icon"/>
<span class="link-card-site-name">playwright.dev</span>
</div>
<div class="link-card-body">
<div class="link-card-content">
<div>
<p class="link-card-title">Reporters | Playwright</p>
</div>
<div class="link-card-description">
Playwright Test comes with a few built-in reporters for different needs and ability to provide custo...
</div>
</div>
<img src="https://repository-images.githubusercontent.com/221981891/8c5c6942-c91f-4df1-825f-4cf474056bd7" class="link-card-image" />
</div>
<a href="https://playwright.dev/docs/test-reporters#html-reporter"></a>
</div>
ããšãã°ãå
ã»ã©ã®ãã¹ãã³ãŒãã®æåŸ
å€ãå€æŽããŠã¿ãŸãããã
```ts
import { test, expect } from "@playwright/test";
test("Test App.svelte", async ({ page }) => {
await page.goto("localhost:5173");
const incrementButton = page.getByText(/^Increment$/);
await incrementButton.click();
const counter = page.locator(':right-of(:text("Count:"))');
// å®éã¯1ã ãã77ã«ããŠãããšå€±æããã
await expect(counter).toHaveText("77");
}
```
ãã¹ããå®è¡ããŸãã
```console
npx playwright test
```
倱æãããšåæã«ããã©ãŠã¶ã§ä»¥äžã®ãããªã¬ããŒããåºåãããŸãã
![[Pasted image 20221030164934.png]]
ãã¹ãã³ãŒãã«å¯ŸããŠã以äžã®ãããªæ
å ±ãåºåãããŠããŸãã
- ã©ã®è¡ãå®è¡ããã
- ã©ã®è¡ã«ã©ããããæéãããã£ãã
- ã©ãã§å€±æããã
- 倱æããå Žåã«æåŸ
å€ãšå®éã®å€ã¯ããããã©ãã ã£ãã
ä»åã¯ãã¹ãã1ã€ãããããŸããããè€æ°ã®æ§é åããããã¹ããå®è¡ããå Žåãããã«æ²¿ã£ãUIãšãªããŸããã³ã³ãœãŒã«ãããçŽæçã§åãããããã§ããã
## [[Trace Viewer]]ã§å€±æã®çç±ããã³ãã€ã³ãã«èª¿ã¹ã
[[#ãããã°ã¢ãŒã]]ã¯äŸ¿å©ã§ããããã¹ãå€æŽäžã§ã¯ãªãCIãªã©å®åžžçãªãã¹ãã§ã¯äœ¿çšã§ããŸãããäžæ¹ããã®ãããªãšãã«å€±æããŠãããããŒã«ã«ã§[[#ãããã°ã¢ãŒã]]ã«ãŠç¢ºèªããã®ãé¢åã§ãããããªãšãã¯[[Trace Viewer]]ã䟿å©ã§ãã
<div class="link-card">
<div class="link-card-header">
<img src="https://playwright.dev/img/playwright-logo.svg" class="link-card-site-icon"/>
<span class="link-card-site-name">playwright.dev</span>
</div>
<div class="link-card-body">
<div class="link-card-content">
<div>
<p class="link-card-title">Trace Viewer | Playwright</p>
</div>
<div class="link-card-description">
Playwright Trace Viewer is a GUI tool that lets you explore recorded Playwright traces of your tests...
</div>
</div>
<img src="https://repository-images.githubusercontent.com/221981891/8c5c6942-c91f-4df1-825f-4cf474056bd7" class="link-card-image" />
</div>
<a href="https://playwright.dev/docs/trace-viewer-intro"></a>
</div>
### ããŒã«ã«ã§å®è¡ããå Žå
`--trace on`ãªãã·ã§ã³ãã€ããŠå®è¡ããŸãã
```console
npx playwright test --trace on
```
ãã¹ãã«å€±æããŠ[[#HTMLã¬ããŒã]]ã衚瀺ããããšã[[Trace Viewer]]ã®å°ç·ãè¿œå ãããŠããŸãã
![[Pasted image 20221030165925.png]]
ç»åãã¯ãªãã¯ãããš[[Trace Viewer]]ãèµ·åããŸããåã¹ãããã®èšé²ã`Actions`ã«èšé²ãããŠããŸãã®ã§ãã¯ãªãã¯ãããšãã®æã®ç»é¢ãšæ
å ±ãé²èŠ§ã§ããŸãã
![[Pasted image 20221030170057.png]]
### CIã§å®è¡ããå Žå
`--trace on`ãªãã·ã§ã³ã¯äŸ¿å©ã§ãããéåžžã®ãã¹ãå®è¡ã«æ¯ã¹ãŠæéãããããŸããçµæããã¹ãŠOKã®å Žåã[[Trace Viewer]]ã®ç¢ºèªã¯äžèŠãªããç¡é§ãçããŠããŸãã§ããããããšãã£ãŠãåé¡ãèµ·ãã£ãŠãã`--trace on`ã§å®è¡ããã®ã¹ããŒããšã¯èšããŸããã
[[Playwright]]ã§ã¯ãããèŠè¶ããŠã`playwright.config.ts`ã«ä»¥äžã®ãããªèšå®ããããŠããŸãã
```ts
retries: process.env.CI ? 2 : 0,
.
.
use: {
.
.
trace: "on-first-retry",
},
```
ããã¯ã**CIã®ãšãã ãã倱æããŠã2åãŸã§ãªãã©ã€ãè¡ãã1åç®ã®ãªãã©ã€ã®ã¿ãã¬ãŒã¹ãæå¹ã«ãã** ãšããæå³ã§ãããããªããçµæããã¹ãŠOKã®ãšãã§ããã¡ãªããã¯ãããŸããã
å®éã«CIã§å®è¡ãã[[#HTMLã¬ããŒã]]ãèŠãŠã¿ãŸãããã1åç®ã®ãã¹ãçµæã«ã¯[[Trace Viewer]]ãžã®å°ç·ããããŸããã
![[Pasted image 20221030170805.png]]
1床ç®ã®ãªãã©ã€ã®ã¿ã[[Trace Viewer]]ãžã®å°ç·ãååšããŸãã
![[Pasted image 20221030170843.png]]
## APIã¬ã¹ãã³ã¹ãããæ¿ãã
Webã¢ããªã±ãŒã·ã§ã³ã®[[E2Eãã¹ã]]ãè¡ãäžã§ãæãåä»ãªåé¡ã®1ã€ãããã¹ãçšã«APIã¬ã¹ãã³ã¹ãã©ãããæ¿ããããšããããšã§ãããããã¹ãå®è¡æã®ã¢ããªã±ãŒã·ã§ã³èµ·åã³ãã³ãã«ç°å¢å€æ°ãæž¡ãããããã¯ã·ã§ã³ã³ãŒãã®äžã§ãããåå²ããŠ[[ã¹ã¿ã]]ã[[ãã§ã€ã¯]]ã䜿ãæ¹æ³ããããŸãããã ããããã¯ãããã¯ã·ã§ã³ã«äžèŠãªã³ãŒãã§ãããã奜ãŸãããããŸããã
幞ããªããšã«ã[[Playwright]]ã«ã¯Networkã¬ã€ã€ãŒã«ä»å
¥ããŠãªã¯ãšã¹ããã¬ã¹ãã³ã¹ãæäœããæ©èœããããŸãã
<div class="link-card">
<div class="link-card-header">
<img src="https://playwright.dev/img/playwright-logo.svg" class="link-card-site-icon"/>
<span class="link-card-site-name">playwright.dev</span>
</div>
<div class="link-card-body">
<div class="link-card-content">
<div>
<p class="link-card-title">Network | Playwright</p>
</div>
<div class="link-card-description">
Playwright provides APIs to monitor and modify network traffic, both HTTP and HTTPS. Any requests th...
</div>
</div>
<img src="https://repository-images.githubusercontent.com/221981891/8c5c6942-c91f-4df1-825f-4cf474056bd7" class="link-card-image" />
</div>
<a href="https://playwright.dev/docs/network"></a>
</div>
### ãã¹ã察象ãããžã§ã¯ãã®å€æŽ
ãã®æ©èœã䜿ãããã`App.svelte`ãAPIãªã¯ãšã¹ãã䌎ãããŒãžã«å€æŽããŸããAPIã®ãšã³ããã€ã³ãã¯[[Reqres]]ã䜿ãããŠããã ããŸããã
```html
<script lang="ts">
interface Member {
id: number;
email: string;
first_name: string;
last_name: string;
avatar?: string;
}
let members: Member[] = [];
const fetchMembers = async () => {
const res = await fetch("https://reqres.in/api/users?page=2");
members = (await res.json()).data;
};
</script>
<main>
<h1>Playwright Svelte Sample</h1>
<h2>Push "Increment/Decrement" button</h2>
<h2>Click to fetch members</h2>
<button on:click={fetchMembers}>Fetch members</button>
<div style="text-align: left">
<ul data-test-id="member-list">
{#each members as member}
<li>{member.first_name} {member.last_name}</li>
{/each}
</ul>
<pre class="json">{JSON.stringify(members, null, 2)}</pre>
</div>
</main>
<style>
.json {
background-color: darkslategray;
color: whitesmoke;
padding: 10px;
}
</style>
```
ãã¿ã³ãã¯ãªãã¯ãããš[[Reqres]]ãããŠãŒã¶ãŒæ
å ±ã[[JSON]]ã§ååŸããäžã«ç®æ¡æžããšããŠãäžã«çããŒã¿ãšããŠè¡šç€ºããããŒãžã§ãã
![[2022-10-30-18-59-07.gif]]
### ã¬ã¹ãã³ã¹ãæžãæãã
ããã§ã¯[[Reqres]]ã®APIã¬ã¹ãã³ã¹ã«ä»å
¥ããŠããã¹ãçšã®ããŒã¿ã«ããæ¿ããŠã¿ãŸãããããŸãã¯ãã¹ãçšã®ããŒã¿ãå®çŸ©ããŸããçé¢ç®ã«ãããªã以äžã®ãªã¯ãšã¹ãçµæãæš¡å£ããå¿
èŠããããŸãã
https://reqres.in/api/users?page=2
ãã ãä»åã®ãã¹ã察象ãããžã§ã¯ãã§å©çšããŠããããŒã¿ã¯äžéšã§ãããããäžèŠãªããŒã¿ã¯ãã¹ãŠã«ããããŸãããã®ãããã®å€æã¯ããã®æã
ã®èŠä»¶ã«ãã£ãŠå€ãããŸãã®ã§ã絶察çãªæ£è§£ã¯ãªããšæã£ãŠããŸãã
ä»åã¯ä»¥äžã®ãããªãããŒ[[JSON]]ãçšæããŸããã
```json
{
data: [
{
first_name: "ããã",
last_name: "æçŽ ãš",
},
{
first_name: "ããã",
last_name: "æçŽ ãš",
},
],
}
```
`tests/example.spec.ts`ãæžãæããŸããåããŠç»å ŽããæŠå¿µã«ã¯ã³ãŒãã³ã¡ã³ããå
¥ããŠããŸãã
```ts
import { test, expect } from "@playwright/test";
test("Test App.svelte", async ({ page }) => {
// URLã®æåŸã /api/users?page=2 ã®å Žåã«ã¹ããŒã¿ã¹200ã§bodyã®stringãè¿ã
await page.route("**/api/users?page=2", (route) =>
route.fulfill({
status: 200,
body: JSON.stringify({
data: [
{
first_name: "ããã",
last_name: "æçŽ ãš",
},
{
first_name: "ããã",
last_name: "æçŽ ãš",
},
],
}),
})
);
await page.goto("localhost:5173");
// ãFetch membersããšããã¹ããäžèŽãããã¿ã³ãLocatorãšããŠååŸããã¯ãªãã¯
const fetchButton = page.getByRole("button", { name: "Fetch members" });
await fetchButton.click();
// data-test-id=member-list ã®DOMãLocatorãšããŠååŸ
const list = page.locator("data-test-id=member-list");
// listã«ããããããšããæååãå«ãŸããŠããããšã確èª
await expect(list).toHaveText(/ããã/);
// listã«ããããããšããæååãå«ãŸããŠããããšã確èª
await expect(list).toHaveText(/ããã/);
}
```
[[#ãããã°ã¢ãŒã]]ã§å®è¡ããŠã¿ãŸãã
```console
npx playwright test --debug
```
ã¡ãããšã¬ã¹ãã³ã¹ãæžãæãã£ãŠããããšã確èªã§ããŸããã
![[Pasted image 20221030193132.png]]
ãã®æ©èœã䜿ãã°ããããã¯ã·ã§ã³ã³ãŒãã«[[ãã¹ãããã«]]ãä»èŸŒãã®ã«æ¯ã¹ãŠé¥ãã«ãã¹ãã®äœæããŒãã«ãäžããã§ããããäœããããããã¯ã·ã§ã³ã³ãŒãã®å®è£
ã[[ã¢ãã¯]]ã[[ã¹ã¿ã]]ã䜿ãã«å°é£ãªèšèšãšãªã£ãŠããŠãé¢ä¿ãªãã®ã§ããã¬ã¬ã·ãŒã³ãŒãã«æ©ãŸãããŠããéçºè
ã«ãšã£ãŠã¯æ£çŽå¥åã ãšæããŸãã
ãšã¯ããããã¹ãã®ããã«å¿
èŠãªããŒã¿ãèšèšããããããã¹ãã³ãŒãã«å®è£
ããããšã ãã§ãããªãã®åŽåã ãšæããŸããæçãããããã¯ãã«å¯ŸããŠã¬ã¹ãã³ã¹ã®ããæ¿ããå®æœããããšããŠããå¿
èŠãªãªã¯ãšã¹ãã®å€ãã«æ«æããŠããŸããšæããŸãã
ãããªããªãããã«ããæ®æ®µããAPIãªã¯ãšã¹ããè¿œå ãããšãã¯ããã¹ãçšã®ããŒã¿ãèšèš/å®çŸ©ãã[[Playwright]]ã®ãã¹ãã³ãŒããšããŠå©çšããç¿æ
£ãã€ããã®ãããã§ããããåãããã³ãã³ããã£ãŠããã°ã1åãããã®æéã¯ãããŸã§ã§ã¯ãããŸãããäœããæ¢åã³ãŒãã«ãã¹ããã¡ãããšæžãããŠããã°ãåŸããjoinããéçºè
ããã¹ãããã£ãœããããšãžã®ææ¢åã«ããªããŸãã
## [[Page Object Model]]ã§ã¡ã³ããã³ã¹ã³ã¹ããäžãã
äžèŠæš¡ä»¥äžã®ãããžã§ã¯ãã§ã¯ãã¹ãã®ã¡ã³ããã³ã¹ã³ã¹ããé«ããªããããã§ããç¹ã«UIå€æŽæã[[UIãã¬ãŒã ã¯ãŒã¯]]æŽæ°æã«[[DOM]]æ§æãå€ãã£ããšããä»ãŸã§ååŸã§ãã[[Locator]]ãååŸã§ããªããªãããšã¯å€ã
ãããŸãã
[[Page Object Model]]ã¯ãã®ãããªãŠãŒã¹ã±ãŒã¹ã«äœ¿ãããšèããŠããŸãã
<div class="link-card">
<div class="link-card-header">
<img src="https://playwright.dev/img/playwright-logo.svg" class="link-card-site-icon"/>
<span class="link-card-site-name">playwright.dev</span>
</div>
<div class="link-card-body">
<div class="link-card-content">
<div>
<p class="link-card-title">Page Object Models | Playwright</p>
</div>
<div class="link-card-description">
Large test suites can be structured to optimize ease of authoring and maintenance. Page object model...
</div>
</div>
<img src="https://repository-images.githubusercontent.com/221981891/8c5c6942-c91f-4df1-825f-4cf474056bd7" class="link-card-image" />
</div>
<a href="https://playwright.dev/docs/pom"></a>
</div>
ããã¯`page`ãªããžã§ã¯ããã©ããããŠãé«ã¬ãã«ã®IFãæäŸããŸãã
å
ã»ã©ã®`tests/example.spec.ts`ã䜿ã£ãŠã[[Page Object Model]]ã®èšèšãå°å
¥ããŠã¿ãŸããããå°å
¥åã®ã³ãŒãã¯ä»¥äžã®ããã«ãªããŸãã
```ts
import { test, expect } from "@playwright/test";
test("Test App.svelte", async ({ page }) => {
await page.route("**/api/users?page=2", (route) =>
route.fulfill({
status: 200,
body: JSON.stringify({
data: [
{
first_name: "ããã",
last_name: "æçŽ ãš",
},
{
first_name: "ããã",
last_name: "æçŽ ãš",
},
],
}),
})
);
await page.goto("localhost:5173");
const fetchButton = page.getByRole("button", { name: "Fetch members" });
await fetchButton.click();
const list = page.locator("data-test-id=member-list");
await expect(list).toHaveText(/ããã/);
await expect(list).toHaveText(/ããã/);
}
```
### [[Locator]]ã¬ãã«ã§wrapãã
ããšãã°ã以äžã®ãããªã³ãŒãã«ãªããŸãã
```ts
import { test as base, expect } from "@playwright/test";
import type { Locator, Page } from "@playwright/test";
class MainPage {
constructor(public page: Page) {}
async setUsersJsonStub(response: Object) {
await this.page.route("**/api/users?page=2", (route) =>
route.fulfill({
status: 200,
body: JSON.stringify(response),
})
);
}
async goto() {
await this.page.goto("localhost:5173");
}
get fetchButton(): Locator {
return this.page.getByRole("button", { name: "Fetch members" });
}
get userList(): Locator {
return this.page.locator("data-test-id=member-list");
}
}
const test = base.extend<{ mainPage: MainPage }>({
mainPage: async ({ page }, use) => {
const mainPage = new MainPage(page);
await mainPage.goto();
// ããã©ã«ãã¯ãã. äžæžããå¿
èŠãªãtesté¢æ°ã®äžã§overrideãã
await mainPage.setUsersJsonStub({
data: [
{
first_name: "ããã",
last_name: "æçŽ ãš",
},
{
first_name: "ããã",
last_name: "æçŽ ãš",
},
],
});
await use(mainPage);
},
});
test("Test App.svelte", async ({ mainPage }) => {
await mainPage.fetchButton.click();
await expect(mainPage.userList).toHaveText(/ããã/);
await expect(mainPage.userList).toHaveText(/ããã/);
});
```
ã³ãŒãè¡æ°ã¯å¢ããŸãããããã¹ãã³ãŒãã¯3è¡ãŸã§ççž®ãããäœããã£ãŠããããèªæã«ãªããŸãããä»åã®èšäºã§ã¯è§ŠããŸããã§ãããã`test`ã®ç¬¬2åŒæ°ã«å«ãŸãã`mainPage`ã¯fixturesã䜿ã£ãŠããŸãã
<div class="link-card">
<div class="link-card-header">
<img src="https://playwright.dev/img/playwright-logo.svg" class="link-card-site-icon"/>
<span class="link-card-site-name">playwright.dev</span>
</div>
<div class="link-card-body">
<div class="link-card-content">
<div>
<p class="link-card-title">Advanced: fixtures | Playwright</p>
</div>
<div class="link-card-description">
Playwright Test is based on the concept of test fixtures. Test fixtures are used to establish enviro...
</div>
</div>
<img src="https://repository-images.githubusercontent.com/221981891/8c5c6942-c91f-4df1-825f-4cf474056bd7" class="link-card-image" />
</div>
<a href="https://playwright.dev/docs/test-fixtures"></a>
</div>
> [!note]
> ä»åã¯ãã¹ãŠ`example.spec.ts`ã«æžããŠããŸããŸãããã[[Page Object Model]]çšã®ã¯ã©ã¹ã¯å¥ãã¡ã€ã«ã«å®çŸ©ããæ¹ããããšæããŸãã
### éãšã³ãžãã¢ã§ãã¡ã³ãå¯èœãªã¬ãã«ãŸã§äœããã
å人çã«ã¯ã[[#Locator ã¬ãã«ã§wrapãã]]ããããå¯èªæ§ãšã¡ã³ããã³ã¹æ§ã®ãã©ã³ã¹ããããšæã£ãŠããŸããããããæ®æ®µãœãŒã¹ã³ãŒããèªãŸãªã人ã«ãã¹ãã³ãŒãã®ã¡ã³ããã³ã¹ãç¹ã«ãã¹ãã±ãŒã¹ã®äœæããé¡ãããå Žåã¯å¥ã§ããããã«ã€ã³ã¿ãŒãã§ãŒã¹ã®ã¬ãã«ãäžããè±èªã®ä»£ããã«æ¥æ¬èªã䜿ããšããéžæè¢ããããŸãã
```ts
import { test as base, expect } from "@playwright/test";
import type { Locator, Page } from "@playwright/test";
class ã¡ã€ã³ããŒãž {
constructor(public page: Page) {}
private get ãã§ãããã¿ã³(): Locator {
return this.page.getByRole("button", { name: "Fetch members" });
}
private get ãŠãŒã¶ãŒãªã¹ã(): Locator {
return this.page.locator("data-test-id=member-list");
}
async setUsersJsonStub(response: Object) {
await this.page.route("**/api/users?page=2", (route) =>
route.fulfill({
status: 200,
body: JSON.stringify(response),
})
);
}
async éã() {
await this.page.goto("localhost:5173");
}
async ãã§ãããã¿ã³ãã¯ãªãã¯() {
await this.ãã§ãããã¿ã³.click();
}
async ãŠãŒã¶ãŒãªã¹ãã«ããã¹ããå«ãŸããããšã確èª(ããã¹ã: string) {
await expect(this.ãŠãŒã¶ãŒãªã¹ã).toHaveText(new RegExp(ããã¹ã));
}
}
const test = base.extend<{ mainPage: ã¡ã€ã³ããŒãž }>({
mainPage: async ({ page }, use) => {
const 察象ããŒãž = new ã¡ã€ã³ããŒãž(page);
await 察象ããŒãž.éã();
// ããã©ã«ãã¯ãã. äžæžããå¿
èŠãªãtesté¢æ°ã®äžã§overrideãã
await 察象ããŒãž.setUsersJsonStub({
data: [
{
first_name: "ããã",
last_name: "æçŽ ãš",
},
{
first_name: "ããã",
last_name: "æçŽ ãš",
},
],
});
await use(察象ããŒãž);
},
});
test("ã¡ã€ã³ããŒãžã®ãã¹ã", async ({ mainPage: 察象ããŒãž }) => {
await 察象ããŒãž.ãã§ãããã¿ã³ãã¯ãªãã¯();
await 察象ããŒãž.ãŠãŒã¶ãŒãªã¹ãã«ããã¹ããå«ãŸããããšã確èª("ããã");
await 察象ããŒãž.ãŠãŒã¶ãŒãªã¹ãã«ããã¹ããå«ãŸããããšã確èª("ããã");
});
```
æ®æ®µè±èªã䜿ããªã人ã«å¯ŸããŠã®å¯èªæ§ã¯äžãã£ããããããŸãããèšèªã«ã€ããŠã¯ãããããã®ç°å¢ã«é©ãããã®ãéžæããã®ãè¯ããšæããŸãããã®æå³ã§ã¯å¥œã¿ã§ãããã
äžæ¹ã[[Locator]]以å€ã®åŠçãç¹ã«`expect`ã[[Page Object Model]]ã®ã¯ã©ã¹ã«æŒã蟌ãã®ã¯æå³åããéããŸãã確èªæ¹æ³ãæ°ã«ããªããŠããåé¢ã**[[#ãããã°ã¢ãŒã]]ã[[Trace Viewer]]ã§ã®åŒã³åºãã³ãŒãäœçœ®ãåããã«ãããªã**ãšããæ¬ ç¹ããããŸãã
[[Trace Viewer]]ã«é¢ããŠã¯ãã¹ã¿ãã¯ãã¬ãŒã¹ãã`test`é¢æ°å
ã®åŒã³åºãå
ã蟿ããŸãããããã[[#ãããã°ã¢ãŒã]]ã«ã€ããŠã¯ãç§ãè©Šããéããããç¥ãæ¹æ³ã¯ãããŸããã§ããã
以äžããããã¹ããæžãã®ãéçºè
ã ãã§ããã°ã[[#Locator ã¬ãã«ã§wrapãã]]ããšãæšå¥šããŸããå°ãªããšãçŸæç¹ã§ã¯ã
## ãã¹ããã©ã¯ãã£ã¹ãåèã«[[Locator]]ã®ååŸæŠç¥ãç«ãŠã
å
¬åŒããã¥ã¡ã³ãã®SelectorããŒãžã«ã¯ãã¹ããã©ã¯ãã£ã¹ã®èšè¿°ããããŸãã
<div class="link-card">
<div class="link-card-header">
<img src="https://playwright.dev/img/playwright-logo.svg" class="link-card-site-icon"/>
<span class="link-card-site-name">playwright.dev</span>
</div>
<div class="link-card-body">
<div class="link-card-content">
<div>
<p class="link-card-title">Selectors | Playwright</p>
</div>
<div class="link-card-description">
Selectors are strings that are used to create Locator]s. Locators are used to perform actions on the...
</div>
</div>
<img src="https://repository-images.githubusercontent.com/221981891/8c5c6942-c91f-4df1-825f-4cf474056bd7" class="link-card-image" />
</div>
<a href="https://playwright.dev/docs/selectors#best-practices"></a>
</div>
èšè¿°æ¹æ³ã¯äžèšãåç
§ãããšããŠãæšå¥šãããæå®æŠç¥ã¯ä»¥äžã«ãªããŸãã
- 人éãæåãšããŠèªèãããã®ããå€æ
- ããã¹ã
- placeholder
- ã©ãã«
- ããŒã«ãšããã¹ãã®çµã¿åãã
- [[data-test-id]]ããå€æ
- ã人éãæåãšããŠèªèãããã®ããããå€æŽããã or ç¹å®ãå°é£ãªãã®
ãªãã¹ãã人éããã©ãŠã¶ãæäœããŠå€æããææšãšãããã圢ã«ãªããŸããããã¹ããªã©ã®æåãšããŠåããããããã®ã¯èšãããããªã[[data-test-id]]ãç»é¢ä»æ§æžã«èšèŒãããããŒãåãšèããã°è
ã«èœã¡ãã§ãããã
ãããã®ææšãåºã«åè£ã2ã€ä»¥äžååšããå ŽåããããããããŸããããã®ãšãã¯(ããã©ã«ãèšå®ãªã)ãšã©ãŒã«ãªããŸãã®ã§ããã®ãšãã«èããã°ããã§ãããã
### åè£ã2ã€ä»¥äžååšãããšãã®å¯ŸåŠæ³
ã人éãæåãšããŠèªèãããã®ããå€æãããŠãåè£ã2ã€ä»¥äžååšããå ŽåããŸãã¯[[data-test-id]]ããå€æã§ããããèããŸãããã
ãã ã[[UIãã¬ãŒã ã¯ãŒã¯]]ãªã©ã䜿ã£ãŠããå Žåã¯ç¹ã«ã[[data-test-id]]ã䜿ããªãããšããããŸãã[[data-test-id]]ãã€ããŠã[[ãã©ã³ã¹ãã€ã«]]ããã[[DOM]]ã§æ©èœããªããªã£ãŠããŸãã±ãŒã¹ãªã©ã§ãããã®ãããªãšãã¯ã¬ã€ã¢ãŠãã«åºã¥ããã»ã¬ã¯ã¿ãŒã䜿ããŸãããã
<div class="link-card">
<div class="link-card-header">
<img src="https://playwright.dev/img/playwright-logo.svg" class="link-card-site-icon"/>
<span class="link-card-site-name">playwright.dev</span>
</div>
<div class="link-card-body">
<div class="link-card-content">
<div>
<p class="link-card-title">Selectors | Playwright</p>
</div>
<div class="link-card-description">
Selectors are strings that are used to create Locator]s. Locators are used to perform actions on the...
</div>
</div>
<img src="https://repository-images.githubusercontent.com/221981891/8c5c6942-c91f-4df1-825f-4cf474056bd7" class="link-card-image" />
</div>
<a href="https://playwright.dev/docs/selectors#selecting-elements-based-on-layout"></a>
</div>
ç¹å®èŠçŽ ãèµ·ç¹ã«ããŠãããããã äž or äž or å·Š or å³ ã«äœçœ®ããèŠçŽ ã察象ãšãªããããç»é¢äžã«è€æ°åè£ãååšããŠãã1ã€ã«çµããããšãå€ãã§ããããã§ãç¹å®ãå³ããå Žåã¯ã`.first()`ã䜿ã£ãŠæãè¿ãèŠçŽ ãååŸããŠãããã§ãããã
åãã®æ¹ã«çŽ¹ä»ãã以äžã®ç»åã§ããã«ãŠã³ã¿ãŒå€ãç¹å®ãããã`:right-of`ã䜿ã£ãŠããŸãã
![[Pasted image 20221030155444.png]]
## ãã©ãŠã¶ã®æäœãã[[Locator]]ãæäœã®ãã¹ãã³ãŒããèªåçæãã
ããŠãä»æŽã§ããã[[Playwright]]ã«ã¯ãã©ãŠã¶æäœãããã¹ãã³ãŒãã®äžéšãäœæããæ©èœããããŸãã
<div class="link-card">
<div class="link-card-header">
<img src="https://playwright.dev/img/playwright-logo.svg" class="link-card-site-icon"/>
<span class="link-card-site-name">playwright.dev</span>
</div>
<div class="link-card-body">
<div class="link-card-content">
<div>
<p class="link-card-title">Test Generator | Playwright</p>
</div>
<div class="link-card-description">
Playwright comes with the ability to generate tests out of the box and is a great way to quickly get...
</div>
</div>
<img src="https://repository-images.githubusercontent.com/221981891/8c5c6942-c91f-4df1-825f-4cf474056bd7" class="link-card-image" />
</div>
<a href="https://playwright.dev/docs/codegen-intro"></a>
</div>
`npm run dev`ã§`localhost:5173`ã«ã¢ããªã±ãŒã·ã§ã³ãèµ·åããŠããç¶æ
ã§ä»¥äžã®ã³ãã³ããå®è¡ããŠã¿ãŸãããã
```console
npx playwright codegen localhost:5173
```
æäœã«å¯ŸããŠããã¹ããã©ã¯ãã£ã¹ã«æ¥µååŸããããªã³ãŒããçæãããŸãã
![[2022-10-30-22-56-05.mp4]]
ãšã¯ãããããã ãã§å®æãšã¯ãããŸããã[[Locator]]ã«ãã£ãŠã¯è€éãªã³ãŒããçæãããŠããŸããããããã®ãŸãŸå©çšããã®ã¯ã¢ã³ããã¿ãŒã³ã§ãã
ãã®æ©èœããã®ã¿ã€ãã³ã°ã§çŽ¹ä»ããã®ã¯ãçŽåã®ã»ã¯ã·ã§ã³ã§[[#ãã¹ããã©ã¯ãã£ã¹ãåèã« Locator ã®ååŸæŠç¥ãç«ãŠã]]æ¹æ³ã玹ä»æžã ããã§ããèªåçæããããã¹ãã³ãŒãã®è¯ãæªããå€æã§ããå¿
èŠã«å¿ããŠã³ãŒããå€æŽã§ããèœåãããã°ããã®æ©èœããã£ãšäœ¿ãããªãããšæããŸãã
## ã¢ããªã±ãŒã·ã§ã³ãèµ·åãã€ã€ãã¹ããã
`webServer`ã®èšå®ãè¿œå ããããšã§ãã¢ããªã±ãŒã·ã§ã³ãèµ·åããçéã§ããããšã確èªããŠãããã¹ããå®è¡ã§ããŸãããŸããã¢ããªã±ãŒã·ã§ã³ã¯ãã¹ãçµäºæã«çµäºããŸãã
<div class="link-card">
<div class="link-card-header">
<img src="https://playwright.dev/img/playwright-logo.svg" class="link-card-site-icon"/>
<span class="link-card-site-name">playwright.dev</span>
</div>
<div class="link-card-body">
<div class="link-card-content">
<div>
<p class="link-card-title">Advanced: configuration | Playwright</p>
</div>
<div class="link-card-description">
Configuration object
</div>
</div>
<img src="https://repository-images.githubusercontent.com/221981891/8c5c6942-c91f-4df1-825f-4cf474056bd7" class="link-card-image" />
</div>
<a href="https://playwright.dev/docs/test-advanced#launching-a-development-web-server-during-the-tests"></a>
</div>
`playwright.config.ts`ã«ä»¥äžã®èšå®ãè¿œå ããŸãã
```ts
webServer: {
command: "npm run dev",
port: 5173,
reuseExistingServer: !process.env.CI,
},
```
`localhost:5173`ã«ã¢ã¯ã»ã¹ã§ããªãããšã確èªãããã®ç¶æ
ãããã¹ããå®è¡ããŸãããã
```console
npx playwright test
```
æ瀺çã«ã¢ããªã±ãŒã·ã§ã³ãèµ·åãããŠããªãã£ãã«ããããããããã¹ããæåããŸãã
> [!hint] `reuseExistingServer`ã«ã€ããŠ
> `true`ã«ãããšæ¢ã«æå®ããããŒãçªå·ã®ãµãŒããŒãèµ·åããŠãããšããããã䜿ã£ãŠãã¹ããéå§ããŸãã`false`ã«ãããšåæ§ã®ã±ãŒã¹ã§ã¯ãšã©ãŒã«ãªããŸãã(defaultã¯`false`)
>
> äžèšã®èšå®ã§ã¯CIã®ãšãã®ã¿`false`ãšãªã£ãŠããŸããããã¯ãéçºäžã ãšãã¹ãå®è¡åã«`npm run dev`ã§éçºãµãŒããŒãç«ã¡äžããŠããããšãå€ã
ããããã®å Žåã«çµäºããŠèµ·åããªããæéãçãããã§ãã(æå³ããªãã®ã§)
>
> `reuseExistingServer`ã`true`ã®å Žåããã¹ããå®äºããŠãèµ·åäžã®ã¢ããªã±ãŒã·ã§ã³ãçµäºããããšã¯ãããŸããã
## [[Docker]]ã³ã³ããã§ãã¹ããå®è¡ãã
æåŸã«ã[[Docker]]ã³ã³ããã䜿ã£ãŠãã¹ããå®è¡ããæ¹æ³ã玹ä»ããŸãã
<div class="link-card">
<div class="link-card-header">
<img src="https://playwright.dev/img/playwright-logo.svg" class="link-card-site-icon"/>
<span class="link-card-site-name">playwright.dev</span>
</div>
<div class="link-card-body">
<div class="link-card-content">
<div>
<p class="link-card-title">Docker | Playwright</p>
</div>
<div class="link-card-description">
[Dockerfile.focal] can be used to run Playwright scripts in Docker environment. These image includes...
</div>
</div>
<img src="https://repository-images.githubusercontent.com/221981891/8c5c6942-c91f-4df1-825f-4cf474056bd7" class="link-card-image" />
</div>
<a href="https://playwright.dev/docs/docker"></a>
</div>
䜿ãæšãŠã®ã³ã³ãããäœæããäžã«å
¥ããŸãã
```console
docker run -it --rm --ipc=host mcr.microsoft.com/playwright:v1.27.0-focal /bin/bash
```
READMEãããã³ãã¬ã®ãŸãŸã§ãããã³ã³ããå
ã§Cloneãããã[[GitHub]]ã«ãªããžããªãäœæããŠpushããŸããã
<div class="link-card">
<div class="link-card-header">
<img src="https://github.githubassets.com/favicons/favicon.svg" class="link-card-site-icon"/>
<span class="link-card-site-name">GitHub</span>
</div>
<div class="link-card-body">
<div class="link-card-content">
<div>
<p class="link-card-title">GitHub - tadashi-aikawa/playwright-svelte-sample</p>
</div>
<div class="link-card-description">
Contribute to tadashi-aikawa/playwright-svelte-sample development by creating an account on GitHub.
</div>
</div>
<img src="https://opengraph.githubassets.com/56e9196beaf1ce98eac68d1ab5a391e1b23a3db303c0269015b9cfa21d6db041/tadashi-aikawa/playwright-svelte-sample" class="link-card-image" />
</div>
<a href="https://github.com/tadashi-aikawa/playwright-svelte-sample.git"></a>
</div>
ã³ã³ããå
ã§cloneããŠå®è¡ããã ãã§ãã[[Playwright]]ã§äœ¿ããã©ãŠã¶ãªã©ã®äŸåé¢ä¿ã¯å
¬éã€ã¡ãŒãžã«å«ãŸããŠããã®ã§æ¥œã¡ãã§ããã
```console
git clone https://github.com/tadashi-aikawa/playwright-svelte-sample.git
cd playwright-svelte-sample
npm i
npx playwright test
```
ä»å觊ããŸããã§ããããåCIãµãŒãã¹ã«ãããæžãæ¹ã¯å
¬åŒããã¥ã¡ã³ãã§çŽ¹ä»ãããŠããŸãã
<div class="link-card">
<div class="link-card-header">
<img src="https://playwright.dev/img/playwright-logo.svg" class="link-card-site-icon"/>
<span class="link-card-site-name">playwright.dev</span>
</div>
<div class="link-card-body">
<div class="link-card-content">
<div>
<p class="link-card-title">Continuous Integration | Playwright</p>
</div>
<div class="link-card-description">
Playwright tests can be executed in CI environments. We have created sample configurations for commo...
</div>
</div>
<img src="https://repository-images.githubusercontent.com/221981891/8c5c6942-c91f-4df1-825f-4cf474056bd7" class="link-card-image" />
</div>
<a href="https://playwright.dev/docs/ci"></a>
</div>
[[Bitbucket Pipelines]]ã®ãããª[[Docker]]ã³ã³ãããæ¯äœãšãªã£ãŠãããµãŒãã¹ã®å Žåãåºæ¬çã«åããããªã³ãã³ããèšè¿°ããããšã«ãªããšæããŸãã[[GitHub Actions]]ã䜿ãå Žåã¯ã[[Playwright]]åæåæã®éžæè¢ã§`yes`ãéžãã æ¹ã楜ã§ãããã
## ãããã«
#2022/10/30 æç¹ã®[[Playwright]]ã«ã€ããŠãç§ãªãã«å©çšé »åºŠãé«ãããªæ©èœããã£ããã¢ããã®æå³åãããããŠããŸãšããŠã¿ãŸããã
æ£çŽãæšå¹Žããã®é²åã«é©ããŸããã以åã¯æ§ã
ãªããŒã«ãçµã¿åãããŠãã©ãã«ã[[E2Eãã¹ã]]ãå®çŸãããšããæãã§ããããä»ã[[Playwright]]åäœã§ã»ãŒãã¹ãŠã®ããšãè³ããŠããŸããŸããä»åã¯çç¥ããŸããããVisual comparsionsã«ãã[[ããžã¥ã¢ã«ãªã°ã¬ãã·ã§ã³ãã¹ã]]ãå®çšã¬ãã«ã«éããŠããŠåããšæããŸããã
<div class="link-card">
<div class="link-card-header">
<img src="https://playwright.dev/img/playwright-logo.svg" class="link-card-site-icon"/>
<span class="link-card-site-name">playwright.dev</span>
</div>
<div class="link-card-body">
<div class="link-card-content">
<div>
<p class="link-card-title">Visual comparisons | Playwright</p>
</div>
<div class="link-card-description">
Playwright Test includes the ability to produce and visually compare screenshots using await expect(...
</div>
</div>
<img src="https://repository-images.githubusercontent.com/221981891/8c5c6942-c91f-4df1-825f-4cf474056bd7" class="link-card-image" />
</div>
<a href="https://playwright.dev/docs/test-snapshots"></a>
</div>
ãŸããä»ãŸã§ã¯[[IDE]]äžã§ã®ãã¹ããå³ããã£ãã®ã§ããã[[Microsoft]]ã[[Playwright Test for VSCode]]ãå
¬éããŠããããããã§å
è¡ãã¯æãããã§ããæåŸã®éå£ãšããŠã¯ãç§ã®ç°å¢ã§ãããã°ã®ããã«ãã©ãŠã¶ç«ã¡äžããå¿
èŠãªæ©èœãåããªãã£ãããšãããã§ããããããããã°æ©èœã¯å¿
é ã§ãã®ã§ãåãããã«ãªã£ããå¬ãããªãšæã£ãŠããŸãã[[GitHub]]ã«Issueã¯äœææžã§ãã
<div class="link-card">
<div class="link-card-header">
<img src="https://github.githubassets.com/favicons/favicon.svg" class="link-card-site-icon"/>
<span class="link-card-site-name">GitHub</span>
</div>
<div class="link-card-body">
<div class="link-card-content">
<div>
<p class="link-card-title">Both "Show browser" or "Run in Debug Mode" are not working · Issue #18424 · microsoft/playwright</p>
</div>
<div class="link-card-description">
Thank you for the great VSCode extension :) However, it doesn't work in both "Show browser&...
</div>
</div>
<img src="https://opengraph.githubassets.com/dcce0b443fe8226a36893a41a9b46db2a9fe5d0f51d848211b2384183973a9fd/microsoft/playwright/issues/18424" class="link-card-image" />
</div>
<a href="https://github.com/microsoft/playwright/issues/18424"></a>
</div>
å人çã«ã¯[[#HTMLã¬ããŒãã§ãã¹ãçµæã確èªãã]]ããšãã§ããã®ã§ãã¿ãŒããã«ã§ãå°ã£ãŠããããšã¯ãããŸããã
æ£çŽãªãšãããä»äºã[[OSS]]éçºã§[[Playwright]]ã匷ãå¿
èŠã«è¿«ãããããšã¯ã»ãŒãããŸãããããã§ã[[TypeScript]]ãäž»ã«æ±ãWebãšã³ãžãã¢å
ŒQAãšã³ãžãã¢ãšããŠã[[Playwright]]ã®ãããªçŽ æŽãããããŒã«ããã£ããã¢ããããå¿
èŠãªæ¹ã«æ®åãã掻åã¯ç¶ããŠãããããšæã£ãŠããŸãã
以äžã¯ã2幎åã®èšäºã®æåŸã«æžããäžç¯ã§ãã
> äžæ¹ãä»ã¯CypressãšPlaywrightã®2匷æ代ãªæ°ãããŠããŸãã
> ããããç¹åŸŽãç°ãªããããã©ã¡ããäžæ¹ãæ®ã..ãšããæãã§ã¯ãªãã®ããªãšãæã£ãŠããŸãã
> 2ã€ãããã¡ã¯ãã¹ã¿ã³ããŒãã«ãªãã°ãGUIãã¹ãã®ã¡ã³ããã³ã¹ã³ã¹ããèœã¡ãã§ãããã
>
> ãã®ãšããæ¥ãã.. ä»ã®Unitãã¹ãã¿ããã«.. 誰ããe2eãã¹ããæžãã..
> ãããªæ代ã®å°æ¥ã楜ãã¿ã«ããŠããŸãð
誰ãã[[E2Eãã¹ã]]ãæžããæ代ã®å°æ¥ãä»åã®èšäºãæžããŠãããæ¢ã«æã®å±ããšãããŸã§æ¥ãŠããããšã確信ããŸãããæ¢ã«æ®åãšæµžéã®ãã§ãŒãºã«å
¥ã£ãŠãããšæã£ãŠããŸãã
ãã4åç®ã®å·çãããæ©äŒãããã°ããã®çãåãããããŸããããããã§ã¯ãŸãã1幎åŸã®ãã®æãŸã§ã