#!/usr/bin/env fuchsia-vendored-python
# Copyright 2021 The Fuchsia Authors. All rights reserved.
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.
"""Wraps a command so that its outputs are timestamp-fresh only if their contents change.

Every declared output is renamed with a temporary suffix in the command.
If the command succeeds, the temporary file is moved over the original declared
output if the output did not already exist or the contents are different.
This conditional move is done for every declared output that appears in the
arguments list.

This is intended to be used in build systems like Ninja that support `restat`:
treating unchanged outputs as up-to-date, which has the potential to prune
the action graph on-the-fly.

Assumptions:
  Output files can be whole shell tokens in the command's arguments.
    We also support filenames as lexical substrings in tokens like
    "--flag=out1,out2" or just "out1,out2".

  If x is a writeable path (output), then x.any_suffix is also writeable.

  If x is a writeable path (output), then dirname(x) is also writeable.

  Command being wrapped does not change behavior with the name of its output
  arguments.

If any of the above assumptions do not hold, then we recommend --disable
wrapping.
"""

import argparse
import filecmp
import os
import shutil
import subprocess
import sys
import time
from typing import Any, Callable, Dict, FrozenSet, Iterable, Sequence
import dataclasses

_SCRIPT_BASENAME = os.path.basename(__file__)


def files_match(file1: str, file2: str):
    """Compares two files, returns True if they both exist and match."""
    # filecmp.cmp does not invoke any subprocesses.
    return filecmp.cmp(file1, file2, shallow=False)


def ensure_file_exists(path):
    """Assert that a file exists, or wait for it to appear.

    It has been shown that some fault tolerance is needed
    regarding expecting files to be produced by a subprocess.

    Args:
      path: path to file that is expected to exist.

    Raises:
      FileNotFoundError if path does not exist, even after waiting.
    """
    for delay in (3, 6, 15):
        if os.path.exists(path):
            return

        # This branch should be highly unlikely, so it is allowed to be slow.
        # Either the original command failed to produce this file, or something
        # could be wrong with file system synchronization or delays.
        # Flush writes, sleep, try again.
        print(
            f"[{_SCRIPT_BASENAME}] Expected output file not found: {path} (Retrying after {delay}s ...)"
        )
        os.sync()
        time.sleep(delay)

    raise FileNotFoundError(
        f"[{_SCRIPT_BASENAME}] *** Expected output file not found: {path}")


def retry_file_op_once_with_delay(
        fileop: Callable[[], Any], failmsg: str, delay: int):
    """Insanity is doing the same thing and expecting a different result."""
    try:
        fileop()
    except FileNotFoundError:
        # one-time retry
        print(
            f'[{_SCRIPT_BASENAME}] {failmsg}  (Retrying once after {delay}s.)')
        time.sleep(delay)
        fileop()
        # If this fails again, exception will be raised.


# Define here for ease of mocking.
def remove(path):
    """Remove, be it file or dir or link."""
    if os.path.isfile(path) or os.path.islink(path):
        return os.remove(path)
    elif os.path.isdir(path):
        return shutil.rmtree(path)


def move_if_identical(src: str, dest: str, verbose: bool = False) -> bool:
    """Moves src -> dest if their contents are identical.

    Args:
      src: source path
      dest: destination path
      verbose: if True, print what happened.

    Returns:
      True if move occurred (the two files matched),
      False if the files did not match, and thus, the src was removed.
    """
    ensure_file_exists(src)  # this was our backup
    if not os.path.exists(dest) or files_match(dest, src):
        if verbose:
            print(f"  === Cached: {dest}")
        shutil.move(src, dest)
        return True
    else:
        if verbose:
            print(f"  === Updated: {dest}")
        remove(src)
        return False


@dataclasses.dataclass
class TempFileTransform(object):
    """Represents a file name transform.

     At least temp_dir or suffix or basename_prefix must be non-blank.

    temp_dir: Write temporary files in here.
      If blank (default), paths are relative to working directory.
      We recommend writing to the same location as the intended output
      so that moves (on the same device) are extremely fast.
    suffix: Add this suffix to temporary files, e.g. ".tmp".
    basename_prefix: Add this prefix to the basename of the path.
      This can be a good choice over suffix when the underlying tool behavior
      is sensitive to the output file extension.
      Example: "foo/bar.txt", with prefix="tmp-" -> foo/tmp-bar.txt
    """
    temp_dir: str = ""
    suffix: str = ""
    basename_prefix: str = ""

    @property
    def valid(self):
        return self.temp_dir or self.suffix or self.basename_prefix

    def transform(self, path: str) -> str:
        return os.path.join(
            self.temp_dir, os.path.dirname(path),
            self.basename_prefix + os.path.basename(path) + self.suffix)


def env_safe_command(command: Sequence[str]) -> Sequence[str]:
    """Automatically prefix a command with env if needed."""
    if command and '=' in command[0]:
        return ['/usr/bin/env'] + command
    return command


def record_existing_outputs(
        outputs: Iterable[str], transform: Callable[[str],
                                                    str]) -> Dict[str, str]:
    """Map output file paths to their backup locations, using a transform.

  Args:
    outputs: collection of output files to backup.
    transform: name transformation to backup file name.

  Returns:
    Dictionary of outputs that already existed, mapped to their backup paths.
  """
    return {
        f: transform(f)
        for f in outputs
        if os.path.exists(f)  # accepts files or directories
    }


def backup_outputs(
        outputs: FrozenSet[str],
        tempfile_transform: TempFileTransform) -> Dict[str, str]:
    """Move pre-existing output files to backup locations.

    This is move, not copy, so this should be paired with some
    sort of restore operation, like `restore_if_unchanged()`.

    Returns:
      Dictionary of outputs that already existed, mapped to their backup paths.
    """
    outputs_to_restore = record_existing_outputs(
        outputs, tempfile_transform.transform)

    # mkdir when needed.
    if tempfile_transform.temp_dir:
        for f in outputs_to_restore.values():
            os.makedirs(os.path.dirname(f), exist_ok=True)

    for output, backup in outputs_to_restore.items():
        retry_file_op_once_with_delay(
            lambda: shutil.move(output, backup),
            f'Failed to backup {output} -> {backup}.',
            5,
        )

    return outputs_to_restore


def restore_if_unchanged(
        files_to_restore: Dict[str, str], verbose: bool = False) -> bool:
    """If backup contents match the new output, restore the backup.

    Otherwise remove the backup.

    Returns:
      True if there were any unrecoverable move errors.
    """
    move_err = False
    # TODO(fangism): This loop could be parallelized.
    for orig, backup in files_to_restore.items():
        try:
            retry_file_op_once_with_delay(
                lambda: move_if_identical(
                    src=backup, dest=orig, verbose=verbose),
                f'Failed to restore {backup} -> {orig}.',
                5,
            )
        except FileNotFoundError as e:
            print(e)
            move_err = True
    return move_err


def restore_all(outputs_to_restore: Dict[str, str]) -> bool:
    """Restores backups to their original location.

    This operation preserves modification timestamps.

    Returns:
      True if there were any unrecoverable move errors.
    """
    move_err = False
    # TODO(fangism): This loop could be parallelized.
    for orig, backup in outputs_to_restore.items():
        try:
            retry_file_op_once_with_delay(
                lambda: shutil.move(backup, orig),
                f'Failed to restore {backup} -> {orig}.',
                5,
            )
        except FileNotFoundError as e:
            print(e)
            move_err = True
    return move_err


@dataclasses.dataclass
class Action(object):
    """Represents a set of parameters of a single build action."""
    command: Sequence[str] = dataclasses.field(default_factory=list)
    outputs: FrozenSet[str] = dataclasses.field(default_factory=set)
    label: str = ""

    def run_cached(
            self,
            tempfile_transform: TempFileTransform,
            verbose: bool = False) -> int:
        """Runs a modified command and conditionally moves outputs in-place.

        Args:
          tempfile_transform: describes transformation to temporary file name.
          verbose: If True, print substituted command before running it.
        """

        outputs_to_restore = backup_outputs(self.outputs, tempfile_transform)

        # Run the modified command.
        retval = subprocess.call(self.command)

        if retval != 0:
            # Old backups will appear stale after being restored.
            restore_all(outputs_to_restore)
            return retval

        # Otherwise command succeeded, so conditionally move outputs in-place.
        move_err = restore_if_unchanged(outputs_to_restore, verbose)
        if move_err:
            print("  *** Aborting due to previous error.")
            return 1

        return 0


def _main_arg_parser() -> argparse.ArgumentParser:
    """Construct the argument parser, called by main()."""
    parser = argparse.ArgumentParser(
        description="Wraps a GN action to preserve unchanged outputs",
        argument_default=[],
    )
    # label is only used for diagnostics
    parser.add_argument(
        "--label",
        type=str,
        default="",
        help="The wrapped target's label",
    )
    parser.add_argument(
        "--outputs",
        nargs="*",
        help="An action's declared outputs.  " +
        "The named output files will be backed-up before the command runs, " +
        "and compared against after the command finishes successfully.",
    )
    parser.add_argument(
        "--temp-suffix",
        type=str,
        default="",
        help="Suffix to use for temporary outputs",
    )
    parser.add_argument(
        "--temp-prefix",
        type=str,
        default="tmp-",
        help="Basename prefix to use for temporary outputs",
    )
    parser.add_argument(
        "--temp-dir",
        type=str,
        default="",
        help=
        "Temporary directory for writing, can be relative to working directory or absolute.",
    )
    parser.add_argument(
        "--verbose",
        action="store_true",
        default=False,
        help="Print information about which outputs were renamed/cached.",
    )
    parser.add_argument(
        "--dry-run",
        action="store_true",
        default=False,
        help="Show transformed command and exit.",
    )
    parser.add_argument(
        "--disable",
        action="store_false",
        dest="enable",
        default=True,
        help="If disabled, run the original command as-is.",
    )

    # Positional args are the command and arguments to run.
    parser.add_argument("command", nargs="*", help="The command to run")
    return parser


_MAIN_ARG_PARSER = _main_arg_parser()


def main(argv: Sequence[str]) -> int:
    args = _MAIN_ARG_PARSER.parse_args(argv)

    tempfile_transform = TempFileTransform(
        temp_dir=args.temp_dir,
        suffix=args.temp_suffix,
        basename_prefix=args.temp_prefix,
    )
    if not tempfile_transform.valid:
        raise ValueError(
            "Need either --temp-dir or --temp-suffix, but both are missing.")

    wrap = args.enable
    # Decided whether or not to wrap the action script.
    ignored_scripts = {
        # If the action is only copying or linking, don't bother wrapping.
        "ln",
        "cp",  # TODO: Could conditionally copy if different.
        "rsync",
    }
    script = args.command[0]
    if os.path.basename(script) in ignored_scripts:
        wrap = False

    command = env_safe_command(args.command)
    # If disabled, run the original command as-is.
    if not wrap:
        return subprocess.call(command)

    # Run a modified command that can leave unchanged outputs untouched.
    action = Action(
        command=command,
        outputs=set(args.outputs),
        label=args.label,
    )

    if args.dry_run:
        return 0

    return action.run_cached(
        tempfile_transform=tempfile_transform,
        verbose=args.verbose,
    )


if __name__ == "__main__":
    sys.exit(main(sys.argv[1:]))
