# Path: flatisfy/tools.py
# LOGGER = logging.getLogger(__name__)
# NAVITIA_ENDPOINT = "https://api.navitia.io/v1/coverage/fr-idf/journeys"
#         MAPBOX_MODES = {
#             TimeToModes.WALK: "mapbox/walking",
#             TimeToModes.BIKE: "mapbox/cycling",
#             TimeToModes.CAR: "mapbox/driving",
#         }
# def next_weekday(d, weekday):
# def convert_arabic_to_roman(arabic):
# def convert_arabic_to_roman_in_text(text):
# def hash_dict(func):
#         def __hash__(self):
#     def wrapped(*args, **kwargs):
#     def default(self, o):  # pylint: disable=locally-disabled,E0202
# def pretty_json(data):
# def batch(iterable, size):
# def is_within_interval(value, min_value=None, max_value=None):
# def normalize_string(string, lowercase=True, convert_arabic_numerals=True):
# def uniqify(some_list):
# def distance(gps1, gps2):
# def sort_list_of_dicts_by(flats_list, key):
# def merge_dicts(*args):
# def get_travel_time_between(latlng_from, latlng_to, mode, config):
# def timeit(func):
#     def wrapped(*args, **kwargs):
#     class HDict(dict):
# class DateAwareJSONEncoder(json.JSONEncoder):
# 
# Path: flatisfy/filters/duplicates.py
# LOGGER = logging.getLogger(__name__)
# def homogeneize_phone_number(numbers):
# def get_or_compute_photo_hash(photo, photo_cache):
# def compare_photos(photo1, photo2, photo_cache, hash_threshold):
# def find_number_common_photos(flat1_photos, flat2_photos, photo_cache, hash_threshold):
# def detect(flats_list, key="id", merge=True, should_intersect=False):
# def get_duplicate_score(flat1, flat2, photo_cache, hash_threshold):
# def deep_detect(flats_list, config):
# 
# Path: flatisfy/filters/cache.py
# class ImageCache(MemoryCache):
#     """
#     A cache for images, stored in memory.
#     """
# 
#     @staticmethod
#     def compute_filename(url):
#         """
#         Compute filename (hash of the URL) for the cached image.
# 
#         :param url: The URL of the image.
#         :return: The filename, with its extension.
#         """
#         # Always store as JPEG
#         return "%s.jpg" % hashlib.sha1(url.encode("utf-8")).hexdigest()
# 
#     def on_miss(self, url):
#         """
#         Helper to actually retrieve photos if not already cached.
#         """
#         # If two many items in the cache, pop one
#         if len(self.map.keys()) > self.max_items:
#             self.map.popitem(last=False)
# 
#         if url.endswith(".svg"):
#             # Skip SVG photo which are unsupported and unlikely to be relevant
#             return None
# 
#         filepath = None
#         # Try to load from local folder
#         if self.storage_dir:
#             filepath = os.path.join(self.storage_dir, self.compute_filename(url))
#             if os.path.isfile(filepath):
#                 return PIL.Image.open(filepath)
#         # Otherwise, fetch it
#         try:
#             LOGGER.debug(f"Download photo from {url} to {filepath}")
#             req = requests.get(url)
#             req.raise_for_status()
#             image = PIL.Image.open(BytesIO(req.content))
#             if filepath:
#                 image.save(filepath, format=image.format)
#             return image
#         except (requests.HTTPError, IOError) as exc:
#             LOGGER.info(f"Download photo from {url} failed: {exc}")
#             return None
# 
#     def __init__(self, max_items=200, storage_dir=None):
#         """
#         :param max_items: Max number of items in the cache, to prevent Out Of
#             Memory errors.
#         :param storage_dir: Directory in which images should be stored.
#         """
#         self.max_items = max_items
#         self.storage_dir = storage_dir
#         if self.storage_dir and not os.path.isdir(self.storage_dir):
#             os.makedirs(self.storage_dir)
#         super(ImageCache, self).__init__()
# 
# Path: flatisfy/constants.py
# BACKENDS_BY_PRECEDENCE = [
#     "foncia",
#     "seloger",
#     "pap",
#     "leboncoin",
#     "explorimmo",
#     "logicimmo",
# ]


import copy
import json
import logging
import os
import random
import sys
import unittest
import tempfile
import PIL
import requests
import requests_mock
from io import BytesIO
from flatisfy import tools
from flatisfy.filters import duplicates
from flatisfy.filters.cache import ImageCache
from flatisfy.constants import BACKENDS_BY_PRECEDENCE
        """
        Compares two matching photos with one being cropped.
        """
        # Fixme: the image hash treshold should be 10 ideally
        self.assertTrue(
            duplicates.compare_photos(
                {"url": TESTS_DATA_DIR + "vertical.jpg"},
                {"url": TESTS_DATA_DIR + "vertical-cropped.jpg"},
                self.IMAGE_CACHE,
                20,
            )
        )

        # Fixme: the image hash treshold should be 10 ideally
        self.assertTrue(
            duplicates.compare_photos(
                {"url": TESTS_DATA_DIR + "13783671@explorimmo.jpg"},
                {"url": TESTS_DATA_DIR + "124910113@seloger.jpg"},
                self.IMAGE_CACHE,
                20,
            )
        )


class TestImageCache(unittest.TestCase):
    """
    Checks image cache is working as expected.
    """

    def __init__(self, *args, **kwargs):

# Path: flatisfy/tools.py
# LOGGER = logging.getLogger(__name__)
# NAVITIA_ENDPOINT = "https://api.navitia.io/v1/coverage/fr-idf/journeys"
#         MAPBOX_MODES = {
#             TimeToModes.WALK: "mapbox/walking",
#             TimeToModes.BIKE: "mapbox/cycling",
#             TimeToModes.CAR: "mapbox/driving",
#         }
# def next_weekday(d, weekday):
# def convert_arabic_to_roman(arabic):
# def convert_arabic_to_roman_in_text(text):
# def hash_dict(func):
#         def __hash__(self):
#     def wrapped(*args, **kwargs):
#     def default(self, o):  # pylint: disable=locally-disabled,E0202
# def pretty_json(data):
# def batch(iterable, size):
# def is_within_interval(value, min_value=None, max_value=None):
# def normalize_string(string, lowercase=True, convert_arabic_numerals=True):
# def uniqify(some_list):
# def distance(gps1, gps2):
# def sort_list_of_dicts_by(flats_list, key):
# def merge_dicts(*args):
# def get_travel_time_between(latlng_from, latlng_to, mode, config):
# def timeit(func):
#     def wrapped(*args, **kwargs):
#     class HDict(dict):
# class DateAwareJSONEncoder(json.JSONEncoder):
# 
# Path: flatisfy/filters/duplicates.py
# LOGGER = logging.getLogger(__name__)
# def homogeneize_phone_number(numbers):
# def get_or_compute_photo_hash(photo, photo_cache):
# def compare_photos(photo1, photo2, photo_cache, hash_threshold):
# def find_number_common_photos(flat1_photos, flat2_photos, photo_cache, hash_threshold):
# def detect(flats_list, key="id", merge=True, should_intersect=False):
# def get_duplicate_score(flat1, flat2, photo_cache, hash_threshold):
# def deep_detect(flats_list, config):
# 
# Path: flatisfy/filters/cache.py
# class ImageCache(MemoryCache):
#     """
#     A cache for images, stored in memory.
#     """
# 
#     @staticmethod
#     def compute_filename(url):
#         """
#         Compute filename (hash of the URL) for the cached image.
# 
#         :param url: The URL of the image.
#         :return: The filename, with its extension.
#         """
#         # Always store as JPEG
#         return "%s.jpg" % hashlib.sha1(url.encode("utf-8")).hexdigest()
# 
#     def on_miss(self, url):
#         """
#         Helper to actually retrieve photos if not already cached.
#         """
#         # If two many items in the cache, pop one
#         if len(self.map.keys()) > self.max_items:
#             self.map.popitem(last=False)
# 
#         if url.endswith(".svg"):
#             # Skip SVG photo which are unsupported and unlikely to be relevant
#             return None
# 
#         filepath = None
#         # Try to load from local folder
#         if self.storage_dir:
#             filepath = os.path.join(self.storage_dir, self.compute_filename(url))
#             if os.path.isfile(filepath):
#                 return PIL.Image.open(filepath)
#         # Otherwise, fetch it
#         try:
#             LOGGER.debug(f"Download photo from {url} to {filepath}")
#             req = requests.get(url)
#             req.raise_for_status()
#             image = PIL.Image.open(BytesIO(req.content))
#             if filepath:
#                 image.save(filepath, format=image.format)
#             return image
#         except (requests.HTTPError, IOError) as exc:
#             LOGGER.info(f"Download photo from {url} failed: {exc}")
#             return None
# 
#     def __init__(self, max_items=200, storage_dir=None):
#         """
#         :param max_items: Max number of items in the cache, to prevent Out Of
#             Memory errors.
#         :param storage_dir: Directory in which images should be stored.
#         """
#         self.max_items = max_items
#         self.storage_dir = storage_dir
#         if self.storage_dir and not os.path.isdir(self.storage_dir):
#             os.makedirs(self.storage_dir)
#         super(ImageCache, self).__init__()
# 
# Path: flatisfy/constants.py
# BACKENDS_BY_PRECEDENCE = [
#     "foncia",
#     "seloger",
#     "pap",
#     "leboncoin",
#     "explorimmo",
#     "logicimmo",
# ]


# Path: flatisfy/tests.py
import copy
import json
import logging
import os
import random
import sys
import unittest
import tempfile
import PIL
import requests
import requests_mock
from io import BytesIO
from flatisfy import tools
from flatisfy.filters import duplicates
from flatisfy.filters.cache import ImageCache
from flatisfy.constants import BACKENDS_BY_PRECEDENCE

        """
        Compares two matching photos with one being cropped.
        """
        # Fixme: the image hash treshold should be 10 ideally
        self.assertTrue(
            duplicates.compare_photos(
                {"url": TESTS_DATA_DIR + "vertical.jpg"},
                {"url": TESTS_DATA_DIR + "vertical-cropped.jpg"},
                self.IMAGE_CACHE,
                20,
            )
        )

        # Fixme: the image hash treshold should be 10 ideally
        self.assertTrue(
            duplicates.compare_photos(
                {"url": TESTS_DATA_DIR + "13783671@explorimmo.jpg"},
                {"url": TESTS_DATA_DIR + "124910113@seloger.jpg"},
                self.IMAGE_CACHE,
                20,
            )
        )


class TestImageCache(unittest.TestCase):
    """
    Checks image cache is working as expected.
    """

    def __init__(self, *args, **kwargs):

        self.IMAGE_CACHE = ImageCache(storage_dir=tempfile.mkdtemp(prefix="flatisfy-"))  # pylint: disable=invalid-name