Skip to content

Commit

Permalink
Merge pull request #1228 from nextcloud/feat/dynamite/warn_dynamite_r…
Browse files Browse the repository at this point in the history
…untimer_version_mismatch

feat(dynamite)!: validate version of dynamite_runtime when generating
  • Loading branch information
Leptopoda authored Dec 13, 2023
2 parents 49efac6 + 40c5f3e commit 39255db
Show file tree
Hide file tree
Showing 4 changed files with 111 additions and 1 deletion.
2 changes: 1 addition & 1 deletion packages/dynamite/dynamite/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ dependencies:
uri: ^1.0.0
dev_dependencies:
build_runner: ^2.4.0
built_value_generator: ^8.8.0
built_value_generator: ^8.8.1
```
# Generating
Expand Down
96 changes: 96 additions & 0 deletions packages/dynamite/dynamite/lib/src/helpers/version_checker.dart
Original file line number Diff line number Diff line change
@@ -0,0 +1,96 @@
import 'package:build/build.dart';
import 'package:pub_semver/pub_semver.dart';
import 'package:pubspec_parse/pubspec_parse.dart';

final dependencies = {
'built_collection': Version.parse('5.0.0'),
'built_value': Version.parse('8.0.0'),
'collection': Version.parse('1.0.0'),
'dynamite_runtime': Version.parse('0.0.1'),
'meta': Version.parse('1.0.0'),
'universal_io': Version.parse('2.0.0'),
'uri': Version.parse('1.0.0'),
};

final devDependencies = {
'built_value_generator': Version.parse('8.8.1'),
};

/// Checks whether the correct version of the dependencies are present in the pubspec.yaml file.
Future<({bool hasFatal, String messages})> helperVersionCheck(final BuildStep buildStep) async {
final pubspecAsset = AssetId(buildStep.inputId.package, 'pubspec.yaml');

if (!await buildStep.canRead(pubspecAsset)) {
return (
hasFatal: false,
messages: 'Failed to read the pubspec.yaml file. Version constraints of required packages can not be validated.',
);
}

final pubspecContent = await buildStep.readAsString(pubspecAsset);
final pubspec = Pubspec.parse(pubspecContent, sourceUrl: pubspecAsset.uri);

final messages = StringBuffer();
var hasFatal = false;

for (final constraint in dependencies.entries) {
final result = _validateVersion(pubspec.dependencies, constraint.key, constraint.value);

if (result.message != null) {
messages.writeln(result.message);
}

if (result.isFatal) {
hasFatal = true;
}
}

for (final constraint in devDependencies.entries) {
final result = _validateVersion(pubspec.devDependencies, constraint.key, constraint.value);

if (result.message != null) {
messages.writeln(result.message);
}

if (result.isFatal) {
hasFatal = true;
}
}

return (hasFatal: hasFatal, messages: messages.toString());
}

({bool isFatal, String? message}) _validateVersion(
final Map<String, Dependency> dependencies,
final String packageName,
final Version minVersion,
) {
final dependency = dependencies[packageName];
final maxVersion = minVersion.nextBreaking;

if (dependency == null) {
return (
isFatal: false,
message:
'Could not find the dependency on `$packageName` in pubspec.yaml file. Compatibility check is being skipped.',
);
} else if (dependency is HostedDependency) {
final constraint = dependency.version;
final invalidConstraintMessage =
'The version constraint $constraint on `$packageName` allows versions before $minVersion or after $maxVersion which is not allowed.';

if (constraint is Version && (constraint < minVersion || constraint > maxVersion)) {
return (isFatal: true, message: invalidConstraintMessage);
}

final range = constraint as VersionRange;
final rangeMin = range.min;
final rangeMax = range.max;

if (rangeMin == null || rangeMax == null || rangeMin < minVersion || rangeMax > maxVersion) {
return (isFatal: true, message: invalidConstraintMessage);
}
}

return (isFatal: false, message: null);
}
12 changes: 12 additions & 0 deletions packages/dynamite/dynamite/lib/src/openapi_builder.dart
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ import 'package:dynamite/src/builder/generate_schemas.dart';
import 'package:dynamite/src/builder/imports.dart';
import 'package:dynamite/src/builder/serializer.dart';
import 'package:dynamite/src/builder/state.dart';
import 'package:dynamite/src/helpers/version_checker.dart';
import 'package:dynamite/src/models/config.dart';
import 'package:dynamite/src/models/openapi.dart' as openapi;
import 'package:version/version.dart';
Expand All @@ -38,6 +39,17 @@ class OpenAPIBuilder implements Builder {

@override
Future<void> build(final BuildStep buildStep) async {
final result = await helperVersionCheck(buildStep);

if (result.messages.isNotEmpty) {
if (result.hasFatal) {
log.severe(result.messages);
return;
} else {
log.info(result.messages);
}
}

try {
final inputId = buildStep.inputId;
final outputId = inputId.changeExtension('.dart');
Expand Down
2 changes: 2 additions & 0 deletions packages/dynamite/dynamite/pubspec.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,8 @@ dependencies:
intersperse: ^2.0.0
meta: ^1.0.0
path: ^1.0.0
pub_semver: ^2.1.4
pubspec_parse: ^1.2.3
uri: ^1.0.0
version: ^3.0.0

Expand Down

0 comments on commit 39255db

Please sign in to comment.