"""
Custom datasource malware detection
===================================

Only when option `--collector malware-detection` is specified, the insights
collection will collect data for malware-detection.  When it is specified,
only the Insights Spec
:py:attr:`insights.specs.default.DefaultSpecs.malware_detection` will be
collected. To collect other specs within the collection of malware-detection,
add them to the "persist" section in the "malware_detection_manifest"
pre-defined in the :py:mod:`insights.specs.datasources.manifests`
"""

import json
import logging

from insights.core.context import HostContext
from insights.core.exceptions import SkipComponent
from insights.core.plugins import datasource
from insights.core.spec_factory import DatasourceProvider
from insights.specs.datasources.malware_detection import MalwareDetectionClient


logger = logging.getLogger(__name__)


# timeout=0 disables the datasource timeout alarm,
# allowing malware-detection to run for as long as necessary
@datasource(HostContext, timeout=0)
def malware_detection(broker):
    """
    Custom datasource to collects content for malware scanner if a scanner is present on the system
    """
    try:
        # Only run malware-detection if it was passed as an option to insights-client
        insights_config = broker.get('client_config')
        if not (
            insights_config
            and hasattr(insights_config, 'app')
            and insights_config.app == 'malware-detection'
        ):
            raise SkipComponent(
                "Only run malware-detection app when specifically requested via --collector option"
            )

        # Manifest of malware-detection is wrapped in the 'insights_config'
        # and was set in the `insights.client.config.InsightsConfig._imply_options`
        mdc = MalwareDetectionClient(insights_config)
        scan_results = mdc.run()
        if scan_results:
            # cleaner is not required for this datasource
            return [
                DatasourceProvider(
                    content=scan_results[0], relative_path="malware-detection-results.json"
                ),
                DatasourceProvider(
                    content=json.dumps(scan_results[1]),
                    relative_path="malware-detection-results-raw.json",
                ),
            ]
        else:
            raise SkipComponent("No scan results were produced")
    except SkipComponent as msg:
        raise SkipComponent("Skipping malware-detection app: {0}".format(str(msg)))
    except Exception as err:
        from traceback import format_exc

        err_msg = "Unexpected exception in malware-detection app: {0}".format(str(err))
        logger.error(err_msg)
        logger.debug(format_exc())
        raise SkipComponent(err_msg)
