from parallels.core import get_logger
from parallels.plesk.source.web import messages
from parallels.plesk.source.web.config import ListFilesModeOption
from parallels.plesk.source.web.utils.list_files.filesystem_runner import ListFilesFilesystemRunner
from parallels.plesk.source.web.utils.list_files.web_rpc_agent import ListFilesWebRPCAgent
from parallels.plesk.source.web.utils.list_files.hybrid import ListFilesHybrid

logger = get_logger(__name__)


def create_list_files(source):
    """
    :type source: parallels.plesk.source.web.connections.WebSource
    :rtype: parallels.plesk.source.web.utils.list_files.base.ListFilesBase
    """
    config_option = source.config.list_files_mode

    logger.fdebug(messages.LIST_FILES_MODE, list_files_mode=config_option)

    if config_option == ListFilesModeOption.FILE_TRANSPORT:
        return ListFilesFilesystemRunner()
    elif config_option == ListFilesModeOption.WEB_RPC_AGENT:
        return ListFilesWebRPCAgent()
    elif config_option == ListFilesModeOption.HYBRID:
        return ListFilesHybrid()
    else:  # Auto mode
        if (
            # When "find" utility is available, we could get listing of the files by one
            # command call, without any web RPC agent calls, so it is preferred to use
            # it from performance point of view.
            # When "find" utility is not available, we fallback to "ls" for which we should perform
            # at least one call per directory, which causes slow listing performance.
            # So, it is better to use hybrid mode when "find" is not available.
            source.is_ssh_available() and
            source.get_ssh_runner().is_utility_find_available()
        ):
            return ListFilesFilesystemRunner()
        else:
            return ListFilesHybrid()
