"""This module contains plugins regarding log information leaked by the node."""

from teatime import Context, Issue, NodeType, Severity
from teatime.plugins.base import IPFSRPCPlugin


class EnumerateLogs(IPFSRPCPlugin):
    """Attempt to list all logging subsystems.

    Severity: Low

    Endpoint: https://docs.ipfs.io/reference/http/api/#api-v0-log-ls

    It is possible to list the logging subsystems that the node
    is using. This may be used by an attacker to find non-standard
    customizations on the node, as well as fingerprint the node setup
    for identification.
    """

    INTRUSIVE = False

    def _check(self, context: Context):
        if context.node_type != NodeType.IPFS:
            return

        payload = self.get_rpc_json(target=context.target, route="/api/v0/log/ls")
        context.report.add_issue(
            Issue(
                title="Exposed Logging Subsystem Data",
                description=(
                    "It is possible to list the logging subsystems that the node "
                    "is using. This may be used by an attacker to find non-standard "
                    "customizations on the node, as well as fingerprint the node setup "
                    "for identification."
                ),
                severity=Severity.LOW,
                raw_data=payload,
            )
        )


class ReadLogs(IPFSRPCPlugin):
    """Gather a sample of log data from the node's subsystems.

    Severity: Medium

    Endpoint: https://docs.ipfs.io/reference/http/api/#api-v0-log-tail

    Anyone can list log messages generated by the node. Log messages,
    especially debug-level ones, can leak sensitive information about
    the node's setup and operations running on it.
    """

    INTRUSIVE = False

    def __init__(self, line_limit: int = 1):
        self.line_limit = line_limit

    def _check(self, context: Context):
        if context.node_type != NodeType.IPFS:
            return

        payload = self.get_rpc_json(
            target=context.target, route="/api/v0/log/tail", stream_limit=2, timeout=5
        )

        context.report.add_issue(
            Issue(
                title="Exposed System Log Data",
                description=(
                    "Anyone can list log messages generated by the node. Log messages, "
                    "especially debug-level ones, can leak sensitive information about "
                    "the node's setup and operations running on it."
                ),
                severity=Severity.MEDIUM,
                raw_data=payload,
            )
        )


class ChangeLogLevel(IPFSRPCPlugin):
    """Attempt to change the log level for the given subsystems.

    Severity: Medium

    Endpoint: https://docs.ipfs.io/reference/http/api/#api-v0-log-level

    Anyone can change the log level of messages generated by the node.
    Log messages, especially debug-level ones, can leak sensitive information
    about the node's setup and operations running on it. An attacker may unlock
    additional information by enabling debug logs. This could also results in
    degraded performance, espeically when logs are stored in local files, or
    in log aggregation systems unable to handle the load.
    """

    INTRUSIVE = True

    def __init__(self, subsystem: str = "all", level: str = "info"):
        self.subsystem = subsystem
        self.level = level

    def _check(self, context: Context):
        if context.node_type != NodeType.IPFS:
            return

        payload = self.get_rpc_json(
            target=context.target,
            route="/api/v0/log/level",
            params=[("arg", self.subsystem), ("arg", "level")],
        )

        context.report.add_issue(
            Issue(
                title="Exposed System Log Management",
                description=(
                    "Anyone can change the log level of messages generated by the node. "
                    "Log messages, especially debug-level ones, can leak sensitive information "
                    "about the node's setup and operations running on it. An attacker may unlock "
                    "additional information by enabling debug logs. This could also results in "
                    "degraded performance, espeically when logs are stored in local files, or "
                    "in log aggregation systems unable to handle the load."
                ),
                severity=Severity.MEDIUM,
                raw_data=payload,
            )
        )
