Building an Explainable AI-Powered Lead Scoring Engine with FastAPI
Introduction
Sales teams often receive many leads, but not every prospect is equally likely to become a customer. Manually reviewing every lead takes time and makes it difficult to identify the most promising opportunities.
I built a personal project called the Lead Qualification and Scoring Engine to explore how AI and rule-based business logic can work together to solve this problem.
The application evaluates lead information, checks Ideal Customer Profile (ICP) fit, calculates a score from 0 to 100, and generates a lead classification and recommended next action.
In this article, I’ll explain the architecture, scoring approach, API design, and engineering lessons behind the project.
Technology stack
The project uses:
- Python for business logic.
- FastAPI for REST API endpoints.
- Pydantic for request and response validation.
- SQLAlchemy for database operations.
- SQLite for data persistence.
- AI integration for interpreting lead information.
- HTML, CSS, and JavaScript for the frontend.
- Pytest for automated testing.
- Understanding the architecture
The application follows a sequence of steps:
- Receive lead information.
- Check for an existing lead and reusable results.
- Gather available company research.
- Use AI to interpret relevant business signals.
- Evaluate ICP fit using configured rules.
- Calculate a deterministic score in Python.
- Generate the classification and recommendations.
- Store the results and return a structured response.
One important design decision is separating AI interpretation from numerical scoring.
AI can help interpret unstructured information, while deterministic application code applies the configured business rules. This makes the final score easier to explain and test.
- Implementing configurable lead scoring
A scoring engine should not be a mysterious black box. Sales teams need to understand why a lead received a particular score.
My project stores scoring configuration in a JSON rules file. The configured criteria cover industry relevance, decision-maker relevance, company size, pain points, buying signals, automation opportunities, and recent activity.
Each criterion contributes its configured weight when the relevant condition is satisfied.
For example, consider a hypothetical lead:

Criterion Points
Target industry 20
Decision-maker relevance 15
Company size 10
Clear pain point 20
Buying signal 0
Automation opportunity 10
Recent activity 5
Total 80
This example demonstrates how a score can be explained through individual criteria rather than returned as a single unexplained number.
The actual scoring rules and thresholds should remain consistent with the application’s configuration.
- Why use rules alongside AI?
AI is useful for interpreting descriptions that do not follow a fixed format. For example, a prospect might describe manual workflows or operational challenges without explicitly labelling them as an automation opportunity.
However, asking an AI model to invent a final score can make results difficult to reproduce.
A hybrid approach separates responsibilities:
- AI interprets available information.
- Business rules evaluate qualification requirements.
- Python calculates the score.
- The API returns the result in a structured format.
This separation makes it easier to test the scoring logic independently of the AI provider.
- Building REST APIs with FastAPI
FastAPI provides endpoints that allow the frontend and other applications to interact with the qualification engine.
The project includes operations for qualifying leads, retrieving stored leads, viewing an individual lead, and checking service health.
Pydantic schemas help validate incoming request data before it reaches the business logic.
A structured API response can expose the score, classification, qualification status, scoring breakdown, matched criteria, and recommended next action.
This structure also makes the engine suitable for integration with a CRM or an internal business dashboard.
- Storing results with SQLAlchemy and SQLite
The application uses SQLAlchemy models and SQLite to persist lead information and qualification results.
Persistence allows the system to retrieve previous results without depending on temporary in-memory data.
Keeping database operations in a separate repository layer also helps separate data access from scoring and analysis.
SQLite is convenient for local development because it requires minimal setup. SQLAlchemy provides a familiar abstraction for working with relational data.
- Reducing repeated work with fingerprint-based caching
Repeatedly analyzing unchanged lead information can increase processing time and AI API usage.
The project uses a lead identity and a fingerprint of qualification-relevant information to determine whether an existing result can be reused.
When the same lead is submitted with unchanged relevant information, the application can reuse its stored result. When relevant information changes, the qualification process can run again.
This approach helps avoid unnecessary work while preserving the ability to refresh results when the underlying information changes.
- Testing the application
Automated tests are important because a correct HTTP response does not necessarily mean the qualification result is correct.
The project includes tests for areas such as scoring, API behaviour, ICP validation, AI services, research, sales action plans, and fingerprint-based caching.
Useful test cases include:
- Verifying the expected score for known assessment inputs.
- Checking that an ICP mismatch is handled correctly.
- Confirming that invalid requests are rejected.
- Ensuring unchanged lead data can reuse an existing result.
- Checking how the application handles failures in external services.
Deterministic business logic is particularly valuable because it can be tested without depending on an AI model producing exactly the same interpretation every time.
- Engineering lessons
Building this project reinforced several useful principles.
Make business rules explicit. Configurable scoring criteria make changes easier to understand and maintain.
Separate AI from deterministic decisions. AI interpretation and numerical calculations have different responsibilities.
Design for failure. External services can become unavailable or return unusable output, so fallback behaviour needs to be tested.
Avoid unnecessary processing. Reusing stored results can reduce repeated analysis for unchanged information.
Test the business logic. Tests should validate qualification outcomes, not just successful API responses.
Conclusion
The Lead Qualification and Scoring Engine combines AI-assisted interpretation, configurable business rules, REST APIs, database persistence, and automated testing.
The goal is not simply to assign a number to a prospect. It is to produce an understandable qualification result that other applications can consume.
This project gave me practical experience with API development, AI integration, data persistence, caching, and testable business logic.

Future improvements could include stronger monitoring, more extensive evaluation of AI-generated assessments, and integration with an internal dashboard for reviewing and managing qualified leads.
Technologies: Python, FastAPI, Pydantic, SQLAlchemy, SQLite, AI integration, JavaScript, HTML, CSS, and Pytest.
Top comments (0)