Commit
[ka2] fix connecteur gestion_legrand: retry wp-json sur réponse non-JSON (escalade proxy) + timeout 45 s
modified
louka/connectors/gestion_legrand.py
+20 −1
@@ -11,7 +11,9 @@ | |||
| 11 | from __future__ import annotations | 11 | from __future__ import annotations |
| 12 | 12 | ||
| 13 | import re | 13 | import re |
| 14 | +import time | ||
| 14 | 15 | ||
| 16 | +import requests | ||
| 15 | from bs4 import BeautifulSoup | 17 | from bs4 import BeautifulSoup |
| 16 | 18 | ||
| 17 | from ..schema import Listing, normalize_unit_type, parse_price | 19 | from ..schema import Listing, normalize_unit_type, parse_price |
@@ -32,9 +34,26 @@ _SECTEUR_RE = re.compile(r"secteur\s+(?:[\w\s]{0,40}?de\s+)?" | |||
| 32 | class GestionLegrandConnector(BaseConnector): | 34 | class GestionLegrandConnector(BaseConnector): |
| 33 | source_id = "gestion_legrand" | 35 | source_id = "gestion_legrand" |
| 34 | request_delay = 0.6 | 36 | request_delay = 0.6 |
| 37 | + timeout = 45 # le site a des lenteurs sporadiques (read timeout à 30 s) | ||
| 38 | + | ||
| 39 | + def _api_posts(self) -> list: | ||
| 40 | + # Un timeout direct fait basculer l'escalade proxy, qui peut renvoyer | ||
| 41 | + # un 200 HTML non-JSON (JSONDecodeError du 2026-08-27) : on retente. | ||
| 42 | + last_exc: Exception | None = None | ||
| 43 | + for attempt in range(3): | ||
| 44 | + if attempt: | ||
| 45 | + time.sleep(5 * attempt) | ||
| 46 | + try: | ||
| 47 | + data = self.get(API_URL).json() | ||
| 48 | + except (ValueError, requests.RequestException) as exc: | ||
| 49 | + last_exc = exc | ||
| 50 | + continue | ||
| 51 | + if isinstance(data, list): | ||
| 52 | + return data | ||
| 53 | + raise RuntimeError(f"wp-json illisible après 3 tentatives ({last_exc})") | ||
| 35 | 54 | ||
| 36 | def fetch(self) -> list[Listing]: | 55 | def fetch(self) -> list[Listing]: |
| 37 | − posts = self.get(API_URL).json() | 56 | + posts = self._api_posts() |
| 38 | 57 | ||
| 39 | # vignettes : la grille Elementor de /a-louer/ (post-<id> -> data-src) | 58 | # vignettes : la grille Elementor de /a-louer/ (post-<id> -> data-src) |
| 40 | thumbs: dict[str, str] = {} | 59 | thumbs: dict[str, str] = {} |
| 41 | 60 | ||