行動測試的痛點:為什麼現有方案不夠好
如果你開發過行動應用程式,一定經歷過這些痛苦:
Appium 太重了。環境建置動輒半天,WebDriver 協議層層封裝,一個簡單的點擊動作要寫十幾行程式碼。測試腳本維護成本高,稍微改個 UI 就要大面積重構。
Espresso 和 XCTest 只能單平台。iOS 用 XCTest,Android 用 Espresso,兩套程式碼、兩套語法、兩套維護成本。對於跨平台應用程式(Flutter、React Native),還要額外適配,效率極低。
Detox 對 React Native 依賴太深。如果你的應用程式不是純 React Native,或者需要測試原生模組,Detox 就力不從心了。
測試門檻太高。寫測試需要懂程式語言、懂測試框架、懂建置工具,產品經理和設計師根本參與不進來。測試變成了開發者的專屬工作,而不是團隊協作的品質保證。
這些問題的根源在於:現有測試工具太複雜,學習曲線太陡峭。我們需要一個更簡單、更現代的方案。
Maestro 是什麼:核心設計理念
Maestro 是一個開源的全平台自動化測試框架,GitHub 星标超過 15,000,採用 Apache 2.0 授權條款。它的核心設計理念是:把測試門檻降到極低,讓每個人都能寫測試。
Maestro 的三大創新:
1. YAML 宣告式語法。不需要寫程式碼,用 YAML 描述測試流程。tapOn、inputText、assertVisible,指令直觀易懂,產品經理都能看懂。
2. 智慧等待機制。內建 flakiness tolerance,自動處理動態 UI、網路延遲、動畫效果,不需要手動寫 sleep() 或 waitFor()。測試更穩定,維護更少。
3. 全平台通吃。一套框架支援 iOS、Android、Web,以及跨平台框架(Flutter、React Native)。不用為每個平台學一套新工具。
Maestro 由 mobile.dev 公司開發,團隊來自 Google、Uber、Lyft,深諳行動測試的痛點。它不是又一個測試框架,而是對現有方案的重新思考。
全平台支援詳解
Maestro 的平台覆蓋範圍是其最大優勢之一:
原生 iOS 和 Android
對於原生應用程式,Maestro 直接支援: - Android:透過 ADB 和 UIAutomator2,支援所有 Android 版本 - iOS:透過 XCUITest,支援 iOS 13+
測試原生應用程式時,Maestro 可以存取原生 UI 元件、系統對話框、權限彈窗,甚至多指手勢。
Flutter 應用程式
Flutter 開發者經常問:用 Flutter Driver 還是 Integration Test?Maestro 提供了第三種選擇:
appId: com.example.myapp
---
- launchApp
- tapOn: "Login"
- inputText: "user@example.com"
- tapOn: "Submit"
- assertVisible: "Welcome"
Maestro 把 Flutter 應用程式當作黑盒測試,不需要修改程式碼、不需要整合 SDK。測試腳本與 Flutter 版本解耦,升級 Flutter 不需要改測試。
React Native 應用程式
對於 React Native,Maestro 同樣採用黑盒測試策略: - 不需要修改 JavaScript 程式碼 - 不需要整合 Detox 或 Appium - 測試腳本獨立於 React Native 版本
這意味著你可以用同一套 Maestro 測試腳本,同時測試 iOS、Android、甚至 Web 版本的 React Native 應用程式。
Web 應用程式
Maestro 最近增加了 Web 支援,透過 Playwright 驅動瀏覽器: - 支援 Chrome、Firefox、Safari - 可以測試響應式版面配置 - 支援 PWA(Progressive Web Apps)
現在,你可以用一套 YAML 語法,測試行動端和 Web 端,真正實現全平台覆蓋。
零程式碼測試:YAML 宣告式測試語法
Maestro 的核心創新是其 YAML 測試語法。讓我們看一個完整的例子:
# login_flow.yaml
appId: com.example.myapp
---
- launchApp
# 登入流程
- tapOn: "Login"
- inputText:
id: "email_field"
text: "user@example.com"
- inputText:
id: "password_field"
text: "password123"
- tapOn: "Sign In"
# 驗證登入成功
- assertVisible: "Welcome, User"
- assertVisible:
id: "dashboard"
# 測試導覽
- tapOn: "Profile"
- assertVisible: "My Profile"
- tapOn: "Settings"
- assertVisible: "Notifications"
核心指令
Maestro 提供了豐富的指令:
互動指令:
- tapOn:點擊元件(支援文字、ID、座標)
- longPressOn:長按元件
- inputText:輸入文字
- swipe:滑動(上下左右)
- scrollUntilVisible:捲動直到元件可見
斷言指令:
- assertVisible:驗證元件可見
- assertNotVisible:驗證元件不可見
- assertTrue:驗證條件為真
流程控制:
- runFlow:呼叫其他 flow(模組化測試)
- repeat:迴圈執行
- if:條件執行
- waitForAnimationToEnd:等待動畫結束
進階功能:
- takeScreenshot:截圖
- startRecording:錄製畫面
- clearState:清除應用程式狀態
- setLocation:模擬地理位置
參數化測試
Maestro 支援參數化,方便做資料驅動測試:
appId: com.example.myapp
env:
USERNAME: "user@example.com"
PASSWORD: "password123"
---
- launchApp
- tapOn: "Login"
- inputText: ${USERNAME}
- inputText: ${PASSWORD}
- tapOn: "Sign In"
- assertVisible: "Welcome"
執行時可以透過環境變數覆寫:
maestro test -e USERNAME=test@example.com -e PASSWORD=test123 login_flow.yaml
模組化與複用
透過 runFlow 指令,可以模組化測試:
# common/login.yaml
appId: com.example.myapp
---
- tapOn: "Login"
- inputText: "user@example.com"
- inputText: "password123"
- tapOn: "Sign In"
- assertVisible: "Dashboard"
# main_flow.yaml
appId: com.example.myapp
---
- launchApp
- runFlow: common/login.yaml
- tapOn: "Profile"
- assertVisible: "My Profile"
這樣,登入邏輯只需寫一次,多個測試流程複用。
與 Appium / Detox / Espresso 對比
讓我們用資料說話,對比主流測試框架:
| 特性 | Maestro | Appium | Detox | Espresso | XCTest |
|---|---|---|---|---|---|
| 學習曲線 | 極低(YAML) | 高 | 中 | 高 | 高 |
| 程式碼量 | 極少 | 多 | 中 | 多 | 多 |
| 跨平台 | ✅ iOS/Android/Web | ✅ 全平台 | ❌ 僅 React Native | ❌ 僅 Android | ❌ 僅 iOS |
| 安裝複雜度 | 1 行指令 | 複雜(Java/Node/SDK) | 中 | 中(Android Studio) | 中(Xcode) |
| 執行速度 | 快 | 慢(WebDriver 協議) | 快 | 快 | 快 |
| 穩定性 | 高(智慧等待) | 低(flaky) | 中 | 高 | 高 |
| 除錯工具 | Maestro Studio | Appium Inspector | Detox Debugger | Android Studio | Xcode |
| CI/CD 整合 | 簡單 | 複雜 | 中 | 中 | 中 |
| 社群活躍度 | 高(15k+ stars) | 極高 | 中 | 高 | 高 |
為什麼選擇 Maestro 而不是 Appium?
Appium 的問題: - 環境建置複雜:需要 Java、Node.js、Android SDK、Xcode - WebDriver 協議慢:每步動作都要 HTTP 請求 - 測試不穩定:flaky tests 是常態 - 程式碼量大:簡單的點擊動作要寫十幾行
Maestro 的優勢:
- 一行指令安裝:curl -fsSL "https://get.maestro.mobile.dev" | bash
- 直接執行:沒有 WebDriver 協議開銷
- 智慧等待:自動處理動態 UI
- YAML 語法:10 行 YAML = 50 行 Appium 程式碼
什麼時候不用 Maestro?
Maestro 不是萬能的,以下情境需要其他工具:
- 需要測試原生 C++ 遊戲:用 Appium 或自訂框架
- 需要單元測試:用 Jest、JUnit、pytest
- 需要 API 測試:用 Postman、REST Assured
- 需要效能測試:用 Android Profiler、Instruments
Maestro 的定位是端到端 UI 測試,不是替代所有測試工具。
AI Agent 測試情境:用 Maestro 驗證 GUI Agent 動作
隨著 AI Agent 的興起(如 Obscura 無頭瀏覽器),測試 Agent 的 UI 互動能力變得重要。Maestro 可以用來驗證 GUI Agent 的動作準確性。
情境 1:驗證 AI Agent 的表單填寫
假設你開發了一個 AI Agent,能自動填寫表單。用 Maestro 驗證:
# test_ai_agent_form.yaml
appId: com.example.myapp
---
- launchApp
- tapOn: "Register"
# AI Agent 應該自動填寫這些欄位
- assertVisible:
id: "name_field"
timeout: 5000
- assertVisible:
id: "email_field"
- assertVisible:
id: "phone_field"
# 驗證 AI Agent 填寫的內容
- assertVisible: "John Doe"
- assertVisible: "john@example.com"
- assertVisible: "+123****7890"
# AI Agent 應該點擊提交
- tapOn: "Submit"
- assertVisible: "Registration successful"
情境 2:測試 AI Agent 的導覽能力
驗證 AI Agent 能否正確導覽到指定頁面:
# test_ai_agent_navigation.yaml
appId: com.example.myapp
---
- launchApp
# AI Agent 應該能找到設定頁面
- repeat:
times: 5
commands:
- swipe: LEFT
- assertNotVisible: "Settings"
# 最終應該到達設定頁面
- assertVisible: "Settings"
- tapOn: "Settings"
- assertVisible: "Notifications"
情境 3:壓力測試 AI Agent 的穩定性
測試 AI Agent 在複雜情境下的表現:
# stress_test_ai_agent.yaml
appId: com.example.myapp
---
- launchApp
- repeat:
times: 10
commands:
- tapOn: "Login"
- inputText: "user@example.com"
- inputText: "password123"
- tapOn: "Sign In"
- assertVisible: "Dashboard"
- tapOn: "Logout"
- assertVisible: "Login"
透過 Maestro,你可以量化 AI Agent 的準確率、回應時間、穩定性,為 Agent 最佳化提供資料支援。
CI/CD 整合:GitHub Actions 與 Jenkins
Maestro 與主流 CI/CD 工具整合簡單。以下是實戰設定:
GitHub Actions
# .github/workflows/maestro-tests.yml
name: Maestro Tests
on:
push:
branches: [main]
pull_request:
branches: [main]
jobs:
test-android:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- name: Set up JDK 17
uses: actions/setup-java@v4
with:
java-version: '17'
distribution: 'temurin'
- name: Install Maestro
run: curl -fsSL "https://get.maestro.mobile.dev" | bash
- name: Setup Android SDK
uses: android-actions/setup-android@v3
- name: Install Android Emulator
run: |
sdkmanager "system-images;android-33;google_apis;x86_64"
echo "no" | avdmanager create avd -n test -k "system-images;android-33;google_apis;x86_64"
- name: Start Emulator
run: |
emulator -avd test -no-snapshot -no-window &
adb wait-for-device shell 'while [[ -z $(getprop sys.boot_completed) ]]; do sleep 1; done'
- name: Install App
run: adb install app/build/outputs/apk/debug/app-debug.apk
- name: Run Maestro Tests
run: maestro test flows/
test-ios:
runs-on: macos-latest
steps:
- uses: actions/checkout@v4
- name: Install Maestro
run: curl -fsSL "https://get.maestro.mobile.dev" | bash
- name: Build iOS App
run: |
cd ios
xcodebuild -workspace MyApp.xcworkspace -scheme MyApp -sdk iphonesimulator -destination 'platform=iOS Simulator,name=iPhone 15'
- name: Install App
run: xcrun simctl install booted ~/Library/Developer/Xcode/DerivedData/MyApp/Build/Products/Debug-iphonesimulator/MyApp.app
- name: Run Maestro Tests
run: maestro test flows/
Jenkins
pipeline {
agent any
stages {
stage('Install Maestro') {
steps {
sh 'curl -fsSL "https://get.maestro.mobile.dev" | bash'
}
}
stage('Build Android') {
steps {
sh './gradlew assembleDebug'
}
}
stage('Test with Maestro') {
steps {
sh '''
emulator -avd test -no-snapshot -no-window &
adb wait-for-device
adb install app/build/outputs/apk/debug/app-debug.apk
maestro test flows/
'''
}
}
}
post {
always {
archiveArtifacts artifacts: 'maestro-report.html', allowEmptyArchive: true
}
}
}
測試報告
Maestro 產生 HTML 測試報告:
maestro test --format junit --output report.xml flows/
可以整合到 Jenkins、GitLab CI 的報告系統,視覺化測試結果。
實際專案建置教學
讓我們從零建置一個 Maestro 測試專案:
步驟 1:安裝 Maestro
# macOS / Linux
curl -fsSL "https://get.maestro.mobile.dev" | bash
# 驗證安裝
maestro --version
步驟 2:準備測試環境
Android:
# 啟動模擬器
emulator -avd Pixel_6_API_33
# 安裝應用程式
adb install app-debug.apk
iOS:
# 啟動模擬器
xcrun simctl boot "iPhone 15"
# 安裝應用程式
xcrun simctl install booted MyApp.app
步驟 3:建立測試目錄
mkdir maestro-tests
cd maestro-tests
mkdir flows
mkdir common
步驟 4:撰寫第一個測試
# flows/01_login.yaml
appId: com.example.myapp
---
- launchApp
- tapOn: "Login"
- inputText: "test@example.com"
- inputText: "password123"
- tapOn: "Sign In"
- assertVisible: "Welcome"
步驟 5:執行測試
# 執行單個測試
maestro test flows/01_login.yaml
# 執行所有測試
maestro test flows/
# 帶環境變數執行
maestro test -e USERNAME=test@example.com flows/01_login.yaml
步驟 6:使用 Maestro Studio
Maestro Studio 是視覺化測試工具:
maestro studio
瀏覽器開啟 http://localhost:9999,你可以:
- 即時檢視裝置螢幕
- 點擊元件自動產生 YAML
- 除錯測試流程
- 檢視元件屬性
步驟 7:組織測試結構
推薦的目錄結構:
maestro-tests/
├── flows/
│ ├── 01_login.yaml
│ ├── 02_register.yaml
│ ├── 03_checkout.yaml
│ └── 04_profile.yaml
├── common/
│ ├── login.yaml
│ └── logout.yaml
└── config/
├── android.yaml
└── ios.yaml
進階功能:視覺回歸與效能測試
視覺回歸測試
Maestro 支援截圖對比:
# visual_test.yaml
appId: com.example.myapp
---
- launchApp
- takeScreenshot: home_screen
- tapOn: "Profile"
- takeScreenshot: profile_screen
執行後產生截圖,可以用工具對比差異:
maestro test visual_test.yaml
# 產生 screenshots/home_screen.png 和 screenshots/profile_screen.png
結合 imagemagick 做像素級對比:
compare home_screen_old.png home_screen_new.png diff.png
效能測試
Maestro 可以測量動作耗時:
# performance_test.yaml
appId: com.example.myapp
---
- launchApp
- startRecording: app_launch
- launchApp
- stopRecording
錄製影片後,分析幀率、回應時間。
條件執行
# conditional_test.yaml
appId: com.example.myapp
---
- launchApp
- if:
visible: "Update Available"
then:
- tapOn: "Later"
- tapOn: "Login"
錯誤處理
# error_handling.yaml
appId: com.example.myapp
---
- launchApp
- runFlow:
when:
visible: "Error"
commands:
- takeScreenshot: error_screen
- tapOn: "Retry"
局限性與社群生態
Maestro 的局限
儘管 Maestro 很強大,但也有局限:
1. 不支援原生 C++ 遊戲 Maestro 基於 UI 自動化,無法測試 OpenGL/Metal 渲染的遊戲畫面。
2. Web 支援較新 Web 測試基於 Playwright,功能不如專門的 Web 測試工具(如 Playwright、Cypress)豐富。
3. 除錯工具還在完善 Maestro Studio 功能強大,但相比 Android Studio、Xcode 的除錯器,還有差距。
4. 社群相對年輕 雖然增長快,但社群規模不如 Appium(10 年歷史),遇到問題可能需要自己摸索。
社群生態
Maestro 的社群正在快速增長:
- GitHub:15,000+ stars,900+ forks
- Slack:活躍的開發者社群
- 文件:docs.maestro.dev 詳細且更新及時
- 外掛:支援自訂指令、第三方整合
商業版本:Maestro Cloud
Maestro 提供商業版本 Maestro Cloud,解決企業級需求:
- 平行執行:同時執行數百個測試
- 真實裝置:支援真機測試(不僅是模擬器)
- 測試報告:詳細的執行日誌、截圖、影片
- 通知整合:Slack、Email、Webhook
- 權限管理:團隊協作、權限控制
定價透明,提供免費試用。對於大型團隊,Maestro Cloud 值得考慮。
總結評價
Maestro 是行動測試領域的一次範式轉移。它不是對現有工具的改進,而是重新定義了「測試應該是什麼樣」。
優點: - ✅ 極低的學習曲線,YAML 語法人人能懂 - ✅ 全平台支援,一套腳本測試 iOS/Android/Web - ✅ 智慧等待機制,測試穩定可靠 - ✅ 安裝簡單,一行指令搞定 - ✅ 開源免費,社群活躍
缺點: - ❌ 不支援原生遊戲測試 - ❌ Web 支援還在完善 - ❌ 社群相對年輕
適用情境: - 行動應用程式端到端測試 - 跨平台應用程式(Flutter、React Native)測試 - 需要產品經理/設計師參與的測試 - 快速迭代的敏捷團隊
不適用情境: - 原生 C++ 遊戲 - 單元測試、API 測試 - 需要深度除錯的複雜情境
我的評價:如果你的團隊需要行動測試,Maestro 是首選方案。它把測試門檻降到最低,讓每個人都能參與品質保證。即使你已經在用 Appium,也值得試試 Maestro——可能會讓你重新思考測試的本質。
常見問題(FAQ)
1. Maestro 和 Appium 哪個更好?
Maestro 更簡單、更快、更穩定,適合大多數行動測試情境。Appium 功能更全面,支援更多平台(如 Windows、Mac 應用程式),但學習曲線陡峭、執行速度慢。如果你是新手或需要快速建置測試,選 Maestro;如果需要測試非行動平台,選 Appium。
2. Maestro 支援哪些程式語言?
Maestro 使用 YAML 語法,不需要程式語言。但你可以通过 JavaScript 撰寫自訂指令,擴展 Maestro 功能。測試腳本本身是純 YAML,產品經理都能看懂。
3. Maestro 可以測試真實裝置嗎?
可以。Maestro 支援模擬器和真實裝置。Android 透過 ADB 連接真機,iOS 透過 Xcode 連接真機。Maestro Cloud 提供雲端真機測試,支援數百種裝置。
4. Maestro 如何處理動態 UI 和網路延遲?
Maestro 內建智慧等待機制。執行指令時,自動等待元件出現、動畫結束、網路請求完成。不需要手動寫 sleep() 或 waitFor()。如果元件在逾時時間內未出現,測試失敗並產生詳細錯誤報告。
5. Maestro 可以整合到現有 CI/CD 流程嗎?
可以。Maestro 提供 GitHub Actions、GitLab CI、Jenkins、CircleCI 的整合範例。測試報告支援 JUnit 格式,可以整合到任何 CI 系統。安裝簡單,一行指令即可在 CI 環境中執行。