From d26c227686ec5b61621e12ad4c87787be5a43e37 Mon Sep 17 00:00:00 2001 From: Ian Hickson Date: Thu, 2 Sep 2021 12:54:46 -0700 Subject: [PATCH] build-examples .pluginToolsConfig.yaml support --- script/tool/CHANGELOG.md | 4 + .../tool/lib/src/build_examples_command.dart | 74 ++++++++++++++++++- script/tool/pubspec.yaml | 2 +- .../test/build_examples_command_test.dart | 48 +++++++++++- 4 files changed, 123 insertions(+), 5 deletions(-) diff --git a/script/tool/CHANGELOG.md b/script/tool/CHANGELOG.md index 098e57a8c62d..aa73c65f3e80 100644 --- a/script/tool/CHANGELOG.md +++ b/script/tool/CHANGELOG.md @@ -1,3 +1,7 @@ +## 0.7.1 + +- Add support for `.pluginToolsConfig.yaml` in the `build-examples` command. + ## 0.7.0 - `native-test` now supports `--linux` for unit tests. diff --git a/script/tool/lib/src/build_examples_command.dart b/script/tool/lib/src/build_examples_command.dart index 56c2f5c7dc87..82ed074c462a 100644 --- a/script/tool/lib/src/build_examples_command.dart +++ b/script/tool/lib/src/build_examples_command.dart @@ -6,6 +6,7 @@ import 'dart:async'; import 'package:file/file.dart'; import 'package:platform/platform.dart'; +import 'package:yaml/yaml.dart'; import 'common/core.dart'; import 'common/package_looping_command.dart'; @@ -16,7 +17,19 @@ import 'common/repository_package.dart'; /// Key for APK. const String _platformFlagApk = 'apk'; +const String _pluginToolsConfigFileName = '.pluginToolsConfig.yaml'; +const String _pluginToolsConfigBuildFlagsKey = 'buildFlags'; +const String _pluginToolsConfigGlobalKey = 'global'; + +const String _pluginToolsConfigExample = ''' +$_pluginToolsConfigBuildFlagsKey: + $_pluginToolsConfigGlobalKey: + - "--no-tree-shake-icons" + - "--dart-define=buildmode=testing" +'''; + const int _exitNoPlatformFlags = 3; +const int _exitInvalidPluginToolsConfig = 4; // Flutter build types. These are the values passed to `flutter build `. const String _flutterBuildTypeAndroid = 'apk'; @@ -99,7 +112,13 @@ class BuildExamplesCommand extends PackageLoopingCommand { @override final String description = 'Builds all example apps (IPA for iOS and APK for Android).\n\n' - 'This command requires "flutter" to be in your path.'; + 'This command requires "flutter" to be in your path.\n\n' + 'A $_pluginToolsConfigFileName file can be placed in an example app ' + 'directory to specify additional build arguments. It should be a YAML ' + 'file with a top-level map containing a single key ' + '"$_pluginToolsConfigBuildFlagsKey" containing a map containing a ' + 'single key "$_pluginToolsConfigGlobalKey" containing a list of build ' + 'arguments.'; @override Future initializeRun() async { @@ -202,6 +221,58 @@ class BuildExamplesCommand extends PackageLoopingCommand { : PackageResult.fail(errors); } + Iterable _readExtraBuildFlagsConfiguration( + Directory directory) sync* { + final File pluginToolsConfig = + directory.childFile(_pluginToolsConfigFileName); + if (pluginToolsConfig.existsSync()) { + final Object? configuration = + loadYaml(pluginToolsConfig.readAsStringSync()); + if (configuration is! YamlMap) { + printError('The $_pluginToolsConfigFileName file must be a YAML map.'); + printError( + 'Currently, the key "$_pluginToolsConfigBuildFlagsKey" is the only one that has an effect.'); + printError( + 'It must itself be a map. Currently, in that map only the key "$_pluginToolsConfigGlobalKey"'); + printError( + 'has any effect; it must contain a list of arguments to pass to the'); + printError('flutter tool.'); + printError(_pluginToolsConfigExample); + throw ToolExit(_exitInvalidPluginToolsConfig); + } + if (configuration.containsKey(_pluginToolsConfigBuildFlagsKey)) { + final Object? buildFlagsConfiguration = + configuration[_pluginToolsConfigBuildFlagsKey]; + if (buildFlagsConfiguration is! YamlMap) { + printError( + 'The $_pluginToolsConfigFileName file\'s "$_pluginToolsConfigBuildFlagsKey" key must be a map.'); + printError( + 'Currently, in that map only the key "$_pluginToolsConfigGlobalKey" has any effect; it must '); + printError( + 'contain a list of arguments to pass to the flutter tool.'); + printError(_pluginToolsConfigExample); + throw ToolExit(_exitInvalidPluginToolsConfig); + } + if (buildFlagsConfiguration.containsKey(_pluginToolsConfigGlobalKey)) { + final Object? globalBuildFlagsConfiguration = + buildFlagsConfiguration[_pluginToolsConfigGlobalKey]; + if (globalBuildFlagsConfiguration is! YamlList) { + printError( + 'The $_pluginToolsConfigFileName file\'s "$_pluginToolsConfigBuildFlagsKey" key must be a map'); + printError('whose "$_pluginToolsConfigGlobalKey" key is a list.'); + printError( + 'That list must contain a list of arguments to pass to the flutter tool.'); + printError( + 'For example, the $_pluginToolsConfigFileName file could look like:'); + printError(_pluginToolsConfigExample); + throw ToolExit(_exitInvalidPluginToolsConfig); + } + yield* globalBuildFlagsConfiguration.cast(); + } + } + } + } + Future _buildExample( RepositoryPackage example, String flutterBuildType, { @@ -231,6 +302,7 @@ class BuildExamplesCommand extends PackageLoopingCommand { 'build', flutterBuildType, ...extraBuildFlags, + ..._readExtraBuildFlagsConfiguration(example.directory), if (enableExperiment.isNotEmpty) '--enable-experiment=$enableExperiment', ], diff --git a/script/tool/pubspec.yaml b/script/tool/pubspec.yaml index 2569e0ede870..689618f06123 100644 --- a/script/tool/pubspec.yaml +++ b/script/tool/pubspec.yaml @@ -1,7 +1,7 @@ name: flutter_plugin_tools description: Productivity utils for flutter/plugins and flutter/packages repository: https://github.com/flutter/plugins/tree/master/script/tool -version: 0.7.0 +version: 0.7.1 dependencies: args: ^2.1.0 diff --git a/script/tool/test/build_examples_command_test.dart b/script/tool/test/build_examples_command_test.dart index d9cbad246d28..c3b0cb9d5cd1 100644 --- a/script/tool/test/build_examples_command_test.dart +++ b/script/tool/test/build_examples_command_test.dart @@ -379,7 +379,6 @@ void main() { ]), ); - print(processRunner.recordedCalls); // Output should be empty since running build-examples --macos with no macos // implementation is a no-op. expect(processRunner.recordedCalls, orderedEquals([])); @@ -407,7 +406,6 @@ void main() { ]), ); - print(processRunner.recordedCalls); expect( processRunner.recordedCalls, containsAll([ @@ -436,7 +434,6 @@ void main() { contains('Creating temporary winuwp folder'), ); - print(processRunner.recordedCalls); expect( processRunner.recordedCalls, orderedEquals([ @@ -679,5 +676,50 @@ void main() { ])); }); }); + + test('The .pluginToolsConfig.yaml file', () async { + mockPlatform.isLinux = true; + final Directory pluginDirectory = createFakePlugin('plugin', packagesDir, + platformSupport: { + kPlatformLinux: const PlatformDetails(PlatformSupport.inline), + kPlatformMacos: const PlatformDetails(PlatformSupport.inline), + }); + + final Directory pluginExampleDirectory = + pluginDirectory.childDirectory('example'); + + final File pluginExampleConfigFile = + pluginExampleDirectory.childFile('.pluginToolsConfig.yaml'); + pluginExampleConfigFile + .writeAsStringSync('buildFlags:\n global:\n - "test argument"'); + + final List output = [ + ...await runCapturingPrint( + runner, ['build-examples', '--linux']), + ...await runCapturingPrint( + runner, ['build-examples', '--macos']), + ]; + + expect( + output, + containsAllInOrder([ + '\nBUILDING plugin/example for Linux', + '\nBUILDING plugin/example for macOS', + ]), + ); + + expect( + processRunner.recordedCalls, + orderedEquals([ + ProcessCall( + getFlutterCommand(mockPlatform), + const ['build', 'linux', 'test argument'], + pluginExampleDirectory.path), + ProcessCall( + getFlutterCommand(mockPlatform), + const ['build', 'macos', 'test argument'], + pluginExampleDirectory.path), + ])); + }); }); }