1// Copyright 2014 The Flutter Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5import 'package:file/memory.dart';
6import 'package:flutter_tools/src/artifacts.dart';
7import 'package:flutter_tools/src/base/file_system.dart';
8import 'package:flutter_tools/src/base/logger.dart';
9import 'package:flutter_tools/src/base/platform.dart';
10import 'package:flutter_tools/src/base/user_messages.dart';
11import 'package:flutter_tools/src/runner/local_engine.dart';
12
13import '../../src/common.dart';
14
15const String kEngineRoot = '/flutter/engine';
16const String kArbitraryEngineRoot = '/arbitrary/engine';
17const String kPackageConfig = '.dart_tool/package_config.json';
18
19void main() {
20 testWithoutContext('works if --local-engine is specified and --local-engine-src-path '
21 'is determined by sky_engine', () async {
22 final FileSystem fileSystem = MemoryFileSystem.test();
23 fileSystem
24 .directory('$kArbitraryEngineRoot/src/out/ios_debug/gen/dart-pkg/sky_engine/lib/')
25 .createSync(recursive: true);
26 fileSystem
27 .directory('$kArbitraryEngineRoot/src/out/host_debug')
28 .createSync(recursive: true);
29 fileSystem
30 .file(kPackageConfig)
31 ..createSync(recursive: true)
32 ..writeAsStringSync('''
33{
34 "configVersion": 2,
35 "packages": [
36 {
37 "name": "sky_engine",
38 "rootUri": "file://$kArbitraryEngineRoot/src/out/ios_debug/gen/dart-pkg/sky_engine",
39 "packageUri": "lib/"
40 }
41 ]
42}
43''');
44 fileSystem
45 .file('bin/cache/pkg/sky_engine/lib')
46 .createSync(recursive: true);
47
48 final BufferLogger logger = BufferLogger.test();
49 final LocalEngineLocator localEngineLocator = LocalEngineLocator(
50 fileSystem: fileSystem,
51 flutterRoot: '',
52 logger: logger,
53 userMessages: UserMessages(),
54 platform: FakePlatform(environment: <String, String>{}),
55 );
56
57 expect(
58 await localEngineLocator.findEnginePath(localEngine: 'ios_debug', localHostEngine: 'host_debug'),
59 matchesEngineBuildPaths(
60 hostEngine: '/arbitrary/engine/src/out/host_debug',
61 targetEngine: '/arbitrary/engine/src/out/ios_debug',
62 ),
63 );
64 expect(logger.traceText, contains('Local engine source at /arbitrary/engine/src'));
65
66 // Verify that this also works if the sky_engine path is a symlink to the engine root.
67 fileSystem.link('/symlink').createSync(kArbitraryEngineRoot);
68 fileSystem
69 .file(kPackageConfig)
70 ..createSync(recursive: true)
71 ..writeAsStringSync('''
72{
73 "configVersion": 2,
74 "packages": [
75 {
76 "name": "sky_engine",
77 "rootUri": "file:///symlink/src/out/ios_debug/gen/dart-pkg/sky_engine/",
78 "packageUri": "lib/"
79 }
80 ]
81}
82''');
83
84 expect(
85 await localEngineLocator.findEnginePath(localEngine: 'ios_debug', localHostEngine: 'host_debug'),
86 matchesEngineBuildPaths(
87 hostEngine: '/symlink/src/out/host_debug',
88 targetEngine: '/symlink/src/out/ios_debug',
89 ),
90 );
91 expect(logger.traceText, contains('Local engine source at /symlink/src'));
92 });
93
94 testWithoutContext('works if --local-engine is specified and --local-engine-src-path '
95 'is specified', () async {
96 final FileSystem fileSystem = MemoryFileSystem.test();
97 // Intentionally do not create a package_config to verify that it is not required.
98 fileSystem.directory('$kArbitraryEngineRoot/src/out/ios_debug').createSync(recursive: true);
99 fileSystem.directory('$kArbitraryEngineRoot/src/out/host_debug').createSync(recursive: true);
100
101 final BufferLogger logger = BufferLogger.test();
102 final LocalEngineLocator localEngineLocator = LocalEngineLocator(
103 fileSystem: fileSystem,
104 flutterRoot: '',
105 logger: logger,
106 userMessages: UserMessages(),
107 platform: FakePlatform(environment: <String, String>{}),
108 );
109
110 expect(
111 await localEngineLocator.findEnginePath(engineSourcePath: '$kArbitraryEngineRoot/src', localEngine: 'ios_debug', localHostEngine: 'host_debug'),
112 matchesEngineBuildPaths(
113 hostEngine: '/arbitrary/engine/src/out/host_debug',
114 targetEngine: '/arbitrary/engine/src/out/ios_debug',
115 ),
116 );
117 expect(logger.traceText, contains('Local engine source at /arbitrary/engine/src'));
118 });
119
120 testWithoutContext('works if --local-engine is specified and --local-engine-host is specified', () async {
121 final FileSystem fileSystem = MemoryFileSystem.test();
122 final Directory localEngine = fileSystem
123 .directory('$kArbitraryEngineRoot/src/out/android_debug_unopt_arm64/')
124 ..createSync(recursive: true);
125 fileSystem.directory('$kArbitraryEngineRoot/src/out/host_debug_unopt_arm64/').createSync(recursive: true);
126
127 final BufferLogger logger = BufferLogger.test();
128 final LocalEngineLocator localEngineLocator = LocalEngineLocator(
129 fileSystem: fileSystem,
130 flutterRoot: 'flutter/flutter',
131 logger: logger,
132 userMessages: UserMessages(),
133 platform: FakePlatform(environment: <String, String>{}),
134 );
135
136 expect(
137 await localEngineLocator.findEnginePath(localEngine: localEngine.path, localHostEngine: 'host_debug_unopt_arm64'),
138 matchesEngineBuildPaths(
139 hostEngine: '/arbitrary/engine/src/out/host_debug_unopt_arm64',
140 targetEngine: '/arbitrary/engine/src/out/android_debug_unopt_arm64',
141 ),
142 );
143 expect(logger.traceText, contains('Local engine source at /arbitrary/engine/src'));
144 });
145
146 testWithoutContext('fails if --local-engine-host is omitted', () async {
147 final FileSystem fileSystem = MemoryFileSystem.test();
148 final Directory localEngine = fileSystem
149 .directory('$kArbitraryEngineRoot/src/out/android_debug_unopt_arm64/')
150 ..createSync(recursive: true);
151 fileSystem.directory('$kArbitraryEngineRoot/src/out/host_debug_unopt/').createSync(recursive: true);
152
153 final BufferLogger logger = BufferLogger.test();
154 final LocalEngineLocator localEngineLocator = LocalEngineLocator(
155 fileSystem: fileSystem,
156 flutterRoot: 'flutter/flutter',
157 logger: logger,
158 userMessages: UserMessages(),
159 platform: FakePlatform(environment: <String, String>{}),
160 );
161
162 await expectLater(
163 localEngineLocator.findEnginePath(localEngine: localEngine.path),
164 throwsToolExit(message: 'You are using a locally built engine (--local-engine) but have not specified --local-engine-host'),
165 );
166 });
167
168 testWithoutContext('works if --local-engine is specified and --local-engine-src-path '
169 'is determined by --local-engine', () async {
170 final FileSystem fileSystem = MemoryFileSystem.test();
171 final Directory localEngine = fileSystem
172 .directory('$kArbitraryEngineRoot/src/out/ios_debug/')
173 ..createSync(recursive: true);
174 fileSystem.directory('$kArbitraryEngineRoot/src/out/host_debug/').createSync(recursive: true);
175
176 final BufferLogger logger = BufferLogger.test();
177 final LocalEngineLocator localEngineLocator = LocalEngineLocator(
178 fileSystem: fileSystem,
179 flutterRoot: 'flutter/flutter',
180 logger: logger,
181 userMessages: UserMessages(),
182 platform: FakePlatform(environment: <String, String>{}),
183 );
184
185 expect(
186 await localEngineLocator.findEnginePath(localEngine: localEngine.path, localHostEngine: 'host_debug'),
187 matchesEngineBuildPaths(
188 hostEngine: '/arbitrary/engine/src/out/host_debug',
189 targetEngine: '/arbitrary/engine/src/out/ios_debug',
190 ),
191 );
192 expect(logger.traceText, contains('Parsed engine source from local engine as /arbitrary/engine/src'));
193 expect(logger.traceText, contains('Local engine source at /arbitrary/engine/src'));
194 });
195
196 testWithoutContext('works if local engine is host engine', () async {
197 final FileSystem fileSystem = MemoryFileSystem.test();
198 final Directory localEngine = fileSystem
199 .directory('$kArbitraryEngineRoot/src/out/host_debug/')
200 ..createSync(recursive: true);
201
202 final BufferLogger logger = BufferLogger.test();
203 final LocalEngineLocator localEngineLocator = LocalEngineLocator(
204 fileSystem: fileSystem,
205 flutterRoot: 'flutter/flutter',
206 logger: logger,
207 userMessages: UserMessages(),
208 platform: FakePlatform(environment: <String, String>{}),
209 );
210
211 expect(
212 await localEngineLocator.findEnginePath(localEngine: localEngine.path, localHostEngine: localEngine.path),
213 matchesEngineBuildPaths(
214 hostEngine: '/arbitrary/engine/src/out/host_debug',
215 targetEngine: '/arbitrary/engine/src/out/host_debug',
216 ),
217 );
218 expect(logger.traceText, contains('Local engine source at /arbitrary/engine/src'));
219 });
220
221 testWithoutContext('works if local engine is host engine with suffixes', () async {
222 final FileSystem fileSystem = MemoryFileSystem.test();
223 final Directory localEngine = fileSystem
224 .directory('$kArbitraryEngineRoot/src/out/host_debug_unopt_arm64/')
225 ..createSync(recursive: true);
226
227 final BufferLogger logger = BufferLogger.test();
228 final LocalEngineLocator localEngineLocator = LocalEngineLocator(
229 fileSystem: fileSystem,
230 flutterRoot: 'flutter/flutter',
231 logger: logger,
232 userMessages: UserMessages(),
233 platform: FakePlatform(environment: <String, String>{}),
234 );
235
236 expect(
237 await localEngineLocator.findEnginePath(localEngine: localEngine.path, localHostEngine: localEngine.path),
238 matchesEngineBuildPaths(
239 hostEngine: '/arbitrary/engine/src/out/host_debug_unopt_arm64',
240 targetEngine: '/arbitrary/engine/src/out/host_debug_unopt_arm64',
241 ),
242 );
243 });
244
245 testWithoutContext('works if local engine is simulator', () async {
246 final FileSystem fileSystem = MemoryFileSystem.test();
247 final Directory localEngine = fileSystem
248 .directory('$kArbitraryEngineRoot/src/out/ios_debug_sim/')
249 ..createSync(recursive: true);
250 fileSystem
251 .directory('$kArbitraryEngineRoot/src/out/host_debug/')
252 .createSync(recursive: true);
253
254 final BufferLogger logger = BufferLogger.test();
255 final LocalEngineLocator localEngineLocator = LocalEngineLocator(
256 fileSystem: fileSystem,
257 flutterRoot: 'flutter/flutter',
258 logger: logger,
259 userMessages: UserMessages(),
260 platform: FakePlatform(environment: <String, String>{}),
261 );
262
263 expect(
264 await localEngineLocator.findEnginePath(localEngine: localEngine.path, localHostEngine: 'host_debug'),
265 matchesEngineBuildPaths(
266 hostEngine: '/arbitrary/engine/src/out/host_debug',
267 targetEngine: '/arbitrary/engine/src/out/ios_debug_sim',
268 ),
269 );
270 });
271
272 testWithoutContext('works if local engine is simulator unoptimized',
273 () async {
274 final FileSystem fileSystem = MemoryFileSystem.test();
275 final Directory localEngine = fileSystem
276 .directory('$kArbitraryEngineRoot/src/out/ios_debug_sim_unopt/')
277 ..createSync(recursive: true);
278 fileSystem
279 .directory('$kArbitraryEngineRoot/src/out/host_debug_unopt/')
280 .createSync(recursive: true);
281
282 final BufferLogger logger = BufferLogger.test();
283 final LocalEngineLocator localEngineLocator = LocalEngineLocator(
284 fileSystem: fileSystem,
285 flutterRoot: 'flutter/flutter',
286 logger: logger,
287 userMessages: UserMessages(),
288 platform: FakePlatform(environment: <String, String>{}),
289 );
290
291 expect(
292 await localEngineLocator.findEnginePath(localEngine: localEngine.path, localHostEngine: 'host_debug_unopt'),
293 matchesEngineBuildPaths(
294 hostEngine: '/arbitrary/engine/src/out/host_debug_unopt',
295 targetEngine: '/arbitrary/engine/src/out/ios_debug_sim_unopt',
296 ),
297 );
298 });
299
300 testWithoutContext('fails if host_debug does not exist', () async {
301 final FileSystem fileSystem = MemoryFileSystem.test();
302 final Directory localEngine = fileSystem
303 .directory('$kArbitraryEngineRoot/src/out/ios_debug/')
304 ..createSync(recursive: true);
305
306 final LocalEngineLocator localEngineLocator = LocalEngineLocator(
307 fileSystem: fileSystem,
308 flutterRoot: 'flutter/flutter',
309 logger: BufferLogger.test(),
310 userMessages: UserMessages(),
311 platform: FakePlatform(environment: <String, String>{}),
312 );
313
314 await expectToolExitLater(
315 localEngineLocator.findEnginePath(localEngine: localEngine.path, localHostEngine: 'host_debug'),
316 contains('No Flutter engine build found at /arbitrary/engine/src/out/host_debug'),
317 );
318 });
319
320 testWithoutContext('works if --local-engine is specified and --local-engine-src-path '
321 'is determined by flutter root', () async {
322 final FileSystem fileSystem = MemoryFileSystem.test();
323 fileSystem
324 .file(kPackageConfig)
325 .createSync(recursive: true);
326 fileSystem
327 .directory('$kEngineRoot/src/out/ios_debug')
328 .createSync(recursive: true);
329 fileSystem
330 .directory('$kEngineRoot/src/out/host_debug')
331 .createSync(recursive: true);
332 fileSystem
333 .file('bin/cache/pkg/sky_engine/lib')
334 .createSync(recursive: true);
335
336 final BufferLogger logger = BufferLogger.test();
337 final LocalEngineLocator localEngineLocator = LocalEngineLocator(
338 fileSystem: fileSystem,
339 flutterRoot: 'flutter/flutter',
340 logger: logger,
341 userMessages: UserMessages(),
342 platform: FakePlatform(environment: <String, String>{}),
343 );
344
345 expect(
346 await localEngineLocator.findEnginePath(localEngine: 'ios_debug', localHostEngine: 'host_debug'),
347 matchesEngineBuildPaths(
348 hostEngine: 'flutter/engine/src/out/host_debug',
349 targetEngine: 'flutter/engine/src/out/ios_debug',
350 ),
351 );
352 expect(logger.traceText, contains('Local engine source at flutter/engine/src'));
353 });
354
355 testWithoutContext('fails if --local-engine is specified and --local-engine-src-path '
356 'cannot be determined', () async {
357 final FileSystem fileSystem = MemoryFileSystem.test();
358
359 final LocalEngineLocator localEngineLocator = LocalEngineLocator(
360 fileSystem: fileSystem,
361 flutterRoot: 'flutter/flutter',
362 logger: BufferLogger.test(),
363 userMessages: UserMessages(),
364 platform: FakePlatform(environment: <String, String>{}),
365 );
366
367 await expectToolExitLater(
368 localEngineLocator.findEnginePath(localEngine: '/path/to/nothing', localHostEngine: '/path/to/nothing'),
369 contains('Unable to detect local Flutter engine src directory'),
370 );
371 });
372
373 testWithoutContext('works for local web engine', () async {
374 final FileSystem fileSystem = MemoryFileSystem.test();
375 final Directory localWasmEngine = fileSystem
376 .directory('$kArbitraryEngineRoot/src/out/wasm_whatever/')
377 ..createSync(recursive: true);
378 final Directory localWebEngine = fileSystem
379 .directory('$kArbitraryEngineRoot/src/out/web_whatever/')
380 ..createSync(recursive: true);
381
382 final BufferLogger wasmLogger = BufferLogger.test();
383 final LocalEngineLocator localWasmEngineLocator = LocalEngineLocator(
384 fileSystem: fileSystem,
385 flutterRoot: 'flutter/flutter',
386 logger: wasmLogger,
387 userMessages: UserMessages(),
388 platform: FakePlatform(environment: <String, String>{}),
389 );
390
391 expect(
392 await localWasmEngineLocator.findEnginePath(localEngine: localWasmEngine.path, localHostEngine: localWasmEngine.path),
393 matchesEngineBuildPaths(
394 hostEngine: '/arbitrary/engine/src/out/wasm_whatever',
395 targetEngine: '/arbitrary/engine/src/out/wasm_whatever',
396 ),
397 );
398 expect(wasmLogger.traceText, contains('Local engine source at /arbitrary/engine/src'));
399
400 final BufferLogger webLogger = BufferLogger.test();
401 final LocalEngineLocator localWebEngineLocator = LocalEngineLocator(
402 fileSystem: fileSystem,
403 flutterRoot: 'flutter/flutter',
404 logger: webLogger,
405 userMessages: UserMessages(),
406 platform: FakePlatform(environment: <String, String>{}),
407 );
408
409 expect(
410 await localWebEngineLocator.findEnginePath(localEngine: localWebEngine.path, localHostEngine: localWebEngine.path),
411 matchesEngineBuildPaths(
412 hostEngine: '/arbitrary/engine/src/out/web_whatever',
413 targetEngine: '/arbitrary/engine/src/out/web_whatever',
414 ),
415 );
416 expect(webLogger.traceText, contains('Local engine source at /arbitrary/engine/src'));
417 });
418
419 test('returns null without throwing if nothing is specified', () async {
420 final LocalEngineLocator localWebEngineLocator = LocalEngineLocator(
421 fileSystem: MemoryFileSystem.test(),
422 flutterRoot: 'flutter/flutter',
423 logger: BufferLogger.test(),
424 userMessages: UserMessages(),
425 platform: FakePlatform(environment: <String, String>{}),
426 );
427
428 final EngineBuildPaths? paths = await localWebEngineLocator.findEnginePath();
429 expect(paths, isNull);
430 });
431
432 test('throws if nothing is specified but the FLUTTER_ENGINE environment variable is set', () async {
433 final LocalEngineLocator localWebEngineLocator = LocalEngineLocator(
434 fileSystem: MemoryFileSystem.test(),
435 flutterRoot: 'flutter/flutter',
436 logger: BufferLogger.test(),
437 userMessages: UserMessages(),
438 platform: FakePlatform(environment: <String, String>{'FLUTTER_ENGINE': 'blah'}),
439 );
440
441 await expectToolExitLater(
442 localWebEngineLocator.findEnginePath(),
443 contains('Unable to detect a Flutter engine build directory in blah'),
444 );
445 });
446}
447
448Matcher matchesEngineBuildPaths({
449 String? hostEngine,
450 String? targetEngine,
451}) {
452 return const TypeMatcher<EngineBuildPaths>()
453 .having((EngineBuildPaths paths) => paths.hostEngine, 'hostEngine', hostEngine)
454 .having((EngineBuildPaths paths) => paths.targetEngine, 'targetEngine', targetEngine);
455}
456

Provided by KDAB

Privacy Policy
Learn more about Flutter for embedded and desktop on industrialflutter.com