#!/usr/bin/env python3
#
# Copyright 2013 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.
""" Generate a Fuchsia FAR Archive from an asset manifest.
"""

import argparse
import collections
import json
import os
import subprocess
import sys

from gather_flutter_runner_artifacts import CreateMetaPackage

# Generates the manifest and returns the file.
def GenerateManifest(package_dir):
  full_paths = []
  for root, dirs, files in os.walk(package_dir):
    for f in files:
      common_prefix = os.path.commonprefix([root, package_dir])
      rel_path = os.path.relpath(os.path.join(root, f), common_prefix)
      from_package = os.path.abspath(os.path.join(package_dir, rel_path))
      assert from_package, 'Failed to create from_package for %s' % os.path.join(root, f)
      full_paths.append('%s=%s' % (rel_path, from_package))

  parent_dir = os.path.abspath(os.path.join(package_dir, os.pardir))
  manifest_file_name = os.path.basename(package_dir) + '.manifest'
  manifest_path = os.path.join(parent_dir, manifest_file_name)
  with open(manifest_path, 'w') as f:
    for item in full_paths:
      f.write("%s\n" % item)
  return manifest_path


def CreateFarPackage(pm_bin, package_dir, signing_key, dst_dir, api_level):
  manifest_path = GenerateManifest(package_dir)

  pm_command_base = [
      pm_bin, '-m', manifest_path, '-k', signing_key, '-o', dst_dir, '--api-level', api_level
  ]

  # Build the package
  subprocess.check_output(pm_command_base + ['build'])

  # Archive the package
  subprocess.check_output(pm_command_base + ['archive'])

  return 0


def main():
  parser = argparse.ArgumentParser()

  parser.add_argument('--pm-bin', dest='pm_bin', action='store', required=True)
  parser.add_argument(
      '--package-dir', dest='package_dir', action='store', required=True)
  parser.add_argument(
      '--manifest-file', dest='manifest_file', action='store', required=False)
  parser.add_argument(
      '--manifest-json-file', dest='manifest_json_file', action='store', required=True)
  parser.add_argument(
      '--far-name', dest='far_name', action='store', required=False)
  parser.add_argument(
      '--api-level', dest='api_level', action='store', required=False)

  args = parser.parse_args()

  assert os.path.exists(args.pm_bin)
  assert os.path.exists(args.package_dir)
  pkg_dir = args.package_dir

  if not os.path.exists(os.path.join(pkg_dir, 'meta', 'package')):
    CreateMetaPackage(pkg_dir, args.far_name)

  output_dir = os.path.abspath(pkg_dir + '_out')
  if not os.path.exists(output_dir):
    os.makedirs(output_dir)

  manifest_file = None
  if args.manifest_file is not None:
    assert os.path.exists(args.manifest_file)
    manifest_file = args.manifest_file
  else:
    manifest_file = GenerateManifest(args.package_dir)

  pm_command_base = [
      args.pm_bin,
      '-o',
      output_dir,
      '-n',
      args.far_name,
      '-m',
      manifest_file,
  ]

  # Build and then archive the package
  # Use check_output so if anything goes wrong we get the output.
  try:

    build_command = ['build', '--output-package-manifest', args.manifest_json_file]

    if args.api_level is not None:
      build_command = ['--api-level', args.api_level] + build_command

    archive_command = ['archive', '--output='+ os.path.join(os.path.dirname(output_dir), args.far_name + "-0")]

    pm_commands = [
        build_command,
        archive_command
    ]

    for pm_command in pm_commands:
      subprocess.check_output(pm_command_base + pm_command)
  except subprocess.CalledProcessError as e:
    print('==================== Manifest contents =========================================')
    with open(manifest_file, 'r') as manifest:
      sys.stdout.write(manifest.read())
    print('==================== End manifest contents =====================================')
    meta_contents_path = os.path.join(output_dir, 'meta', 'contents')
    if os.path.exists(meta_contents_path):
      print('==================== meta/contents =============================================')
      with open(meta_contents_path, 'r') as meta_contents:
        sys.stdout.write(meta_contents.read())
      print('==================== End meta/contents =========================================')
    raise

  return 0


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