整合測試介紹
Unit tests 和 Widget tests 在測試獨立的類、函式或者元件時非常方便。然而,它們並不能夠測試單獨的模組形成的整體或者獲取真實裝置上應用執行狀態。這些任務需要整合測試 (integration tests) 來處理。
整合測試由 SDK 直接提供支援,使用 integration_test 這個 package 實現。
在這個章節中,我們將會學習如何去測試一個計數器應用,包括如何設定整合測試、如何驗證指定文字能否在應用內正常顯示、如何模擬點選指定元件和如何執行整合測試。
本教程將包含以下步驟:
-
建立一個應用用於測試。
-
新增
integration_test
依賴。 -
建立測試檔案。
-
編寫整合測試。
-
執行整合測試。
1. 建立一個應用用於測試
首先,我們需要建立一個應用用於測試。在這個範例中,我們將會測試一個由 flutter create
指令建立的計數器應用。這個應用允許使用者點選按鈕增加計數。
import 'package:flutter/material.dart';
void main() => runApp(const MyApp());
class MyApp extends StatelessWidget {
const MyApp({super.key});
@override
Widget build(BuildContext context) {
return const MaterialApp(
title: 'Counter App',
home: MyHomePage(title: 'Counter App Home Page'),
);
}
}
class MyHomePage extends StatefulWidget {
const MyHomePage({super.key, required this.title});
final String title;
@override
State<MyHomePage> createState() => _MyHomePageState();
}
class _MyHomePageState extends State<MyHomePage> {
int _counter = 0;
void _incrementCounter() {
setState(() {
_counter++;
});
}
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text(widget.title),
),
body: Center(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
const Text(
'You have pushed the button this many times:',
),
Text(
'$_counter',
style: Theme.of(context).textTheme.headlineMedium,
),
],
),
),
floatingActionButton: FloatingActionButton(
// Provide a Key to this button. This allows finding this
// specific button inside the test suite, and tapping it.
key: const Key('increment'),
onPressed: _incrementCounter,
tooltip: 'Increment',
child: const Icon(Icons.add),
),
);
}
}
integration_test
依賴
2. 新增 接著,我們需要用到 integration_test
和 flutter_test
package
來編寫整合測試,把依賴新增到應用pubspec.yaml
檔案的
dev_dependencies
區域。
$ flutter pub add 'dev:flutter_test:{"sdk":"flutter"}' 'dev:integration_test:{"sdk":"flutter"}'
"flutter_test" is already in "dev_dependencies". Will try to update the constraint.
Resolving dependencies...
collection 1.17.2 (1.18.0 available)
+ file 6.1.4 (7.0.0 available)
+ flutter_driver 0.0.0 from sdk flutter
+ fuchsia_remote_debug_protocol 0.0.0 from sdk flutter
+ integration_test 0.0.0 from sdk flutter
material_color_utilities 0.5.0 (0.8.0 available)
meta 1.9.1 (1.10.0 available)
+ platform 3.1.0 (3.1.2 available)
+ process 4.2.4 (5.0.0 available)
stack_trace 1.11.0 (1.11.1 available)
stream_channel 2.1.1 (2.1.2 available)
+ sync_http 0.3.1
test_api 0.6.0 (0.6.1 available)
+ vm_service 11.7.1 (11.10.0 available)
+ webdriver 3.0.2
Changed 9 dependencies!
3. 建立測試檔案
建立一個名為 integration_test
的新檔案夾,並在資料夾中建立一個空的 app_test.dart
檔案:
counter_app/
lib/
main.dart
integration_test/
app_test.dart
4. 編寫整合測試檔案
現在我們可以來寫測試檔案了,步驟如下列三項:
-
初始化一個單例
IntegrationTestWidgetsFlutterBinding
,這將用於在物理裝置上執行測試; -
使用
WidgetTester
類測試並與 widget 發生互動; -
測試重要的應用場景。
import 'package:flutter/material.dart';
import 'package:flutter_test/flutter_test.dart';
import 'package:integration_test/integration_test.dart';
import 'package:introduction/main.dart';
void main() {
IntegrationTestWidgetsFlutterBinding.ensureInitialized();
group('end-to-end test', () {
testWidgets('tap on the floating action button, verify counter',
(tester) async {
// Load app widget.
await tester.pumpWidget(const MyApp());
// Verify the counter starts at 0.
expect(find.text('0'), findsOneWidget);
// Finds the floating action button to tap on.
final fab = find.byKey(const Key('increment'));
// Emulate a tap on the floating action button.
await tester.tap(fab);
// Trigger a frame.
await tester.pumpAndSettle();
// Verify the counter increments by 1.
expect(find.text('1'), findsOneWidget);
});
});
}
5. 執行整合測試
整合測試的執行情況會根據需要進行測試的平台不同而不盡相同,你可以針對行動平台或者 Web 平台進行測試。
5a. 行動平台
在 iOS 或 Android 平台進行真機測試的時候,首先需要連線裝置並在工程的根目錄執行下面的指令:
$ flutter test integration_test/app_test.dart
或者你可以在指定目錄下執行所有的整合測試:
$ flutter test integration_test
這個指令可以在目標裝置上執行應用並執行整合測試,更多相關訊息,請參閱文件:整合測試 頁面。
5b. Web 平台
在網頁瀏覽器裡開始進行整合測試,首先要下載 ChromeDriver。
接下來,新建一個資料夾,命名為 test_driver
,幷包含一個新的檔案,命名為
integration_test.dart
。
import 'package:integration_test/integration_test_driver.dart';
Future<void> main() => integrationDriver();
執行 chromedriver
,執行如下指令:
$ chromedriver --port=4444
在工程的根目錄下,執行如下指令:
$ flutter drive \
--driver=test_driver/integration_test.dart \
--target=integration_test/app_test.dart \
-d chrome
如需 Headless 測試體驗,你同樣可以執行 flutter drive
指令,並加入 web-server
作為目標裝置,參考如下指令:
flutter drive \
--driver=test_driver/integration_test.dart \
--target=integration_test/app_test.dart \
-d web-server