# Copyright (c) 2014 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.

import argparse
import os
import sys
import shutil
import tempfile
import re
import json
import subprocess

import tracing_project

def _PopulatePackageJSON(staging_dir):
  package_path = os.path.join(staging_dir, 'tracing', 'package.json')
  with open(package_path, 'r') as f:
    package_text = f.read()
  package = json.loads(package_text)
  version = package['version']
  m = re.match(r'(\d+\.\d+)\.(\d+)', version)
  assert m
  minor_ver = int(m.group(2))
  new_version = m.group(1) + '.' + str(minor_ver + 1)

  package['version'] = new_version

  # Write inner package.json
  with open(package_path, 'w') as f:
    f.write(json.dumps(package))

  # Now twiddle with the package and write a slightly modified one
  # toplevel directory.
  toplevel_package_path = os.path.join(staging_dir, 'package.json')
  package['main'] = 'tracing/' + package['main']
  with open(toplevel_package_path, 'w') as f:
    f.write(json.dumps(package, indent=2))
    f.write('\n')


def _PopulateStagingDir(staging_dir):
  project = tracing_project.TracingProject()

  def CopyTree(part):
    src_dir = os.path.join(project.catapult_path, part)
    dst_dir = os.path.join(staging_dir, part)
    shutil.copytree(src_dir, dst_dir)

  for part in os.listdir(project.catapult_path):
    if part in ['tracing', 'catapult_build']:
      CopyTree(part)
  CopyTree(os.path.join('third_party', 'vinn'))

  _PopulatePackageJSON(staging_dir)
  shutil.copy(os.path.join(staging_dir, 'tracing', 'README.md'), staging_dir)


def _PublishToNPM(staging_dir):
  args = ['npm', 'publish']
  p = subprocess.Popen(args, cwd=staging_dir,
                       stdout=sys.stdout, stderr=sys.stderr)
  p.communicate()
  assert p.returncode == 0

def Main(args):
  parser = argparse.ArgumentParser(usage='%(prog)s --outdir=<directory>')
  parser.add_argument('--staging-dir', dest='staging_dir',
                      help='Where to place the data before upload')
  parser.add_argument('--dry-run', default=False, action='store_true',
                      help='Prepare the directory but dont publish it')
  args = parser.parse_args(args)

  if args.staging_dir == None:
    staging_dir = tempfile.mkdtemp()
    staging_dir_is_temporary = True
  else:
    staging_dir = args.staging_dir
    staging_dir_is_temporary = False
    if os.path.exists(os.path.join(staging_dir, 'package.json')):
      parser.error('%s has a package in it. Remove it first.')
      return 1

  try:
    _PopulateStagingDir(staging_dir)
    if args.dry_run:
      if staging_dir_is_temporary:
        print staging_dir
      return 1

    _PublishToNPM(staging_dir)

  finally:
    if staging_dir_is_temporary and not args.dry_run:
      shutil.rmtree(staging_dir)
