# -*- coding: utf-8 -*-
# Copyright 2020 The Chromium OS Authors. All rights reserved.
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.

"""Utilities for setting up Portage objects for testing."""

from __future__ import print_function
from __future__ import division

import itertools
import os
import pathlib
from typing import Dict, Iterable, Tuple, Union

from chromite.lib import constants
from chromite.lib import cros_build_lib
from chromite.lib import osutils
from chromite.lib.parser import package_info

__all__ = ['Overlay', 'Package', 'Profile', 'Sysroot']

_EXCLUDED_OVERLAYS = ('chromiumos', 'portage-stable')


def _dict_to_conf(dictionary):
  """Helper to format a dictionary into a layout.conf file."""
  output = []
  for key in sorted(dictionary.keys()):
    output.append('%s = %s' % (key, dictionary[key]))

  output.append('\n')
  return '\n'.join(output)


def _dict_to_ebuild(dictionary):
  """Helper to format a dictionary into an ebuild file."""
  output = []
  for key in dictionary.keys():
    output.append(f'{key}="{dictionary[key]}"')

  output.append('\n')
  return '\n'.join(output)


class Overlay(object):
  """Portage overlay object, responsible for all writes to its directory."""

  HIERARCHY_NAMES = ('stable', 'project', 'chipset', 'baseboard', 'board',
                     'board-private')

  def __init__(self, root_path, name, masters=None):
    self.path = pathlib.Path(root_path)
    self.name = str(name)
    self.masters = tuple(masters) if masters else None
    self.packages = []
    self.profiles = dict()
    self.categories = set()

    self._write_layout_conf()

  def __contains__(self, item: Union[package_info.CPV,
                                     package_info.PackageInfo]):
    if not isinstance(item, (package_info.CPV, package_info.PackageInfo)):
      raise TypeError(f'Expected a CPV but received a {type(item)}')

    if isinstance(item, package_info.CPV):
      ebuild_path = (
          self.path / item.category / item.package / f'{item.pv}.ebuild')
    else:
      ebuild_path = self.path / item.relative_path

    return ebuild_path.is_file()

  def _write_layout_conf(self):
    """Write out the layout.conf as part of this Overlay's initialization."""
    layout_conf_path = self.path / 'metadata' / 'layout.conf'
    master_names = ' '.join(m.name for m in self.masters or [])
    conf = {
        'masters': 'portage-stable chromiumos eclass-overlay' + master_names,
        'profile-formats': 'portage-2 profile-default-eapi',
        'profile_eapi_when_unspecified': '5-progress',
        'repo-name': str(self.name),
        'thin-manifests': 'true',
        'use-manifests': 'strict',
    }

    osutils.WriteFile(layout_conf_path, _dict_to_conf(conf), makedirs=True)

  def add_package(self, pkg):
    """Add a package to this overlay.

    Adds the package to the Overlay object's internal storage and writes the
    package metadata to the Overlay's directory.
    """
    self.packages.append(pkg)
    self._write_ebuild(pkg)
    if pkg.category not in self.categories:
      self.categories.add(pkg.category)
      osutils.WriteFile(
          self.path / 'profiles' / 'categories',
          pkg.category + '\n',
          mode='a',
          makedirs=True)

  def _write_ebuild(self, pkg: 'Package'):
    """Write a Package object out to an ebuild file in this Overlay."""
    ebuild_path = self.path / pkg.category / pkg.package / (
        pkg.package + '-' + pkg.version + '.ebuild')

    # EAPI must be the first thing defined in a ebuild, so write this config
    # before anything else.
    base_conf = {
        'EAPI': pkg.eapi,
        'KEYWORDS': pkg.keywords,
        'SLOT': pkg.slot,
    }

    osutils.WriteFile(ebuild_path, _dict_to_ebuild(base_conf), makedirs=True)

    # Write additional miscellaneous variables declared in the Package object.
    for k, v in pkg.variables.items():
      osutils.WriteFile(ebuild_path, f'{k}="{v}"\n', mode='a')

    # Write an eclass inheritance line, if needed.
    if pkg.format_eclass_line():
      osutils.WriteFile(ebuild_path, pkg.format_eclass_line(), mode='a')

    extra_conf = {
        'DEPEND': pkg.depend,
        'RDEPEND': pkg.rdepend,
    }

    osutils.WriteFile(ebuild_path, _dict_to_ebuild(extra_conf), mode='a')

  def create_profile(self, path=None, profile_parents=None, make_defaults=None):
    """Create a profile in this overlay.

    Creates a profile with the given settings and writes the profile with those
    settings to the Overlay's directory.
    """
    path = pathlib.Path(path) if path else pathlib.Path('base')
    if path in self.profiles:
      raise KeyError('A profile with that path already exists!')

    prof = Profile(
        self, path, parents=profile_parents, make_defaults=make_defaults)

    self._write_profile(prof)
    self.profiles[path] = prof

    return prof

  def _write_profile(self, profile):
    """Write a Profile object out to this Overlay's directory."""
    osutils.WriteFile(
        self.path / 'profiles' / profile.path / 'make.defaults',
        _dict_to_ebuild(profile.make_defaults),
        makedirs=True)
    if profile.parents:
      formatted_parents = []
      for parent in profile.parents:
        formatted_parents.append(str(parent.overlay) + ':' + str(parent.path))
      osutils.WriteFile(self.path / 'profiles' / profile.path / 'parents',
                        '\n'.join(formatted_parents) + '\n')


class Sysroot(object):
  """Sysroot object representing a functional Portage directory for testing."""

  # These PORTDIR_OVERLAY entries are necessary for any Portage operations to
  # function as the chroot's profile is parsed first, even if that profile is
  # not used by the sysroot at all.
  # This tuple should effectively be:
  # /mnt/host/source/src/third_party/portage-stable
  # /mnt/host/source/src/third_party/chromiumos-overlay
  # /mnt/host/source/src/third_party/eclass-overlay
  _BOOTSTRAP_PORTDIR_OVERLAYS = (
      os.path.join(constants.CHROOT_SOURCE_ROOT,
                   constants.PORTAGE_STABLE_OVERLAY_DIR),
      os.path.join(constants.CHROOT_SOURCE_ROOT,
                   constants.CHROMIUMOS_OVERLAY_DIR),
      os.path.join(constants.CHROOT_SOURCE_ROOT, constants.ECLASS_OVERLAY_DIR),
  )

  def __init__(self, path, profile, overlays):
    self.path = path

    osutils.SafeMakedirs(path / 'etc' / 'portage' / 'profile')
    osutils.SafeMakedirs(path / 'etc' / 'portage' / 'hooks')

    osutils.SafeSymlink(profile.full_path,
                        path / 'etc' / 'portage' / 'make.profile')

    sysroot_conf = {
        'ACCEPT_KEYWORDS':
            'amd64',
        'ROOT':
            str(self.path),
        'SYSROOT':
            str(self.path),
        'ARCH':
            'amd64',
        'PORTAGE_CONFIGROOT':
            str(self.path),
        'PORTDIR':
            str(overlays[0].path),
        'PORTDIR_OVERLAY':
            '\n'.join(
                itertools.chain((str(o.path) for o in overlays),
                                Sysroot._BOOTSTRAP_PORTDIR_OVERLAYS)),
        'PORTAGE_BINHOST':
            '',
        'USE':
            '',
        'PKGDIR':
            str(self.path / 'packages'),
        'PORTAGE_TMPDIR':
            str(self.path / 'tmp'),
        'DISTDIR':
            str(self.path / 'var' / 'lib' / 'portage' / 'distfiles'),
    }

    osutils.WriteFile(self.path / 'etc' / 'portage' / 'make.conf',
                      _dict_to_ebuild(sysroot_conf))

    osutils.WriteFile(self.path / 'etc' / 'portage' / 'package.mask',
                      ''.join(f'*/*::{o}\n' for o in _EXCLUDED_OVERLAYS))

  @property
  def _env(self):
    """Return a dict of the environment variables for this sysroot."""
    return {
        'PORTAGE_CONFIGROOT': str(self.path),
        'ROOT': str(self.path),
        'SYSROOT': str(self.path),
        'BROOT': str(self.path),
    }

  def run(self, cmd, **kwargs):
    """Run a command against this sysroot.

    This method sets up the equivalent calling environment to the `emerge`
    wrappers we generate but targeted at this specific sysroot, which has
    an arbitrary path in the test environment. This means that Portage commands
    such as `equery list '*'` will correctly run against this sysroot.
    """
    extra_env = self._env
    extra_env.update(kwargs.pop('extra_env', {}))
    kwargs.setdefault('encoding', 'utf-8')

    return cros_build_lib.run(cmd, extra_env=extra_env, **kwargs)


class Profile(object):
  """Portage profile, lives in an overlay."""

  def __init__(self, overlay, path, parents=None, make_defaults=None):
    self.overlay = overlay.name
    self.path = path
    self.full_path = overlay.path / 'profiles' / path
    self.parents = tuple(parents) if parents else None
    self.make_defaults = make_defaults if make_defaults else {'USE': ''}


class Package(object):
  """Portage package, lives in an overlay."""

  inherit: Tuple[str]
  variables: Dict[str, str]

  def __init__(self,
               category,
               package,
               version='1',
               eapi='7',
               keywords='*',
               slot='0',
               depend='',
               rdepend='',
               inherit: Union[Iterable[str], str] = tuple(),
               **kwargs):
    self.category = category
    self.package = package
    self.version = version
    self.eapi = eapi
    self.keywords = keywords
    self.slot = slot
    self.depend = depend
    self.rdepend = rdepend
    self.inherit = (inherit,) if isinstance(inherit, str) else tuple(inherit)
    self.variables = kwargs

  @classmethod
  def from_cpv(cls, pkg_str: str):
    """Creates a Package from a CPV string."""
    cpv = package_info.parse(pkg_str)
    return cls(category=cpv.category, package=cpv.package, version=cpv.vr)

  @property
  def cpv(self) -> package_info.CPV:
    """Returns a CPV object constructed from this package's metadata.

    Deprecated, use package_info instead.
    """
    return package_info.SplitCPV(self.category + '/' + self.package + '-' +
                                 self.version)

  @property
  def package_info(self) -> package_info.PackageInfo:
    """Returns a PackageInfo object constructed from this package's metadata."""
    return package_info.parse(f'{self.category}/{self.package}-{self.version}')

  def format_eclass_line(self) -> str:
    """Returns a string containing this package's eclass inheritance line."""
    if self.inherit and isinstance(self.inherit, str):
      return f'inherit {self.inherit}\n'
    elif self.inherit:
      return f'inherit {" ".join(self.inherit)}\n'
    else:
      return ''
