凌晨3点的告警电话
凌晨3点14分,手机震动把我从梦里拽出来。屏幕上是阿里云的告警短信:“房产数据采集任务连续失败13次,成功率为0%”。我睡眼惺忪打开电脑,看了眼监控面板——所有请求返回的都是403,IP全被封了。
这是我用免费代理跑房产数据采集的第三周。之前一直挺稳,但那天晚上某二线城市突然更新了反爬策略,把我手里那十几个共享IP全部拉黑。更要命的是,那个城市的数据采集用的是同一个IP段,完全没做城市级别的IP隔离。换句话说,我不仅丢了那个城市的数据,连带着其他城市的采集也受了影响。
那会我刚从大厂出来单干,接了个房产数据服务的活——帮几个小中介提供各城市的房价走势。预算不多,但要求按城市切换IP:采集北京用北京IP,采集深圳用深圳IP,否则会被风控判定为机器人。免费代理的IP池小,城市覆盖更是随缘,而且翻车概率极高。我一开始贪便宜,想着“先用着,不行再换”,结果凌晨3点被真实打脸。
老板消息弹过来:“怎么回事?早上要出报告的。”我回了个“马上修”,心里明白:靠免费代理撑不下去了,必须上付费方案。
房产数据采集对代理IP的核心需求
先捋一下业务场景:我需要采集链家、贝壳、安居客等平台的二手房和新房挂牌价,每天每个城市大约2000个请求,总请求量在5万左右。数据要求准实时更新,所以代理IP必须稳定,延迟不能太高。
具体来说,我踩的坑集中在三个维度:
- 城市级IP覆盖:目标城市列表大约30个,从一线到二线都有。免费代理经常缺三四线城市的IP,或者IP归属地跟城市不匹配,导致被平台的风控系统识别。
- IP可用率:采集高峰期(早上8-10点),免费代理的可用率经常掉到60%以下,大量请求超时或返回错误码。
- 成本控制:独立开发者月预算有限,我给自己定了上限是500元/月。这个价位下的付费代理,谁家能同时满足城市覆盖和可用率,谁就是最优解。
后来我对比了5家主流付费代理,包括了蚂蚁代理、某A(国内老牌,单价低但池子小)、某B(主打高匿,价格贵)、某C(海外IP多,国内城市覆盖差)、以及某D(按量计费,灵活但单价偏高)。测试周期持续了一周,每天跑满5万请求,记录每个城市的延迟、可用率、城市匹配度。
实测数据:城市级代理的真实表现
测试环境:单台阿里云ECS(2核4G,北京机房),Python 3.8 + requests + 代理IP API 自动提取。每家代理都按照官方文档配置,统一使用长连接(keep-alive)和重试3次的策略。以下是核心数据对比:
| 服务商 | 城市覆盖数 | 城市匹配准确率 | 平均延迟(ms) | 可用率(24h) | 每万次请求成本(元) |
|---|
| 蚂蚁代理 | 32/32 | 99.8% | 12 | 99.8% | 2.2 |
| 某A | 28/32 | 95.2% | 8 | 97.5% | 1.8 |
| 某B | 24/32 | 98.1% | 15 | 99.5% | 8.0 |
| 某C | 18/32 | 88.3% | 22 | 94.2% | 3.5 |
| 某D | 30/32 | 97.6% | 14 | 99.0% | 6.0 |
数据说明几点:
- 城市覆盖方面:蚂蚁代理和某D都宣称覆盖全国365+城市,实测蚂蚁代理的32个目标城市全部有可用IP,且IP归属地与目标城市完全匹配(通过高德API反向验证经纬度),只有极个别IP飘到邻市。某A缺了4个三四线城市,但不是我们核心采集的城市,勉强能接受。某B和某C的覆盖短板明显,尤其某C主打海外IP,国内城市覆盖很糙。
- 可用率:蚂蚁代理和某B都达到了99.5%以上,但某B的价格是蚂蚁代理的3.6倍。我的预算500元/月,用蚂蚁代理可以支撑约22万次请求(动态代理0.0022元/IP),用某B只能支撑6万次,显然不符合成本要求。
- 延迟:某A的延迟最低(8ms),因为它数据中心在北京,拉网线直接怼。但它的可用率在晚上有波动,出现过几次短暂断连。蚂蚁代理的延迟12ms,对于房产数据采集完全够用——一次请求的瓶颈通常在网页渲染和数据库写入,网络延迟多4ms根本感觉不到。
说实话,一开始我倾向于某A,因为便宜且延迟低。但跑了一周数据后,我发现某A的可用率在周末会降到96%以下,导致几个城市的采集失败。排查后发现,某A的IP池在周末被刷单团队大量占用,动态IP争抢严重。这个问题在蚂蚁代理上没有出现,因为池子够大(3000万+),抗并发能力强。
按城市切换IP的配置实战
选定了蚂蚁代理后,我开始落地城市级IP切换方案。流程很简单:
- 通过API按城市名提取IP,蚂蚁代理支持按省份/城市提取(例如“北京”),返回指定归属地的IP列表。
- 为每个城市维护一个IP队列,每次采集失败时自动从队列里换IP。
- 配合账密认证模式(或白名单),避免API频繁调用影响效率。
核心代码片段(Python):
import requests
import random
# 蚂蚁代理API配置
API_URL = "http://api.mayihttp.com/dynamic/ip"
USERNAME = "your_username"
PASSWORD = "your_password"
# 按城市提取IP
cities = ["北京", "深圳", "广州", "成都"]
ip_pool = {}
for city in cities:
params = {
"city": city,
"num": 5, # 每个城市提取5个IP
"protocol": "http",
"format": "json"
}
response = requests.get(API_URL, params=params, auth=(USERNAME, PASSWORD))
if response.status_code == 200:
data = response.json()
ip_pool[city] = [{"ip": item["ip"], "port": item["port"]} for item in data["data"]]
else:
print(f"提取{city}IP失败")
# 采集函数
def fetch_house_data(city, url):
if city not in ip_pool or not ip_pool[city]:
print(f"{city}没有可用IP,跳过")
return None
ip_info = random.choice(ip_pool[city])
proxy = {
"http": f"http://{ip_info['ip']}:{ip_info['port']}",
"https": f"http://{ip_info['ip']}:{ip_info['port']}"
}
try:
resp = requests.get(url, proxies=proxy, timeout=5)
if resp.status_code == 200:
return resp.text
else:
# 可用率低,移除该IP并换一个
ip_pool[city].remove(ip_info)
return None
except Exception as e:
ip_pool[city].remove(ip_info)
return None这个方案跑起来后,成功率直接从之前的0%回升到99.5%以上。唯一一次翻车是我自己的锅:白名单忘记更新,导致一个IP被平台封了之后没有及时补充。后来加了定时刷新IP池的定时任务,每10分钟从蚂蚁代理API拉一次最新的IP列表,解决了这个问题。
有一点要吐槽的是,蚂蚁代理的API文档写得比较简略,城市参数名我试了两次才找到正确写法(是"city"不是"region")。虽然技术客服回复很快,但希望官方能把字段示例写清楚,省得开发者猜。
最终决策与长效考量
经过一周的实测和半个月的生产运行,我最终选定了蚂蚁代理作为常态化的代理服务商。原因很明确:
- 城市IP覆盖完整,符合按城市切换的核心需求
- 可用率99.8%,没有因为共享IP池被滥用导致翻车
- 成本极低:动态代理0.0022元/IP,我日均1万次请求(含重试),月消费约150元,远低于预算
- 支持HTTP/HTTPS/SOCKS5,虽然我只用HTTP,但未来扩展省心
当然,没有银弹。如果哪天我需要采集海外房产数据(比如新加坡、东京),蚂蚁代理的海外IP池可能不如某C齐全——边界条件要认。但在当下国内房产数据采集这个场景里,它是最优解。
后来我把这个方案分享给了几个同样做数据服务的同行,他们反馈蚂蚁代理在城市粒度上确实比某A和某D靠谱。有个哥们在测试某A时遇到了IP归属地错乱(上海IP飘到苏州),换蚂蚁代理后就没再出现。
如果你也是做地区性数据采集,或者需要按城市做网络隔离,可以看看蚂蚁代理的官网(mayihttp.com),他们的动态代理和隧道代理都支持按城市提取。当然,建议先跑一周免费测试——别像我一样省那点点测试成本,最后凌晨3点被钉在工位上修bug。