SPB Git forge

spb/fabri-ka

Public

Agrégateur de produits québécois — www.fabri-ka.com

217commits 1branches 0releases
66.1 MBsize
maindefault branch
4 h agolast push
Python 38.4% HTML 30.3% TypeScript 17.2% CSS 11% JavaScript 3.2%

[ka6] fix connecteur qublivre.ca: catalogue >25 000 produits — l'endpoint public Shopify /products.json renvoie HTTP 400 « Page * Limit exceeds the 25000 limit » à la page 101, et le connecteur propageait ce 400 comme une panne (3 syncs à 0, jamais un succès). Le site est de surcroît derrière un challenge Cloudflare (429 cf-mitigated même en direct), donc tout passe par l'escalade Scrapfly existante — c'est elle qui remontait le « scrapfly upstream 400 ». shopify.py: nouvelle _PageCapError levée sur HTTP 400 (curl direct, sans retry inutile) et sur « upstream 400 » Scrapfly (court-circuite les 3 retries), attrapée dans fetch(): fin de pagination propre si page>1 avec des produits déjà récoltés, re-levée sinon. Sync réel: 0→25 000 produits en 538 s (0 erreur, cap Shopify atteint proprement), 25 000/25 000 avec prix, 24 866 avec image, 1 fiche vérifiée contre la page live (N'écoute pas la nuit, 27,95 $).

Simon-Pierre Boucher committed 1 mo ago (Aug 23, 2026) parent 9c42c6f

1 changed file +16 −1

modified fabrika/connectors/shopify.py +16 −1
@@ -20,6 +20,12 @@ _MIN_INTERVAL = 0.7
20 20 _last_shopify_req = [0.0]
21 21
22 22
23 +class _PageCapError(RuntimeError):
24 + """HTTP 400 « Page * Limit exceeds the 25000 limit » : /products.json
25 + refuse toute page au-delà de 25 000 produits — fin de pagination, pas
26 + une panne (ex. qublivre.ca, >25 k livres)."""
27 +
28 +
23 29 class ShopifyConnector(BaseConnector):
24 30 platform = "shopify"
25 31
@@ -62,6 +68,8 @@ class ShopifyConnector(BaseConnector):
62 68 elif code == "429":
63 69 time.sleep(8 * (attempt + 1))
64 70 last_err = RuntimeError("429 Too Many Requests")
71 + elif code == "400":
72 + raise _PageCapError(f"HTTP 400 {url}")
65 73 else:
66 74 last_err = RuntimeError(f"HTTP {code or 'error'} {p.stderr[:120]}")
67 75 time.sleep(2)
@@ -84,6 +92,8 @@ class ShopifyConnector(BaseConnector):
84 92 try:
85 93 return scrapfly.scrapfly_json(url)
86 94 except Exception as exc:
95 + if "upstream 400" in str(exc):
96 + raise _PageCapError(str(exc)) from exc
87 97 last_err = exc
88 98 time.sleep(3 * (attempt + 1))
89 99 raise RuntimeError(f"{url}: scrapfly: {last_err}")
@@ -92,7 +102,12 @@ class ShopifyConnector(BaseConnector):
92 102 out: list[Product] = []
93 103 page = 1
94 104 while page <= self.max_pages:
95 − data = self._get_json(f"{self.base}/products.json?limit=250&page={page}")
105 + try:
106 + data = self._get_json(f"{self.base}/products.json?limit=250&page={page}")
107 + except _PageCapError:
108 + if page > 1 and out:
109 + break
110 + raise
96 111 items = data.get("products", [])
97 112 if not items:
98 113 break
99 114