La consulta nunca cambia; lo que cambia es el rectángulo. Concatenar la ciudad al texto —«tatuajes Madrid»— introduce el sesgo del buscador y hace que el resultado dependa de una frase. Aquí todas las celdas envían la misma consulta, tatuajes, y cada búsqueda queda restringida con locationRestriction.rectangle al perímetro exacto de su celda. Así la cobertura es completa y comparable: si una celda sale vacía, es que no hay negocios ahí, no que mi frase estaba mal escrita.
Y esto está probado. La prueba de extremo a extremo intercepta la petición, comprueba que el texto enviado es exactamente tatuajes y que el rectángulo corresponde a la celda, y luego hace la aserción que de verdad vale: si le quito el token de paginación, el cuerpo de la segunda página es idéntico al de la primera. No es una convención que espero respetar, es una igualdad que el test rompe si alguien la rompe.
La retícula no es una cuadrícula uniforme. Se construye a partir del Nomenclátor Geográfico de Municipios y Entidades de Población del CNIG: se descarga el ZIP nacional, el programa localiza solo el fichero de entidades —admite también el de municipios o una carpeta, y acepta que le arrastres el ZIP a la ventana— y genera una retícula adaptativa. Conserva núcleos con población mayor que cero, evita contar varias veces la jerarquía municipio-capital-entidad-núcleo, garantiza al menos un punto por municipio habitado, hace celdas pequeñas donde hay concentración urbana y agrupa el resto solo cuando contienen población. No se desperdician peticiones cubriendo monte, mar o polígono vacío.
El control de coste es la parte que más uso en mi trabajo diario. Las celdas crecen automáticamente hasta que el peor caso de tres páginas por celda no supera 4.500 llamadas, dejando margen frente al bloqueo de 4.800 del plan contratado. Hay un presupuesto con límite duro que lanza excepción al pasarse —y ojo, incluso con presupuesto ilimitado se sigue registrando el uso—, y la cabecera de campos devueltos se reduce al mínimo necesario para que cada llamada cueste lo menos posible.
ZIP nacional del Nomenclátor → ENTIDADES.csv
→ núcleos con población > 0 · sin contar dos veces la jerarquía
→ celda pequeña en ciudad · celda territorial agrupada en el resto
→ agrandar hasta que 3 páginas/celda ≤ 4.500 llamadas
→ misma consulta «tatuajes» + locationRestriction.rectangle por celda
→ presupuesto con límite duro · el uso se apunta siempre