Volver al blog
Guías y tutoriales2025-08-31·8 min de lectura

Extraer datos de Google Maps con JavaScript: Guía completa

Por Ibrahim DemolCEO IBLeadActualizado el 26 de marzo de 2026

Google Maps contiene más de 5 millones de fichas comerciales. Cada ficha = dirección, teléfono, opiniones, horarios, fotos, sitio web. Es una mina de oro para la prospección, el estudio de mercado y el análisis competitivo.

Pero, ¿cómo extraer estos datos a gran escala? Existen tres enfoques: la API oficial de Google Maps, el web scraping personalizado en JavaScript o una herramienta dedicada. Este artículo cubre las tres — con sus costos reales, límites y cuándo usar cada una.


¿Por qué extraer datos de Google Maps?

Antes de entrar en la técnica, aclara tu necesidad. Los casos de uso no son los mismos.

Prospección comercial

Una agencia de limpieza quiere encontrar 500 restaurantes en un radio de 10 km. Exporta: nombre, dirección, teléfono, email. Realiza llamadas en frío dirigidas.

Necesidad: datos básicos (nombre, contacto), rapidez, volumen medio.

Análisis competitivo

Un restaurador analiza 50 restaurantes competidores: opiniones en Google, número de opiniones, horarios, precios (a través del sitio web), fotos, tecnologías utilizadas (¿usan Uber Eats? ¿Deliveroo? ¿Su propio sitio?).

Necesidad: datos enriquecidos (opiniones, stack tecnológico), contexto, volumen bajo a medio.

Estudio de mercado

Un franquiciador analiza más de 1,000 peluquerías en Francia para identificar las zonas desatendidas. Extrae: localización, calificación en Google, número de opiniones, horarios, ficha reclamada o no.

Necesidad: datos estructurados, filtrado avanzado, alto volumen, actualización mensual.

Detección de leads calificados

Una agencia de SEO busca restaurantes con calificación < 3 estrellas (clientes potenciales insatisfechos). Exporta aquellos con más de 50 opiniones (tamaño significativo) y sitio web sin Google Analytics.

Necesidad: opiniones en Google (texto + calificación + fecha), detección de tecnologías, filtros complejos, volumen medio.

Cada caso de uso implica un enfoque diferente. Veamos las opciones.


Opción 1: La API oficial de Google Maps JavaScript

Google ofrece una API JavaScript gratuita (con cuotas). Funciona en el navegador o en Node.js del lado del servidor.

Funcionalidades básicas

La API de Google Maps JavaScript permite 3 cosas principales:

  1. Geocodificación: convertir una dirección → coordenadas GPS
  2. Places API: buscar lugares (restaurantes, fontaneros, etc.) alrededor de una posición
  3. Detalles del lugar: recuperar la información detallada de un lugar (opiniones, horarios, fotos, URL, etc.)

Paso 1: Obtener una clave API

  1. Ve a Google Cloud Console
  2. Crea un proyecto
  3. Activa estas APIs: - Maps JavaScript API - Places API - Geocoding API
  4. Crea una clave API (tipo: clave de navegador o servidor según tu uso)
  5. Configura las restricciones (dominios permitidos, cuotas)

Importante: Google cobra más allá de las cuotas gratuitas. Por defecto: 25,000 llamadas/día gratuitas para Places, luego €0.017 por llamada.

Paso 2: Implementar la Geocodificación

Convertir una dirección en latitud/longitud.

const geocoder = new google.maps.Geocoder();

geocoder.geocode(
  { address: '75 Rue de Rivoli, Paris' },
  (results, status) => {
    if (status === 'OK') {
      const lat = results[0].geometry.location.lat();
      const lng = results[0].geometry.location.lng();
      console.log(`Coordenadas: ${lat}, ${lng}`);
    } else {
      console.error(`Error: ${status}`);
    }
  }
);

Encontrar todos los restaurantes en un radio de 5 km alrededor de París.

const map = new google.maps.Map(document.getElementById('map'), {
  center: { lat: 48.8566, lng: 2.3522 }, // París
  zoom: 15
});

const service = new google.maps.places.PlacesService(map);

const request = {
  location: new google.maps.LatLng(48.8566, 2.3522),
  radius: 5000, // 5 km
  type: 'restaurant',
  keyword: 'pizza' // Opcional: filtrar por palabra clave
};

service.nearbySearch(request, (results, status) => {
  if (status === google.maps.places.PlacesServiceStatus.OK) {
    results.forEach(place => {
      console.log(`${place.name} - ${place.vicinity}`);
    });
  }
});

Limitación importante: nearbySearch() devuelve máx 60 resultados por consulta, con paginación. Para obtener 500 restaurantes, debes hacer 9 consultas.

Paso 4: Recuperar los detalles completos (Place Details)

Cada lugar devuelto por nearbySearch() tiene un place_id. Úsalo para obtener los detalles completos.

const request = {
  placeId: 'ChIJIQBpAG2ahYAR_6128GltTXQ', // Ejemplo: Torre Eiffel
  fields: [
    'name',
    'formatted_address',
    'formatted_phone_number',
    'website',
    'opening_hours',
    'reviews',
    'rating',
    'user_ratings_total',
    'photos'
  ]
};

service.getDetails(request, (place, status) => {
  if (status === google.maps.places.PlacesServiceStatus.OK) {
    console.log(`Nombre: ${place.name}`);
    console.log(`Dirección: ${place.formatted_address}`);
    console.log(`Teléfono: ${place.formatted_phone_number}`);
    console.log(`Sitio web: ${place.website}`);
    console.log(`Calificación: ${place.rating} (${place.user_ratings_total} opiniones)`);
    console.log(`Horarios:`, place.opening_hours.weekday_text);

    // Opiniones en Google
    place.reviews.forEach(review => {
      console.log(`${review.author_name}: ${review.rating}/5 - "${review.text}"`);
    });
  }
});

Costos reales de la API de Google Maps

Operación Cuota gratuita Precio más allá
Geocodificación 25,000/día €0.005 por llamada
Nearby Search 25,000/día €0.032 por llamada
Place Details 25,000/día €0.017 por llamada
Búsqueda de texto 25,000/día €0.032 por llamada

Ejemplo real: extraer 1,000 restaurantes con detalles completos.

  • 1,000 Nearby Search = 17 llamadas (máx 60 resultados/llamada) = €0.54
  • 1,000 Place Details = €17

Total: ~€17.50 por 1,000 restaurantes.

Parece poco, pero: - Debes hacerlo cada mes para las actualizaciones - Estás limitado a 60 resultados por consulta (difícil de paginar) - Las opiniones en Google devueltas son limitadas (máx 5 por lugar) - No obtienes las tecnologías detectadas (WordPress, Shopify, etc.)

Límites de la API de Google Maps JavaScript

Limitación Impacto
Máx 60 resultados por consulta Paginación manual compleja
Máx 5 opiniones por lugar No hay análisis completo de opiniones
No hay filtrado por calificación en Google Recuperas todos los resultados
No hay filtrado por número de opiniones No hay enfoque en las fichas "maduras"
No hay detección de tecnologías No sabes si el sitio usa WordPress, Shopify, etc.
No hay datos SIRET (Francia) No hay enriquecimiento jurídico/financiero
Cuotas limitadas Costos que aumentan rápidamente a gran escala

Opción 2: Web scraping personalizado en JavaScript con Puppeteer

Si deseas eludir los límites de la API oficial, puedes hacer scraping directamente del sitio de Google Maps con Puppeteer (una biblioteca de Node.js que automatiza un navegador Chrome).

¿Por qué Puppeteer?

Puppeteer lanza un navegador Chrome automatizado, va a Google Maps, simula clics/desplazamientos y extrae el HTML. Así puedes recuperar más de 60 resultados, las opiniones completas, las fotos, etc.

Instalación

npm install puppeteer

Ejemplo: Scraper los restaurantes de París

const puppeteer = require('puppeteer');

(async () => {
  const browser = await puppeteer.launch();
  const page = await browser.newPage();

  // Ir a Google Maps
  await page.goto('https://www.google.com/maps/search/restaurants+paris', {
    waitUntil: 'networkidle2'
  });

  // Esperar a que se carguen los resultados
  await page.waitForSelector('[role="listitem"]');

  // Desplazar para cargar más resultados
  const resultsContainer = await page.$('[role="main"]');
  for (let i = 0; i < 5; i++) {
    await resultsContainer.evaluate(el => {
      el.scrollTop = el.scrollHeight;
    });
    await page.waitForTimeout(1000); // Esperar a que se cargue
  }

  // Extraer los datos
  const restaurants = await page.evaluate(() => {
    const items = document.querySelectorAll('[role="listitem"]');
    return Array.from(items).map(item => {
      const nameEl = item.querySelector('[role="heading"]');
      const ratingEl = item.querySelector('[aria-label*="estrella"]');
      const addressEl = item.querySelector('[data-item-id*="address"]');

      return {
        name: nameEl ? nameEl.textContent : 'N/A',
        rating: ratingEl ? ratingEl.getAttribute('aria-label') : 'N/A',
        address: addressEl ? addressEl.textContent : 'N/A'
      };
    });
  });

  console.log(restaurants);

  await browser.close();
})();

Problemas con este enfoque

  1. Google bloquea rápidamente: Después de 10-20 consultas, Google detecta el scraping y te pide que confirmes que no eres un robot (CAPTCHA).

  2. Mantenimiento constante: Google cambia su HTML regularmente. Tu código se rompe cada 2-3 meses.

  3. Lento: Puppeteer debe lanzar un navegador completo para cada búsqueda. Hacer scraping de 10,000 restaurantes = 10,000 navegadores lanzados = horas de ejecución.

  4. Costoso en recursos: Cada navegador consume 100-200 MB de RAM. Hacer scraping en paralelo = servidor potente requerido.

  5. En contra de los términos de uso: Google prohíbe explícitamente el scraping de Maps.

Veredicto: Puppeteer funciona para pruebas puntuales (50-100 resultados), no para una extracción a gran escala.


Opción 3: Utilizar una herramienta dedicada (sin código)

Esta es la solución más pragmática para el 95% de los casos de uso. En lugar de codificar, utilizas una herramienta que:

  • Gestiona la extracción a gran escala
  • Elude los bloqueos de Google
  • Devuelve los datos estructurados (CSV, JSON, API)
  • Incluye las opiniones completas de Google
  • Detecta las tecnologías utilizadas
  • Actualiza los datos mensualmente

¿Por qué una herramienta dedicada?

Criterio API de Google Puppeteer Herramienta dedicada
Costo por 10,000 resultados €170+ Gratis (pero lento) €44-99/mes
Tiempo para 10,000 resultados 2-3 días (cuotas) 4-6 horas 5 minutos
Opiniones completas de Google Máx 5 por lugar
Filtrado por calificación en Google No No
Detección de tecnologías No No
Mantenimiento Alto (cambios en la API) Alto (cambios en HTML) Cero
Bloqueo de Google Raro Frecuente Nunca

Casos de uso prácticos con JavaScript

A continuación, 3 escenarios reales y cómo implementarlos.

Caso 1: Buscar 50 fontaneros en Lyon con la API de Google Maps

Necesidad: nombre, dirección, teléfono, sitio web, calificación. Volumen bajo. Presupuesto limitado.

Solución: API oficial de Google Maps.

async function findPlumbers(city, limit = 50) {
  const geocoder = new google.maps.Geocoder();

  // Geocodificar la ciudad
  const cityCoords = await new Promise((resolve) => {
    geocoder.geocode({ address: city }, (results) => {
      resolve(results[0].geometry.location);
    });
  });

  const map = new google.maps.Map(document.getElementById('map'), {
    center: cityCoords,
    zoom: 12
  });

  const service = new google.maps.places.PlacesService(map);
  const allResults = [];

  // Hacer múltiples consultas (máx 60 por consulta)
  for (let i = 0; i < Math.ceil(limit / 60); i++) {
    const results = await new Promise((resolve) => {
      service.nearbySearch(
        {
          location: cityCoords,
          radius: 15000,
          type: 'plumber',
          pageToken: i === 0 ? null : nextPageToken
        },
        (results, status, pagination) => {
          nextPageToken = pagination.nextPage ? pagination.nextPageToken : null;
          resolve(results || []);
        }
      );
    });

    allResults.push(...results);
    if (allResults.length >= limit) break;
  }

  // Recuperar los detalles para cada resultado
  const details = await Promise.all(
    allResults.slice(0, limit).map(place => {
      return new Promise((resolve) => {
        service.getDetails(
          {
            placeId: place.place_id,
            fields: ['name', 'formatted_address', 'formatted_phone_number', 'website', 'rating']
          },
          (place) => resolve(place)
        );
      });
    })
  );

  return details.map(p => ({
    name: p.name,
    address: p.formatted_address,
    phone: p.formatted_phone_number,
    website: p.website,
    rating: p.rating
  }));
}

// Uso
findPlumbers('Lyon').then(plumbers => {
  console.table(plumbers);
  // Exportar a CSV
  downloadCSV(plumbers);
});

Costo: ~€0.50 (17 consultas Nearby + 50 Place Details)

Tiempo: 30 segundos

Limitación: No sabes cuáles están reclamadas, cuántas opiniones tienen, o si utilizan un sitio personalizado/Wix/Squarespace.


Caso 2: Analizar 200 restaurantes competidores (opiniones, tecnologías)

Necesidad: opiniones completas, calificación, número de opiniones, tecnologías utilizadas. Volumen medio. Presupuesto medio.

Solución: Herramienta dedicada (la API de Google Maps solo da un máximo de 5 opiniones).

Con una herramienta, exportas en 5 minutos:

Nombre,Dirección,Calificación,Número de opiniones,Opiniones (texto),Opiniones (fecha),Opiniones (autor),Sitio web,Tecnologías detectadas
Le Jules Verne,5 Rue Eiffel,4.8,1250,"Excelente relación calidad/precio",2024-01-15,Pierre M.,lejulesverne.fr,"WordPress, WooCommerce, Google Analytics"
Septime,80 Rue Charonne,4.7,890,"Servicio impecable",2024-01-14,Marie D.,septimeparis.com,"Personalizado, Shopify"

Entonces puedes: - Identificar los restaurantes bien calificados (4.5+) con más de 500 opiniones (tamaño significativo) - Leer las opiniones negativas para identificar los puntos débiles de los competidores - Ver qué restaurantes utilizan Shopify (venden en línea) vs WordPress (sitio personalizado)


Caso 3: Prospección ABM — Encontrar 500 restaurantes con sitio sin Google Analytics

Necesidad: restaurantes de tamaño medio (50-200 opiniones), calificación 3.5+, sitio web sin Google Analytics (lead potencial para agencia de SEO/analytics).

Solución: Herramienta dedicada con filtros avanzados y detección de tecnologías.

```javascript // Pseudo-código (la API de Google Maps no puede hacer esto) const restaurants = await tool.search({ location: 'Francia', category: 'restaurant', minRating: 3.5, minReviews: 50, maxReviews: 200, hasWebsite: true, missingTechnology: 'Google Analytics' // EXCLUSIVO });

// Resultado: 500 restaurantes calificados // Los contactas con: "Hemos visto que su sitio no tiene"

¿Listo para empezar?

Accede a todas las empresas de Google Maps, enriquecidas con emails y datos legales.

Prueba IBLead gratis