100,000 candidate profiles → top 100 best matches in under 3 seconds. Five orthogonal signals. Zero API calls. Full explainability.
Eight production-grade features — from adversarial detection to blind screening — in one CPU-native pipeline.
Embed 100K profiles with all-MiniLM-L6-v2 in ~4 min on GPU. Artifacts cached — ranking is instant on every subsequent run.
Phase ADrag a weight slider → entire 100K pool re-scored in ~50 ms. One float32 matrix multiply. No pipeline re-run needed.
~50msEvery score claim traces to a specific declared skill or career sentence. The reasoning string never invents evidence.
Explainable AICatches honeypots (impossible YoE), ghost profiles (unverified, empty), and pure-research candidates before scoring begins.
35 caughtShortlist vs full-pool distributions by education tier, country, and years of experience — detect encoded bias at a glance.
Bias detectionMaximal Marginal Relevance slider penalizes near-duplicate profiles so the shortlist surfaces distinct candidate archetypes.
MMRToggle to hide names, companies, and institutions. Reduce reviewer bias — evaluate candidates on skills and signals only.
DEISubmission CSV + personalized outreach pack (top-10 draft messages) + reproducible ranking config JSON — all from the dashboard.
ExportExpensive GPU work separated from the CPU-only ranking sandbox. Artifacts baked into Docker — zero network at inference time.
Stream 100K candidates from 487 MB candidates.jsonl
Hard-remove honeypots, ghosts, pure-research profiles
Headline + summary + career descriptions + top skills → 1024 char
all-MiniLM-L6-v2 · batch=2048 · 384-dim normalized vectors
Technical fit, career quality, availability, seniority per candidate
embeddings.npy · subscores.pkl · disqualified.json · candidate_ids.npy
Memory-map numpy arrays — no full file parse
embeddings @ jd_embedding — single dot product broadcast
penalty × (subscore_matrix @ weights + w_sem × sim)
np.argsort → top-k with deterministic tie-breaking
Byte-offset seek index → load 100 records, cite actual skills
validate_submission.py → submission.csv
Drag any weight → single matrix multiply → instant re-rank
Paste any job description → embed on the fly → re-rank 100K
λ slider → penalize near-duplicate profiles in shortlist
200 Monte Carlo trials → ±20% weight perturbation frequency
No single signal can game the system. Keyword stuffers score high on technical fit but low on career quality and availability.
S = penalty × ( 0.35 × technical_fit + 0.25 × career_quality + 0.20 × availability + 0.12 × seniority_fit + 0.08 × semantic_sim )
All sub-scores ∈ [0, 1]
Penalty ∈ [0.12, 1.0]
| Signal | Weight | What It Checks |
|---|---|---|
| 🔧 Technical Fit | 0.35 | JD must-haves scored by proficiency (expert=1.0, advanced=0.75, intermediate=0.4, beginner=0.1). Platform assessment scores override self-reported proficiency. |
| 🏢 Career Quality | 0.25 | Non-consulting role presence (+0.30), ML/AI title at ≥50-person company (+0.15), median tenure ≥36mo (+0.25), upward title progression (+0.20). |
| 📡 Availability | 0.20 | Open-to-work flag, last active ≤30d/90d/180d, recruiter response rate, interview completion rate, notice period, applications submitted. |
| 📏 Seniority Fit | 0.12 | YoE bands: 6–9yr → 1.0, 4–5/10–12yr → 0.7, 3/13–15yr → 0.4, else → 0.1. Tier-1 education +0.05. |
| 🔎 Semantic Match | 0.08 | Cosine similarity between 384-dim profile embedding and JD embedding. Safety net for strong candidates who describe skills in plain language. |
The dataset seeds ~80 fake profiles to catch naive rankers. SignalHire's disqualification layer hard-removes them before scoring begins.
Claimed years of experience exceeds what the career timeline allows. A candidate claiming 20yr experience with earliest role starting in 2018 is impossible.
Near-empty profiles with no verified contact. Profile completeness below 5% with neither verified email nor verified phone — they're not real candidates.
All career roles titled "researcher" with zero deployment or production evidence in descriptions. Academic-only profiles don't fit a Senior AI Engineer role.
Every role at TCS, Infosys, Wipro, Capgemini, Cognizant, Accenture, HCL etc. These profiles rarely have the deep technical work required.
85% penaltyLast active >548 days ago with no current role. Skills may be significantly stale in a fast-moving AI/ML field.
20% penaltyHas computer vision, speech recognition, or robotics domain skills but zero retrieval/search signals. Domain misalignment with this JD.
15% penaltyAn interactive ranking environment — not just a results page. Every control re-ranks the full pool in real time.
Zero circular dependencies. Every module has a single responsibility. Leaf modules have no project imports.
candidate_id,rank,score,reasoning CAND_0081846,1,8.70,"6.7yr Lead AI Engineer at Razorpay; strong match on embeddings, vector search, python, information retrieval; production evidence (serving, ndcg); actively looking, 73% response rate, 30d notice." CAND_0055905,2,8.69,"8.1yr Senior ML Engineer at Flipkart; strong match on embeddings, vector search, python, information retrieval; production evidence (deployed, serving); actively looking, 87% response rate."
Contributors who made SignalHire happen. Every commit, review, and idea counted.
Interactive dashboard on HuggingFace Spaces — try all features on 50 sample candidates
→ huggingface.coFull source code — 9 Python modules, Dockerfile, tests, and complete documentation
→ DevanshSrajput/SignalHireMore projects and work from Devansh Singh Rajput — AI/ML engineer and open source contributor
→ devanshsingh.devModule reference, data schemas, function signatures, FAQ, and initial planning documents
→ docs.htmlResearch Intern at IIT (ISM) Dhanbad — building efficient AI systems and real-world ML applications
→ @DevanshSrajputFull demo walkthrough — pipeline, dashboard features, scoring methodology explained
→ YouTube