uTPro.Feature.GeoLocation
18.1.1
dotnet add package uTPro.Feature.GeoLocation --version 18.1.1
NuGet\Install-Package uTPro.Feature.GeoLocation -Version 18.1.1
<PackageReference Include="uTPro.Feature.GeoLocation" Version="18.1.1" />
<PackageVersion Include="uTPro.Feature.GeoLocation" Version="18.1.1" />
<PackageReference Include="uTPro.Feature.GeoLocation" />
paket add uTPro.Feature.GeoLocation --version 18.1.1
#r "nuget: uTPro.Feature.GeoLocation, 18.1.1"
#:package uTPro.Feature.GeoLocation@18.1.1
#addin nuget:?package=uTPro.Feature.GeoLocation&version=18.1.1
#tool nuget:?package=uTPro.Feature.GeoLocation&version=18.1.1
uTPro Geo Location for Umbraco
Documentation: https://docs.utpro.dev/uTPro.Feature.GeoLocation/
IP-based visitor country detection for Umbraco multi-language sites. Resolves visitor country via
CDN headers (Cloudflare, AWS CloudFront, Azure Front Door) with an offline MMDB fallback —
then maps the country code to a .NET CultureInfo so your site can switch language automatically.
Works with Umbraco 16, 17 and 18 (multi-targeted net9.0 / net10.0).
Features
- Multi-source detection chain (first hit wins):
- Cloudflare —
CF-IPCountryheader - Akamai —
X-Akamai-Edgescapeheader (parsescountry_code=XX) - Fastly —
X-Geo-CountryorFastly-Client-Countryheader - Vercel —
X-Vercel-IP-Countryheader - Netlify —
X-Countryheader - AWS CloudFront —
CloudFront-Viewer-Countryheader - Azure Front Door —
X-Azure-ClientIP-Country/X-Azure-Geo-Countryheader - Forwarded IP resolution — handles
X-Forwarded-For,X-Real-IP,CF-Connecting-IP,True-Client-IP - Offline MMDB — local iplocate.io database (no external API calls)
- Cloudflare —
- Two output modes:
GetCountryCode()— raw ISO 3166-1 alpha-2 code (e.g. "VN", "US")Detect()→ fullGeoLocationResultwith mappedCultureInfo
- Culture mapping:
- Custom map via
appsettings.json(country → specific culture) - Automatic fallback using .NET
RegionInfo(ISO standard derivation)
- Custom map via
- Cookie persistence — skip detection on subsequent requests
- Optional auto-culture — middleware sets
CurrentCulture/CurrentUICulturefor the entire Umbraco pipeline (SurfaceControllers, ViewComponents, Views, API controllers) - Pluggable — add custom
IGeoLocationProviderimplementations via DI - Zero-config install — self-wires via Umbraco composers, no
Program.cschanges - Offline DB update — replace the
.mmdbfile manually or upgrade the NuGet package
Quick Start
dotnet add package uTPro.Feature.GeoLocation
That's it. The middleware runs automatically. Access the result from any controller or view:
// In a SurfaceController, RenderController, or ViewComponent:
var geo = HttpContext.GetGeoLocation();
// geo.CountryCode → "VN"
// geo.Culture → CultureInfo("vi-VN")
// geo.Provider → "Cloudflare"
// Or inject IGeoLocationService for raw detection:
var countryCode = _geoService.GetCountryCode(HttpContext); // "US"
var culture = _geoService.MapToCulture("US"); // CultureInfo("en-US")
| Umbraco | .NET | Target |
|---|---|---|
| 16 | .NET 9 | net9.0 |
| 17 & 18 | .NET 10 | net10.0 |
Configuration
All settings are optional — the package works out of the box. Configure under
uTPro:Feature:GeoLocation in appsettings.json:
{
"uTPro": {
"Feature": {
"GeoLocation": {
"EnableProviders": {
"Cloudflare": true
},
"CultureMap": {
"VN": "vi-VN",
"US": "en-US",
"JP": "ja-JP"
}
}
}
}
}
| Key | Default | Description |
|---|---|---|
EnableProviders |
all false |
Toggle CDN providers: Cloudflare, Akamai, Fastly, Vercel, Netlify, AwsCloudFront, AzureFrontDoor. Only enable what you use. |
CustomCountryHeader |
"" |
Custom header with 2-letter country code (highest priority, only active when set). |
CustomIpHeader |
"" |
Custom header with client IP (only active when set). |
AutoSetCulture |
false |
When true, middleware sets Thread.CurrentThread.CurrentCulture for the Umbraco pipeline. |
DatabasePath |
App_Data/GeoLocation/iplocate-country.mmdb |
Path to the offline MMDB file (relative to ContentRoot or absolute). |
UseCookie |
true |
Persist detected country in a cookie to skip detection on subsequent requests. |
CookieName |
utpro_geo_country |
Cookie name. |
CookieMaxAgeDays |
30 |
Cookie lifetime in days. |
FallbackCulture |
en |
Culture used when no country is detected. |
CultureMap |
{} |
Custom country→culture overrides. Keys: ISO 3166-1 alpha-2. Values: .NET culture names. |
Note: By default only Forwarded (IP resolution) and Offline (MMDB) providers are active. CDN providers must be explicitly enabled via
EnableProviders.
Culture Mapping Strategy
The package provides two levels of country-to-culture resolution:
- Custom map (
CultureMapin config): highest priority. You define exact country→culture pairs. - ISO standard (automatic): uses .NET
RegionInfoto derive the default culture for a country. For example,"DE"→de-DE,"BR"→pt-BR.
This means you only need to configure CultureMap for exceptions or preferences — the ISO standard
handles the rest.
Updating the Offline Database
The offline .mmdb ships with the NuGet package. You can update it manually at any time:
- Download the latest
ip-to-country.mmdbfrom iplocate.io - Rename to
iplocate-country.mmdb - Replace
App_Data/GeoLocation/iplocate-country.mmdbin your deployed site - Restart the application
NuGet package upgrades will not overwrite your manually updated file — your custom DB is safe.
Extensibility
Custom provider
Implement IGeoLocationProvider and register it in your own composer:
public sealed class MyCustomGeoProvider : IGeoLocationProvider
{
public string Name => "MyCustom";
public int Priority => 5; // Runs before Cloudflare (10)
public string? Detect(HttpContext httpContext)
{
// Your custom detection logic.
return httpContext.Request.Headers["X-My-Country"].ToString();
}
}
// In your composer:
builder.Services.AddSingleton<IGeoLocationProvider, MyCustomGeoProvider>();
Documentation
Full documentation is available at the uTPro Docs site:
| Guide | Description |
|---|---|
| Getting Started | Install, first boot, access the result |
| Configuration | All appsettings keys and their effects |
| Culture Mapping | Custom map vs ISO standard derivation |
| Offline Database | MMDB source, update strategies |
| Extensibility | Custom providers, advanced usage |
Screenshots
Security
- No external API calls — all detection uses request headers or the local MMDB file.
- The cookie is functional (not tracking) and marked
Secure,SameSite=Lax,IsEssential=true. - IP addresses are not persisted — they're used only during the request lifetime.
License & Author
By T4VN. Free to use — including in commercial projects — under a proprietary End User License Agreement. Issues welcome on the GitHub repository.
| Product | Versions Compatible and additional computed target framework versions. |
|---|---|
| .NET | net10.0 is compatible. net10.0-android was computed. net10.0-browser was computed. net10.0-ios was computed. net10.0-maccatalyst was computed. net10.0-macos was computed. net10.0-tvos was computed. net10.0-windows was computed. |
-
net10.0
- MaxMind.Db (>= 4.1.0)
- Umbraco.Cms.Web.Common (>= 18.0.0 && < 19.0.0)
NuGet packages (1)
Showing the top 1 NuGet packages that depend on uTPro.Feature.GeoLocation:
| Package | Downloads |
|---|---|
|
uTPro.Feature.AdProtect
Invalid-click protection and ad-serving control for Umbraco sites monetized with Google AdSense (or any ad network). Decides per visitor whether ad code is served at all: blocks bots/scanners via IP/CIDR/country/ASN rules, counts ad-click intent per IP and per anonymous cookie, auto-cools down repeat clickers, and ships a backoffice dashboard (rules, active blocks, click log, live settings). Cache-safe by design (the Razor slot stays empty; a tiny fetch decides), CGNAT-aware, optional hashed-IP storage, works on Umbraco 17 and 18. |
GitHub repositories
This package is not used by any popular GitHub repositories.
v17.1.1 / v18.1.1: Version lines now follow the Umbraco major (17.x for Umbraco 17, 18.x for Umbraco 18) and each line's Umbraco.Cms.Web.Common dependency is boxed to a single major - [17.0.0, 18.0.0) and [18.0.0, 19.0.0) respectively. Previously a single net10.0 build declared [17.0.0, 19.0.0), which let a host pinned to Umbraco 17 be pulled up to Umbraco 18 whenever another package in the project graph demanded 18. Boxing the range per major prevents that cross-major drift: installing into an Umbraco 17 site always resolves the 17.x line and never forces an 18 upgrade. Umbraco 16 (the old net9.0 target) is no longer supported. No functional, API, UI or database changes - this is a packaging/compatibility change only. v1.0.1: The backoffice package manifest now ships correctly - the project uses the Razor SDK with StaticWebAssetBasePath so umbraco-package.json is packed and discovered under App_Plugins/utpro-geo-location/, and the manifest version stays in sync with the package version. No runtime changes. v1.0.0: Initial release. IP-based geolocation with CDN header detection (Cloudflare, AWS, Azure) and offline MMDB fallback. Country-to-culture mapping, Umbraco middleware integration, and configurable provider chain.