#!/usr/bin/env python
# Copyright 2015 The Chromium Authors. All rights reserved.
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.

"""Toolbox to manage all the json files in this directory.

It can reformat them in their canonical format or ensures they are well
formatted.
"""

import argparse
import ast
import collections
import glob
import json
import os
import subprocess
import sys


THIS_DIR = os.path.dirname(os.path.abspath(__file__))
SRC_DIR = os.path.dirname(os.path.dirname(THIS_DIR))
BLINK_DIR = os.path.join(SRC_DIR, 'third_party', 'WebKit')
sys.path.insert(0, os.path.join(SRC_DIR, 'third_party', 'colorama', 'src'))

import colorama


SKIP = {
  # These are not 'builders'.
  'compile_targets', 'gtest_tests', 'filter_compile_builders',
  'non_filter_builders', 'non_filter_tests_builders',

  # These are not supported on Swarming yet.

  # Android Cloud is still experimental and involves spinning up an Android
  # instance on GCE.  Swarming doesn't work in that environment yet.
  'Android Cloud Tests',

  # Recipes don't promise execution on jelly bean.  This could work if the
  # OS dimensions go into the recipe, they're set in the json file, and
  # jelly bean devices are in the pool.  For now, just blacklist.
  'Jelly Bean Tester',
  'KitKat Tablet Tester',
  'Lollipop Consumer Tester',
  'Lollipop Low-end Tester',
  'Lollipop Phone Tester',
  'Lollipop Tablet Tester',
  'Marshmallow 64 bit Tester',
  'Marshmallow Tablet Tester',

  # Android bots need custom dimension_sets entries for swarming, and capacity
  # is not there yet -- so don't let manage.py add swarming automatically there.
  'Android User Builder Tests',
  'Android GN',
  'Android Tests',
  'Android Tests (dbg)',

  # http://crbug.com/441429
  'Linux Trusty (32)', 'Linux Trusty (dbg)(32)',

  # swarming may not work on Mac10.10 and 10.11, need to
  # re-investigate and confirm
  'WebKit Mac10.10',
  'WebKit Mac10.11',
  'WebKit Mac10.11 (dbg)',
  'WebKit Mac10.11 (retina)',
  'Chromium Mac10.10 Tests',
  'Chromium Mac10.11 Tests',
  'Mac GN',
  'Mac GN (dbg)',

  # The memory.fyi waterfall is in the process of being converted to recipes,
  # and swarming doesn't work yet.
  'Chromium Mac (valgrind)(1)',
  'Chromium Mac (valgrind)(2)',
  'Chromium OS (valgrind)(1)',
  'Chromium OS (valgrind)(2)',
  'Chromium OS (valgrind)(3)',
  'Chromium OS (valgrind)(4)',
  'Chromium OS (valgrind)(5)',
  'Chromium OS (valgrind)(6)',
  'Linux Tests (valgrind)(1)',
  'Linux Tests (valgrind)(2)',
  'Linux Tests (valgrind)(3)',
  'Linux Tests (valgrind)(4)',
  'Linux Tests (valgrind)(5)',
  'Windows Browser (DrMemory full) (1)',
  'Windows Browser (DrMemory full) (2)',
  'Windows Browser (DrMemory full) (3)',
  'Windows Browser (DrMemory full) (4)',
  'Windows Browser (DrMemory full) (5)',
  'Windows Browser (DrMemory full) (6)',
  'Windows Browser (DrMemory full) (7)',
  'Windows Browser (DrMemory full) (8)',
  'Windows Browser (DrMemory full) (9)',
  'Windows Browser (DrMemory full) (10)',
  'Windows Browser (DrMemory full) (11)',
  'Windows Browser (DrMemory full) (12)',
  'Windows Content Browser (DrMemory)',
  'Windows Content Browser (DrMemory full) (1)',
  'Windows Content Browser (DrMemory full) (2)',
  'Windows Content Browser (DrMemory full) (3)',
  'Windows Content Browser (DrMemory full) (4)',
  'Windows Content Browser (DrMemory full) (5)',
  'Windows Content Browser (DrMemory full) (6)',
  'Windows Unit (DrMemory full) (1)',
  'Windows Unit (DrMemory full) (2)',
  'Windows Unit (DrMemory full) (3)',
  'Windows Unit (DrMemory full) (4)',
  'Windows Unit (DrMemory full) (5)',
  'Windows Unit (DrMemory full) (6)',
  'Windows Unit (DrMemory full) (7)',
  'Windows Unit (DrMemory full) (8)',
  'Windows Unit (DrMemory full) (9)',
  'Windows Unit (DrMemory full) (10)',
  'Windows Unit (DrMemory full) (11)',
  'Windows Unit (DrMemory full) (12)',
  'Windows Unit (DrMemory x64)',
  'Windows Unit (DrMemory)',

  # This builder is fine, but win8_chromium_ng uses GN and this configuration,
  # which breaks everything.
  'Win8 Aura',

  # One off builders. Note that Swarming does support ARM.
  'Linux ARM Cross-Compile',
  'Site Isolation Android',
  'Site Isolation Linux',
  'Site Isolation Win',
}


SKIP_GN_ISOLATE_MAP_TARGETS = {
  # This target is magic and not present in gn_isolate_map.pyl.
  'all',

  # These targets are listed only in build-side recipes.
  'All_syzygy',
  'aura_builder',
  'blink_tests',
  'cast_shell',
  'cast_shell_apk',
  'chrome_official_builder_no_unittests',
  'chromium_builder_asan',
  'chromium_builder_dbg_drmemory_win',
  'chromium_builder_lkgr_drmemory_win',
  'chromium_builder_perf',
  'chromium_builder_tests',
  'chromium_swarm_tests',
  'chromiumos_preflight',
  'ios_chrome_unittests',
  'ios_net_unittests',
  'ios_web_inttests',
  'ios_web_unittests',
  'mini_installer',
  'next_version_mini_installer',

  # this is used at least on iOS
  'gn_all',
  'cronet_test',

  # These are listed in Builders that are skipped for other reasons.
  'chrome_junit_tests',
  'components_invalidation_impl_junit_tests',
  'components_policy_junit_tests',
  'components_web_restrictions_junit_tests',
  'content_junit_tests',
  'content_junit_tests',
  'junit_unit_tests',
  'net_junit_tests',
  'net_junit_tests',
  'ui_junit_tests',
  'webapk_client_junit_tests',
  'webapk_shell_apk_junit_tests',

  # These tests are only run on WebRTC CI.
  'AppRTCMobileTest',
  'android_junit_tests',
  'audio_decoder_unittests',
  'common_audio_unittests',
  'common_video_unittests',
  'frame_analyzer',
  'libjingle_peerconnection_android_unittest',
  'modules_tests',
  'modules_unittests',
  'peerconnection_unittests',
  'rtc_media_unittests',
  'rtc_pc_unittests',
  'rtc_stats_unittests',
  'rtc_unittests',
  'system_wrappers_unittests',
  'test_support_unittests',
  'tools_unittests',
  'video_engine_tests',
  'voice_engine_unittests',
  'webrtc_nonparallel_tests',
  'xmllite_xmpp_unittests',
}


class Error(Exception):
  """Processing error."""


def get_isolates():
  """Returns the list of all isolate files."""

  def git_ls_files(cwd):
    return subprocess.check_output(['git', 'ls-files'], cwd=cwd).splitlines()

  files = git_ls_files(SRC_DIR) + git_ls_files(BLINK_DIR)
  return [os.path.basename(f) for f in files if f.endswith('.isolate')]


def process_builder_convert(data, test_name):
  """Converts 'test_name' to run on Swarming in 'data'.

  Returns True if 'test_name' was found.
  """
  result = False
  for test in data['gtest_tests']:
    if test['test'] != test_name:
      continue
    test.setdefault('swarming', {})
    if not test['swarming'].get('can_use_on_swarming_builders'):
      test['swarming']['can_use_on_swarming_builders'] = True
    result = True
  return result


def process_builder_remaining(data, filename, builder, tests_location):
  """Calculates tests_location when mode is --remaining."""
  for test in data['gtest_tests']:
    name = test['test']
    if test.get('swarming', {}).get('can_use_on_swarming_builders'):
      tests_location[name]['count_run_on_swarming'] += 1
    else:
      tests_location[name]['count_run_local'] += 1
      tests_location[name]['local_configs'].setdefault(
          filename, []).append(builder)


def process_file(mode, test_name, tests_location, filepath, ninja_targets,
                 ninja_targets_seen):
  """Processes a json file describing what tests should be run for each recipe.

  The action depends on mode. Updates tests_location.

  Return False if the process exit code should be 1.
  """
  filename = os.path.basename(filepath)
  with open(filepath) as f:
    content = f.read()
  try:
    config = json.loads(content)
  except ValueError as e:
    raise Error('Exception raised while checking %s: %s' % (filepath, e))

  for builder, data in sorted(config.iteritems()):
    if builder in SKIP:
      # Oddities.
      continue
    if not isinstance(data, dict):
      raise Error('%s: %s is broken: %s' % (filename, builder, data))
    if ('gtest_tests' not in data and
        'isolated_scripts' not in data and
        'additional_compile_targets' not in data):
      continue

    for d in data.get('junit_tests', []):
      test = d['test']
      if (test not in ninja_targets and
          test not in SKIP_GN_ISOLATE_MAP_TARGETS):
        raise Error('%s: %s / %s is not listed in gn_isolate_map.pyl' %
                    (filename, builder, test))
      elif test in ninja_targets:
        ninja_targets_seen.add(test)

    for target in data.get('additional_compile_targets', []):
      if (target not in ninja_targets and
          target not in SKIP_GN_ISOLATE_MAP_TARGETS):
        raise Error('%s: %s / %s is not listed in gn_isolate_map.pyl' %
                    (filename, builder, target))
      elif target in ninja_targets:
        ninja_targets_seen.add(target)

    gtest_tests = data.get('gtest_tests', [])
    if not isinstance(gtest_tests, list):
      raise Error(
          '%s: %s is broken: %s' % (filename, builder, gtest_tests))
    if not all(isinstance(g, dict) for g in gtest_tests):
      raise Error(
          '%s: %s is broken: %s' % (filename, builder, gtest_tests))

    seen = set()
    for d in gtest_tests:
      test = d['test']
      if (test not in ninja_targets and
          test not in SKIP_GN_ISOLATE_MAP_TARGETS):
        raise Error('%s: %s / %s is not listed in gn_isolate_map.pyl.' %
                    (filename, builder, test))
      elif test in ninja_targets:
        ninja_targets_seen.add(test)

      name = d.get('name', d['test'])
      if name in seen:
        raise Error('%s: %s / %s is listed multiple times.' %
                    (filename, builder, name))
      seen.add(name)
      d.setdefault('swarming', {}).setdefault(
          'can_use_on_swarming_builders', False)

    if gtest_tests:
      config[builder]['gtest_tests'] = sorted(
          gtest_tests, key=lambda x: x['test'])

    for d in data.get('isolated_scripts', []):
      name = d['isolate_name']
      if (name not in ninja_targets and
          name not in SKIP_GN_ISOLATE_MAP_TARGETS):
        raise Error('%s: %s / %s is not listed in gn_isolate_map.pyl.' %
                    (filename, builder, name))
      elif name in ninja_targets:
        ninja_targets_seen.add(name)

    # The trick here is that process_builder_remaining() is called before
    # process_builder_convert() so tests_location can be used to know how many
    # tests were converted.
    if mode in ('convert', 'remaining'):
      process_builder_remaining(data, filename, builder, tests_location)
    if mode == 'convert':
      process_builder_convert(data, test_name)

  expected = json.dumps(
      config, sort_keys=True, indent=2, separators=(',', ': ')) + '\n'
  if content != expected:
    if mode in ('convert', 'write'):
      with open(filepath, 'wb') as f:
        f.write(expected)
      if mode == 'write':
        print('Updated %s' % filename)
    else:
      print('%s is not in canonical format' % filename)
      print('run `testing/buildbot/manage.py -w` to fix')
    return mode != 'check'
  return True


def print_convert(test_name, tests_location):
  """Prints statistics for a test being converted for use in a CL description.
  """
  data = tests_location[test_name]
  print('Convert %s to run exclusively on Swarming' % test_name)
  print('')
  print('%d configs already ran on Swarming' % data['count_run_on_swarming'])
  print('%d used to run locally and were converted:' % data['count_run_local'])
  for master, builders in sorted(data['local_configs'].iteritems()):
    for builder in builders:
      print('- %s: %s' % (master, builder))
  print('')
  print('Ran:')
  print('  ./manage.py --convert %s' % test_name)
  print('')
  print('R=')
  print('BUG=98637')


def print_remaining(test_name, tests_location):
  """Prints a visual summary of what tests are yet to be converted to run on
  Swarming.
  """
  if test_name:
    if test_name not in tests_location:
      raise Error('Unknown test %s' % test_name)
    for config, builders in sorted(
        tests_location[test_name]['local_configs'].iteritems()):
      print('%s:' % config)
      for builder in sorted(builders):
        print('  %s' % builder)
    return

  isolates = get_isolates()
  l = max(map(len, tests_location))
  print('%-*s%sLocal       %sSwarming  %sMissing isolate' %
      (l, 'Test', colorama.Fore.RED, colorama.Fore.GREEN,
        colorama.Fore.MAGENTA))
  total_local = 0
  total_swarming = 0
  for name, location in sorted(tests_location.iteritems()):
    if not location['count_run_on_swarming']:
      c = colorama.Fore.RED
    elif location['count_run_local']:
      c = colorama.Fore.YELLOW
    else:
      c = colorama.Fore.GREEN
    total_local += location['count_run_local']
    total_swarming += location['count_run_on_swarming']
    missing_isolate = ''
    if name + '.isolate' not in isolates:
      missing_isolate = colorama.Fore.MAGENTA + '*'
    print('%s%-*s %4d           %4d    %s' %
        (c, l, name, location['count_run_local'],
          location['count_run_on_swarming'], missing_isolate))

  total = total_local + total_swarming
  p_local = 100. * total_local / total
  p_swarming = 100. * total_swarming / total
  print('%s%-*s %4d (%4.1f%%)   %4d (%4.1f%%)' %
      (colorama.Fore.WHITE, l, 'Total:', total_local, p_local,
        total_swarming, p_swarming))
  print('%-*s                %4d' % (l, 'Total executions:', total))


def main():
  colorama.init()
  parser = argparse.ArgumentParser(description=sys.modules[__name__].__doc__)
  group = parser.add_mutually_exclusive_group(required=True)
  group.add_argument(
      '-c', '--check', dest='mode', action='store_const', const='check',
      default='check', help='Only check the files')
  group.add_argument(
      '--convert', dest='mode', action='store_const', const='convert',
      help='Convert a test to run on Swarming everywhere')
  group.add_argument(
      '--remaining', dest='mode', action='store_const', const='remaining',
      help='Count the number of tests not yet running on Swarming')
  group.add_argument(
      '-w', '--write', dest='mode', action='store_const', const='write',
      help='Rewrite the files')
  parser.add_argument(
      'test_name', nargs='?',
      help='The test name to print which configs to update; only to be used '
           'with --remaining')
  args = parser.parse_args()

  if args.mode == 'convert':
    if not args.test_name:
      parser.error('A test name is required with --convert')
    if args.test_name + '.isolate' not in get_isolates():
      parser.error('Create %s.isolate first' % args.test_name)

  # Stats when running in --remaining mode;
  tests_location = collections.defaultdict(
      lambda: {
        'count_run_local': 0, 'count_run_on_swarming': 0, 'local_configs': {}
      })

  with open(os.path.join(THIS_DIR, "gn_isolate_map.pyl")) as fp:
    gn_isolate_map = ast.literal_eval(fp.read())
    ninja_targets = {k: v['label'] for k, v in gn_isolate_map.items()}

  try:
    result = 0
    ninja_targets_seen = set()
    for filepath in glob.glob(os.path.join(THIS_DIR, '*.json')):
      if not process_file(args.mode, args.test_name, tests_location, filepath,
                          ninja_targets, ninja_targets_seen):
        result = 1

    extra_targets = (set(ninja_targets) - ninja_targets_seen -
                     SKIP_GN_ISOLATE_MAP_TARGETS)
    if extra_targets:
      if len(extra_targets) > 1:
        extra_targets_str = ', '.join(extra_targets) + ' are'
      else:
        extra_targets_str = list(extra_targets)[0] + ' is'
      raise Error('%s listed in gn_isolate_map.pyl but not in any .json '
                  'files' % extra_targets_str)

    if args.mode == 'convert':
      print_convert(args.test_name, tests_location)
    elif args.mode == 'remaining':
      print_remaining(args.test_name, tests_location)
    return result
  except Error as e:
    sys.stderr.write('%s\n' % e)
    return 1


if __name__ == "__main__":
  sys.exit(main())
