SPB Git forge

spb/job-ka

Public
227commits 1branches 0releases
37.7 MBsize
maindefault branch
1 h agolast push
HTML 82.1% Python 14.6% TypeScript 1.9% CSS 1% JavaScript 0.5%

docs: README v3 — chiffres live vérifiés, pastilles dynamiques, sections complètes

Simon-Pierre Boucher committed 1 mo ago (Aug 24, 2026) parent 71c7648

1 changed file +109 −44

modified README.md +109 −44
@@ -25,17 +25,46 @@ Créé : 2026-08-17 Modifié : 2026-08-24
25 25 ![Nœud](https://img.shields.io/badge/n%C5%93ud-M3U96a-1f6feb?style=flat-square)
26 26 ![Port](https://img.shields.io/badge/port-8096-0c8599?style=flat-square)
27 27 ![PM2](https://img.shields.io/badge/process-PM2-2b037a?style=flat-square)
28 +
29 +[![Offres actives](https://img.shields.io/badge/dynamic/json?url=https%3A%2F%2Fwww.job-ka.com%2Fapi%2Fstats&query=%24.total&label=offres%20actives&color=0c8599&style=flat-square)](https://www.job-ka.com/api/stats)
30 +[![Offres directes](https://img.shields.io/badge/dynamic/json?url=https%3A%2F%2Fwww.job-ka.com%2Fapi%2Fstats&query=%24.direct_jobs&label=offres%20directes&color=0c8599&style=flat-square)](https://www.job-ka.com/api/stats)
31 +[![Employeurs](https://img.shields.io/badge/dynamic/json?url=https%3A%2F%2Fwww.job-ka.com%2Fapi%2Fstats&query=%24.employers&label=employeurs&color=0c8599&style=flat-square)](https://www.job-ka.com/api/stats)
32 +[![Sources](https://img.shields.io/badge/dynamic/json?url=https%3A%2F%2Fwww.job-ka.com%2Fapi%2Fstats&query=%24.sources&label=sources&color=0c8599&style=flat-square)](https://www.job-ka.com/api/stats)
33 +[![Avec salaire](https://img.shields.io/badge/dynamic/json?url=https%3A%2F%2Fwww.job-ka.com%2Fapi%2Fstats&query=%24.with_salary&label=avec%20salaire%20affich%C3%A9&color=0c8599&style=flat-square)](https://www.job-ka.com/api/stats)
34 +[![Télétravail](https://img.shields.io/badge/dynamic/json?url=https%3A%2F%2Fwww.job-ka.com%2Fapi%2Fstats&query=%24.remote&label=t%C3%A9l%C3%A9travail&color=0c8599&style=flat-square)](https://www.job-ka.com/api/stats)
35 +[![Géocodées](https://img.shields.io/badge/dynamic/json?url=https%3A%2F%2Fwww.job-ka.com%2Fapi%2Fstats&query=%24.geocoded&label=g%C3%A9ocod%C3%A9es&color=0c8599&style=flat-square)](https://www.job-ka.com/api/stats)
36 +
28 37 ![Python](https://img.shields.io/badge/Python-FastAPI-3776ab?style=flat-square&logo=python&logoColor=white)
38 +![FastAPI](https://img.shields.io/badge/FastAPI-API%20%2B%20SSR-009688?style=flat-square&logo=fastapi&logoColor=white)
29 39 ![React](https://img.shields.io/badge/React-18%20%2B%20Vite-61dafb?style=flat-square&logo=react&logoColor=black)
40 +![TypeScript](https://img.shields.io/badge/TypeScript-frontend-141814?style=flat-square&logo=typescript)
30 41 ![SQLite](https://img.shields.io/badge/SQLite-diff%20engine-141814?style=flat-square&logo=sqlite)
31 42 ![MapLibre](https://img.shields.io/badge/carte-MapLibre-396cb2?style=flat-square)
43 +![pytest](https://img.shields.io/badge/pytest-74%20tests%20hors%20ligne-141814?style=flat-square&logo=pytest)
44 +![ngrok](https://img.shields.io/badge/tunnel-ngrok-140a3c?style=flat-square&logo=ngrok)
32 45 ![Groupe KA](https://img.shields.io/badge/Groupe-KA-b7f000?style=flat-square)
46 +![remote-first](https://img.shields.io/badge/remote--first-spbgit-24292f?style=flat-square&logo=git&logoColor=white)
33 47
34 48 </div>
35 49
36 −Les grands sites d'emploi mélangent annonces payantes, doublons repostés et offres mortes. L'offre originale — celle de la page carrière de l'employeur — est la seule source fiable. **Job·Ka** se branche **directement sur les systèmes de recrutement (ATS)** des employeurs québécois : **968 connecteurs employeurs directs** sur **17 plateformes ATS** (Workday, Lever, Greenhouse, SmartRecruiters, BambooHR, Breezy, Recruitee, Ashby, Workable, Taleo, Njoyn, UltiPro, iCIMS, SuccessFactors, ADP WFN, Digital Recruiters, Workland), complétés par **3 portails publics** (Guichet-Emplois, Jobillico, Espresso-Jobs) — l'offre directe gagne toujours.
50 +Les grands sites d'emploi mélangent annonces payantes, doublons repostés et offres mortes. L'offre originale — celle de la page carrière de l'employeur — est la seule source fiable. **Job·Ka** se branche **directement sur les systèmes de recrutement (ATS)** des employeurs québécois : **969 connecteurs employeurs directs** sur **21 plateformes ATS** (Workday, SmartRecruiters, Dayforce, Workable, Workland/réseau Atlas, SuccessFactors, Njoyn, Greenhouse, WP Job Manager, Lever, Breezy, Ashby, Recruitee, BambooHR, Taleo Business Edition, Taleo, Digital Recruiters, iCIMS, UltiPro/UKG, ADP WFN + sites carrières maison), complétés par **3 portails publics** (Guichet-Emplois, Jobillico, Espresso-Jobs) — l'offre directe gagne toujours.
51 +
52 +Résultat en base (au 2026-08-24) : **21 492 offres actives** de **1 653 employeurs** (963 sources), dont **19 856 offres directes** et **6 856 avec salaire affiché** (moyenne 62 283 $/an) — salaires **normalisés en $/h et $/an**, jamais inventés. Chaque offre est traçable à sa source et la candidature se fait chez l'employeur. Pour qui ? Les chercheurs d'emploi québécois qui veulent l'inventaire réel, à jour et transparent, des postes affichés dans la province — resynchronisé jour et nuit.
37 53
38 −Résultat en base : plus de **21 000 offres actives** de plus de **1 600 employeurs** (≈960 sources), dont ~**19 800 offres directes** et près de **6 900 avec salaire affiché** — salaires **normalisés en $/h et $/an**, jamais inventés. Chaque offre est traçable à sa source et la candidature se fait chez l'employeur. Pour qui ? Les chercheurs d'emploi québécois qui veulent l'inventaire réel, à jour et transparent, des postes affichés dans la province — resynchronisé jour et nuit.
54 +## Chiffres clés (live sur [/api/stats](https://www.job-ka.com/api/stats), vérifiés au 2026-08-24)
55 +
56 +| Métrique | Valeur |
57 +|---|---|
58 +| Offres actives | **21 492** (98 doublons inter-sources masqués, 227 en quarantaine qualité) |
59 +| Offres directes (pages carrières / ATS) | **19 856** — de 1 048 employeurs directs |
60 +| Offres portails (complément) | 1 863 |
61 +| Employeurs | **1 653** |
62 +| Sources actives | **963** (registre : 973 entrées ; 969 employeurs directs connectés via 21 plateformes ATS + 3 portails + dépôt direct) |
63 +| Avec salaire affiché | **6 856** — salaire moyen affiché ≈ **62 283 $/an** |
64 +| Télétravail | **1 013** |
65 +| Offres géocodées (carte) | **16 303** |
66 +| Top villes | Montréal 7 645 · Québec 3 637 · Dorval 734 · Laval 733 |
67 +| Top catégories | TI 2 699 · Santé 2 302 · Service à la clientèle 1 380 · Ventes 1 297 |
39 68
40 69 ## Visite guidée
41 70
@@ -61,75 +90,99 @@ Résultat en base : plus de **21 000 offres actives** de plus de **1 600 employe
61 90
62 91 ## Fonctionnalités
63 92
64 −- **Recherche filtrée** — texte, ville, catégorie (16 catégories : TI, Santé, Finance, Ingénierie…), mode de travail (dont télétravail), type d'emploi, **salaire minimum / « salaire affiché »**, tri, pagination.
93 +- **Recherche filtrée** — texte, ville, catégorie (16 catégories : TI, Santé, Finance, Ingénierie…), région, langue, mode de travail (dont télétravail), type d'emploi, **salaire minimum / « salaire affiché »**, tri, pagination.
65 94 - **Connecteurs auto-découverts** — toute sous-classe de `BaseConnector` avec un `source_id` est enregistrée par `pkgutil` ; brancher un nouvel employeur sur une plateforme ATS = **~10 lignes**. Politesse : throttling par source, User-Agent identifiable `JobKaBot/1.0`, budgets de requêtes, cache des pages détail.
66 95 - **Diff engine anti-dérive** — comparaison par `content_hash` à chaque sync ; une offre absente 2 syncs passe `active=0` (jamais de DELETE) ; si une source retourne ≤ 25 % de sa médiane historique, alerte et retraits suspendus.
67 96 - **Salaires normalisés, jamais inventés** — `parse_salary()` exige un signe monétaire ou une unité explicite, bornes de plausibilité, conversion $/h ↔ $/an, historique des changements (`salary_log`).
68 97 - **Géocodage sans invention** — Nominatim + repli officiel Adresses Québec (MERN), cache persistant, validation par bounding box provinciale ; carte des offres (MapLibre, sans jeton) via `GET /api/jobs.geojson`.
69 98 - **Déduplication inter-sources direct-prioritaire** — union-find avec second signal concordant ; en cas de doublon, l'offre de la page carrière (badge « Offre directe ») devient la canonique, les copies portail sont masquées (`dup_of`), jamais supprimées.
99 +- **Quarantaine qualité** — offres douteuses exclues des points d'accès publics (`jobka/quality.py`), supervisables via `quarantined=1`.
70 100 - **Dépôt direct employeurs** — `/employeurs` (`POST /api/employeurs/offres`), modération manuelle.
71 −- **Page /stats** — tableau de bord analytique + rapports PDF Groupe-KA (kit kacharts/kapdf) ; **favoris « Mon univers Ka »** (KA ID, cœur sur cartes et fiche, page `/favoris`).
72 −- **Conformité documentée** — `docs/CONFORMITE.md` (base d'accès par famille de sources, attribution, zéro donnée personnelle de candidat) + une fiche générée par connecteur dans `docs/connecteurs/`.
73 −- **Tests hors ligne** — fixtures HTTP enregistrées et rejouées (pytest), invariants (uid uniques, URLs absolues, salaires plausibles).
101 +- **SEO programmatique** — SSR léger (accueil, fiches JSON-LD JobPosting, pages statiques), robots.txt, sitemaps, pages `/villes` + `/ville/{slug}` rendues en HTML.
102 +- **Page /stats** — tableau de bord analytique + rapports PDF Groupe-KA (kit kacharts/kapdf v3, rapports personnalisés) ; **favoris « Mon univers Ka »** (KA ID, cœur sur cartes et fiche, page `/favoris`).
103 +- **Conformité documentée** — `docs/CONFORMITE.md` (base d'accès par famille de sources, attribution, zéro donnée personnelle de candidat) + une fiche générée par connecteur dans `docs/connecteurs/` (995 fiches).
104 +- **Tests hors ligne** — **74 tests pytest** : fixtures HTTP enregistrées et rejouées, invariants (uid uniques, URLs absolues, salaires plausibles).
74 105
75 106 ## Connecteurs & sources
76 107
77 108 | Famille | Détail | Volume |
78 109 |---|---|---|
79 −| **Employeurs directs (ATS)** | 968 connecteurs sur 17 plateformes : Workday, Lever, Greenhouse, SmartRecruiters, BambooHR, Breezy, Recruitee, Ashby, Workable, Taleo, Njoyn, UltiPro, iCIMS, SuccessFactors, ADP WFN, Digital Recruiters, Workland | ~19 800 offres directes |
110 +| **Employeurs directs (ATS)** | **969 connecteurs sur 21 plateformes** : Workday (206 employeurs), SmartRecruiters (158), Greenhouse (129), Dayforce (122), Breezy (72), Workable (70), Lever (57), Ashby (40), BambooHR (34), Recruitee (30), SuccessFactors (9), WP Job Manager (8), Njoyn (6), Taleo Business Edition (6), iCIMS (6), ADP WFN (5), Taleo (4), UltiPro/UKG (3), Digital Recruiters (2), réseau Atlas Workland (1 connecteur ≈ 80 employeurs QC), sites maison | **19 856 offres directes** (au 2026-08-24) |
80 111 | **Sites carrières maison** | pages carrières sans ATS standard (certaines via Scrapfly) | inclus ci-dessus |
81 −| **Portails publics** | Guichet-Emplois, Jobillico, Espresso-Jobs — complément, jamais prioritaire sur l'offre directe | le reste des ~21 000 offres |
112 +| **Portails publics** | Guichet-Emplois, Jobillico, Espresso-Jobs — complément, jamais prioritaire sur l'offre directe | 1 863 offres |
82 113 | **Dépôt direct** | formulaire `/employeurs`, modération manuelle | à la demande |
83 114
84 −Registre descriptif : `data/sources.json` (~970 entrées) ; une fiche de conformité par connecteur dans `docs/connecteurs/` (`scripts/gen_connector_docs.py`).
115 +Registre descriptif : `data/sources.json` (**973 entrées**, dont 1 en modération) ; une fiche de conformité par connecteur dans `docs/connecteurs/` (995 fiches, index : `docs/connecteurs/INDEX.md`, régénérables par `scripts/gen_connector_docs.py`).
85 116
86 −**Cadence de resync : horaire, jour et nuit** — le watcher PM2 `job-ka-sync` (`run.py watch 60`) enchaîne sync + géocodage + déduplication ; le diff engine par `content_hash` gère le cycle de vie (retrait après 2 syncs d'absence, anti-dérive à ≤ 25 % de la médiane historique).
117 +**Cadence de resync : horaire, jour et nuit** — le watcher PM2 `job-ka-sync` (`run.py watch 60`) enchaîne sync + géocodage + déduplication ; le diff engine par `content_hash` gère le cycle de vie (retrait après 2 syncs d'absence, anti-dérive à ≤ 25 % de la médiane historique). Les connecteurs fragiles passent par une **chaîne de fetch anti-bot résiliente** (Oxylabs → Scrapfly → Bright Data).
87 118
88 119 ## Architecture
89 120
90 121 ```
91 −Sources (17 plateformes ATS + sites maison + 3 portails)
122 +Sources (21 plateformes ATS + sites maison + 3 portails)
92 123 → connecteurs auto-découverts (jobka/connectors/)
93 124 → finalize() — normalisation commune (schema.py, normalize.py)
94 125 → SQLite data/jobka.db — diff par content_hash, cycle de vie, anti-dérive (db.py)
95 − → géocodage (geocode.py) + déduplication (dedup.py)
126 + → géocodage (geocode.py) + déduplication (dedup.py) + quarantaine (quality.py)
96 127 → API FastAPI (web.py) + frontend React/Vite servi en statique (frontend/dist)
97 128 ```
98 129
99 −- **Backend** : Python + **FastAPI** (uvicorn) — API JSON, stats, PDF, SSO/favoris KA ID.
130 +- **Backend** : Python + **FastAPI** (uvicorn) — API JSON, SSR SEO léger, stats, PDF (fpdf2), SSO/favoris KA ID.
100 131 - **Base de données** : **SQLite** (`data/jobka.db`, non versionnée) — offres, historique salarial, cache de géocodage, journal des syncs.
101 132 - **Frontend** : **React 18 + Vite + TypeScript**, carte **MapLibre GL** (sans jeton), design system Groupe KA ; build servi en statique par FastAPI.
102 −- **Anti-bot** : Scrapfly pour certaines pages carrières maison (`SCRAPFLY_API_KEY`).
133 +- **Anti-bot** : chaîne résiliente Oxylabs → Scrapfly → Bright Data pour certaines pages carrières maison (`SCRAPFLY_API_KEY`).
103 134
104 135 ## API — endpoints principaux
105 136
106 −| Endpoint | Rôle |
107 −|---|---|
108 −| `GET /api/jobs` | recherche filtrée : texte, ville, catégorie, mode de travail, type, salaire, tri, pagination |
109 −| `GET /api/jobs/{uid}` | fiche complète d'une offre (source, salaire normalisé, lien de candidature direct) |
110 −| `GET /api/jobs.geojson` | offres géocodées pour la carte MapLibre |
111 −| `GET /api/facets` | facettes de filtres (villes, catégories, types, modes) |
112 −| `GET /api/sources` | registre des sources et état des connecteurs |
113 −| `POST /api/employeurs/offres` | dépôt direct d'offres par les employeurs (modération manuelle) |
114 −| `GET /api/stats` · `/api/stats/catalog` · `/api/stats/dashboard` · `/api/stats/report(/custom)` | tableau de bord + rapports PDF Groupe-KA |
115 −| `GET /api/favorites` · `POST /api/favorites/toggle` | favoris « Mon univers Ka » (KA ID) |
116 −| `POST /api/sync` | déclenchement de synchronisation (interne) |
117 −| `GET /health` | santé du service |
137 +| Endpoint | Méthode | Rôle |
138 +|---|---|---|
139 +| `/api/jobs` | GET | recherche filtrée : texte, ville, catégorie, région, langue, mode de travail, type, salaire, tri, pagination |
140 +| `/api/jobs/{uid}` | GET | fiche complète d'une offre (source, salaire normalisé, logo, lien de candidature direct) |
141 +| `/api/jobs.geojson` | GET | offres géocodées pour la carte MapLibre |
142 +| `/api/facets` | GET | facettes de filtres (villes, catégories, types, modes, régions, langues) |
143 +| `/api/sources` | GET | registre des sources et état des connecteurs |
144 +| `/api/employeurs/offres` | POST | dépôt direct d'offres par les employeurs (modération manuelle) |
145 +| `/api/stats` | GET | agrégats publics (source des pastilles dynamiques ci-dessus) |
146 +| `/api/stats/catalog` · `/api/stats/dashboard` | GET | catalogue de blocs + tableau de bord (kit stats v3 Groupe KA) |
147 +| `/api/stats/report` · `/api/stats/report/custom` | GET/POST | rapports PDF Groupe-KA (5 modes + personnalisés) |
148 +| `/api/favorites` · `/api/favorites/toggle` | GET/POST | favoris « Mon univers Ka » (KA ID) |
149 +| `/api/sync` | POST | déclenchement de synchronisation (interne) |
150 +| `/health` | GET | santé du service |
151 +
152 +## Données & conformité
153 +
154 +- **Provenance** : API publiques des plateformes ATS (base légale documentée dans `docs/CONFORMITE.md`), pages carrières publiques, portails publics ; **zéro donnée personnelle de candidat** — Job·Ka n'indexe que des offres.
155 +- **Attribution** : chaque offre conserve son URL originale ; la candidature se fait **chez l'employeur** (badge « Offre directe » sur les sources directes).
156 +- **Cadence** : resync horaire jour et nuit (`run.py watch 60`) ; retrait doux après 2 syncs d'absence ; anti-dérive à ≤ 25 % de la médiane historique.
157 +- **Salaires** : jamais inventés — signe monétaire ou unité explicite obligatoire, bornes de plausibilité, conversion $/h ↔ $/an documentée.
158 +- **Traçabilité** : 995 fiches de conformité générées (`docs/connecteurs/`), registre `data/sources.json` auditable (sources écartées documentées avec raisons).
118 159
119 160 ## Structure du repo
120 161
121 162 | Répertoire / fichier | Rôle |
122 163 |---|---|
123 −| `jobka/` | paquet Python : schéma `JobPosting`, normalisation, DB/diff, ingestion, dédup, géocodage, web/API, stats, PDF, auth KA ID |
124 −| `jobka/connectors/` | base commune + 17 plateformes ATS + ~970 connecteurs (1 fichier = 1 employeur) + portails |
164 +| `jobka/` | paquet Python : schéma `JobPosting`, normalisation, DB/diff, ingestion, dédup, géocodage, quarantaine qualité, web/API, stats, PDF, auth KA ID |
165 +| `jobka/connectors/` | base commune + 21 plateformes ATS + ~970 connecteurs (1 fichier = 1 employeur) + portails — 995 modules au total |
125 166 | `frontend/` | React 18 + Vite + TS (carte MapLibre) — `dist/` non versionné ; guide `/doc` dans `frontend/public/doc/` |
126 −| `data/` | `sources.json` (registre descriptif, ~970 entrées) + `jobka.db` (non versionnée) |
127 −| `tests/` | pytest : normalisation + rejeu hors ligne des fixtures connecteurs |
128 −| `scripts/` | `check_headers.py` (en-tête d'auteur obligatoire), `gen_connector_docs.py` (fiches connecteurs) |
129 −| `docs/` | `CONFORMITE.md`, `connecteurs/`, `deploiement.md`, captures d'écran |
167 +| `data/` | `sources.json` (registre descriptif, 973 entrées) + `jobka.db` (non versionnée) |
168 +| `tests/` | pytest : normalisation + rejeu hors ligne des fixtures connecteurs — 74 tests |
169 +| `scripts/` | `check_headers.py` (en-tête d'auteur obligatoire), `gen_connector_docs.py` (fiches connecteurs), `probe_ats.py` + éclaireur Serper (campagnes connecteurs) |
170 +| `docs/` | `CONFORMITE.md`, `connecteurs/` (995 fiches + INDEX), `deploiement.md`, captures d'écran |
130 171 | `run.py` | CLI : `sync` · `watch` · `serve` · `geocode` · `record` |
131 172 | `requirements.txt` | fastapi, uvicorn, requests, beautifulsoup4, fpdf2 |
132 173
174 +## Démarrage rapide
175 +
176 +```bash
177 +ssh M3U96a && cd ~/apps/job-ka
178 +python3 -m venv .venv && .venv/bin/pip install -r requirements.txt # au besoin
179 +.venv/bin/python -m pytest # 74 tests hors ligne (fixtures rejouées)
180 +.venv/bin/python run.py sync <source> # valider un connecteur précis
181 +.venv/bin/python run.py sync # sync complet (toutes les sources)
182 +.venv/bin/python run.py serve 8096 # API + frontend statique
183 +cd frontend && npm install && npm run build # rebuild du frontend (tsc -b && vite build)
184 +```
185 +
133 186 ## Développement (remote-first)
134 187
135 188 ⚠️ **La source de vérité est le repo git sur le nœud M3U96a** (`~/apps/job-ka`) — on n'édite **jamais** les copies laptop. Toute modification se fait sur le nœud via SSH : édition, tests, build frontend au besoin, redémarrage PM2, puis commit + push **depuis le nœud**.
@@ -138,22 +191,24 @@ Sources (17 plateformes ATS + sites maison + 3 portails)
138 191 - On ne pousse **que le code** : `data/*.db`, `frontend/dist/` et `.env` ne sont jamais versionnés — le serveur maintient ses données lui-même.
139 192
140 193 ```bash
141 −ssh M3U96a
142 194 cd ~/apps/job-ka
143 −.venv/bin/python -m pytest # tests hors ligne
144 −.venv/bin/python run.py sync <source> # valider un connecteur
195 +.venv/bin/python -m pytest # avant de pousser
145 196 cd frontend && npm run build && cd .. # si le frontend a changé
146 197 pm2 restart job-ka-web # après changement
147 198 git add <fichiers> && git commit -m "…" && git push origin main
148 199 ```
149 200
150 −### Configuration notable (sans secrets)
201 +## Variables d'environnement
202 +
203 +Noms seulement — **aucun secret n'est versionné**.
151 204
152 205 | Variable | Rôle |
153 206 |---|---|
154 207 | `SCRAPFLY_API_KEY` | anti-bot pour certaines pages carrières maison |
155 −| `JOBKA_WORKDAY_DETAIL_LIMIT` · `JOBKA_SR_DETAIL_LIMIT` | budgets de requêtes détail (Workday, SmartRecruiters) |
156 −| autres `JOBKA_<PLATEFORME>_*` | budgets par plateforme ATS — documentés dans `docs/connecteurs/INDEX.md` |
208 +| `KA_SSO_SECRET` · `KA_HUB_URL` | SSO KA ID (hub groupe-ka.com) |
209 +| `JOBKA_BASE_URL` | URL canonique du site (SEO, liens absolus) |
210 +| `JOBKA_WORKDAY_DETAIL_LIMIT` · `JOBKA_SR_DETAIL_LIMIT` · `JOBKA_DAYFORCE_DETAIL_LIMIT` … | budgets de requêtes détail par plateforme ATS (`JOBKA_<PLATEFORME>_DETAIL_LIMIT`) |
211 +| `JOBKA_GUICHET_PAGES` · `JOBKA_GUICHET_DAYS` · `JOBKA_ESPRESSO_PAGES` · `JOBKA_JOBILLICO_TRACK` … | réglages des portails — documentés dans `docs/connecteurs/INDEX.md` |
157 212
158 213 ## Déploiement
159 214
@@ -163,11 +218,11 @@ git add <fichiers> && git commit -m "…" && git push origin main
163 218 | **Port** | **8096** |
164 219 | **Domaine** | [www.job-ka.com](https://www.job-ka.com) via tunnel ngrok |
165 220
166 −| Processus PM2 | Rôle |
167 −|---|---|
168 −| `job-ka-web` | `run.py serve 8096` — API FastAPI + frontend statique |
169 −| `job-ka-sync` | `run.py watch 60` — resync horaire + géocodage + dédup, jour et nuit |
170 −| `job-ka-ngrok` | tunnel ngrok vers www.job-ka.com |
221 +| Processus PM2 | Commande réelle | Rôle |
222 +|---|---|---|
223 +| `job-ka-web` | `.venv/bin/python run.py serve 8096` | API FastAPI + frontend statique |
224 +| `job-ka-sync` | `.venv/bin/python run.py watch 60` | resync horaire + géocodage + dédup, jour et nuit |
225 +| `job-ka-ngrok` | `ngrok http --url=www.job-ka.com 8096` | tunnel vers www.job-ka.com |
171 226
172 227 Détails : `docs/deploiement.md`.
173 228
@@ -175,7 +230,17 @@ Détails : `docs/deploiement.md`.
175 230
176 231 - **Guide utilisateur en ligne** : [www.job-ka.com/doc/](https://www.job-ka.com/doc/) — à quoi sert le site, utilisation en 4 étapes, provenance des données, FAQ.
177 232 - **Guide PDF téléchargeable** : [job-ka-documentation.pdf](https://www.job-ka.com/doc/job-ka-documentation.pdf).
178 −- **Conformité & connecteurs** : `docs/CONFORMITE.md` + une fiche par connecteur dans `docs/connecteurs/` (index : `docs/connecteurs/INDEX.md`).
233 +- **Conformité & connecteurs** : `docs/CONFORMITE.md` + une fiche par connecteur dans `docs/connecteurs/` (995 fiches, index : `docs/connecteurs/INDEX.md`).
234 +
235 +## Historique
236 +
237 +| Date | Jalon |
238 +|---|---|
239 +| 2026-08-17 | fondation Job·Ka (socle backend, 5 connecteurs pilotes, frontend, tests) puis **création massive : 135 connecteurs sur 9 plateformes ATS** + intégration écosystème Groupe KA |
240 +| 2026-08-19 | phase 2-3 qualité : salaires structurés, langue fr/en, quarantaine, régions MAMH ; **nouvelles familles** Taleo Business Edition, WP Job Manager (Santé Québec), réseau Atlas Workland (~80 employeurs, 1 connecteur) ; registre 244 sources + conformité |
241 +| 2026-08-22 | **vague B : +110 sources** (dont la famille Dayforce, 26 connecteurs) ; SEO SSR (fiches JobPosting, sitemaps) ; chaîne de fetch anti-bot résiliente ; page Publier |
242 +| 2026-08-23 | **vague C : +620 connecteurs employeurs directs (350 → 968)** ; SEO villes programmatique ; stats v3 (rapports PDF personnalisés) ; favoris « Mon univers Ka » |
243 +| 2026-08-24 | page `/doc` (guide + captures + PDF), README v3 — état : 969 employeurs directs, 21 plateformes ATS, 21 492 offres actives |
179 244
180 245 ## Écosystème Groupe KA
181 246
182 247