# Path: applitools/core/logger.py
# _DEFAULT_EYES_LOGGER_NAME = 'eyes'
# _DEFAULT_EYES_FORMATTER = logging.Formatter('%(asctime)s [%(levelname)s] %(name)s: %(message)s')
# _DEFAULT_LOGGER_LEVEL = int(os.environ.get('LOGGER_LEVEL', logging.INFO))
# _DEBUG_SCREENSHOT_PREFIX = os.environ.get('DEBUG_SCREENSHOT_PREFIX', 'screenshot_')
# _DEBUG_SCREENSHOT_PATH = os.environ.get('DEBUG_SCREENSHOT_PATH', '.')
# class _Logger(ABC):
# class StdoutLogger(_Logger):
# class FileLogger(_Logger):
# class NullLogger(_Logger):
#     def __init__(self, name=__name__, level=_DEFAULT_LOGGER_LEVEL, handler_factory=lambda: None,
#                  formatter=None):
#     def open(self):
#     def close(self):
#     def info(self, msg):
#     def debug(self, msg):
#     def __init__(self, name=_DEFAULT_EYES_LOGGER_NAME, level=_DEFAULT_LOGGER_LEVEL):
#     def __init__(self, filename="eyes.log", mode='a', encoding=None, delay=0,
#                  name=_DEFAULT_EYES_LOGGER_NAME, level=_DEFAULT_LOGGER_LEVEL):
#     def __init__(self, name=_DEFAULT_EYES_LOGGER_NAME, level=_DEFAULT_LOGGER_LEVEL):
# def set_logger(logger=None):
# def open_():
# def close():
# def info(msg):
# def debug(msg):
# def warning(msg):
# def deprecation(msg):
# def save_screenshot(image, suffix, region=None):
# 
# Path: applitools/utils/general_utils.py
# class _UtcTz(tzinfo):
#     _ZERO = timedelta(0)
# UTC = _UtcTz()
#     def utcoffset(self, dt):
#     def tzname(self, dt):
#     def dst(self, dt):
# def to_json(obj):
# def create_proxy_property(property_name, target_name, is_settable=False):
#     def _proxy_get(self):
#     def _proxy_set(self, val):
# def create_forwarded_method(from_,  # type: tp.Union[EyesWebDriver, EyesWebElement, _EyesSwitchTo]
#                             to,  # type: tp.Union[WebDriver, WebElement, SwitchTo]
#                             func_name,  # type: str
#                             ):
#     def forwarded_method(self_, *args, **kwargs):
# def create_proxy_interface(from_,  # type: tp.Union[EyesWebDriver, EyesWebElement, _EyesSwitchTo]
#                            to,  # type: tp.Union[WebDriver, WebElement, SwitchTo]
#                            ignore_list=None,  # type: tp.List[str]
#                            override_existing=False,  # type: bool
#                            ):
# def cached_property(f):
#     def get(self):
# def is_absolute_url(url):
# def is_url_with_scheme(url):
# def timeit(method):
#     def timed(*args, **kw):
# def retry(delays=(0, 1, 5),
#           exception=Exception,
#           report=lambda *args: None):
#     def wrapper(function):
#         def wrapped(*args, **kwargs):
# 
# Path: applitools/utils/compat.py
# PY3 = sys.version_info >= (3,)
#     ABC = abc.ABC
#     ABC = abc.ABCMeta(str("ABC"), (), {})
#     def gzip_compress(data, compresslevel=9):
# def iteritems(dct):


import json
import typing as tp
import multiprocessing as mp
import requests
import tinycss2
from collections import OrderedDict
from applitools.core import logger
from applitools.utils import general_utils
from applitools.utils.compat import urljoin
    from applitools.selenium.webdriver import EyesWebDriver
            return ''
        return requests.get(url, timeout=CSS_DOWNLOAD_TIMEOUT).text.strip()

    def iterate_css_sub_nodes(node, text=None):
        if text is None:
            text = node.text
            if node.text is None:
                text = get_css(node.url)

        for sub_node in _parse_and_serialize_css(node, text, minimize_css):
            if sub_node.url:
                text = get_css(sub_node.url)
                # yield from
                for res in iterate_css_sub_nodes(sub_node, text):
                    yield res
                continue
            yield sub_node.text

    return ''.join(iterate_css_sub_nodes(node))


def _parse_and_serialize_css(node, text, minimize=False):
    # type: (CssNode, tp.Text, bool) -> tp.Generator
    is_import_node = lambda n: n.type == 'at-rule' and n.lower_at_keyword == 'import'
    stylesheet = tinycss2.parse_stylesheet(text, skip_comments=True,
                                           skip_whitespace=True)
    for style_node in stylesheet:
        if is_import_node(style_node):
            for tag in style_node.prelude:
                if tag.type == 'url':

# Path: applitools/core/logger.py
# _DEFAULT_EYES_LOGGER_NAME = 'eyes'
# _DEFAULT_EYES_FORMATTER = logging.Formatter('%(asctime)s [%(levelname)s] %(name)s: %(message)s')
# _DEFAULT_LOGGER_LEVEL = int(os.environ.get('LOGGER_LEVEL', logging.INFO))
# _DEBUG_SCREENSHOT_PREFIX = os.environ.get('DEBUG_SCREENSHOT_PREFIX', 'screenshot_')
# _DEBUG_SCREENSHOT_PATH = os.environ.get('DEBUG_SCREENSHOT_PATH', '.')
# class _Logger(ABC):
# class StdoutLogger(_Logger):
# class FileLogger(_Logger):
# class NullLogger(_Logger):
#     def __init__(self, name=__name__, level=_DEFAULT_LOGGER_LEVEL, handler_factory=lambda: None,
#                  formatter=None):
#     def open(self):
#     def close(self):
#     def info(self, msg):
#     def debug(self, msg):
#     def __init__(self, name=_DEFAULT_EYES_LOGGER_NAME, level=_DEFAULT_LOGGER_LEVEL):
#     def __init__(self, filename="eyes.log", mode='a', encoding=None, delay=0,
#                  name=_DEFAULT_EYES_LOGGER_NAME, level=_DEFAULT_LOGGER_LEVEL):
#     def __init__(self, name=_DEFAULT_EYES_LOGGER_NAME, level=_DEFAULT_LOGGER_LEVEL):
# def set_logger(logger=None):
# def open_():
# def close():
# def info(msg):
# def debug(msg):
# def warning(msg):
# def deprecation(msg):
# def save_screenshot(image, suffix, region=None):
# 
# Path: applitools/utils/general_utils.py
# class _UtcTz(tzinfo):
#     _ZERO = timedelta(0)
# UTC = _UtcTz()
#     def utcoffset(self, dt):
#     def tzname(self, dt):
#     def dst(self, dt):
# def to_json(obj):
# def create_proxy_property(property_name, target_name, is_settable=False):
#     def _proxy_get(self):
#     def _proxy_set(self, val):
# def create_forwarded_method(from_,  # type: tp.Union[EyesWebDriver, EyesWebElement, _EyesSwitchTo]
#                             to,  # type: tp.Union[WebDriver, WebElement, SwitchTo]
#                             func_name,  # type: str
#                             ):
#     def forwarded_method(self_, *args, **kwargs):
# def create_proxy_interface(from_,  # type: tp.Union[EyesWebDriver, EyesWebElement, _EyesSwitchTo]
#                            to,  # type: tp.Union[WebDriver, WebElement, SwitchTo]
#                            ignore_list=None,  # type: tp.List[str]
#                            override_existing=False,  # type: bool
#                            ):
# def cached_property(f):
#     def get(self):
# def is_absolute_url(url):
# def is_url_with_scheme(url):
# def timeit(method):
#     def timed(*args, **kw):
# def retry(delays=(0, 1, 5),
#           exception=Exception,
#           report=lambda *args: None):
#     def wrapper(function):
#         def wrapped(*args, **kwargs):
# 
# Path: applitools/utils/compat.py
# PY3 = sys.version_info >= (3,)
#     ABC = abc.ABC
#     ABC = abc.ABCMeta(str("ABC"), (), {})
#     def gzip_compress(data, compresslevel=9):
# def iteritems(dct):


# Path: applitools/selenium/capture/dom_capture.py
import json
import typing as tp
import multiprocessing as mp
import requests
import tinycss2
from collections import OrderedDict
from applitools.core import logger
from applitools.utils import general_utils
from applitools.utils.compat import urljoin
    from applitools.selenium.webdriver import EyesWebDriver

            return ''
        return requests.get(url, timeout=CSS_DOWNLOAD_TIMEOUT).text.strip()

    def iterate_css_sub_nodes(node, text=None):
        if text is None:
            text = node.text
            if node.text is None:
                text = get_css(node.url)

        for sub_node in _parse_and_serialize_css(node, text, minimize_css):
            if sub_node.url:
                text = get_css(sub_node.url)
                # yield from
                for res in iterate_css_sub_nodes(sub_node, text):
                    yield res
                continue
            yield sub_node.text

    return ''.join(iterate_css_sub_nodes(node))


def _parse_and_serialize_css(node, text, minimize=False):
    # type: (CssNode, tp.Text, bool) -> tp.Generator
    is_import_node = lambda n: n.type == 'at-rule' and n.lower_at_keyword == 'import'
    stylesheet = tinycss2.parse_stylesheet(text, skip_comments=True,
                                           skip_whitespace=True)
    for style_node in stylesheet:
        if is_import_node(style_node):
            for tag in style_node.prelude:
                if tag.type == 'url':

                    logger.debug('The node has import')