// Copyright 2019 The Flutter Authors. 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:async';

import 'package:cocoon_service/ci_yaml.dart';
import 'package:collection/collection.dart';
import 'package:github/github.dart';
import 'package:meta/meta.dart';
import 'package:yaml/yaml.dart';

import '../../protos.dart' as pb;
import '../foundation/utils.dart';
import '../request_handling/api_request_handler.dart';
import '../request_handling/body.dart';
import '../service/bigquery.dart';
import '../service/config.dart';
import '../service/github_service.dart';
import 'flaky_handler_utils.dart';

/// A handler to deflake builders if the builders are no longer flaky.
///
/// This handler gets flaky builders from ci.yaml in flutter/flutter and check
/// the following conditions:
/// 1. The builder is not in [ignoredBuilders].
/// 2. The flaky issue of the builder is closed if there is one.
/// 3. Does not have any existing pr against the target.
/// 4. The builder has been passing for most recent [kRecordNumber] consecutive
///    runs.
/// 5. The builder is not marked with ignore_flakiness.
///
/// If all the conditions are true, this handler will file a pull request to
/// make the builder unflaky.
@immutable
class CheckFlakyBuilders extends ApiRequestHandler<Body> {
  const CheckFlakyBuilders({
    required super.config,
    required super.authenticationProvider,
  });

  static int kRecordNumber = 50;

  static final RegExp _issueLinkRegex = RegExp(r'https://github.com/flutter/flutter/issues/(?<id>[0-9]+)');

  /// Builders that are purposefully marked flaky and should be ignored by this
  /// handler.
  static const Set<String> ignoredBuilders = <String>{
    'Mac_ios32 flutter_gallery__transition_perf_e2e_ios32',
    'Mac_ios32 native_ui_tests_ios',
  };

  @override
  Future<Body> get() async {
    final RepositorySlug slug = Config.flutterSlug;
    final GithubService gitHub = config.createGithubServiceWithToken(await config.githubOAuthToken);
    final BigqueryService bigquery = await config.createBigQueryService();
    final String ciContent = await gitHub.getFileContent(
      slug,
      kCiYamlPath,
    );
    final YamlMap? ci = loadYaml(ciContent) as YamlMap?;
    final pb.SchedulerConfig unCheckedSchedulerConfig = pb.SchedulerConfig()..mergeFromProto3Json(ci);
    final CiYaml ciYaml = CiYaml(
      slug: slug,
      branch: Config.defaultBranch(slug),
      config: unCheckedSchedulerConfig,
    );

    final pb.SchedulerConfig schedulerConfig = ciYaml.config;
    final List<pb.Target> targets = schedulerConfig.targets;

    final List<_BuilderInfo> eligibleBuilders =
        await _getEligibleFlakyBuilders(gitHub, slug, content: ciContent, ciYaml: ciYaml);
    final String testOwnerContent = await gitHub.getFileContent(
      slug,
      kTestOwnerPath,
    );

    for (final _BuilderInfo info in eligibleBuilders) {
      final BuilderType type = getTypeForBuilder(info.name, ciYaml);
      final TestOwnership testOwnership = getTestOwnership(
        targets.singleWhere((element) => element.name == info.name!),
        type,
        testOwnerContent,
      );
      final List<BuilderRecord> builderRecords =
          await bigquery.listRecentBuildRecordsForBuilder(kBigQueryProjectId, builder: info.name, limit: kRecordNumber);
      if (_shouldDeflake(builderRecords)) {
        await _deflakyPullRequest(gitHub, slug, info: info, ciContent: ciContent, testOwnership: testOwnership);
        // Manually add a 1s delay between consecutive GitHub requests to deal with secondary rate limit error.
        // https://docs.github.com/en/rest/guides/best-practices-for-integrators#dealing-with-secondary-rate-limits
        await Future.delayed(config.githubRequestDelay);
      }
    }
    return Body.forJson(const <String, dynamic>{
      'Status': 'success',
    });
  }

  /// A builder should be deflaked if satisfying three conditions.
  /// 1) There are enough data records.
  /// 2) There is no flake
  /// 3) There is no failure
  bool _shouldDeflake(List<BuilderRecord> builderRecords) {
    return builderRecords.length >= kRecordNumber &&
        builderRecords.every((BuilderRecord record) => !record.isFlaky && !record.isFailed);
  }

  /// Gets the builders that match conditions:
  /// 1. The builder's ignoreFlakiness is false.
  /// 2. The builder is flaky
  /// 3. The builder is not in [ignoredBuilders].
  /// 4. The flaky issue of the builder is closed if there is one.
  /// 5. Does not have any existing pr against the builder.
  Future<List<_BuilderInfo>> _getEligibleFlakyBuilders(
    GithubService gitHub,
    RepositorySlug slug, {
    required String content,
    required CiYaml ciYaml,
  }) async {
    final YamlMap ci = loadYaml(content) as YamlMap;
    final YamlList targets = ci[kCiYamlTargetsKey] as YamlList;
    final List<YamlMap?> flakyTargets = targets
        .where((dynamic target) => target[kCiYamlTargetIsFlakyKey] == true)
        .map<YamlMap?>((dynamic target) => target as YamlMap?)
        .toList();
    final List<_BuilderInfo> result = <_BuilderInfo>[];
    final List<String> lines = content.split('\n');
    final Map<String?, PullRequest> nameToExistingPRs = await getExistingPRs(gitHub, slug);
    for (final YamlMap? flakyTarget in flakyTargets) {
      final String? builder = flakyTarget![kCiYamlTargetNameKey] as String?;
      // If target specified ignore_flakiness, then skip.
      if (getIgnoreFlakiness(builder, ciYaml)) {
        continue;
      }
      if (ignoredBuilders.contains(builder)) {
        continue;
      }
      // Skip the flaky target if the issue or pr for the flaky target is still
      // open.
      if (nameToExistingPRs.containsKey(builder)) {
        continue;
      }

      //TODO (ricardoamador): Refactor this so we don't need to parse the entire yaml looking for commented issues, https://github.com/flutter/flutter/issues/113232
      int builderLineNumber = lines.indexWhere((String line) => line.contains('name: $builder')) + 1;
      while (builderLineNumber < lines.length && !lines[builderLineNumber].contains('name:')) {
        if (lines[builderLineNumber].contains('$kCiYamlTargetIsFlakyKey:')) {
          final RegExpMatch? match = _issueLinkRegex.firstMatch(lines[builderLineNumber]);
          if (match == null) {
            result.add(_BuilderInfo(name: builder));
            break;
          }
          final Issue issue = await gitHub.getIssue(slug, issueNumber: int.parse(match.namedGroup('id')!))!;
          if (issue.isClosed) {
            result.add(_BuilderInfo(name: builder, existingIssue: issue));
          }
          break;
        }
        builderLineNumber += 1;
      }
    }
    return result;
  }

  @visibleForTesting
  static bool getIgnoreFlakiness(String? builderName, CiYaml ciYaml) {
    final Target? target =
        ciYaml.postsubmitTargets.singleWhereOrNull((Target target) => target.value.name == builderName);
    return target == null ? false : target.getIgnoreFlakiness();
  }

  Future<void> _deflakyPullRequest(
    GithubService gitHub,
    RepositorySlug slug, {
    required _BuilderInfo info,
    required String ciContent,
    required TestOwnership testOwnership,
  }) async {
    final String modifiedContent = _deflakeBuilderInContent(ciContent, info.name);
    final GitReference masterRef = await gitHub.getReference(slug, kMasterRefs);
    final DeflakePullRequestBuilder prBuilder = DeflakePullRequestBuilder(
      name: info.name,
      recordNumber: kRecordNumber,
      ownership: testOwnership,
      issue: info.existingIssue,
    );
    final PullRequest pullRequest = await gitHub.createPullRequest(
      slug,
      title: prBuilder.pullRequestTitle,
      body: prBuilder.pullRequestBody,
      commitMessage: prBuilder.pullRequestTitle,
      baseRef: masterRef,
      entries: <CreateGitTreeEntry>[
        CreateGitTreeEntry(
          kCiYamlPath,
          kModifyMode,
          kModifyType,
          content: modifiedContent,
        ),
      ],
    );
    await gitHub.assignReviewer(slug, reviewer: prBuilder.pullRequestReviewer, pullRequestNumber: pullRequest.number);
  }

  /// Removes the `bringup: true` for the builder in the ci.yaml.
  String _deflakeBuilderInContent(String content, String? builder) {
    final List<String> lines = content.split('\n');
    final int builderLineNumber = lines.indexWhere((String line) => line.contains('name: $builder'));
    int nextLine = builderLineNumber + 1;
    while (nextLine < lines.length && !lines[nextLine].contains('name:')) {
      if (lines[nextLine].contains('$kCiYamlTargetIsFlakyKey:')) {
        lines.removeAt(nextLine);
        return lines.join('\n');
      }
      nextLine += 1;
    }
    throw 'Cannot find the flaky flag, is the test really marked flaky?';
  }
}

/// The info of the builder's name and if there is any existing issue opened
/// for the builder.
class _BuilderInfo {
  _BuilderInfo({this.name, this.existingIssue});
  final String? name;
  final Issue? existingIssue;
}
