Expand description
The country gate: whitelist_countries and blocked_countries.
This is the Rust family’s port of the reference engine’s global country
check - the country branch of check_ip_access
(guard_core/_utils/access_control.py) with the verdict logic of
_resolve_country_verdict and _evaluate_country_access, plus the
config coercion of _validate_country_set_value. One call,
check_countries, decides a request IP’s country access:
skip (a global whitelist match set it): pass
no rules configured: pass
loopback address: pass (the loopback exemption)
geolocation unresolved (or empty):
blocked iff whitelist_countries is non-empty
whitelist_countries non-empty:
country in the whitelist: pass
anything else: blocked
blocked_countries non-empty:
country in the blocklist: blocked
anything else: pass§Details that mirror the reference exactly
- The country lists are sets of ISO 3166-1 alpha-2 codes, uppercased at
config time (
_validate_country_set_valuecoerces withupper()) and compared exactly - a handler returning"us"does not match"US". - The loopback exemption runs before geolocation:
127.0.0.1and::1pass even under a restrictive whitelist. - An unresolved country is blocked only under a restrictive
whitelist (the reference
return bool(config.whitelist_countries)), with the generic list reason instead of a country reason. - An explicit whitelist match outranks
blocked_countries: the whitelist branch decides first, exactly as the reference_evaluate_country_accessreturns from it. - The reference initializes its geo handler on first use
(
is_initialized/initialize()); the Rust handler trait is sync and assumed ready.
The geolocation itself comes from the GeoIpHandler seam: the
reference resolves countries through an IPInfo MMDB database (or a
custom handler); the MMDB reading is adapter work, the gate takes the
resolved country code.
§Example
use std::net::IpAddr;
use std::str::FromStr;
use guard_core_engine::geo::{
check_countries, parse_country_lists, CountryGate, GeoIpHandler,
};
struct FixedUS;
impl GeoIpHandler for FixedUS {
fn get_country(&self, _ip: IpAddr) -> Option<String> {
Some("US".to_owned())
}
}
// A restrictive whitelist: only US traffic passes.
let gate: CountryGate = parse_country_lists(["us"], [] as [&str; 0]);
let handler = FixedUS;
let passed = check_countries(
IpAddr::from_str("192.0.2.1").unwrap(),
&gate,
&handler,
false,
);
assert!(passed.is_none(), "US is whitelisted");
// Under the same rules a non-US address is blocked with the reference
// reason, and a whitelist match carries the skip flag past this check.
struct FixedDE;
impl GeoIpHandler for FixedDE {
fn get_country(&self, _ip: IpAddr) -> Option<String> {
Some("DE".to_owned())
}
}
let blocked = check_countries(
IpAddr::from_str("192.0.2.2").unwrap(),
&gate,
&FixedDE,
false,
)
.expect("blocked");
assert_eq!(blocked.reason, "IP from blocked country: DE");
let skipped = check_countries(
IpAddr::from_str("192.0.2.2").unwrap(),
&gate,
&FixedDE,
true,
);
assert!(skipped.is_none(), "a whitelist match skips the country check");Structs§
- Country
Block - The block answer of a failed country check: the reference
IpAccessResultreason and the resolved country when one exists. - Country
Gate - The country gate: the parsed
whitelist_countriesandblocked_countriessets.
Traits§
- GeoIp
Handler - The geolocation seam: the ISO 3166-1 alpha-2 country code of an
address,
Nonewhen the address is not geolocated.
Functions§
- check_
countries - The country branch of the reference
check_ip_access. - check_
route_ country - The route-level country verdict: the reference
check_country_access(guard_core/core/checks/helpers.py), the country arm ofcheck_route_ip_access. - generic_
list_ block_ reason - The generic block reason (
_GENERIC_LIST_BLOCK_REASONwith the IP filled in) used when an address under a restrictive whitelist is not geolocated. - generic_
list_ block_ reason_ for - The generic block reason for an arbitrary identity string: the
reference formats the same template with
UNKNOWN_CLIENT_IDENTITY("unknown") when a request carries no client IP. - parse_
country_ lists - Coerce the two country-code lists into the gate: every code is
uppercased and duplicates dropped (
_validate_country_set_value’sfrozenset(str(item).upper())).