spb/lou-ka Public
Lou·Ka — tous les logements à louer du Québec, un seul endroit.
HTML 99.7%
1// -----------------------------------------------------------------------------2// Lou-Ka — Agrégateur de logements à louer (province de Québec)3// Auteur : Simon-Pierre Boucher — contact@spboucher.ai4// pages/Sources.tsx : registre des gestionnaires immobiliers agrégés5// -----------------------------------------------------------------------------6import { useEffect, useState } from "react";7import { Source, fetchSources } from "../api";89export default function SourcesPage() {10 const [sources, setSources] = useState<Source[] | null>(null);11 const [error, setError] = useState<string | null>(null);1213 useEffect(() => {14 fetchSources()15 .then((r) => setSources(r.sources))16 .catch((e) => setError(String(e)));17 }, []);1819 return (20 <div className="container sources">21 <span className="kicker">Registre — gestionnaires immobiliers</span>22 <h1>Sources agrégées</h1>23 <p className="sub">24 Gestionnaires immobiliers de Québec, Lévis et du Grand Montréal recensés par Lou-Ka. Chaque source «25 active » est synchronisée périodiquement par un connecteur dédié; les autres sont en26 attente de connecteur.27 </p>2829 {error && <div className="notice">⚠️ {error}</div>}30 {!sources && !error && <div className="notice">Chargement…</div>}3132 {sources && (33 <div className="src-wrap">34 <table className="src-table">35 <thead>36 <tr>37 <th>Gestionnaire</th>38 <th>Secteurs</th>39 <th>Statut</th>40 <th style={{ textAlign: "right" }}>Annonces actives</th>41 <th>Dernière synchro</th>42 </tr>43 </thead>44 <tbody>45 {sources.map((s) => (46 <tr key={s.id}>47 <td>48 <a href={s.url} target="_blank" rel="noopener noreferrer">{s.name}</a>49 </td>50 <td style={{ color: "var(--ink-2)", maxWidth: 380 }}>{s.sectors}</td>51 <td>52 {s.connector ? (53 <span className="pill ok">connecté</span>54 ) : (55 <span className="pill todo">{s.status}</span>56 )}57 </td>58 <td style={{ textAlign: "right" }}>59 <span className="count-pill">{s.active_listings || "—"}</span>60 </td>61 <td style={{ color: "var(--ink-3)" }}>62 {s.last_sync63 ? new Date(s.last_sync * 1000).toLocaleString("fr-CA")64 : "—"}65 </td>66 </tr>67 ))}68 </tbody>69 </table>70 </div>71 )}72 </div>73 );74}75