Browse 1000+ Public APIs

8 Best Free Geocoding APIs for Location-Based Apps in 2026

a month ago

Building a location-based app? Geocoding APIs convert addresses to coordinates (and vice versa), enabling maps, delivery tracking, and location search. This guide compares the best free geocoding APIs for developers in 2026.

Quick Comparison Table

Provider Free Tier Rate Limit Best For
Google Maps $200/mo credit 50 req/sec Accuracy
Mapbox 100K req/mo 600 req/min Modern apps
OpenCage 2,500 req/day 1 req/sec Privacy
Nominatim Unlimited 1 req/sec Open source
HERE 250K req/mo 5 req/sec Enterprise
LocationIQ 5K req/day 2 req/sec Budget
Geoapify 3K req/day 5 req/sec EU data
Positionstack 25K req/mo - Simple

1. Google Maps Geocoding API

Google Maps offers the most accurate geocoding with comprehensive global coverage.

Free Tier:

  • $200 monthly credit (covers ~40,000 geocode requests)
  • Pay-as-you-go after credit
  • No credit card for first $200

Pricing (after free credit):

  • 0-100K requests: $5/1,000
  • 100K-500K: $4/1,000

Key Features:

  • Industry-leading accuracy
  • 200+ countries
  • Place autocomplete
  • Place details
  • Component filtering
  • Address validation

JavaScript Example:

const axios = require('axios');

const GOOGLE_API_KEY = process.env.GOOGLE_MAPS_API_KEY;

async function geocode(address) {
  const response = await axios.get(
    'https://maps.googleapis.com/maps/api/geocode/json',
    {
      params: {
        address,
        key: GOOGLE_API_KEY
      }
    }
  );

  if (response.data.status !== 'OK') {
    throw new Error(`Geocoding failed: ${response.data.status}`);
  }

  const result = response.data.results[0];
  return {
    formattedAddress: result.formatted_address,
    lat: result.geometry.location.lat,
    lng: result.geometry.location.lng,
    placeId: result.place_id,
    components: result.address_components
  };
}

// Usage
const location = await geocode('1600 Amphitheatre Parkway, Mountain View, CA');
console.log(location);
// { lat: 37.4224764, lng: -122.0842499, ... }

Reverse Geocoding:

async function reverseGeocode(lat, lng) {
  const response = await axios.get(
    'https://maps.googleapis.com/maps/api/geocode/json',
    {
      params: {
        latlng: `${lat},${lng}`,
        key: GOOGLE_API_KEY
      }
    }
  );

  if (response.data.status !== 'OK') {
    throw new Error(`Reverse geocoding failed: ${response.data.status}`);
  }

  return response.data.results[0].formatted_address;
}

const address = await reverseGeocode(37.4224764, -122.0842499);
// "1600 Amphitheatre Pkwy, Mountain View, CA 94043, USA"

With Component Filtering:

// Restrict to specific country
const response = await axios.get(
  'https://maps.googleapis.com/maps/api/geocode/json',
  {
    params: {
      address: 'Paris',
      components: 'country:FR',
      key: GOOGLE_API_KEY
    }
  }
);

Best For: Apps requiring the highest accuracy and global coverage.

Get API Key →


2. Mapbox Geocoding API

Mapbox provides beautiful maps with powerful geocoding and a generous free tier.

Free Tier:

  • 100,000 requests/month
  • No credit card required
  • Permanent places search
  • Batch geocoding (50K/mo)

Key Features:

  • Forward and reverse geocoding
  • Autocomplete/typeahead
  • Batch geocoding
  • Custom data integration
  • Bias by proximity
  • Language support

JavaScript Example:

const mbxGeocoding = require('@mapbox/mapbox-sdk/services/geocoding');

const geocodingClient = mbxGeocoding({
  accessToken: process.env.MAPBOX_ACCESS_TOKEN
});

async function geocode(query) {
  const response = await geocodingClient.forwardGeocode({
    query,
    limit: 1,
    types: ['address', 'place']
  }).send();

  const feature = response.body.features[0];
  return {
    placeName: feature.place_name,
    coordinates: feature.center, // [lng, lat]
    context: feature.context
  };
}

// Usage
const result = await geocode('Empire State Building, New York');
console.log(result.coordinates);
// [-73.9857, 40.7484]

Autocomplete Search:

async function searchPlaces(query, proximity) {
  const response = await geocodingClient.forwardGeocode({
    query,
    autocomplete: true,
    limit: 5,
    proximity: proximity, // [lng, lat] to bias results
    types: ['poi', 'address', 'place']
  }).send();

  return response.body.features.map(f => ({
    name: f.place_name,
    coordinates: f.center,
    category: f.properties.category
  }));
}

// Search near user's location
const suggestions = await searchPlaces('coffee', [-73.99, 40.73]);

Batch Geocoding:

async function batchGeocode(addresses) {
  // Mapbox batch geocoding via their API
  const requests = addresses.map(addr =>
    geocodingClient.forwardGeocode({ query: addr, limit: 1 }).send()
  );

  const results = await Promise.all(requests);
  return results.map((r, i) => ({
    input: addresses[i],
    result: r.body.features[0]?.center || null
  }));
}

Best For: Modern web apps with maps integration.

Get Access Token →


3. OpenCage Geocoding API

OpenCage aggregates multiple data sources with a focus on privacy and GDPR compliance.

Free Tier:

  • 2,500 requests/day
  • No credit card required
  • HTTPS included
  • All features available

Key Features:

  • Multiple data sources (OSM, government data)
  • GDPR compliant
  • No tracking
  • Annotations (timezone, currency, etc.)
  • Bounds filtering
  • 100+ languages

JavaScript Example:

const opencage = require('opencage-api-client');

async function geocode(address) {
  const response = await opencage.geocode({
    q: address,
    key: process.env.OPENCAGE_API_KEY
  });

  if (response.results.length === 0) {
    throw new Error('No results found');
  }

  const result = response.results[0];
  return {
    formatted: result.formatted,
    lat: result.geometry.lat,
    lng: result.geometry.lng,
    confidence: result.confidence,
    annotations: result.annotations
  };
}

const location = await geocode('Brandenburg Gate, Berlin');
console.log(location.annotations.timezone);
// { name: "Europe/Berlin", offset_string: "+0100", ... }

With Bounds Filtering:

const response = await opencage.geocode({
  q: 'Main Street',
  key: process.env.OPENCAGE_API_KEY,
  bounds: '-122.5,37.5,-122.0,38.0', // SW lng,lat to NE lng,lat
  countrycode: 'us',
  limit: 5
});

Annotations Example:

// OpenCage provides rich annotations
const result = await geocode('Tokyo, Japan');

console.log(result.annotations);
// {
//   currency: { iso_code: "JPY", symbol: "¥" },
//   timezone: { name: "Asia/Tokyo", offset_sec: 32400 },
//   sun: { rise: { apparent: 1706, ... }, set: { ... } },
//   what3words: { words: "skirt.presented.ranger" },
//   flag: "🇯🇵"
// }

Best For: Privacy-focused apps and GDPR compliance.

Get API Key →


4. Nominatim (OpenStreetMap)

Nominatim is the free geocoding service powered by OpenStreetMap data.

Free Tier:

  • Unlimited (with rate limits)
  • 1 request/second
  • No API key required
  • Self-hosting available

Key Features:

  • Completely free
  • OpenStreetMap data
  • Self-hostable
  • Good for open source projects
  • Structured queries
  • Address parsing

JavaScript Example:

const axios = require('axios');

// Using public Nominatim (respect rate limits!)
async function geocode(address) {
  const response = await axios.get(
    'https://nominatim.openstreetmap.org/search',
    {
      params: {
        q: address,
        format: 'json',
        limit: 1,
        addressdetails: 1
      },
      headers: {
        'User-Agent': 'YourApp/1.0 (your@email.com)' // Required!
      }
    }
  );

  if (response.data.length === 0) {
    throw new Error('No results found');
  }

  const result = response.data[0];
  return {
    displayName: result.display_name,
    lat: parseFloat(result.lat),
    lon: parseFloat(result.lon),
    address: result.address,
    type: result.type
  };
}

const location = await geocode('Eiffel Tower, Paris');

Reverse Geocoding:

async function reverseGeocode(lat, lon) {
  const response = await axios.get(
    'https://nominatim.openstreetmap.org/reverse',
    {
      params: {
        lat,
        lon,
        format: 'json',
        addressdetails: 1
      },
      headers: {
        'User-Agent': 'YourApp/1.0 (your@email.com)'
      }
    }
  );

  return {
    displayName: response.data.display_name,
    address: response.data.address
  };
}

Structured Query:

// More precise results with structured query
const response = await axios.get(
  'https://nominatim.openstreetmap.org/search',
  {
    params: {
      street: '221B Baker Street',
      city: 'London',
      country: 'UK',
      format: 'json'
    },
    headers: {
      'User-Agent': 'YourApp/1.0'
    }
  }
);

Best For: Open source projects and self-hosted solutions.

Documentation →


5. HERE Geocoding API

HERE offers enterprise-grade geocoding with a generous free tier.

Free Tier:

  • 250,000 requests/month
  • All geocoding features
  • No credit card required

Key Features:

  • Autosuggest
  • Batch geocoding
  • Address parsing
  • Quality scores
  • Enterprise SLAs
  • Traffic integration

JavaScript Example:

const axios = require('axios');

const HERE_API_KEY = process.env.HERE_API_KEY;

async function geocode(address) {
  const response = await axios.get(
    'https://geocode.search.hereapi.com/v1/geocode',
    {
      params: {
        q: address,
        apiKey: HERE_API_KEY
      }
    }
  );

  const item = response.data.items[0];
  return {
    title: item.title,
    position: item.position,
    address: item.address,
    scoring: item.scoring
  };
}

const result = await geocode('Statue of Liberty, New York');
console.log(result.position);
// { lat: 40.68927, lng: -74.04445 }

Autosuggest (Typeahead):

async function autosuggest(query, location) {
  const response = await axios.get(
    'https://autosuggest.search.hereapi.com/v1/autosuggest',
    {
      params: {
        q: query,
        at: `${location.lat},${location.lng}`,
        limit: 5,
        apiKey: HERE_API_KEY
      }
    }
  );

  return response.data.items.map(item => ({
    title: item.title,
    address: item.address?.label,
    position: item.position,
    distance: item.distance
  }));
}

Best For: Enterprise apps needing reliability and SLAs.

Get API Key →


6. LocationIQ

LocationIQ provides affordable geocoding using OpenStreetMap data with added features.

Free Tier:

  • 5,000 requests/day
  • 2 requests/second
  • All basic features

Key Features:

  • OSM-based data
  • Balance API
  • Autocomplete
  • Nearby POI search
  • Affordable paid plans
  • Static maps

JavaScript Example:

const axios = require('axios');

const LOCATIONIQ_KEY = process.env.LOCATIONIQ_KEY;

async function geocode(address) {
  const response = await axios.get(
    'https://us1.locationiq.com/v1/search',
    {
      params: {
        key: LOCATIONIQ_KEY,
        q: address,
        format: 'json',
        limit: 1
      }
    }
  );

  const result = response.data[0];
  return {
    displayName: result.display_name,
    lat: parseFloat(result.lat),
    lon: parseFloat(result.lon),
    importance: result.importance
  };
}

Autocomplete:

async function autocomplete(query) {
  const response = await axios.get(
    'https://api.locationiq.com/v1/autocomplete',
    {
      params: {
        key: LOCATIONIQ_KEY,
        q: query,
        limit: 5,
        dedupe: 1
      }
    }
  );

  return response.data;
}

Best For: Budget-conscious developers needing reliable geocoding.

Get API Key →


7. Geoapify

Geoapify offers geocoding with a focus on European data and GDPR compliance.

Free Tier:

  • 3,000 requests/day
  • Batch geocoding included
  • All features available

Key Features:

  • European focus
  • GDPR compliant
  • Batch geocoding
  • Address autocomplete
  • Isochrones
  • Routing

JavaScript Example:

const axios = require('axios');

const GEOAPIFY_KEY = process.env.GEOAPIFY_KEY;

async function geocode(address) {
  const response = await axios.get(
    'https://api.geoapify.com/v1/geocode/search',
    {
      params: {
        text: address,
        apiKey: GEOAPIFY_KEY,
        format: 'json'
      }
    }
  );

  const result = response.data.results[0];
  return {
    formatted: result.formatted,
    lat: result.lat,
    lon: result.lon,
    country: result.country,
    timezone: result.timezone
  };
}

Batch Geocoding:

async function batchGeocode(addresses) {
  const response = await axios.post(
    `https://api.geoapify.com/v1/batch/geocode/search?apiKey=${GEOAPIFY_KEY}`,
    addresses, // Array of address strings
    {
      headers: { 'Content-Type': 'application/json' }
    }
  );

  // Returns a job URL for async processing
  return response.data.url;
}

Best For: European apps and batch processing needs.

Get API Key →


8. Positionstack

Positionstack offers simple, straightforward geocoding with a generous free tier.

Free Tier:

  • 25,000 requests/month
  • Forward geocoding
  • Reverse geocoding
  • Basic features

Key Features:

  • Simple API
  • No credit card required
  • Global coverage
  • JSON/XML output
  • Batch requests (paid)

JavaScript Example:

const axios = require('axios');

const ACCESS_KEY = process.env.POSITIONSTACK_KEY;

async function geocode(address) {
  const response = await axios.get(
    'http://api.positionstack.com/v1/forward',
    {
      params: {
        access_key: ACCESS_KEY,
        query: address,
        limit: 1
      }
    }
  );

  const result = response.data.data[0];
  return {
    label: result.label,
    latitude: result.latitude,
    longitude: result.longitude,
    country: result.country,
    region: result.region
  };
}

const location = await geocode('1600 Pennsylvania Avenue, Washington DC');

Best For: Simple projects needing basic geocoding.

Get API Key →


Geocoding Best Practices

1. Cache Results

const NodeCache = require('node-cache');
const cache = new NodeCache({ stdTTL: 86400 }); // 24 hour cache

async function geocodeWithCache(address) {
  const cacheKey = `geo:${address.toLowerCase().trim()}`;

  const cached = cache.get(cacheKey);
  if (cached) return cached;

  const result = await geocode(address);
  cache.set(cacheKey, result);

  return result;
}

2. Handle Rate Limits

const Bottleneck = require('bottleneck');

const limiter = new Bottleneck({
  minTime: 1000, // 1 request per second
  maxConcurrent: 1
});

const rateLimitedGeocode = limiter.wrap(geocode);

// Use rate-limited version
const results = await Promise.all(
  addresses.map(addr => rateLimitedGeocode(addr))
);

3. Validate Coordinates

function isValidCoordinate(lat, lng) {
  return (
    typeof lat === 'number' &&
    typeof lng === 'number' &&
    lat >= -90 && lat <= 90 &&
    lng >= -180 && lng <= 180 &&
    !isNaN(lat) && !isNaN(lng)
  );
}

Choosing the Right Geocoding API

Need Recommended
Best accuracy Google Maps
Free + accurate Mapbox
Privacy/GDPR OpenCage
Completely free Nominatim
Enterprise HERE
Budget LocationIQ
Europe focus Geoapify
Simple projects Positionstack

Conclusion

For most developers, Mapbox offers the best balance of free tier limits and accuracy. If accuracy is critical, Google Maps remains the gold standard. For privacy-focused applications, OpenCage or self-hosted Nominatim are excellent choices.

Related Resources: