Weave Code
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

Geocoder Laravel Laravel Package

toin0u/geocoder-laravel

View on GitHub
Deep Wiki
Context7

Getting Started

Minimal Steps

  1. Installation:

    composer require toin0u/geocoder-laravel
    

    For Laravel 5.5+, auto-discovery handles the service provider registration. For older versions, add Geocoder\Laravel\Providers\GeocoderService::class to config/app.php.

  2. Publish Config (if customization is needed):

    php artisan vendor:publish --provider="Geocoder\Laravel\Providers\GeocoderService" --tag="config"
    
  3. First Use Case: Geocode an address:

    $addresses = app('geocoder')->geocode('Los Angeles, CA')->get();
    

Where to Look First

  • Configuration: config/geocoder.php (default providers, cache settings, adapter).
  • Facade/Helper: Use app('geocoder') or Geocoder::geocode() in your code.
  • Providers: Default includes GoogleMaps and GeoPlugin in a Chain. Add/remove as needed.

Implementation Patterns

Core Workflows

  1. Basic Geocoding:

    // Geocode an address
    $addresses = app('geocoder')->geocode('1600 Amphitheatre Parkway')->get();
    
    // Reverse geocode (lat, long)
    $address = app('geocoder')->reverse(37.422, -122.084)->first();
    
  2. Localized Queries:

    // Set locale globally
    $results = app('geocoder')->locale('fr')->geocode('Paris')->get();
    
    // Per-query locale
    $query = GeocodeQuery::create('Bologna')->withLocale('it');
    $results = app('geocoder')->geocodeQuery($query)->get();
    
  3. Provider-Specific Queries:

    // Use a specific provider (e.g., GoogleMaps)
    $results = app('geocoder')->using('google_maps')->geocode('Berlin')->get();
    
  4. Caching:

    • Disable caching per query:
      $results = app('geocoder')->doNotCache()->geocode('New York')->get();
      
    • Configure cache duration in config/geocoder.php (default: 9999999 seconds).
  5. Dependency Injection:

    use Geocoder\Laravel\ProviderAndDumperAggregator as Geocoder;
    
    class AddressController {
        public function __construct(private Geocoder $geocoder) {}
    
        public function show() {
            $addresses = $this->geocoder->geocode('San Francisco')->get();
        }
    }
    

Integration Tips

  • Testing: Leverage Laravel’s Http::fake() for mocking API calls:

    use Illuminate\Support\Facades\Http;
    
    Http::fake();
    $addresses = app('geocoder')->geocode('Test Address')->get();
    Http::assertSent(function ($request) {
        return $request->url() === 'https://maps.googleapis.com/...';
    });
    
  • Queueing Long-Running Geocodes: Dispatch a job for heavy geocoding tasks (e.g., bulk IP geolocation):

    GeocodeJob::dispatch('8.8.8.8')->onQueue('geocode');
    
  • Form Validation: Use Laravel’s validation rules to ensure geocodable addresses:

    $request->validate([
        'address' => 'required|geocodable', // Custom rule
    ]);
    
  • Database Storage: Store geocoded results in a model:

    $address = app('geocoder')->geocode($request->address)->first();
    Location::create([
        'latitude' => $address->getLatitude(),
        'longitude' => $address->getLongitude(),
        'formatted' => $address->getStreet(),
    ]);
    

Gotchas and Tips

Pitfalls

  1. Laravel 13 Cache Serialization:

    • Issue: Caching fails silently with __PHP_Incomplete_Class errors if cache.serializable_classes is not configured.
    • Fix: The package auto-registers geocoder model classes, but opt out with:
      'auto_register_serializable_classes' => false,
      
      in config/geocoder.php. Alternatively, disable caching per query or set cache.duration to 0.
  2. HTTPS Requirement for GoogleMaps:

    • Issue: GoogleMaps API requires HTTPS. If using an API key, ensure HTTPS is enabled in your config or environment.
    • Fix: Set 'https' => true in your GoogleMaps provider config.
  3. Rate Limits:

    • Issue: Free-tier APIs (e.g., GoogleMaps) have strict rate limits. Uncached queries may hit limits unexpectedly.
    • Fix: Implement exponential backoff in your adapter or use a local cache (Redis) with a short TTL (e.g., 3600 seconds).
  4. Provider Order in Chain:

    • Issue: The first provider in the Chain is prioritized. If it fails, subsequent providers are tried.
    • Fix: Reorder providers based on reliability/cost. Example:
      'providers' => [
          Chain::class => [
              GeoPlugin::class => [], // Cheaper, but less accurate
              GoogleMaps::class => [env('GOOGLE_MAPS_API_KEY')],
          ],
      ],
      
  5. Locale-Specific Caching:

    • Issue: Results are cached per locale. Switching locales may trigger unnecessary API calls if not cached.
    • Fix: Pre-cache common locales or use a shared cache key strategy.

Debugging Tips

  1. Log API Responses: Add middleware to log geocoder requests/responses:

    app('geocoder')->getHttpClient()->getEmitter()->attach(
        new \Geocoder\HttpAdapter\Log\LogEmitter()
    );
    
  2. Validate API Keys:

    • Test with a known invalid key to ensure errors are caught:
      $results = app('geocoder')->using('google_maps')->geocode('Test');
      // Check for exceptions or empty results
      
  3. Check Cache Keys:

    • Inspect cached keys to debug stale data:
      $cacheKey = app('geocoder')->getCache()->getPrefix() . ':geocode:Los Angeles, CA';
      
  4. Provider-Specific Errors:

    • Handle provider-specific exceptions (e.g., Geocoder\Exception\UnsupportedProvider):
      try {
          $results = app('geocoder')->using('nonexistent_provider')->geocode('Test');
      } catch (\Geocoder\Exception\UnsupportedProvider $e) {
          Log::error('Unsupported provider: ' . $e->getProvider());
      }
      

Extension Points

  1. Custom Providers:

    • Extend the Chain with a custom provider (e.g., Mapbox):
      'providers' => [
          Chain::class => [
              // Existing providers...
              \Geocoder\Provider\Mapbox::class => [env('MAPBOX_API_KEY')],
          ],
      ],
      
  2. Adapter Customization:

    • Replace the default LaravelHttpClient with a custom PSR-18 client (e.g., Guzzle with retries):
      'adapter' => [\Http\Client\Curl\Client::class => [
          null,
          null,
          [CURLOPT_TIMEOUT => 10, CURLOPT_RETRYDELAY => 5],
      ]],
      
  3. Post-Processing Results:

    • Use Laravel’s service container to modify results:
      app()->bindAfter('geocoder', function ($geocoder) {
          return new class($geocoder) {
              public function __construct(private $geocoder) {}
      
              public function geocode($query) {
                  $results = $this->geocoder->geocode($query)->get();
                  return collect($results)->map(function ($address) {
                      return (object) array_merge(
                          $address->toArray(),
                          ['custom_field' => 'value']
                      );
                  });
              }
          };
      });
      
  4. Bulk Geocoding:

    • Process batches asynchronously:
      $addresses = ['NYC', 'LA', 'Chicago'];
      foreach ($addresses as $address) {
          GeocodeJob::dispatch($address)->onQueue('geocode');
      }
      
  5. Fallback Logic:

    • Implement a fallback chain if the primary provider fails:
      $results = app('geocoder')->geocode('Rare Address')->get();
      if ($results->isEmpty()) {
          $results = app('geocoder')->using('geo_plugin')->geocode('Rare Address')->get();
      }
      
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.
apiboxsym/user-bundle
apiboxsym/health-check-bundle
jayeshmepani/jpl-moshier-ephemeris-php
elnasnato/laraliveui
labrodev/rest-sdk
sampaui/sampaui
babelqueue/php-sdk
facebook/capi-param-builder-php
babelqueue/symfony
hamzi/corewatch
minionfactory/raw-hydrator
hexters/coinpayment
rjcodes/rjcms
act-training/laravel-permissions-manager
alimarchal/laravel-chart-of-accounts
babenkoivan/elastic-scout-driver
mkwebdesign/filament-watchdog-v5
renatomarinho/laravel-page-speed
zedmagdy/filament-business-hours
renatovdemoura/blade-elements-ui