# Copyright 2018 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.

import subprocess

# Full path of the CUPS configuration file
_CUPS_CONF_FILE = '/etc/cups/cupsd.conf'

class CommandFailedException(Exception):
    """
    An simple exception that is thrown when OS command fails.

    """
    pass

class Configurator():
    """
    An instance of this class is responsible for an initial configuration of
    the system. This is performed by the method configure(). To restore the
    system to the state before a configure() call, the method  restore() must
    be called.

    """

    def __init__(self):
        """
        Constructor.

        """
        self._cupsd_conf_loglevel_line_no = None
        self._cupsd_conf_loglevel_content = None


    def _run_as_root(self, argv):
        """
        Run given command as root.

        @param argv: an array of command-line parameters

        @returns standard output produced by the command

        @raises Exception if the command returns code different than 0

        """
        p1 = subprocess.Popen(["echo", "test0000"], stdout=subprocess.PIPE)
        p2 = subprocess.Popen(["sudo", "--stdin", "--prompt="] + argv,
                stdin=p1.stdout, stdout=subprocess.PIPE)
        p1.stdout.close()
        out,err = p2.communicate()
        if p2.returncode != 0:
            raise CommandFailedException("The command '%s' returns %d" %
                    (' '.join(argv),p2.returncode));
        return out


    def _set_cups_logging_level(self):
        """
        Modify the CUPS configuration file to set log level to 'debug'.

        @raises Exception in case of any errors

        """
        # parse content of the CUPS configuration file and find a number of
        # a line with 'LogLevel' option
        lines = self._run_as_root(["cat", _CUPS_CONF_FILE]).splitlines()

        for index, line in enumerate(lines):
            if line.startswith('LogLevel'):
                line_no = index
                break
        if line_no is None:
            raise Exception('Cannot find a line with LogLevel in cupsd.conf')
        # save the original line and replace it with 'LogLevel debug'
        self._cupsd_conf_loglevel_content = lines[line_no]
        self._cupsd_conf_loglevel_line_no = line_no + 1
        self._run_as_root(['sed', '-i', '%ds/.*/LogLevel debug/' % (line_no+1),
                _CUPS_CONF_FILE])
        # if CUPS is started, we have to stop
        try:
            self._run_as_root(['stop', 'cupsd'])
        except CommandFailedException:
            pass


    def _restore_cups_logging_level(self):
        """
        Restore content of the CUPS configuration file to this one before
        calling _set_cups_logging_level(). Do nothing if the method
        _set_cups_logging_level() was not called earlier.

        """
        if self._cupsd_conf_loglevel_content is None:
            return
        self._run_as_root(['sed', '-i', '%ds/.*/%s/' %
                (self._cupsd_conf_loglevel_line_no,
                self._cupsd_conf_loglevel_content), _CUPS_CONF_FILE])
        self._cupsd_conf_loglevel_content = None
        self._cupsd_conf_loglevel_line_no = None


    def _set_root_partition_as_read_write(self):
        """
        Remount the root partition in read-write mode.

        """
        self._run_as_root(['mount', '-o', 'rw,remount', '/'])


    def configure(self, set_cups_logging_level):
        """
        Apply the configuration required by the test.

        @param set_cups_logging_level: True or False; if True then
                the root partition is remounted in R/W mode and the CUPS
                configuration file is updated to set "LogLevel" to "debug".
        """
        # Update CUPS logging level
        if set_cups_logging_level:
            self._set_root_partition_as_read_write()
            self._set_cups_logging_level()


    def restore(self):
        """
        Restore the system state before configure(). It is safe to run
        this method, even if configure() failed or has not been called.

        """
        # Restore CUPS logging level
        if self._cupsd_conf_loglevel_content is not None:
            self._restore_cups_logging_level()
