.. versionadded:: 2017.7.0
    .. versionchanged:: 2018.3.0
        Renamed from ``docker.compare_container`` to
        ``docker.compare_containers`` (old function name remains as an alias)

    Compare two containers' Config and and HostConfig and return any
    differences between the two.

    first
        Name or ID of first container

    second
        Name or ID of second container

    ignore
        A comma-separated list (or Python list) of keys to ignore when
        comparing. This is useful when comparing two otherwise identical
        containers which have different hostnames.


    CLI Examples:

    .. code-block:: bash

        salt myminion docker.compare_containers foo bar
        salt myminion docker.compare_containers foo bar ignore=Hostname

def compare_containers(first, second, ignore=None):
    '''
    .. versionadded:: 2017.7.0
    .. versionchanged:: 2018.3.0
        Renamed from ``docker.compare_container`` to
        ``docker.compare_containers`` (old function name remains as an alias)

    Compare two containers' Config and and HostConfig and return any
    differences between the two.

    first
        Name or ID of first container

    second
        Name or ID of second container

    ignore
        A comma-separated list (or Python list) of keys to ignore when
        comparing. This is useful when comparing two otherwise identical
        containers which have different hostnames.


    CLI Examples:

    .. code-block:: bash

        salt myminion docker.compare_containers foo bar
        salt myminion docker.compare_containers foo bar ignore=Hostname
    '''
    ignore = __utils__['args.split_input'](ignore or [])
    result1 = inspect_container(first)
    result2 = inspect_container(second)
    ret = {}
    for conf_dict in ('Config', 'HostConfig'):
        for item in result1[conf_dict]:
            if item in ignore:
                continue
            val1 = result1[conf_dict][item]
            val2 = result2[conf_dict].get(item)
            if item in ('OomKillDisable',) or (val1 is None or val2 is None):
                if bool(val1) != bool(val2):
                    ret.setdefault(conf_dict, {})[item] = {
                        'old': val1, 'new': val2}
            elif item == 'Image':
                image1 = inspect_image(val1)['Id']
                image2 = inspect_image(val2)['Id']
                if image1 != image2:
                    ret.setdefault(conf_dict, {})[item] = {
                        'old': image1, 'new': image2}
            else:
                if item == 'Links':
                    val1 = sorted(_scrub_links(val1, first))
                    val2 = sorted(_scrub_links(val2, second))
                if item == 'Ulimits':
                    val1 = _ulimit_sort(val1)
                    val2 = _ulimit_sort(val2)
                if item == 'Env':
                    val1 = sorted(val1)
                    val2 = sorted(val2)
                if val1 != val2:
                    ret.setdefault(conf_dict, {})[item] = {
                        'old': val1, 'new': val2}
        # Check for optionally-present items that were in the second container
        # and not the first.
        for item in result2[conf_dict]:
            if item in ignore or item in ret.get(conf_dict, {}):
                # We're either ignoring this or we already processed this
                # when iterating through result1. Either way, skip it.
                continue
            val1 = result1[conf_dict].get(item)
            val2 = result2[conf_dict][item]
            if item in ('OomKillDisable',) or (val1 is None or val2 is None):
                if bool(val1) != bool(val2):
                    ret.setdefault(conf_dict, {})[item] = {
                        'old': val1, 'new': val2}
            elif item == 'Image':
                image1 = inspect_image(val1)['Id']
                image2 = inspect_image(val2)['Id']
                if image1 != image2:
                    ret.setdefault(conf_dict, {})[item] = {
                        'old': image1, 'new': image2}
            else:
                if item == 'Links':
                    val1 = sorted(_scrub_links(val1, first))
                    val2 = sorted(_scrub_links(val2, second))
                if item == 'Ulimits':
                    val1 = _ulimit_sort(val1)
                    val2 = _ulimit_sort(val2)
                if item == 'Env':
                    val1 = sorted(val1)
                    val2 = sorted(val2)
                if val1 != val2:
                    ret.setdefault(conf_dict, {})[item] = {
                        'old': val1, 'new': val2}
    return ret