Weave Code
Weaver
Helps Laravel developers discover, compare, and choose open-source packages. See popularity, security, maintainers, and scores at a glance to make better decisions.
Feedback
Share your thoughts, report bugs, or suggest improvements.
Subject
Message

Sypex Geo Bundle Laravel Package

farit-slv/sypex-geo-bundle

Symfony bundle for Sypex Geo that resolves visitor IP addresses to country, region, and city data using the Sypex Geo database. Provides ready-made services and configuration for fast, offline IP geolocation in PHP applications.

View on GitHub
Deep Wiki
Context7

Getting Started

SypexGeo is an IP‑geolocation library backed by a binary .dat database (sxgeo.dat / SxGeoCity.dat). FaritSlv/SypexGeoBundle is a Symfony bundle that wires that library into a container service — there is no Laravel auto‑discovery, so treat it as a plain library plus a thin service wrapper.

Minimal path:

  1. composer require faritslv/sypexgeo-bundle (or just sypexgeo/sypexgeo if you only want the SxGeo class).
  2. Drop the .dat file somewhere outside public/ (e.g. storage/app/geo/SxGeoCity.dat) and point config at it via an env var, not a hardcoded path.
  3. Register it as a singleton in a service provider — the DB is parsed into memory on construction, so instantiating per request is the single biggest performance mistake.
  4. First use case: a GeoLocaleMiddleware or helper that maps the request IP to country.iso / city.name and sets locale + currency for the rest of the request.
$this->app->singleton(GeoResolver::class, fn () => new GeoResolver(
    storage_path('app/geo/SxGeoCity.dat')
));

Implementation Patterns

Wrap, don't sprinkle. Put the bundle's service behind your own GeoResolver interface (resolve(string $ip): ?GeoLocation). This lets you swap to MaxMind/ip-api later and lets you fake it in tests.

Cache per IP. Lookups are fast but not free. Cache::remember("geo:{$ip}", now()->addDay(), ...) — but normalize first: hash the IP or use it directly as the key, and skip caching for private ranges.

Fallback chain for unresolvable IPs. Local/dev traffic (127.0.0.1, 10.x, 192.168.x) returns nothing. Have an explicit contract: config‑driven default locale, X-Forwarded-For/CF-Connecting-IP header trust behind a proxy (TrustProxies), and a null return rather than a thrown exception.

Batch enrichment. For backfilling geo onto existing users/orders rows, don't call the resolver inside a model accessor. Chunk jobs (->chunkById(1000)) and write the resolved country/city as plain columns — you want to query and index on those later without re-resolving.

Data refresh as a scheduled task. The bundled DB goes stale quarterly. Keep the file out of git, download it in a deploy step or a scheduled command, write to a temp file, then atomically rename() over the live path so in‑flight requests never see a half‑written DB. Bust any long‑lived cache keys on refresh.

Config over code. Path, load mode, and default locale belong in config/geo.php reading from env. The bundle's own config is Symfony YAML — you'll be translating it, so keep it in one place.

Gotchas and Tips

  • Memory footprint. SxGeoCity.dat is large (tens to hundreds of MB depending on edition). Loading it fully into memory per PHP‑FPM worker is fine on a big box and terrible on a small one — check the library's load mode (memory vs. file handle) against your worker count. Under Octane this is loaded once; under classic FPM it's once per request lifecycle.
  • This is a Symfony bundle. Don't expect php artisan vendor:publish. Either use the underlying SxGeo class directly or register the bundle's service manually. The Symfony‑style services.yaml config won't apply.
  • IPv6 coverage is weak in the free editions, and city‑level accuracy drops sharply outside Russia/CIS. Do not build tax, legal, or compliance logic on city precision — use country‑level only, and even then treat it as a hint.
  • Never trust the client IP without TrustProxies configured; behind a load balancer the raw REMOTE_ADDR is your balancer.
  • Check the data licence before shipping — Sypex Geo's terms differ from MaxMind's and are stricter for redistributing the DB inside your artifact.
  • Testing. Bind a stub GeoResolver in the container returning a fixed country; never let the real .dat file into CI.
  • On 2.0.3: this is a patch bump from 2.0.2 with no published changelog beyond a diff link. Nothing in the notes suggests breaking changes, new features, or deprecations, so it should be a drop‑in for existing 2.x installs — but since the diff is the only source of truth, pin the version, skim the compare link, and run your geo smoke test (one known IP → expected country) before rolling it out.
Weaver

How can I help you explore Laravel packages today?

Conversation history is not saved when not logged in.
Prompt
Add packages to context
No packages found.
mrnewport/laravel-plaid
mrnewport/laravel-repo
mrnewport/laravel-docsign
mrnewport/laravel-stow
mrnewport/laravel-flow
mrnewport/laravel-priceable
mrnewport/laravel-nestedterms
fredmeng/laravel-apidoc-generator
itstructure/laravel-multilingual-tools
pdustdar/elasticsearch
markupai/php-sdk
rlacerda83/lumem-microservice-shipment
uni-method/symfony-lib
tacticmedia/scim-server-bundle
neika-ai/symfony-bundle
mattleads/agent-publishing-bundle
glavweb/framework-bundle
glavweb/extra-bundle
glavweb/api-bundle
glavweb/admin-bundle