iT邦幫忙

2025 iThome 鐵人賽

DAY 15
1
Software Development

Playwright 玩家攻略:從新手村到魔王關系列 第 15

Day 15:破解隱形敵人與敵軍陣列|如何鎖定沒有「真名」的怪物

  • 分享至 

  • xImage
  •  

上一篇我們已經學會運用序列以及篩選的方式來準確定位,但除此之外,我們還可能遇到畫面上沒有文字(無法用 getByRolegetByText),也沒有 label (無法用 getByLebel),標籤內更沒有屬性,面對這種令人頭痛的怪物(元素),我們該怎麼定位呢?

首先,如果 html 結構較單純,同樣可以使用上一篇介紹的序列定位或是篩選方式取得元素位置,但若是結構比較複雜,前面認識的定位方法已無法定位到想要的目標,就必須使用其他方式來定位,我們可以嘗試用這兩種方式來定位:

  1. 依靠 「有文字或明顯屬性」的鄰居定位,也就是先定位到可辨識的元素,再利用父子/兄弟關係查找該元素。

  2. 使用 XPath 表達式定位,這是一種將網頁上每一個元素、文字、屬性,甚至是注釋都視為一個節點的定位方式,並且以路徑的方式表達,關於 XPath 更詳細的說明可以參考:XPath 入門指南:輕鬆理解網頁數據抓取

不多說,我們直接進入猶如初階副本的挑戰,運用上面第一種方式在 開放博物館 - 國家寶藏 這個尋寶遊戲網站中闖關,成功找出所有寶物吧!

第 1 關:進入首頁,點擊中文版

難易度 ★☆☆☆☆
https://ithelp.ithome.com.tw/upload/images/20250924/20168913HDJmm0dnPk.png

看起來非常簡單,只需要鎖定「中文版」的文字就能點擊目標元素:

await page.getByText('中文版').click();

📜破關秘笈:
必須特別注意,點擊中文版後,無法確定需要等多久時間畫面才準備完成,所以加上 { waitUntil: 'load' } 等待畫面完成,否則直接執行後續動作,會超過 timeout 導致測試失敗。

第 2 關:點擊向下箭頭

難易度 ★★☆☆☆
https://ithelp.ithome.com.tw/upload/images/20250924/20168913vMSdjpyu4q.png

這個箭頭是一張圖片,alt 是空字串,所以無法使用 page.getByRole('img', { name: alt }) 來找到它,雖然有來源 src,可以使用 CSS 屬性選擇器定位,但會變得很冗長,不易閱讀,且如果圖片來源更換,測試就會壞掉,如此,最適合的方式是先選擇這張圖片的父元素<span>,再往子元素選擇:

await page.locator('span[class="open--next"] > img').click();

第 3 關:點擊說明文字

難易度 ★★★☆☆
https://ithelp.ithome.com.tw/upload/images/20250924/20168913DVEIjuegIW.png
這一關,並不如畫面上這麼簡單,只需要點擊文字即可過關,如果用getByText()定位,那麼會得到超過 timeout 還找不到元素的結果,為什麼會這樣呢?我們打開 devtool 查看:

會發現它是偽元素並非真實的元素,不存在於 DOM 當中,因此 Playwright 無法操作,這時,我們定位它的父元素,但定位在父元素<div class="open--card open--card-1" style="top: -10px;"></div>仍然找不到,因此只能再往上一層找,終於能成功點擊啦!

await page.locator('div[class="open--dialog open--dialog-2"]').click();

第 4 關:點擊寶物圖片,找出第一個寶物

難易度 ★★☆☆☆
https://ithelp.ithome.com.tw/upload/images/20250924/20168913g83qdGI26v.png
這一關的怪物狀態與第 2 關向下箭頭相同,相信各位玩家已經駕輕就熟,先選擇父元素,再選擇圖片:

await page.locator('#tr4-1 > img').click();

恭喜!我們找到第一個寶物了!!!
https://ithelp.ithome.com.tw/upload/images/20250924/20168913lU03mdZnAf.png


完整程式碼:

import { test, expect } from '@playwright/test';

test('find the all treasure', async ({ page }) => {
  // 第 1 關:進入首頁,點擊中文版
  await page.goto('https://openmuseum.tw/treasure');
  await expect(page.getByRole('link', { name: '中文版' })).toBeVisible();
  await page.getByText('中文版').click();
  await page.waitForURL('**/main?lang=zh-Hant', { waitUntil: 'load' });
  await expect(page.getByText('山壑間的國家寶藏').nth(1)).toBeVisible();

  // 第 2 關:點擊向下箭頭
  await page.locator('span[class="open--next"] > img').click();

  // 第 3 關:點擊說明文字
  await page.locator('div[class="open--dialog open--dialog-2"]').click();
  await page.locator('div[class="open--dialog open--dialog-3"]').click();
  await page.locator('div[class="open--dialog open--dialog-4"]').click();

  // 第 4 關:找出第一個寶物
  await page.locator('#tr4-1 > img').click();
})

執行結果:
https://ithelp.ithome.com.tw/upload/images/20250924/20168913diTc4I0TWM.png


動動腦:找出所有寶物

難易度 ★★★★☆

最後這一關,就留給各位玩家動動腦啦 ~ 同時,也可以嘗試將元素定位方式改成 XPath 唷!
如何快速地找出所有寶物,是測試時很重要的策略,這樣才能在有限的時間與資源裡,取得最高的測試效益。


到這裡,我們透過尋寶遊戲網站,學會了如何鎖定沒有「真名」的怪物,定位到想攻擊的目標,接下來,下一個初階副本任務是檔案上傳與下載,同樣經由實戰的方式,讓你進一步擴展測試的攻擊範圍與驗證深度。


上一篇
Day 14:群體控制技|表格中重複怪物的定位技巧
系列文
Playwright 玩家攻略:從新手村到魔王關15
圖片
  熱門推薦
圖片
{{ item.channelVendor }} | {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言