You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用GeoDjango获取双位置时遭遇GeocoderUnavailable错误求助

GeoDjango根路径访问触发GeocoderUnavailable错误解决

我在使用GeoDjango开发两地位置信息获取功能时,访问根路径遇到错误:GeocoderUnavailable at /,相关视图代码如下:

from django.shortcuts import render, get_object_or_404
from .models import Measurement
from .forms import MeasurementModelForm
from geopy.geocoders import Nominatim
from geopy.distance import geodesic
from .utils import get_geo, get_center_coordinates, get_zoom
import folium

# Create your views here.
def calculate_distance_view(request):
    # initial values
    distance = None
    destination = None

    obj = get_object_or_404(Measurement, id=1)
    form = MeasurementModelForm(request.POST or None)
    geolocator = Nominatim(user_agent='measurements')

    ip = '72.14.207.99'
    country, city, lat, lon = get_geo(ip)
    location = geolocator.geocode(city)

    # location coordinates
    l_lat = lat
    l_lon = lon
    pointA = (l_lat, l_lon)

    # initial folium map
    m = folium.Map(width=800, height=500, location=get_center_coordinates(l_lat, l_lon), zoom_start=8)
    # location marker
    folium.Marker([l_lat, l_lon], tooltip='click here for more', popup=city['city'],
                  icon=folium.Icon(color='purple')).add_to(m)

    if form.is_valid():
        instance = form.save(commit=False)
        destination_ = form.cleaned_data.get('destination')
        destination = geolocator.geocode(destination_)

        # destination coordinates
        d_lat = destination.latitude
        d_lon = destination.longitude
        pointB = (d_lat, d_lon)
        # distance calculation
        distance = round(geodesic(pointA, pointB).km, 2)

        # folium map modification
        m = folium.Map(width=800, height=500, location=get_center_coordinates(l_lat, l_lon, d_lat, d_lon), zoom_start=get_zoom(distance))
        # location marker
        folium.Marker([l_lat, l_lon], tooltip='click here for more', popup=city['city'],
                      icon=folium.Icon(color='purple')).add_to(m)
        # destination marker
        folium.Marker([d_lat, d_lon], tooltip='click here for more', popup=destination,
                      icon=folium.Icon(color='red', icon='cloud')).add_to(m)


        # draw the line between location and destination
        line = folium.PolyLine(locations=[pointA, pointB], weight=5, color='blue')
        m.add_child(line)
        
        instance.location = location
        instance.distance = distance
        instance.save()

    m = m._repr_html_()

    context = {
        'distance' : distance,
        'destination': destination,
        'form': form,
        'map': m,
    }

    return render(request, 'measurements/main.html', context)

错误原因分析

GeocoderUnavailable错误表示无法连接到Nominatim地理编码服务,常见诱因:

  • 网络问题导致无法访问Nominatim服务器
  • 请求频率过高触发Nominatim的限流机制
  • User-Agent设置不规范被服务拦截
  • 服务临时维护或故障

解决办法

1. 添加异常捕获,避免程序崩溃

在调用geolocator.geocode()的位置增加异常处理,即使服务不可用也能返回友好响应:

from geopy.exc import GeocoderUnavailable, GeocoderTimedOut

# ... 其他代码 ...

# 处理初始位置的地理编码
try:
    location = geolocator.geocode(city)
except (GeocoderUnavailable, GeocoderTimedOut):
    location = None
    # 可以在context中添加错误提示,前端显示给用户

# 处理表单提交后的目标位置地理编码
if form.is_valid():
    instance = form.save(commit=False)
    destination_ = form.cleaned_data.get('destination')
    try:
        destination = geolocator.geocode(destination_)
    except (GeocoderUnavailable, GeocoderTimedOut):
        destination = None
        # 同样添加错误提示到context

2. 规范Nominatim请求配置

  • 设置合规的User-Agent:Nominatim要求User-Agent包含项目信息和联系方式,避免被拦截
geolocator = Nominatim(user_agent="your-project-name/1.0 (your-contact-email@example.com)")
  • 添加请求延迟:Nominatim限制每秒最多1次请求,添加延迟避免触发限流
from time import sleep

# 在每次geocode请求后添加延迟
location = geolocator.geocode(city)
sleep(1)

3. 检查网络连通性

确认服务器可以访问https://nominatim.openstreetmap.org/,国内服务器可能需要配置代理才能正常访问。

4. 切换备用地理编码服务

如果Nominatim稳定性无法满足需求,可以考虑使用其他服务,比如Google Geocoding API或Mapbox Geocoding API(需申请API密钥)。

内容的提问来源于stack exchange,提问作者Rashid Khan

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.07 06:00:45