// 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 'package:_fe_analyzer_shared/src/sdk/allowed_experiments.dart';
import 'package:analyzer/dart/analysis/features.dart';
import 'package:analyzer/file_system/file_system.dart';
import 'package:analyzer/src/context/packages.dart';
import 'package:analyzer/src/generated/sdk.dart';
import 'package:analyzer/src/generated/source.dart';
import 'package:analyzer/src/util/uri.dart';
import 'package:pub_semver/pub_semver.dart';

class FeatureSetProvider {
  /// This flag will be turned to `true` and inlined when we un-fork SDK,
  /// so that the only SDK is the Null Safe SDK.
  static const isNullSafetySdk = true;

  final Version _sdkLanguageVersion;
  final AllowedExperiments _allowedExperiments;
  final ResourceProvider _resourceProvider;
  final Packages _packages;
  final FeatureSet _packageDefaultFeatureSet;
  final Version _nonPackageDefaultLanguageVersion;
  final FeatureSet _nonPackageDefaultFeatureSet;

  FeatureSetProvider._({
    required Version sdkLanguageVersion,
    required AllowedExperiments allowedExperiments,
    required ResourceProvider resourceProvider,
    required Packages packages,
    required FeatureSet packageDefaultFeatureSet,
    required Version nonPackageDefaultLanguageVersion,
    required FeatureSet nonPackageDefaultFeatureSet,
  })   : _sdkLanguageVersion = sdkLanguageVersion,
        _allowedExperiments = allowedExperiments,
        _resourceProvider = resourceProvider,
        _packages = packages,
        _packageDefaultFeatureSet = packageDefaultFeatureSet,
        _nonPackageDefaultLanguageVersion = nonPackageDefaultLanguageVersion,
        _nonPackageDefaultFeatureSet = nonPackageDefaultFeatureSet;

  FeatureSet featureSetForExperiments(List<String> experiments) {
    return FeatureSet.fromEnableFlags2(
      sdkLanguageVersion: _sdkLanguageVersion,
      flags: experiments,
    );
  }

  /// Return the [FeatureSet] for the package that contains the file.
  ///
  /// Note, that [getLanguageVersion] returns the default language version
  /// for libraries in the package, but this method does not restrict the
  /// [FeatureSet] of this version. The reason is that we allow libraries to
  /// "upgrade" to higher version than the default package language version,
  /// and want this to preserve experimental features.
  FeatureSet getFeatureSet(String path, Uri uri) {
    if (uri.isScheme('dart')) {
      var pathSegments = uri.pathSegments;
      if (pathSegments.isNotEmpty) {
        var libraryName = pathSegments.first;
        var experiments = _allowedExperiments.forSdkLibrary(libraryName);
        return featureSetForExperiments(experiments);
      } else {
        return featureSetForExperiments([]);
      }
    }

    var package = _findPackage(uri, path);
    if (package != null) {
      var experiments = _allowedExperiments.forPackage(package.name);
      if (experiments != null) {
        return featureSetForExperiments(experiments);
      }

      return _packageDefaultFeatureSet;
    }

    return _nonPackageDefaultFeatureSet;
  }

  /// Return the language version for the package that contains the file.
  ///
  /// Each individual file might use `// @dart` to override this version, to
  /// be either lower, or higher than the package language version.
  Version getLanguageVersion(String path, Uri uri) {
    if (uri.isScheme('dart')) {
      return _sdkLanguageVersion;
    }
    var package = _findPackage(uri, path);
    if (package != null) {
      var languageVersion = package.languageVersion;
      if (languageVersion != null) {
        return languageVersion;
      }
      return _sdkLanguageVersion;
    }

    return _nonPackageDefaultLanguageVersion;
  }

  /// Return the package corresponding to the [uri] or [path], `null` if none.
  ///
  /// For `package` and `asset` schemes the package name is retrieved from the
  /// first path segment of [uri].
  ///
  /// For `file` schemes this tries to look up by the normalized [uri] path.
  ///
  /// If unable to find a package through other mechanisms mechanisms, or it is
  /// an unrecognized uri scheme, then the package is looked up by [path].
  Package? _findPackage(Uri uri, String path) {
    if (uri.isScheme('package') || uri.isScheme('asset')) {
      var pathSegments = uri.pathSegments;
      if (pathSegments.isNotEmpty) {
        var packageName = pathSegments.first;
        var package = _packages[packageName];
        if (package != null) {
          return package;
        }
      }
    } else if (uri.isScheme('file')) {
      var uriPath = fileUriToNormalizedPath(_resourceProvider.pathContext, uri);
      var package = _packages.packageForPath(uriPath);
      if (package != null) {
        return package;
      }
    }

    return _packages.packageForPath(path);
  }

  static FeatureSetProvider build({
    required SourceFactory sourceFactory,
    required ResourceProvider resourceProvider,
    required Packages packages,
    required FeatureSet packageDefaultFeatureSet,
    required Version nonPackageDefaultLanguageVersion,
    required FeatureSet nonPackageDefaultFeatureSet,
  }) {
    var sdk = sourceFactory.dartSdk!;
    var allowedExperiments = _experimentsForSdk(sdk);
    return FeatureSetProvider._(
      sdkLanguageVersion: sdk.languageVersion,
      allowedExperiments: allowedExperiments,
      resourceProvider: resourceProvider,
      packages: packages,
      packageDefaultFeatureSet: packageDefaultFeatureSet,
      nonPackageDefaultLanguageVersion: nonPackageDefaultLanguageVersion,
      nonPackageDefaultFeatureSet: nonPackageDefaultFeatureSet,
    );
  }

  static AllowedExperiments _experimentsForSdk(DartSdk sdk) {
    var experimentsContent = sdk.allowedExperimentsJson;
    if (experimentsContent != null) {
      try {
        return parseAllowedExperiments(experimentsContent);
      } catch (_) {}
    }

    return AllowedExperiments(
      sdkDefaultExperiments: [],
      sdkLibraryExperiments: {},
      packageExperiments: {},
    );
  }
}
