Resto·Ka — tous les restaurants du Québec, menus complets et prix réels (famille ·Ka)
Python 69.3%
TypeScript 16.7%
CSS 7.9%
JavaScript 4.7%
HTML 1.4%
1# ==============================================================================2# Author: Simon-Pierre Boucher <contact@spboucher.ai>3# File: tests/test_sitefinder.py4# Desc: Connecteur site-finder (découverte des sites web via l'API Serper5# /maps) — croisement HORS LIGNE de fiches Google Maps réelles6# (payloads captés le 2026-08-23) : nom + distance GPS <= 400 m,7# ambigu = ignoré ; nettoyage/classification des URLs (utm_* retirés,8# réseaux sociaux et plateformes de livraison rejetés, réservation9# séparée).10# ==============================================================================11from restoka.connectors.sitefinder import (classify_website, clean_website,12 match_place, _dist_m)1314# Réponses RÉELLES de l'API Serper /maps (2026-08-23), abrégées aux champs lus.15_AMOS_PLACES = [16 {"title": "Pizzéria Amos Inc",17 "address": "341 6e Rue O, Amos, QC J9T 2V5, Canada",18 "latitude": 48.568842, "longitude": -78.1315157,19 "website": "http://pizzeriaamos.com/",20 "phoneNumber": "+1 819-732-4398", "cid": "9963617425105215735"},21 {"title": "Pizza Salvatoré", # à ~350 m : nom différent -> jamais croisé22 "address": "12 Rte 111 Ouest, Amos, Quebec J9T 2X6, Canada",23 "latitude": 48.5720841, "longitude": -78.1315975,24 "website": "https://salvatore.com/fr/restaurant/sal-amos"25 "?utm_id=92&utm_source=google&utm_medium=business-profile",26 "phoneNumber": "+1 819-834-5555", "cid": "15827771869290584642"},27 {"title": "Mia Pasta - Amos", # à ~1,4 km : hors rayon28 "address": "82 1re Avenue E, Amos, QC J9T 2E7, Canada",29 "latitude": 48.571788, "longitude": -78.11258169999999,30 "website": "https://commandeenligne.miapasta.com/commandeenligne/",31 "phoneNumber": "+1 819-727-2021", "cid": "18357615835954532349"},32]3334_TIMS_PLACES = [35 {"title": "Tim Hortons",36 "address": "208 Bd Saint-Raymond, Gatineau, QC J9A 3H6, Canada",37 "latitude": 45.4367899, "longitude": -75.76653309999999,38 "website": "https://locations.timhortons.ca/en/qc/gatineau/"39 "208-boul-st-raymond",40 "phoneNumber": "+1 819-778-6481", "cid": "5309096764678078556"},41 {"title": "Tim Hortons", # autre succursale à ~4 km : hors rayon42 "address": "200 Prom. du Portage, Gatineau, QC J8X 4B7, Canada",43 "latitude": 45.4267914, "longitude": -75.71292389999999,44 "website": "https://locations.timhortons.ca/en/qc/gatineau/"45 "200-promenade-du-portage",46 "phoneNumber": "+1 613-293-7168", "cid": "591025576747174253"},47]484950def _row(name, address, city, lat, lng):51 return {"name": name, "address": address, "city": city,52 "lat": lat, "lng": lng, "phone": ""}535455def test_match_typo_and_legal_suffix():56 # fiche OSM réelle « Pizzaria Amos » (coquille) vs « Pizzéria Amos Inc »57 row = _row("Pizzaria Amos", "341 6e Rue Ouest", "Amos",58 48.5689429, -78.1316743)59 hit = match_place(row, _AMOS_PLACES)60 assert hit is not None and hit["cid"] == "9963617425105215735"616263def test_match_chain_disambiguated_by_distance():64 # deux Tim Hortons à Gatineau : seul celui à <400 m est croisé65 row = _row("Tim Hortons", "208 Boulevard Saint-Raymond", "Gatineau",66 45.4367943, -75.7665445)67 hit = match_place(row, _TIMS_PLACES)68 assert hit is not None and hit["cid"] == "5309096764678078556"697071def test_no_match_far_or_different_name():72 # un resto au nom sans rapport, même s'il est proche, n'est pas croisé73 row = _row("Sushi Miko", "339 6e Rue Ouest", "Amos",74 48.5689429, -78.1316743)75 assert match_place(row, _AMOS_PLACES) is None767778def test_ambiguous_two_distinct_places():79 # deux fiches distinctes (cid) qui matchent toutes deux -> on s'abstient80 near = dict(_TIMS_PLACES[1], latitude=45.4368, longitude=-75.7666)81 row = _row("Tim Hortons", "208 Boulevard Saint-Raymond", "Gatineau",82 45.4367943, -75.7665445)83 assert match_place(row, [_TIMS_PLACES[0], near]) is None848586def test_dist_m_scale():87 assert _dist_m(45.5, -73.5, 45.5, -73.5) == 0.088 assert 340 < _dist_m(48.5689429, -78.1316743,89 48.5720841, -78.1315975) < 400909192def test_clean_website_strips_tracking():93 url = _AMOS_PLACES[1]["website"]94 assert clean_website(url) == "https://salvatore.com/fr/restaurant/sal-amos"95 assert clean_website("javascript:alert(1)") == ""96 assert clean_website("") == ""979899def test_classify_website():100 assert classify_website("http://pizzeriaamos.com/") == \101 ("site", "http://pizzeriaamos.com/")102 # une page Facebook n'est pas « le site du resto »103 kind, _ = classify_website("https://www.facebook.com/cafeologueduquartier/")104 assert kind == "rejected"105 # un lien de livraison contaminerait le pipeline dine-in de site-resto106 assert classify_website("https://www.ubereats.com/ca/store/x")[0] == "rejected"107 # plateforme de réservation -> details.reservation_url108 assert classify_website("https://www.opentable.ca/r/toque-montreal")[0] == \109 "reservation"110 # la plateforme de commande en ligne du resto lui-même reste un site valide111 assert classify_website(112 "https://commandeenligne.miapasta.com/commandeenligne/")[0] == "site"113