// Copyright (c) 2019, 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.

import 'dart:convert';

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

import 'language_version.dart';

/// Contents of a `.dart_tool/package_config.json` file.
class PackageConfig {
  /// Version of the configuration in the `.dart_tool/package_config.json` file.
  ///
  /// The only supported value as of writing is `2`.
  int configVersion;

  /// Packages configured.
  List<PackageConfigEntry> packages;

  /// Date-time the `.dart_tool/package_config.json` file was generated.
  ///
  /// `null` if not given.
  DateTime? generated;

  /// Tool that generated the `.dart_tool/package_config.json` file.
  ///
  /// For `pub` this is always `'pub'`.
  ///
  /// `null` if not given.
  String? generator;

  /// Version of the tool that generated the `.dart_tool/package_config.json`
  /// file.
  ///
  /// For `pub` this is the Dart SDK version from which `pub get` was called.
  ///
  /// `null` if not given.
  Version? generatorVersion;

  /// Additional properties not in the specification for the
  /// `.dart_tool/package_config.json` file.
  Map<String, dynamic> additionalProperties;

  PackageConfig({
    required this.configVersion,
    required this.packages,
    this.generated,
    this.generator,
    this.generatorVersion,
    Map<String, dynamic>? additionalProperties,
  }) : additionalProperties = additionalProperties ?? {};

  /// Create [PackageConfig] from JSON [data].
  ///
  /// Throws [FormatException], if format is invalid, this does not validate the
  /// contents only that the format is correct.
  factory PackageConfig.fromJson(Object data) {
    if (data is! Map<String, dynamic>) {
      throw FormatException('package_config.json must be a JSON object');
    }
    final root = data;

    void throwFormatException(String property, String mustBe) =>
        throw FormatException(
          '"$property" in .dart_tool/package_config.json $mustBe',
        );

    /// Read the 'configVersion' property
    final configVersion = root['configVersion'];
    if (configVersion is! int) {
      throwFormatException('configVersion', 'must be an integer');
    }
    if (configVersion != 2) {
      throwFormatException(
        'configVersion',
        'must be 2 (the only supported version)',
      );
    }

    final packagesRaw = root['packages'];
    if (packagesRaw is! List) {
      throwFormatException('packages', 'must be a list');
    }
    final packages = <PackageConfigEntry>[];
    for (final entry in packagesRaw) {
      packages.add(PackageConfigEntry.fromJson(entry));
    }

    // Read the 'generated' property
    DateTime? generated;
    final generatedRaw = root['generated'];
    if (generatedRaw != null) {
      if (generatedRaw is! String) {
        throwFormatException('generated', 'must be a string, if given');
      }
      generated = DateTime.parse(generatedRaw);
    }

    // Read the 'generator' property
    final generator = root['generator'];
    if (generator != null && generator is! String) {
      throw FormatException(
        '"generator" in package_config.json must be a string, if given',
      );
    }

    // Read the 'generatorVersion' property
    Version? generatorVersion;
    final generatorVersionRaw = root['generatorVersion'];
    if (generatorVersionRaw != null) {
      if (generatorVersionRaw is! String) {
        throwFormatException('generatorVersion', 'must be a string, if given');
      }
      try {
        generatorVersion = Version.parse(generatorVersionRaw);
      } on FormatException catch (e) {
        throwFormatException(
          'generatorVersion',
          'must be a semver version, if given, error: ${e.message}',
        );
      }
    }

    return PackageConfig(
      configVersion: configVersion as int,
      packages: packages,
      generated: generated,
      generator: generator,
      generatorVersion: generatorVersion,
      additionalProperties: Map.fromEntries(
        root.entries.where(
          (e) => !{
            'configVersion',
            'packages',
            'generated',
            'generator',
            'generatorVersion',
          }.contains(e.key),
        ),
      ),
    );
  }

  /// Convert to JSON structure.
  Map<String, Object?> toJson() => {
        'configVersion': configVersion,
        'packages': packages.map((p) => p.toJson()).toList(),
        'generated': generated?.toUtc().toIso8601String(),
        'generator': generator,
        'generatorVersion': generatorVersion?.toString(),
      }..addAll(additionalProperties);

  // We allow the package called 'flutter_gen' to be injected into
  // package_config.
  //
  // This is somewhat a hack. But it allows flutter to generate code in a
  // package as it likes.
  //
  // See https://github.com/flutter/flutter/issues/73870 .
  Iterable<PackageConfigEntry> get nonInjectedPackages =>
      packages.where((package) => package.name != 'flutter_gen');
}

class PackageConfigEntry {
  /// Package name.
  String name;

  /// Root [Uri] of the package.
  ///
  /// This specifies the root folder of the package, all files below this folder
  /// is considered part of this package.
  Uri rootUri;

  /// Relative URI path of the library folder relative to [rootUri].
  ///
  /// Import statements in Dart programs are resolved relative to this folder.
  /// This must be in the sub-tree under [rootUri].
  ///
  /// `null` if not given.
  Uri? packageUri;

  /// Language version used by package.
  ///
  /// Given as `<major>.<minor>` version, similar to the `// @dart = X.Y`
  /// comment. This is derived from the lower-bound on the Dart SDK requirement
  /// in the `pubspec.yaml` for the given package.
  LanguageVersion? languageVersion;

  /// Additional properties not in the specification for the
  /// `.dart_tool/package_config.json` file.
  Map<String, dynamic>? additionalProperties;

  PackageConfigEntry({
    required this.name,
    required this.rootUri,
    this.packageUri,
    this.languageVersion,
    this.additionalProperties = const {},
  });

  /// Create [PackageConfigEntry] from JSON [data].
  ///
  /// Throws [FormatException], if format is invalid, this does not validate the
  /// contents only that the format is correct.
  factory PackageConfigEntry.fromJson(Object data) {
    if (data is! Map<String, dynamic>) {
      throw FormatException(
        'packages[] entries in package_config.json must be JSON objects',
      );
    }
    final root = data;

    Never throwFormatException(String property, String mustBe) =>
        throw FormatException(
          '"packages[].$property" in .dart_tool/package_config.json $mustBe',
        );

    final name = root['name'];
    if (name is! String) {
      throwFormatException('name', 'must be a string');
    }

    final Uri rootUri;
    final rootUriRaw = root['rootUri'];
    if (rootUriRaw is! String) {
      throwFormatException('rootUri', 'must be a string');
    }
    try {
      rootUri = Uri.parse(rootUriRaw);
    } on FormatException {
      throwFormatException('rootUri', 'must be a URI');
    }

    Uri? packageUri;
    var packageUriRaw = root['packageUri'];
    if (packageUriRaw != null) {
      if (packageUriRaw is! String) {
        throwFormatException('packageUri', 'must be a string');
      }
      if (!packageUriRaw.endsWith('/')) {
        packageUriRaw = '$packageUriRaw/';
      }
      try {
        packageUri = Uri.parse(packageUriRaw);
      } on FormatException {
        throwFormatException('packageUri', 'must be a URI');
      }
    }

    LanguageVersion? languageVersion;
    final languageVersionRaw = root['languageVersion'];
    if (languageVersionRaw != null) {
      if (languageVersionRaw is! String) {
        throwFormatException('languageVersion', 'must be a string');
      }
      try {
        languageVersion = LanguageVersion.parse(languageVersionRaw);
      } on FormatException {
        throwFormatException(
          'languageVersion',
          'must be on the form <major>.<minor>',
        );
      }
    }

    return PackageConfigEntry(
      name: name,
      rootUri: rootUri,
      packageUri: packageUri,
      languageVersion: languageVersion,
    );
  }

  /// Convert to JSON structure.
  Map<String, Object?> toJson() => {
        'name': name,
        'rootUri': rootUri.toString(),
        if (packageUri != null) 'packageUri': packageUri.toString(),
        if (languageVersion != null) 'languageVersion': '$languageVersion',
      }..addAll(additionalProperties ?? {});

  @override
  String toString() {
    // TODO: implement toString
    return JsonEncoder.withIndent('  ').convert(toJson());
  }

  String resolvedRootDir(String packageConfigPath) {
    return p.join(p.dirname(packageConfigPath), p.fromUri(rootUri));
  }
}
