Skip to content

Commit ad7727a

Browse files
authored
[web] enable CanvasKit tests using a local bundle fetched from CIPD (flutter#92134)
1 parent e7c809e commit ad7727a

File tree

15 files changed

+425
-30
lines changed

15 files changed

+425
-30
lines changed

.ci.yaml

+168
Original file line numberDiff line numberDiff line change
@@ -1184,6 +1184,174 @@ targets:
11841184
- bin/
11851185
- .ci.yaml
11861186

1187+
- name: Linux web_canvaskit_tests_0
1188+
bringup: true
1189+
recipe: flutter/flutter_drone
1190+
timeout: 60
1191+
properties:
1192+
dependencies: >-
1193+
[
1194+
{"dependency": "android_sdk"},
1195+
{"dependency": "chrome_and_driver"},
1196+
{"dependency": "goldctl"}
1197+
]
1198+
shard: web_canvaskit_tests
1199+
subshard: "0"
1200+
tags: >
1201+
["framework","hostonly","shard"]
1202+
scheduler: luci
1203+
runIf:
1204+
- dev/
1205+
- packages/
1206+
- bin/
1207+
1208+
- name: Linux web_canvaskit_tests_1
1209+
bringup: true
1210+
recipe: flutter/flutter_drone
1211+
timeout: 60
1212+
properties:
1213+
dependencies: >-
1214+
[
1215+
{"dependency": "android_sdk"},
1216+
{"dependency": "chrome_and_driver"},
1217+
{"dependency": "goldctl"}
1218+
]
1219+
shard: web_canvaskit_tests
1220+
subshard: "1"
1221+
tags: >
1222+
["framework","hostonly","shard"]
1223+
scheduler: luci
1224+
runIf:
1225+
- dev/
1226+
- packages/
1227+
- bin/
1228+
1229+
- name: Linux web_canvaskit_tests_2
1230+
bringup: true
1231+
recipe: flutter/flutter_drone
1232+
timeout: 60
1233+
properties:
1234+
dependencies: >-
1235+
[
1236+
{"dependency": "android_sdk"},
1237+
{"dependency": "chrome_and_driver"},
1238+
{"dependency": "goldctl"}
1239+
]
1240+
shard: web_canvaskit_tests
1241+
subshard: "2"
1242+
tags: >
1243+
["framework","hostonly","shard"]
1244+
scheduler: luci
1245+
runIf:
1246+
- dev/
1247+
- packages/
1248+
- bin/
1249+
1250+
- name: Linux web_canvaskit_tests_3
1251+
bringup: true
1252+
recipe: flutter/flutter_drone
1253+
timeout: 60
1254+
properties:
1255+
dependencies: >-
1256+
[
1257+
{"dependency": "android_sdk"},
1258+
{"dependency": "chrome_and_driver"},
1259+
{"dependency": "goldctl"}
1260+
]
1261+
shard: web_canvaskit_tests
1262+
subshard: "3"
1263+
tags: >
1264+
["framework","hostonly","shard"]
1265+
scheduler: luci
1266+
runIf:
1267+
- dev/
1268+
- packages/
1269+
- bin/
1270+
1271+
- name: Linux web_canvaskit_tests_4
1272+
bringup: true
1273+
recipe: flutter/flutter_drone
1274+
timeout: 60
1275+
properties:
1276+
dependencies: >-
1277+
[
1278+
{"dependency": "android_sdk"},
1279+
{"dependency": "chrome_and_driver"},
1280+
{"dependency": "goldctl"}
1281+
]
1282+
shard: web_canvaskit_tests
1283+
subshard: "4"
1284+
tags: >
1285+
["framework","hostonly","shard"]
1286+
scheduler: luci
1287+
runIf:
1288+
- dev/
1289+
- packages/
1290+
- bin/
1291+
1292+
- name: Linux web_canvaskit_tests_5
1293+
bringup: true
1294+
recipe: flutter/flutter_drone
1295+
timeout: 60
1296+
properties:
1297+
dependencies: >-
1298+
[
1299+
{"dependency": "android_sdk"},
1300+
{"dependency": "chrome_and_driver"},
1301+
{"dependency": "goldctl"}
1302+
]
1303+
shard: web_canvaskit_tests
1304+
subshard: "5"
1305+
tags: >
1306+
["framework","hostonly","shard"]
1307+
scheduler: luci
1308+
runIf:
1309+
- dev/
1310+
- packages/
1311+
- bin/
1312+
1313+
- name: Linux web_canvaskit_tests_6
1314+
bringup: true
1315+
recipe: flutter/flutter_drone
1316+
timeout: 60
1317+
properties:
1318+
dependencies: >-
1319+
[
1320+
{"dependency": "android_sdk"},
1321+
{"dependency": "chrome_and_driver"},
1322+
{"dependency": "goldctl"}
1323+
]
1324+
shard: web_canvaskit_tests
1325+
subshard: "6"
1326+
tags: >
1327+
["framework","hostonly","shard"]
1328+
scheduler: luci
1329+
runIf:
1330+
- dev/
1331+
- packages/
1332+
- bin/
1333+
1334+
- name: Linux web_canvaskit_tests_7_last
1335+
bringup: true
1336+
recipe: flutter/flutter_drone
1337+
timeout: 60
1338+
properties:
1339+
dependencies: >-
1340+
[
1341+
{"dependency": "android_sdk"},
1342+
{"dependency": "chrome_and_driver"},
1343+
{"dependency": "goldctl"}
1344+
]
1345+
shard: web_canvaskit_tests
1346+
subshard: "7_last"
1347+
tags: >
1348+
["framework","hostonly","shard"]
1349+
scheduler: luci
1350+
runIf:
1351+
- dev/
1352+
- packages/
1353+
- bin/
1354+
11871355
- name: Linux web_tool_tests
11881356
recipe: flutter/flutter_drone
11891357
timeout: 60

TESTOWNERS

+1
Original file line numberDiff line numberDiff line change
@@ -225,6 +225,7 @@
225225
# web_integration_tests @yjbanov @flutter/web
226226
# web_long_running_tests @yjbanov @flutter/web
227227
# web_tests @yjbanov @flutter/web
228+
# web_canvaskit_tests @yjbanov @flutter/web
228229
# web_tool_tests @zanderso @flutter/tool
229230
# fuchsia_precache @zanderso @flutter/tool
230231
# skp_generator @Hixie

dev/bots/test.dart

+81-15
Original file line numberDiff line numberDiff line change
@@ -74,13 +74,66 @@ const String kSubshardKey = 'SUBSHARD';
7474
int get webShardCount => Platform.environment.containsKey('WEB_SHARD_COUNT')
7575
? int.parse(Platform.environment['WEB_SHARD_COUNT']!)
7676
: 8;
77-
/// Tests that we don't run on Web for compilation reasons.
77+
78+
/// Tests that we don't run on Web.
79+
///
80+
/// In general avoid adding new tests here. If a test cannot run on the web
81+
/// because it fails at runtime, such as when a piece of functionality is not
82+
/// implemented or not implementable on the web, prefer using `skip` in the
83+
/// test code. Only add tests here that cannot be skipped using `skip`. For
84+
/// example:
85+
///
86+
/// * Test code cannot be compiled because it uses Dart VM-specific
87+
/// functionality. In this case `skip` doesn't help because the code cannot
88+
/// reach the point where it can even run the skipping logic.
89+
/// * Migrations. It is OK to put tests here that need to be temporarily
90+
/// disabled in certain modes because of some migration or initial bringup.
91+
///
92+
/// The key in the map is the renderer type that the list applies to. The value
93+
/// is the list of tests known to fail for that renderer.
7894
//
7995
// TODO(yjbanov): we're getting rid of this as part of https://github.com/flutter/flutter/projects/60
80-
const List<String> kWebTestFileKnownFailures = <String>[
81-
'test/services/message_codecs_vm_test.dart',
82-
'test/examples/sector_layout_test.dart',
83-
];
96+
const Map<String, List<String>> kWebTestFileKnownFailures = <String, List<String>>{
97+
'html': <String>[
98+
// These tests are not compilable on the web due to dependencies on
99+
// VM-specific functionality.
100+
'test/services/message_codecs_vm_test.dart',
101+
'test/examples/sector_layout_test.dart',
102+
],
103+
'canvaskit': <String>[
104+
// These tests are not compilable on the web due to dependencies on
105+
// VM-specific functionality.
106+
'test/services/message_codecs_vm_test.dart',
107+
'test/examples/sector_layout_test.dart',
108+
109+
// These tests are broken and need to be fixed.
110+
// TODO(yjbanov): https://github.com/flutter/flutter/issues/71604
111+
'test/painting/decoration_test.dart',
112+
'test/material/text_selection_theme_test.dart',
113+
'test/material/date_picker_test.dart',
114+
'test/rendering/layers_test.dart',
115+
'test/painting/text_style_test.dart',
116+
'test/widgets/image_test.dart',
117+
'test/cupertino/colors_test.dart',
118+
'test/cupertino/slider_test.dart',
119+
'test/material/text_field_test.dart',
120+
'test/rendering/proxy_box_test.dart',
121+
'test/widgets/app_overrides_test.dart',
122+
'test/material/calendar_date_picker_test.dart',
123+
'test/material/ink_paint_test.dart',
124+
'test/rendering/editable_test.dart',
125+
'test/cupertino/dialog_test.dart',
126+
'test/widgets/shape_decoration_test.dart',
127+
'test/material/time_picker_theme_test.dart',
128+
'test/cupertino/picker_test.dart',
129+
'test/material/chip_theme_test.dart',
130+
'test/cupertino/nav_bar_test.dart',
131+
'test/widgets/performance_overlay_test.dart',
132+
'test/widgets/html_element_view_test.dart',
133+
'test/cupertino/scaffold_test.dart',
134+
'test/rendering/platform_view_test.dart',
135+
],
136+
};
84137

85138
const String kSmokeTestShardName = 'smoke_tests';
86139
const List<String> _kAllBuildModes = <String>['debug', 'profile', 'release'];
@@ -143,8 +196,10 @@ Future<void> main(List<String> args) async {
143196
// web_tool_tests is also used by HHH: https://dart.googlesource.com/recipes/+/refs/heads/master/recipes/dart/flutter_engine.py
144197
'web_tool_tests': _runWebToolTests,
145198
'tool_integration_tests': _runIntegrationToolTests,
146-
// All the unit/widget tests run using `flutter test --platform=chrome`
147-
'web_tests': _runWebUnitTests,
199+
// All the unit/widget tests run using `flutter test --platform=chrome --web-renderer=html`
200+
'web_tests': _runWebHtmlUnitTests,
201+
// All the unit/widget tests run using `flutter test --platform=chrome --web-renderer=canvaskit`
202+
'web_canvaskit_tests': _runWebCanvasKitUnitTests,
148203
// All web integration tests
149204
'web_long_running_tests': _runWebLongRunningTests,
150205
'flutter_plugins': _runFlutterPluginsTests,
@@ -802,7 +857,15 @@ Future<void> _runFrameworkCoverage() async {
802857
}
803858
}
804859

805-
Future<void> _runWebUnitTests() async {
860+
Future<void> _runWebHtmlUnitTests() {
861+
return _runWebUnitTests('html');
862+
}
863+
864+
Future<void> _runWebCanvasKitUnitTests() {
865+
return _runWebUnitTests('canvaskit');
866+
}
867+
868+
Future<void> _runWebUnitTests(String webRenderer) async {
806869
final Map<String, ShardRunner> subshards = <String, ShardRunner>{};
807870

808871
final Directory flutterPackageDirectory = Directory(path.join(flutterRoot, 'packages', 'flutter'));
@@ -817,7 +880,7 @@ Future<void> _runWebUnitTests() async {
817880
)
818881
.whereType<File>()
819882
.map<String>((File file) => path.relative(file.path, from: flutterPackageDirectory.path))
820-
.where((String filePath) => !kWebTestFileKnownFailures.contains(path.split(filePath).join('/')))
883+
.where((String filePath) => !kWebTestFileKnownFailures[webRenderer]!.contains(path.split(filePath).join('/')))
821884
.toList()
822885
// Finally we shuffle the list because we want the average cost per file to be uniformly
823886
// distributed. If the list is not sorted then different shards and batches may have
@@ -832,6 +895,7 @@ Future<void> _runWebUnitTests() async {
832895
// This for loop computes all but the last shard.
833896
for (int index = 0; index < webShardCount - 1; index += 1) {
834897
subshards['$index'] = () => _runFlutterWebTest(
898+
webRenderer,
835899
flutterPackageDirectory.path,
836900
allTests.sublist(
837901
index * testsPerShard,
@@ -846,19 +910,22 @@ Future<void> _runWebUnitTests() async {
846910
// between `.cirrus.yml` and `test.dart`.
847911
subshards['${webShardCount - 1}_last'] = () async {
848912
await _runFlutterWebTest(
913+
webRenderer,
849914
flutterPackageDirectory.path,
850915
allTests.sublist(
851916
(webShardCount - 1) * testsPerShard,
852917
allTests.length,
853918
),
854919
);
855920
await _runFlutterWebTest(
921+
webRenderer,
856922
path.join(flutterRoot, 'packages', 'flutter_web_plugins'),
857923
<String>['test'],
858924
);
859925
await _runFlutterWebTest(
860-
path.join(flutterRoot, 'packages', 'flutter_driver'),
861-
<String>[path.join('test', 'src', 'web_tests', 'web_extension_test.dart')],
926+
webRenderer,
927+
path.join(flutterRoot, 'packages', 'flutter_driver'),
928+
<String>[path.join('test', 'src', 'web_tests', 'web_extension_test.dart')],
862929
);
863930
};
864931

@@ -1421,7 +1488,7 @@ Future<void> _runWebDebugTest(String target, {
14211488
}
14221489
}
14231490

1424-
Future<void> _runFlutterWebTest(String workingDirectory, List<String> tests) async {
1491+
Future<void> _runFlutterWebTest(String webRenderer, String workingDirectory, List<String> tests) async {
14251492
await runCommand(
14261493
flutter,
14271494
<String>[
@@ -1430,9 +1497,8 @@ Future<void> _runFlutterWebTest(String workingDirectory, List<String> tests) asy
14301497
'--concurrency=1', // do not parallelize on Cirrus, to reduce flakiness
14311498
'-v',
14321499
'--platform=chrome',
1433-
// TODO(ferhatb): Run web tests with both rendering backends.
1434-
'--web-renderer=html', // use html backend for web tests.
1435-
'--sound-null-safety', // web tests do not autodetect yet.
1500+
'--web-renderer=$webRenderer',
1501+
'--sound-null-safety',
14361502
...flutterTestArgs,
14371503
...tests,
14381504
],

packages/flutter_goldens_client/lib/skia_client.dart

+8-1
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@ import 'package:process/process.dart';
1919
const String _kFlutterRootKey = 'FLUTTER_ROOT';
2020
const String _kGoldctlKey = 'GOLDCTL';
2121
const String _kTestBrowserKey = 'FLUTTER_TEST_BROWSER';
22+
const String _kWebRendererKey = 'FLUTTER_WEB_RENDERER';
2223

2324
/// A client for uploading image tests and making baseline requests to the
2425
/// Flutter Gold Dashboard.
@@ -368,6 +369,9 @@ class SkiaGoldClient {
368369
if (platform.environment[_kTestBrowserKey] != null) {
369370
keys['Browser'] = platform.environment[_kTestBrowserKey];
370371
keys['Platform'] = '${keys['Platform']}-browser';
372+
if (platform.environment[_kWebRendererKey] == 'canvaskit') {
373+
keys['WebRenderer'] = 'canvaskit';
374+
}
371375
}
372376
return json.encode(keys);
373377
}
@@ -413,7 +417,10 @@ class SkiaGoldClient {
413417
/// the image keys.
414418
String getTraceID(String testName) {
415419
final Map<String, dynamic> keys = <String, dynamic>{
416-
if (platform.environment[_kTestBrowserKey] != null) 'Browser' : platform.environment[_kTestBrowserKey],
420+
if (platform.environment[_kTestBrowserKey] != null)
421+
'Browser' : platform.environment[_kTestBrowserKey],
422+
if (platform.environment[_kTestBrowserKey] != null && platform.environment[_kWebRendererKey] == 'canvaskit')
423+
'WebRenderer' : 'canvaskit',
417424
'CI' : 'luci',
418425
'Platform' : platform.operatingSystem,
419426
'name' : testName,

0 commit comments

Comments
 (0)