1. Overview
The HibpProvider module integrates BastionGuard’s Identity Leak subsystem with the Have I Been Pwned (HIBP) v3 API to retrieve breach exposure information for an email address.
The provider:
- Queries the HIBP
breachedaccountendpoint for a given email identity - Authenticates requests using the HIBP API key header
- Implements explicit handling for common HTTP outcomes (no breach, invalid key, rate limit)
- Parses the returned JSON array of breaches into BastionGuard’s canonical
LeakRecordformat - Computes a deterministic severity score based on the reported
DataClasses
2. Dependencies
- HttpClient – HTTPS transport, headers, URL encoding
- nlohmann/json – JSON parsing and traversal
- glib/gi18n – localized error messages via
_() - C++ standard library – exceptions, containers, string handling
3. Provider Construction and Configuration
3.1 Constructor
The provider is constructed with an API key:
HibpProvider::HibpProvider(const std::string& key)
The key is stored internally as apiKey and must be present for any successful query.
4. Email Lookup Flow
4.1 Input Preconditions
checkEmail() returns an empty result set if:
- The input email string is empty
- The configured API key is empty
This avoids unnecessary network calls and maintains predictable behavior for unconfigured systems.
4.2 URL Encoding
The email address is URL-encoded before being embedded in the request path:
encodedEmail = HttpClient::urlEncode(email)
This prevents path-breaking characters (e.g., +, @) from producing malformed requests.
4.3 API Endpoint
The provider uses the HIBP v3 breachedaccount endpoint with full response enabled:
https://haveibeenpwned.com/api/v3/breachedaccount/<email>?truncateResponse=false
truncateResponse=false instructs HIBP to return full breach data (including descriptions and data classes) rather than a reduced payload.
4.4 Request Headers
The provider sends the following headers:
- hibp-api-key – API key required by HIBP
- User-Agent –
BastionGuard/IdentityLeak - Accept –
application/json
The User-Agent improves compatibility and aligns with common API policy expectations.
4.5 Timeout Policy
The request is executed with a 20-second timeout via:
HttpClient::get(url, headers, 20)
5. HTTP Status Handling
The provider treats specific HIBP HTTP codes explicitly:
- 404: No breach found for this account
- Returns an empty result set
- This is not considered an error condition
- 401: Invalid or missing API key
- Throws
std::runtime_errorwith a localized message
- Throws
- 429: Rate limit exceeded
- Throws
std::runtime_errorwith a localized message
- Throws
- Other non-200: Generic HTTP error
- Throws
std::runtime_errorwith the HTTP status code embedded
- Throws
This behavior allows upstream logic (e.g., LeakAggregator or UI) to differentiate “no breach” from genuine errors such as authentication or throttling.
6. JSON Parsing and Record Mapping
6.1 Parse Strategy
If the response status is 200, the body is parsed as JSON:
- Parsing errors trigger a
std::runtime_errorwith a localized message - The provider expects the top-level JSON value to be an array
- Non-array JSON results yield an empty set (defensive behavior)
6.2 LeakRecord Construction
For each breach object in the array, a LeakRecord is created and populated:
provider="HIBP"breachNamefrom JSON fieldName(default:Unknown)breachDatefrom JSON fieldBreachDate(default: empty)descriptionfrom JSON fieldDescription(default: empty)dataClassesfrom JSON arrayDataClasses(if present)
Each constructed record is appended to the returned vector. The implementation uses move semantics when pushing the record to reduce copies.
7. Severity Computation
7.1 Deterministic Severity Policy
The provider computes a reproducible severity score based on the data classes reported by HIBP. The logic classifies exposure by the presence of:
- Passwords (including “Password hints”)
- Email addresses
- Other PII (any other data classes)
Classification flags:
hasPassword– true if"Passwords"or"Password hints"is presenthasEmail– true if"Email addresses"is presenthasPII– true if any other data class is present
7.2 Severity Mapping
The computed severity follows this decision tree:
- If password + email present →
CRITICAL - If password present (without email) →
HIGH - If email + other PII present →
MEDIUM - If email only →
LOW - Otherwise →
INFO
This policy prioritizes credential compromise and credential linkage as the highest-risk scenario.
8. Runtime and Security Considerations
- API key handling: the API key is passed via
hibp-api-keyheader; storage and retrieval should be protected (e.g., config file permissions or secure storage) - Rate limiting: explicit 429 handling enables upstream retry/backoff strategies and clearer UX messaging
- Privacy: the email address is transmitted to HIBP (after URL encoding). This should be controlled by user consent and product privacy policy
- Exception semantics: authentication and throttling errors throw exceptions; aggregation layers should catch and isolate provider failures where appropriate
- Severity reproducibility: deterministic mapping ensures consistent UI classification across sessions and builds
- Localization: error messages are localized via
_(), supporting multi-language UI surfaces - TLS assurance: the underlying
HttpClientkeeps TLS verification enabled to prevent MITM downgrade