#!/usr/bin/env python
# Copyright 2019 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.

from __future__ import print_function

import argparse
import logging
import mimetypes
import os
import re
import subprocess
import sys
import tempfile

# Add third_party directory to the Python import path
sys.path.append(os.path.dirname(os.path.dirname(os.path.abspath(__file__))))
import jinja2

# Oldest version of this directory that works for serving. Used to limit git
# history searches.
FIRST_REVISION = '08a37e09f110ab9cb2af3180f054f26a2fd274d6'
TEST_SUBDIR = 'webxr-samples'
INDEX_TEMPLATE = 'bucket_index.html'
LATEST_TEMPLATE = 'bucket_latest.html'

# Google Cloud storage bucket destination.
BUCKET = 'gs://chromium-webxr-test'

# URL templates used for creating the index page.
LINK_OMAHAPROXY = ('https://storage.googleapis.com/'
                   'chromium-find-releases-static/index.html#%s')
LINK_CRREV = 'https://crrev.com/%s'
LINK_CHROMIUMDASH = 'https://chromiumdash.appspot.com/commit/%s'

CR_POSITION_RE = re.compile(r'^Cr-Commit-Position:.*\#(\d+)')
BUCKET_COPY_RE = re.compile(r'^r(\d+)')

WINDOWS_EXES = {
  'git': 'git.bat',
  'gsutil.py': 'gsutil.py.bat',
}

SUFFIX_TYPES = {
  'js': 'application/javascript',
  'css': 'text/css',
  'html': 'text/html',
}

g_flags = None

def binary_name(cmd):
  """Finds the platform-appropriate name for an executable command."""

  # On Windows, the "subprocess" execution requires a name with extension.
  # Since we just need a couple of commands, use a simple replacement that
  # work for Chromium build environments. This isn't a general solution.
  if sys.platform != 'win32':
    return cmd
  if cmd in WINDOWS_EXES:
    return WINDOWS_EXES[cmd]
  raise Exeption('No known Windows executable for command "%s"' % cmd)

def run_command(*args):
  """Runs a shell command and returns output."""
  platform_args = list(args)
  platform_args[0] = binary_name(platform_args[0])
  logging.debug('Executing: %s', platform_args)
  return subprocess.check_output(platform_args)

def run_readonly(*args):
  """Runs command expected to have no side effects, safe for dry runs."""
  return run_command(*args)

def run_modify(*args):
  """Runs command with side effects, skipped for dry runs."""
  if g_flags.dry_run:
    print('Dry-Run:', *args)
    return
  return run_command(*args)

def get_cr_positions():
  """Retrieves list of Cr-Commit-Position entries for local commits"""
  revs = run_readonly('git', 'log', '--format=%H', FIRST_REVISION+'^..', '--',
                      TEST_SUBDIR)
  cr_positions = []
  for rev in revs.splitlines():
    cr_position = None
    msg = run_readonly('git', 'show', '-s', '--format=%B', rev)
    for line in msg.splitlines():
      m = CR_POSITION_RE.match(line)
      if m:
        cr_position = m.group(1)
    cr_positions.append(cr_position)
  return cr_positions

def get_commit_from_cr_position(position):
  """Given the Cr-Commit-Position, returns a string with commit hash.

  The function works on a best-effort basis. If commit hash cannot be found,
  it will return an empty string.

  Args:
    position: String containing Cr-Commit-Position number."""
  try:
    git_hash = run_readonly('git', 'crrev-parse', position).strip()
    logging.debug('`git crrev-parse %s` returned hash %s', position, git_hash)
    return git_hash
  except subprocess.CalledProcessError:
    logging.debug('`git crrev-parse %s` returned an error', position)
    return ''

def get_bucket_copies():
  """Retrieves list of test subdirectories from Cloud Storage"""
  copies = []
  dirs = run_readonly('gsutil.py', 'ls', '-d', BUCKET)
  strip_len = len(BUCKET) + 1
  for rev in dirs.splitlines():
    pos = rev[strip_len:]
    m = BUCKET_COPY_RE.search(pos)
    if m:
      copies.append(m.group(1))
  return copies

def is_working_dir_clean():
  """Checks if the git working directory has unsaved changes"""
  status = run_readonly('git', 'status', '--porcelain', '--untracked-files=no')
  return status.strip() == ''

def write_to_bucket(cr_position):
  """Copies the test directory to Cloud Storage"""
  destination = BUCKET + '/r' + cr_position
  run_modify('gsutil.py', '-m', 'rsync', '-x', 'media', '-r', './' + TEST_SUBDIR,
          destination)

  # The copy used mime types based on system-local mappings which may be
  # misconfigured. Sanity check and fix if needed.
  check_and_fix_content_types(destination)

def direct_publish_samples(source, dest_subfolder):
  destination = 'gs://chromium-webxr-samples' + '/' + dest_subfolder
  run_modify('gsutil.py', '-m', 'rsync', '-x', 'media', '-r', './' + source,
          destination)

  # The copy used mime types based on system-local mappings which may be
  # misconfigured. Sanity check and fix if needed.
  check_and_fix_content_types(destination)

def check_and_fix_content_types(destination):
  mimetypes.init()
  for suffix, content_type in SUFFIX_TYPES.iteritems():
    configured_type = mimetypes.types_map.get('.' + suffix)
    if configured_type != content_type:
      logging.info('Fixing content type mismatch for .%s: found %s, '
                   'expected %s.' % (suffix, configured_type, content_type))
      run_modify('gsutil.py', '-m', 'setmeta', '-h',
                 'Content-type:' + content_type,
                 destination + '/**.' + suffix)

def write_index():
  """Updates Cloud Storage index.html based on available test copies"""
  cr_positions = get_bucket_copies()
  cr_positions.sort(key=int, reverse=True)
  logging.debug('Index: %s', cr_positions)

  items = []

  for pos in cr_positions:
    rev = 'r' + pos
    links = []
    links.append({'href': '%s/index.html' % rev,
                  'anchor': 'index.html'})
    links.append({'href': LINK_CRREV % pos,
                  'anchor': '[crrev]'})
    links.append({'href': LINK_OMAHAPROXY % rev,
                  'anchor': '[find in releases]'})
    commit_hash = get_commit_from_cr_position(pos)
    if commit_hash:
      links.append({'href': LINK_CHROMIUMDASH % commit_hash,
                    'anchor' : '[chromium dash]'})
    items.append({'text': rev, 'links': links})

  template = jinja2.Template(open(INDEX_TEMPLATE).read())
  content = template.render({'items': items})
  logging.debug('index.html content:\n%s', content)

  with tempfile.NamedTemporaryFile(suffix='.html', delete=False) as temp:
    try:
      temp.write(content)
      temp.seek(0)
      temp.close()
      run_modify('gsutil.py', 'cp', temp.name, BUCKET + '/index.html')
    finally:
      os.unlink(temp.name)

def write_latest():
  """Updates Cloud Storage latest.html based on available test copies, pointing
  to the latest copy."""
  cr_positions = get_bucket_copies()
  cr_positions.sort(key=int, reverse=True)
  logging.debug('Index: %s', cr_positions)

  if not cr_positions:
    logging.debug('No cr_positions found, skipping generation of latest.html')
    return

  logging.debug('Latest cr position: %s', cr_positions[0])

  template = jinja2.Template(open(LATEST_TEMPLATE).read())
  content = template.render({'revisionString' : cr_positions[0]})
  logging.debug('latest.html content:\n%s', content)

  with tempfile.NamedTemporaryFile(suffix='.html', delete=False) as temp:
    try:
      temp.write(content)
      temp.seek(0)
      temp.close()
      run_modify('gsutil.py', 'cp', temp.name, BUCKET + '/latest.html')
    finally:
      os.unlink(temp.name)

def update_test_copies():
  """Uploads a new test copy if available"""

  if not is_working_dir_clean() and not g_flags.ignore_unclean_status:
    raise Exception('Working directory is not clean, check "git status"')

  cr_positions = get_cr_positions()
  logging.debug('Found git commit positions: %s', cr_positions)
  if not cr_positions:
    raise Exception('No commit positions found')

  latest_cr_position = cr_positions[0]
  if latest_cr_position is None and not g_flags.force_destination_cr_position:
    raise Exception('Top commit has no Cr-Commit-Position. Sync to master?')

  existing_copies = get_bucket_copies()
  logging.debug('Found bucket copies: %s', existing_copies)

  out_cr_position = g_flags.force_destination_cr_position or latest_cr_position

  need_index_update = False
  if out_cr_position in existing_copies:
    logging.info('Destination "r%s" already exists, skipping write',
                 out_cr_position)
  else:
    write_to_bucket(out_cr_position)
    need_index_update = True

  return need_index_update

def numeric_string(value):
  """Ensure value is a string containing an integer."""
  # This is used for validating flag values - the usual idiom would be to use
  # "type=int", but that would convert the value to an integer, and it's more
  # convenient to keep it string-valued for use in concatenation elsewhere.
  # Throws an exception if the integer conversion fails.
  return str(int(value))

def main():
  parser = argparse.ArgumentParser(
      description="""
Copies the current '%s' content to a Google Cloud Storage bucket
subdirectory named after the Cr-Commit-Position, and writes an index.html file
linking to the known test directories, newest first.

The intended workflow is as follows:

- Create a CL that modifies the webxr_test_pages content. Ideally, if this
  reflects an incompatible WebXR API change, the code change and test change
  should be combined in the same CL.

- After review, submit the CL as usual.

- Rebase, or check out a fresh branch that includes the merged CL. The
  "git log" history of the webxr_test_pages should contain the merged CL and
  its Cr-Commit-Position, and there should be no local commits in the history.

- Run this script to upload the new test snapshot and update the index.html
  file to include it.

The script has sanity checks to confirm that the state is as expected. It will
not overwrite existing data, you need to manually remove bad or incomplete
content from failed uploads using the cloud console before retrying.
""" % TEST_SUBDIR,
      formatter_class=argparse.RawDescriptionHelpFormatter)

  parser.add_argument('-v', '--verbose', action="store_true",
                      help="Print debugging info")
  parser.add_argument('-n', '--dry-run', action="store_true",
                      help="Don't run state-changing commands")
  parser.add_argument('--update-index-only', action="store_true",
                      help=("Generate a new index.html file based on already "
                            "existing directories, ignoring local changes"))
  parser.add_argument('--ignore-unclean-status', action="store_true",
                      help=("Proceed with copy even if there are uncommitted "
                            "local changes in the git working directory"))
  parser.add_argument('--force-destination-cr-position', metavar='NUMBER',
                      type=numeric_string,
                      help=("Force writing current content to the specified "
                            "destination CR position instead of determining "
                            "the name based on local git history, bypassing "
                            "history sanity checks"))
  parser.add_argument('--bucket', default=BUCKET,
                      help=("Destination Cloud Storage location, including "
                            "'gs://' prefix"))
  parser.add_argument('--direct-publish-samples-source', default=None,
                      help=("Publish samples from this folder directly to a "
                            "bucket."))
  parser.add_argument('--direct-publish-samples-dest', default=None,
                      help=("Publish samples directly to this subfolder in the "
                            "chromium-webxr-samples bucket."))

  global g_flags
  g_flags = parser.parse_args()

  if g_flags.verbose:
    logging.basicConfig(level=logging.DEBUG)

  if not os.path.isdir(TEST_SUBDIR):
    raise Exception('Must be run from webxr_test_pages directory')

  node_modules = os.path.join(TEST_SUBDIR, 'js', 'cottontail', 'node_modules')
  if os.path.isdir(node_modules):
    raise Exception('Please delete the obsolete directory "%s"' % node_modules)

  if g_flags.direct_publish_samples_source and g_flags.direct_publish_samples_dest:
    direct_publish_samples(
      g_flags.direct_publish_samples_source,
      g_flags.direct_publish_samples_dest)
    return

  need_index_update = False
  if g_flags.update_index_only:
    need_index_update = True
  else:
    need_index_update = update_test_copies()

  # Create an index.html file covering all found test copies.
  if need_index_update:
    write_index()
    write_latest()
  else:
    logging.info('No changes, skipping index.html and latest.html update.')


if __name__ == '__main__':
  main()
