# Copyright (c) 2017 The WebRTC project authors. All Rights Reserved.
#
# Use of this source code is governed by a BSD-style license
# that can be found in the LICENSE file in the root of the source
# tree. An additional intellectual property rights grant can be found
# in the file PATENTS.  All contributing project authors may
# be found in the AUTHORS file in the root of the source tree.
"""Class implementing a wrapper for APM simulators.
"""

import cProfile
import logging
import os
import subprocess

from . import data_access
from . import exceptions


class AudioProcWrapper(object):
    """Wrapper for APM simulators.
  """

    DEFAULT_APM_SIMULATOR_BIN_PATH = os.path.abspath(
        os.path.join(os.pardir, 'audioproc_f'))
    OUTPUT_FILENAME = 'output.wav'

    def __init__(self, simulator_bin_path):
        """Ctor.

    Args:
      simulator_bin_path: path to the APM simulator binary.
    """
        self._simulator_bin_path = simulator_bin_path
        self._config = None
        self._output_signal_filepath = None

        # Profiler instance to measure running time.
        self._profiler = cProfile.Profile()

    @property
    def output_filepath(self):
        return self._output_signal_filepath

    def Run(self,
            config_filepath,
            capture_input_filepath,
            output_path,
            render_input_filepath=None):
        """Runs APM simulator.

    Args:
      config_filepath: path to the configuration file specifying the arguments
                       for the APM simulator.
      capture_input_filepath: path to the capture audio track input file (aka
                              forward or near-end).
      output_path: path of the audio track output file.
      render_input_filepath: path to the render audio track input file (aka
                             reverse or far-end).
    """
        # Init.
        self._output_signal_filepath = os.path.join(output_path,
                                                    self.OUTPUT_FILENAME)
        profiling_stats_filepath = os.path.join(output_path, 'profiling.stats')

        # Skip if the output has already been generated.
        if os.path.exists(self._output_signal_filepath) and os.path.exists(
                profiling_stats_filepath):
            return

        # Load configuration.
        self._config = data_access.AudioProcConfigFile.Load(config_filepath)

        # Set remaining parameters.
        if not os.path.exists(capture_input_filepath):
            raise exceptions.FileNotFoundError(
                'cannot find capture input file')
        self._config['-i'] = capture_input_filepath
        self._config['-o'] = self._output_signal_filepath
        if render_input_filepath is not None:
            if not os.path.exists(render_input_filepath):
                raise exceptions.FileNotFoundError(
                    'cannot find render input file')
            self._config['-ri'] = render_input_filepath

        # Build arguments list.
        args = [self._simulator_bin_path]
        for param_name in self._config:
            args.append(param_name)
            if self._config[param_name] is not None:
                args.append(str(self._config[param_name]))
        logging.debug(' '.join(args))

        # Run.
        self._profiler.enable()
        subprocess.call(args)
        self._profiler.disable()

        # Save profiling stats.
        self._profiler.dump_stats(profiling_stats_filepath)
