Geo-Coder-GeoApify
view release on metacpan or search on metacpan
lib/Geo/Coder/GeoApify.pm view on Meta::CPAN
use Geo::Coder::GeoApify;
my $geo_coder = Geo::Coder::GeoApify->new(apiKey => $ENV{'GEOAPIFY_KEY'});
my $location = $geo_coder->geocode(location => '10 Downing St., London, UK');
=head1 DESCRIPTION
Geo::Coder::GeoApify provides an interface to https://www.geoapify.com/maps-api/,
a free Geo-Coding database covering many countries.
=over 4
=item * Caching
Identical geocode requests are cached (using L<CHI> or a user-supplied caching object),
reducing the number of HTTP requests to the API and speeding up repeated queries.
This module leverages L<CHI> for caching geocoding responses.
When a geocode request is made,
a cache key is constructed from the request.
If a cached response exists,
it is returned immediately,
avoiding unnecessary API calls.
=item * Rate-Limiting
A minimum interval between successive API calls can be enforced to ensure that the API is not overwhelmed and to comply with any request throttling requirements.
Rate-limiting is implemented using L<Time::HiRes>.
A minimum interval between API
calls can be specified via the C<min_interval> parameter in the constructor.
Before making an API call,
the module checks how much time has elapsed since the
last request and,
if necessary,
sleeps for the remaining time.
=back
=head1 METHODS
=head2 new
$geo_coder = Geo::Coder::GeoApify->new(apiKey => $ENV{'GEOAPIFY_KEY'});
Creates a new C<Geo::Coder::GeoApify> object with the provided apiKey.
It takes several optional parameters:
=over 4
=item * C<cache>
A caching object.
If not provided,
an in-memory cache is created with a default expiration of one hour.
=item * C<host>
The API host endpoint.
Defaults to L<https://api.geoapify.com/v1/geocode>.
=item * C<min_interval>
Minimum number of seconds to wait between API requests.
Defaults to C<0> (no delay).
Use this option to enforce rate-limiting.
=item * C<ua>
An object to use for HTTP requests.
If not provided, a default user agent is created.
=back
=cut
sub new
{
my $class = shift;
# Handle hash or hashref arguments
my %args = (ref($_[0]) eq 'HASH') ? %{$_[0]} : @_;
# Ensure the correct instantiation method is used
unless (defined $class) {
carp(__PACKAGE__, ' Use ->new() not ::new() to instantiate');
return;
}
# If $class is an object, clone it with new arguments
return bless { %{$class}, %args }, ref($class) if ref($class);
# Validate that the apiKey is provided and is a scalar
my $apiKey = $args{'apiKey'};
unless (defined $apiKey && !ref($apiKey)) {
carp(__PACKAGE__, defined $apiKey ? ' apiKey must be a scalar' : ' apiKey not given');
return;
}
# Set up user agent (ua) if not provided
my $ua = $args{'ua'} // LWP::UserAgent->new(agent => __PACKAGE__ . "/$VERSION");
$ua->default_header(accept_encoding => 'gzip,deflate');
$ua->env_proxy(1);
# Disable SSL verification if the host is not defined (not recommended in production)
$ua->ssl_opts(verify_hostname => 0) unless defined $args{'host'};
# Set host, defaulting to 'api.geoapify.com/v1/geocode'
my $host = $args{'host'} // 'api.geoapify.com/v1/geocode';
# Set up caching (default to an in-memory cache if none provided)
my $cache = $args{cache} || CHI->new(
driver => 'Memory',
global => 1,
expires_in => '1 day',
);
# Set up rate-limiting: minimum interval between requests (in seconds)
my $min_interval = $args{min_interval} || 0; # default: no delay
( run in 1.486 second using v1.01-cache-2.11-cpan-140bd7fdf52 )