Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

introduces force-use-flutter argument for commands #178

Merged
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,8 @@
# Changelog

## Version 0.19.0
- introduces `force-use-flutter` option for all commands to force dart_apitool to use the `flutter` command.

## Version 0.18.0
- add missing export to json output for `extract` command
- adds analysis of readability and writability of fields.
Expand Down
11 changes: 10 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -56,6 +56,10 @@ Usage: dart-apitool extract [arguments]
--[no-]remove-example Removes examples from the package to analyze.
(defaults to on)
--[no-]set-exit-on-missing-export Sets exit code to != 0 if missing exports are detected in the API.
--force-use-flutter If present forces dart_apitool to use Flutter
(instead of Dart if the project is Dart only)

Run "dart-apitool help" to see global options.
```

### diff
Expand Down Expand Up @@ -91,10 +95,15 @@ Usage: dart-apitool diff [arguments]
[none, allowAdding (default), strict]
--[no-]remove-example Removes examples from the package to analyze.
(defaults to on)
--[no-]ignore-requiredness Whether to ignore the required aspect of interfaces (yielding less strict version bump requirements)
--[no-]ignore-requiredness Whether to ignore the required aspect of interfaces
(yielding less strict version bump requirements)
--report-format Which output format should be used
[cli (default), markdown, json]
--report-file-path Where to store the report file (no effect on cli option)
--force-use-flutter If present forces dart_apitool to use Flutter
(instead of Dart if the project is Dart only)

Run "dart-apitool help" to see global options.
```

## Integration
Expand Down
54 changes: 48 additions & 6 deletions lib/src/cli/commands/command_mixin.dart
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import 'dart:convert';
import 'dart:io';

import 'package:args/args.dart';
import 'package:dart_apitool/api_tool.dart';
import 'package:dart_apitool/src/cli/source_item.dart';
import 'package:path/path.dart' as p;
Expand All @@ -22,17 +23,41 @@ Package reference can be one of:
OBSOLETE: Has no effect anymore.
''';

static final String _flagNameForceUseFlutter = 'force-use-flutter';
static final String _helpTextForceUseFlutter =
'If present forces dart_apitool to use Flutter\n(instead of Dart if the project is Dart only)';

void init(ArgParser argParser) {
argParser.addFlag(
_flagNameForceUseFlutter,
help: _helpTextForceUseFlutter,
defaultsTo: false,
negatable: false,
);
}

/// prepares given [ref]. Depending on the type of ref this can include
/// - copying the package to a temporary directory
/// - running pub get
/// If you use [analyze] with this result then it will take care to clean up
/// everything (e.g. removing temp directory)
Future<PreparedPackageRef> prepare(PackageRef ref) async {
Future<PreparedPackageRef> prepare(
ArgResults argResults,
PackageRef ref,
) async {
final stdoutSession = StdoutSession();

final forceUseFlutterTool =
(argResults[_flagNameForceUseFlutter] as bool?) ?? false;

List<SourceItem> sources = [];
String? packageRelativePath;
if (ref.isDirectoryPath) {
await stdoutSession.writeln('Preparing ${ref.ref}');
String forceUseFlutterSuffix = '';
if (forceUseFlutterTool) {
forceUseFlutterSuffix = ' (forced Flutter)';
}
await stdoutSession.writeln('Preparing ${ref.ref}$forceUseFlutterSuffix');
String sourceDir = ref.ref;
if (sourceDir.endsWith(p.separator)) {
sourceDir =
Expand Down Expand Up @@ -70,10 +95,18 @@ OBSOLETE: Has no effect anymore.
await _copyPath(sourceItem.sourceDir,
sourceItem.destinationPath(forPrefix: tempDir.path));
if (!sourceItem.isInCache) {
String forceUseFlutterSuffix = '';
if (forceUseFlutterTool) {
forceUseFlutterSuffix = ' (forced Flutter)';
}

await stdoutSession.writeln(
'Preparing package dependencies for local package ${sourceItem.sourceDir}');
await PubInteraction.runPubGet(sourceItem.sourceDir,
stdoutSession: stdoutSession);
'Preparing package dependencies for local package ${sourceItem.sourceDir}$forceUseFlutterSuffix');
await PubInteraction.runPubGet(
sourceItem.sourceDir,
stdoutSession: stdoutSession,
forceUseFlutterTool: forceUseFlutterTool,
);
final sourcePackageConfig =
File(_getPackageConfigPathForPackage(sourceItem.sourceDir));
final targetPackageConfig =
Expand Down Expand Up @@ -106,11 +139,16 @@ OBSOLETE: Has no effect anymore.
/// [doMergeBaseClasses] defines if base classes should be merged into derived ones. This allows to remove private base classes from the list of interface declarations.
/// [doAnalyzePlatformConstraints] defines if the platform constraints of the package shall be analyzed.
Future<PackageApi> analyze(
ArgResults argResults,
PreparedPackageRef preparedRef, {
bool doAnalyzePlatformConstraints = true,
bool doRemoveExample = true,
}) async {
final stdoutSession = StdoutSession();

final forceUseFlutterTool =
(argResults[_flagNameForceUseFlutter] as bool?) ?? false;

String? path;
if (preparedRef.packageRef.isDirectoryPath) {
path = preparedRef.packageRef.ref;
Expand Down Expand Up @@ -141,7 +179,11 @@ OBSOLETE: Has no effect anymore.
final packageConfig = File(_getPackageConfigPathForPackage(packagePath));
if (!packageConfig.existsSync()) {
await stdoutSession.writeln('Running pub get');
await PubInteraction.runPubGet(packagePath, stdoutSession: stdoutSession);
await PubInteraction.runPubGet(
packagePath,
stdoutSession: stdoutSession,
forceUseFlutterTool: forceUseFlutterTool,
);
} else {
await stdoutSession
.writeln('Omitting pub get (package config already present)');
Expand Down
11 changes: 9 additions & 2 deletions lib/src/cli/commands/diff_command.dart
Original file line number Diff line number Diff line change
Expand Up @@ -97,8 +97,10 @@ You may want to do this if you want to make sure
);
argParser.addFlag(
_optionNameIgnoreRequiredness,
help:
'Whether to ignore the required aspect of interfaces (yielding less strict version bump requirements)',
help: '''
Whether to ignore the required aspect of interfaces
(yielding less strict version bump requirements)
''',
defaultsTo: false,
negatable: true,
);
Expand All @@ -114,6 +116,7 @@ You may want to do this if you want to make sure
help: 'Where to store the report file (no effect on cli option)',
mandatory: false,
);
init(argParser);
}

@override
Expand Down Expand Up @@ -150,18 +153,22 @@ You may want to do this if you want to make sure
argResults![_optionNameIgnoreRequiredness] as bool;

final preparedOldPackageRef = await prepare(
argResults!,
oldPackageRef,
);
final preparedNewPackageRef = await prepare(
argResults!,
newPackageRef,
);

final oldPackageApi = await analyze(
argResults!,
preparedOldPackageRef,
doAnalyzePlatformConstraints: !noAnalyzePlatformConstraints,
doRemoveExample: doRemoveExample,
);
final newPackageApi = await analyze(
argResults!,
preparedNewPackageRef,
doAnalyzePlatformConstraints: !noAnalyzePlatformConstraints,
doRemoveExample: doRemoveExample,
Expand Down
3 changes: 3 additions & 0 deletions lib/src/cli/commands/extract_command.dart
Original file line number Diff line number Diff line change
Expand Up @@ -60,6 +60,7 @@ If not specified the extracted API will be printed to the console.
defaultsTo: false,
negatable: true,
);
init(argParser);
}

@override
Expand All @@ -72,9 +73,11 @@ If not specified the extracted API will be printed to the console.
argResults![_optionNameSetExitCodeOnMissingExport] as bool;

final preparedPackageRef = await prepare(
argResults!,
packageRef,
);
final packageApi = await analyze(
argResults!,
preparedPackageRef,
doAnalyzePlatformConstraints: !noAnalyzePlatformConstraints,
doRemoveExample: doRemoveExample,
Expand Down
31 changes: 22 additions & 9 deletions lib/src/tooling/dart_interaction.dart
Original file line number Diff line number Diff line change
Expand Up @@ -11,22 +11,35 @@ import '../utils/utils.dart';
/// Helper class for interacting with Dart and Flutter
abstract class DartInteraction {
/// runs the dart or flutter command with the given [args].
/// The decision which command to run is taken from the pubspeck.yaml file in
/// The decision which command to run is taken from the pubspec.yaml file in
/// [forDirectory]
/// This command determines which tool to use based on the pubspec.yaml file.
/// If [forceUseFlutterTool] is given then this value will be used to
/// determine which tool to use. [true] means Flutter, [false] means Dart
static Future runDartOrFlutterCommand(
String forDirectory, {
List<String> args = const [],
StdoutSession? stdoutSession,
bool forceUseFlutterTool = false,
}) async {
final pubspecPath = path.join(forDirectory, 'pubspec.yaml');
final pubspecExists = await File(pubspecPath).exists();
if (!pubspecExists) {
throw RunDartError(
'Error running pub get in $forDirectory:\nThis is not a valid dart package directory');
bool useFlutter = false;
if (!forceUseFlutterTool) {
// if we are not forced to use Flutter then we get this information
// from the pubspec.yaml file
final pubspecPath = path.join(forDirectory, 'pubspec.yaml');
final pubspecExists = await File(pubspecPath).exists();
if (!pubspecExists) {
throw RunDartError(
'Error running pub get in $forDirectory:\nThis is not a valid dart package directory');
}
final yamlContent = await File(pubspecPath).readAsString();
final pubSpec = Pubspec.parse(yamlContent);
useFlutter = pubSpec.dependencies.containsKey('flutter');
} else {
// here we are forced to use Flutter (forceUseFlutterTool == true)
useFlutter = true;
}
final yamlContent = await File(pubspecPath).readAsString();
final pubSpec = Pubspec.parse(yamlContent);
if (!pubSpec.dependencies.containsKey('flutter')) {
if (!useFlutter) {
return _runDartOrFlutterCommand(
_getDartExecutablePath(),
workingDirectory: forDirectory,
Expand Down
2 changes: 2 additions & 0 deletions lib/src/tooling/pub_interaction.dart
Original file line number Diff line number Diff line change
Expand Up @@ -111,6 +111,7 @@ abstract class PubInteraction {
static Future runPubGet(
String packageDirectory, {
StdoutSession? stdoutSession,
bool forceUseFlutterTool = false,
}) async {
return DartInteraction.runDartOrFlutterCommand(
packageDirectory,
Expand All @@ -119,6 +120,7 @@ abstract class PubInteraction {
'get',
],
stdoutSession: stdoutSession,
forceUseFlutterTool: forceUseFlutterTool,
);
}
}
2 changes: 1 addition & 1 deletion pubspec.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ name: dart_apitool
description: A tool to analyze the public API of a package, create a model of it and diff it against another version to check semver.
repository: https://github.com/bmw-tech/dart_apitool

version: 0.18.1-dev
version: 0.19.0-dev

environment:
sdk: ">=3.0.0 <4.0.0"
Expand Down
Loading