#!/usr/bin/env dart

/// Generates the repo's ".dart_tool/package_config.json" file.

// @dart = 2.9

import 'dart:convert';
import 'dart:io';

import 'package:args/args.dart';
import 'package:path/path.dart' as p;
import 'package:pub_semver/pub_semver.dart';
import 'package:yaml/yaml.dart';

bool _parseOptions(List<String> args) {
  const usage = "Usage: dart generate_package_config.dart [flags...]";

  var parser = ArgParser();

  parser.addFlag("help", abbr: "h");

  parser.addFlag("check",
      abbr: "c",
      help: "Return with a non-zero exit code if not up-to-date",
      negatable: false);

  var results = parser.parse(args);

  if (results["help"] as bool) {
    print("Regenerate the .dart_tool/package_config.json file.");
    print("");
    print(usage);
    print("");
    print(parser.usage);
    exit(0);
  }

  return results["check"] as bool;
}

final repoRoot = p.dirname(p.dirname(p.fromUri(Platform.script)));
final configFilePath = p.join(repoRoot, '.dart_tool/package_config.json');

void main(List<String> args) {
  bool checkOnly = _parseOptions(args);

  var packageDirs = [
    ...listSubdirectories('pkg'),
    ...listSubdirectories('third_party/pkg'),
    ...listSubdirectories('third_party/pkg_tested'),
    ...listSubdirectories('third_party/pkg/file/packages'),
    ...listSubdirectories('third_party/pkg/test/pkgs'),
    packageDirectory('runtime/observatory'),
    packageDirectory(
        'runtime/observatory/tests/service/observatory_test_package'),
    packageDirectory('runtime/observatory_2'),
    packageDirectory(
        'runtime/observatory_2/tests/service_2/observatory_test_package_2'),
    packageDirectory('sdk/lib/_internal/sdk_library_metadata'),
    packageDirectory('third_party/devtools/devtools_server'),
    packageDirectory('third_party/devtools/devtools_shared'),
    packageDirectory('third_party/pkg/protobuf/protobuf'),
    packageDirectory('third_party/pkg/webdev/frontend_server_client'),
    packageDirectory('tools/package_deps'),
  ];

  var cfePackageDirs = [
    packageDirectory('pkg/front_end/testcases/'),
  ];

  var feAnalyzerSharedPackageDirs = [
    packageDirectory(
        'pkg/_fe_analyzer_shared/test/flow_analysis/assigned_variables/'),
    packageDirectory(
        'pkg/_fe_analyzer_shared/test/flow_analysis/definite_assignment/'),
    packageDirectory(
        'pkg/_fe_analyzer_shared/test/flow_analysis/definite_unassignment/'),
    packageDirectory('pkg/_fe_analyzer_shared/test/flow_analysis/nullability/'),
    packageDirectory(
        'pkg/_fe_analyzer_shared/test/flow_analysis/reachability/'),
    packageDirectory(
        'pkg/_fe_analyzer_shared/test/flow_analysis/type_promotion/'),
    packageDirectory(
        'pkg/_fe_analyzer_shared/test/flow_analysis/why_not_promoted//'),
    packageDirectory('pkg/_fe_analyzer_shared/test/inheritance/'),
  ];

  var packages = [
    ...makePackageConfigs(packageDirs),
    ...makeCfePackageConfigs(cfePackageDirs),
    ...makeFeAnalyzerSharedPackageConfigs(feAnalyzerSharedPackageDirs)
  ];
  packages.sort((a, b) => a["name"].compareTo(b["name"]));

  var configFile = File(p.join(repoRoot, '.dart_tool', 'package_config.json'));
  var json =
      jsonDecode(configFile.readAsStringSync()) as Map<dynamic, dynamic>;
  var oldPackages = json['packages'] as List<dynamic>;

  // Validate the packages entry only, to avoid spurious failures from changes
  // in the dates embedded in the other entries.
  if (jsonEncode(packages) == jsonEncode(oldPackages)) {
    print("Package config up to date");
    exit(0);
  } else if (checkOnly) {
    print("Package config out of date");
    print("Run `gclient sync -D && dart tools/generate_package_config.dart` "
        "to update.");
    exit(1);
  }

  var year = DateTime.now().year;
  var config = <String, dynamic>{
    'copyright': [
      'Copyright (c) $year, the Dart project authors. Please see the AUTHORS ',
      'file for details. All rights reserved. Use of this source code is ',
      'governed by a BSD-style license that can be found in the LICENSE file.'
    ],
    'comment': [
      'Package configuration for all packages in /pkg, and checked out by DEPS',
      'into /third_party/pkg and /third_party/pkg_tested.',
      'If you add a package to DEPS or /pkg or change a package\'s SDK',
      'constraint, update this by running tools/generate_package_config.dart.'
    ],
    'configVersion': 2,
    'generated': DateTime.now().toIso8601String(),
    'generator': 'tools/generate_package_config.dart',
    'packages': packages,
  };

  // TODO(rnystrom): Consider using package_config_v2 to generate this instead.
  var jsonString = JsonEncoder.withIndent('  ').convert(config);
  configFile.writeAsStringSync('$jsonString\n');
  print('Generated .dart_tool/package_config.dart containing '
      '${packages.length} packages.');
}

/// Generates package configurations for each package in [packageDirs].
Iterable<Map<String, String>> makePackageConfigs(
    List<String> packageDirs) sync* {
  for (var packageDir in packageDirs) {
    var version = pubspecLanguageVersion(packageDir);
    var hasLibDirectory = Directory(p.join(packageDir, 'lib')).existsSync();

    yield {
      'name': p.basename(packageDir),
      'rootUri': p
          .toUri(p.relative(packageDir, from: p.dirname(configFilePath)))
          .toString(),
      if (hasLibDirectory) 'packageUri': 'lib/',
      'languageVersion': '${version.major}.${version.minor}'
    };
  }
}

/// Generates package configurations for the special pseudo-packages used by
/// the CFE unit tests (`pkg/front_end/test/unit_test_suites.dart`).
Iterable<Map<String, String>> makeCfePackageConfigs(
    List<String> packageDirs) sync* {
  for (var packageDir in packageDirs) {
    yield {
      'name': 'front_end_${p.basename(packageDir)}',
      'rootUri': p
          .toUri(p.relative(packageDir, from: p.dirname(configFilePath)))
          .toString(),
      'packageUri': '.nonexisting/',
    };
  }
}

/// Generates package configurations for the special pseudo-packages used by
/// the _fe_analyzer_shared id tests.
Iterable<Map<String, String>> makeFeAnalyzerSharedPackageConfigs(
    List<String> packageDirs) sync* {
  for (var packageDir in packageDirs) {
    yield {
      'name': '_fe_analyzer_shared_${p.basename(packageDir)}',
      'rootUri': p
          .toUri(p.relative(packageDir, from: p.dirname(configFilePath)))
          .toString(),
      'packageUri': '.nonexisting/',
    };
  }
}

/// Generates a path to [relativePath] within the repo.
String packageDirectory(String relativePath) => p.join(repoRoot, relativePath);

/// Finds the paths of the immediate subdirectories of [packagesDir] that
/// contain pubspecs.
Iterable<String> listSubdirectories(String packagesDir) sync* {
  for (var entry in Directory(p.join(repoRoot, packagesDir)).listSync()) {
    if (entry is! Directory) continue;
    if (!File(p.join(entry.path, 'pubspec.yaml')).existsSync()) continue;
    yield entry.path;
  }
}

/// Infers the language version from the SDK constraint in the pubspec for
/// [packageDir].
///
/// Returns `null` if there is no pubspec or no SDK constraint.
Version pubspecLanguageVersion(String packageDir) {
  var pubspecFile = File(p.join(packageDir, 'pubspec.yaml'));
  var relative = p.relative(packageDir, from: repoRoot);

  if (!pubspecFile.existsSync()) {
    print("Error: Missing pubspec for $relative.");
    exit(1);
  }

  var pubspec =
      loadYaml(pubspecFile.readAsStringSync()) as Map<dynamic, dynamic>;
  if (!pubspec.containsKey('environment')) {
    print("Error: Pubspec for $relative has no SDK constraint.");
    exit(1);
  }

  var environment = pubspec['environment'] as Map<dynamic, dynamic>;
  if (!environment.containsKey('sdk')) {
    print("Error: Pubspec for $relative has no SDK constraint.");
    exit(1);
  }

  var sdkConstraint = VersionConstraint.parse(environment['sdk'] as String);
  if (sdkConstraint is VersionRange) return sdkConstraint.min;

  print("Error: SDK constraint $relative is not a version range.");
  exit(1);
}
