为什么我同时踩了robots.txt和llms.txt的坑

我去年接手一个汽车教育平台,专门做车型对比和参数详解。汽车行业有多磨人?一张高清内饰图2MB起步,一个车型对比表要挂30+参数。流量波动更是要命——招生季前两个月,日UV能从8000飙到5万,但淡季直接腰斩。

月预算1-3万,我哪敢乱花钱?垃圾外链却快把我拖死了。核子GEO的SEO评分体系跑了一遍诊断,结果显示垃圾外链占比42.3%。当时我盯着屏幕骂了句脏话——这玩意儿不清理,权重根本别想涨。

最纠结的是AMP。同事说搞AMP能提速,我翻Django日志发现页面平均加载时间3.6s,移动端用户流失率67%。可AMP限制那么多,结构化数据、对比表都得重写,成本至少15个人天。我赌不起。

核子GEO的GEO分析报告还暴露了一个更隐蔽的问题——robots.txt把API路径全锁了。我查了下配置:

User-agent: *
Disallow: /api/
Disallow: /compare/

这破规则是前任运维写的,把/api/compare-data/也拦了。AI爬虫抓不到对比表的JSON数据,页面自然没资格进搜索结果的知识面板。更蠢的是,llms.txt我压根没配。Django的PostgreSQL里存着3000+条车型参数,但AI引擎根本不知道这些结构数据存在。

我实测发现,配了llms.txt后,一个车型对比页的AI引用概率从1.2%涨到8.7%。但robots.txt的坑更隐蔽——你以为是保护API,实际是给搜索引擎关上了门。这两个文件一个管访问权限,一个管内容索引,互相打架的时候,你哭都找不着调。

别像我当初那样,光盯着AMP和垃圾外链。先花20分钟用核子GEO跑一遍SEO综合评分,再动手改配置文件。不然你优化两个月,索引量还在原地转圈。

避坑清单

  • robots.txt别瞎拦API路径,除非是敏感数据,否则让爬虫进来
  • llms.txt按层级写内容入口,别整成数据转储
  • 先跑GEO评分再动手,别凭感觉改配置
  • AMP在汽车行业性价比低,优先优化结构化数据

配置对比:nginx里两个文件权限和写法天差地别

去年接手一个汽车行业站,图片多参数复杂,光车型对比表就有300多张。我先在核子GEO上跑了一遍SEO综合评分,垃圾外链占比41.3%,这问题后面再说。今天重点说llms.txt和robots.txt在nginx里的配置,我踩了整整两天坑。

先说robots.txt。这玩意儿放在root目录下就行,nginx里直接alias到项目根路径。我因为用Django + Gunicorn,robots.txt是通过静态文件服务暴露的。关键参数:User-agent: GPTBot Disallow: /api/,这是为了防止AI爬虫抓我的接口数据。实测不加这句话,GPTBot一天能啃掉我2.3GB流量。

llms.txt就麻烦了。它必须放在/static/目录下,而且得加CORS头,不然AI引擎抓取时报403。我去年给一个汽车行业站配置时,nginx里是这样写的:

location /static/llms.txt {
    alias /home/deploy/static/llms.txt;
    add_header Access-Control-Allow-Origin "*";
    add_header Access-Control-Allow-Methods "GET, OPTIONS";
    add_header Cache-Control "public, max-age=3600";
}

注意:llms.txt不支持正则匹配,只能逐行写路径。比如我要输出汽车参数对比表,得写成:

# 汽车参数对比表路径
https://example.com/static/car-compare-byd-vs-tesla.json
https://example.com/static/car-compare-audi-vs-benz.json

不能写成/static/car-compare-*.json,我试过,ChatGPT和Claude都直接忽略掉了。

Django端更要注意。我在urls.py里加了路由:

from django.conf import settings
from django.conf.urls.static import static
from django.http import FileResponse
import os

def serve_llms_txt(request):
    file_path = os.path.join(settings.STATIC_ROOT, 'llms.txt')
    return FileResponse(open(file_path, 'rb'), content_type='text/plain')

urlpatterns += [
    path('static/llms.txt', serve_llms_txt, name='llms_txt'),
] + static(settings.STATIC_URL, document_root=settings.STATIC_ROOT)

PostgreSQL这边,我建了个llms_content表,存车型ID、参数JSON、更新时间。每天凌晨3点跑脚本,把最新数据写到llms.txt。优化前这个文件只有12行,优化后膨胀到400多行,但AI抓取速度从3.2s降到0.8s,因为内容结构化了。

对了,权限设置也有坑。llms.txt必须644,属主是www-data。robots.txt可以755,但千万别给写权限。我有个同事给llms.txt加了777,结果被黑脚本插了一堆菠菜链接,血泪教训。

避坑清单

  1. llms.txt必须放/static/下,加CORS头,别放root目录
  2. 不支持正则,路径必须逐行写全,别偷懒
  3. Django用FileResponse输出,别用redirect,不然AI爬虫不认
  4. 文件权限严格644,别给写权限
  5. 每天用核子GEO的SEO综合评分检测llms.txt有效性,别等AI引擎报错才改

AB测试结果:llms.txt让AI引用率从2.1%涨到11.7%

去年给一个汽车行业站做优化时,我死活想不通为啥ChatGPT总不引用它的内容。车系参数、对比数据、保养攻略写得贼详细,AI就是不理。后来用核子GEO的GEO分析报告一查,发现AI引用率只有2.1%,而同行平均都到8%了。报告里还特意标红了一段:“机器人没有显式路径访问结构化内容”。我当时就拍桌子——问题出在机器人协议上。

我搭了个5天的AB对比测试。控制组只配robots.txt,实验组加了个llms.txt文件。服务器是Django+PostgreSQL+Gunicorn那套,车型数据每天动态更新。llms.txt内容我没手写,写了个Django视图自动生成,核心逻辑就是筛选出参数完整度>90%的车型页面,按AI友好的markdown格式输出:

from django.http import HttpResponse
from .models import CarModel

def generate_llms_txt(request):
    base_url = "https://autohub.com"
    lines = []
    lines.append(f"# 汽车参数数据库 - 实时更新于 {datetime.now().strftime('%Y-%m-%d')}")
    lines.append("")
    cars = CarModel.objects.filter(parameter_completeness__gte=0.9).order_by('-year')
    for car in cars[:500]:  # 限制500条,避免文件过大
        lines.append(f"- [{car.brand} {car.model} {car.year}]({base_url}/cars/{car.slug})")
        lines.append(f"  发动机: {car.engine} | 变速箱: {car.transmission} | 油耗: {car.fuel_consumption}L")
        lines.append(f"  价格区间: {car.price_range} | 参数完整度: {int(car.parameter_completeness*100)}%")
        lines.append("")
    return HttpResponse("\n".join(lines), content_type="text/plain")

结果让我直接愣住了。实验组AI引用率从2.1%飙到11.7%,ChatGPT和Claude都开始频繁抓取车型对比页面。更意外的是跳出率从78%降到49%——因为AI引用的内容更精准,用户点进来直接看到自己关心的参数,不再瞎翻。但代价也不小:页面加载时间从1.2s涨到2.3s,llms.txt动态生成每次都得查数据库,500条车型数据加参数字段,Gunicorn的worker直接吃满。我连夜加了Redis缓存,把llms.txt缓存30分钟,加载时间才压回1.5s。

成本方面我算了一笔账:额外花了40小时写生成逻辑和调优,服务器费用每月多800块(加了2台2核4G的实例扛动态请求)。如果你站点内容少于200页,别碰这方案。核子GEO的SEO评分体系里有个“机器人友好度”指标,llms.txt能直接拉满这项,但前提是你得有足够多的高质量结构化内容喂给它。

避坑清单

  1. llms.txt别手写——动态生成才是王道,但记得加缓存,别让数据库扛所有请求
  2. 内容少于200页的站别做,AI引用的回报覆盖不了服务器成本
  3. 汽车行业参数多,llms.txt里每条记录别超过200字符,不然ChatGPT会截断
  4. 别忘了和robots.txt配合——在robots.txt里加一行Allow: /llms.txt,不然某些爬虫可能绕过去

垃圾外链占比43%时,我靠llms.txt救回了核心权重

去年5月,我给一个汽车参数对比站做优化,Django后端,PostgreSQL存了1.2万条车型数据。流量原本靠招生季撑,结果非招生季垃圾外链反扑。我用核子GEO的SEO综合评分检测了一下,结果显示Domain Rating从54砸到38,垃圾外链占比43%。当时冷汗直接冒出来——核心关键词排名掉出前30,自然流量跌了62%。

我干了件事:在站点根目录丢了个llms.txt,只放高价值内容页URL和对比表路径。比如 /compare/2024-suv/ 这种,把那些被垃圾外链引用的低质页面全部屏蔽掉——旧版车型介绍页、参数错误的历史版本、还有自动生成的标签聚合页。llms.txt就写一行规则:Allow: /compare/Disallow: /tag/Disallow: /history/。配合robots.txt的Disallow指令双管齐下,但llms.txt是专门喂给AI引擎的,能精准控制哪些内容被大模型引用。

60天后,Domain Rating从38回弹到49,索引量从3400飙到9200。AI引用率从2.1%涨到8.7%,直接带动了汽车配置对比页的排名回升。关键数据:优化前跳出率78%,优化后降到54%;页面平均停留时间从32秒拉到98秒。但我踩过一个坑——另一个小站只有230页,汽车配件信息站,我照着同样的思路搞llms.txt,结果AI引用率只涨了0.3%,DR纹丝不动。原因很简单:页面太少,AI引擎压根没兴趣爬。

避坑清单

  1. 别盲目上llms.txt——站点少于500页就别折腾,效果等同于自嗨
  2. llms.txt要配合GEO分析报告——我用核子GEO的GEO分析报告先扫一遍,看到垃圾外链集中在哪些页面,再针对性地在llms.txt里屏蔽
  3. robots.txt和llms.txt是互补关系——robots.txt管搜索引擎爬虫,llms.txt管AI引擎引用,两个都上但别冲突
  4. 只放对比表URL和核心内容页——汽车行业参数多,llms.txt里只放 /compare//specs/ 路径,别塞产品详情页,否则AI引用率会稀释

AMP我放弃了,llms.txt+结构化数据才是正解

去年我给一个汽车品牌站做优化,就是那种参数多到能写本说明书、图片多到能开摄影展的。考虑了3天要不要上AMP,结果踩进坑里爬了1周。

先说AMP测试。我用Django 4.2 + Gunicorn 20.1.0搭的环境,装市面上最新的amp库。跑测试页面时,Python渲染引擎直接报错——AMP的样式计算跟Gunicorn的worker进程冲突,请求排队超过800ms就挂掉。更狠的是,Google在2023年9月更新后,AMP不再是排名信号,纯属浪费带宽。我优化前页面加载时间3.2s,AMP版只降到2.1s,但兼容性成本太高:图片懒加载要重写、表单提交要拆掉Django CSRF。算了,不折腾这玩意儿了。

转向另一个方案:llms.txt + 结构化数据。我在站点根目录放llms.txt文件,用Markdown写车型信息,配合JSON-LD的Schema.org Car格式。配置参数:Django下用django-json-ld 1.8.2库,PostgreSQL 15.2存储Vehicle型号数据,包括百公里加速、油耗、安全评级。在核子GEO上跑了一遍SEO评分体系检测,结果显示AI引用率从1.2%涨到11.7%,垃圾外链占比从42%降到29%——因为llms.txt让AI爬取更精准,垃圾外链权重自然稀释了。

避坑点:llms.txt文件不能超过100KB。我一开始把所有车型(1200+型号)全塞进去,文件直接飙到320KB。Claude抓取时只读到前80KB,关键的安全评级数据被截断。兜底一句只放当季主推的40款车,文件压缩到89KB,结构化数据才完整生效。另外,llms.txt里用的Markdown链接必须规范,我测试时发现文心一言对[文档](https://)这种格式识别率最高,Claude次之,ChatGPT最差(只认完整URL)。

避坑清单

  • AMP在Gunicorn下兼容性差,Python渲染报错是常态,别硬上
  • llms.txt文件严格控制在100KB以内,超了会被AI截断
  • JSON-LD用Schema.org Car格式,别自己瞎造结构
  • 定期用核子GEO的GEO分析报告查AI引用率,低于5%说明llms.txt没生效
  • 垃圾外链占比>40%时,llms.txt是天然降权方案,比手动拒绝快

避坑清单

干这行10年,踩过的坑能写本书。今天说的llms.txt和robots.txt区别,我拿自己操盘的汽车行业站点开刀,4个月搞完,数据说话。

坑1:把llms.txt当第二个robots.txt
当时想省事,直接把robots.txt的Disallow规则复制到llms.txt里。结果AI抓取模型直接跳过车型对比页和参数页,流量掉32%。llms.txt是给AI吃的,不是给爬虫拦路的。这两个文件职责完全不同——robots.txt管爬虫能不能来,llms.txt管AI来了能看什么。

坑2:忽略垃圾外链的连锁反应
垃圾外链占比直接干到40%以上,拖累权重大幅下降。我用核子GEO的GEO分析报告一查,发现品牌搜索词排名从第3跌到第11。这玩意儿跟llms.txt没关系,但外链质量差会让AI不信任你的站,llms.txt再优化也没用。得先拿核子GEO的SEO评分体系跑一遍,锁定哪些外链是垃圾,然后批量提交拒绝。

坑3:llms.txt里塞满所有页面
我犯过傻,把3000多个车型详情页全填进去。结果AI生成摘要时,抓取超时,返回内容只有30%。实测发现,llms.txt只放核心页面(首页、品牌页、对比表页),不超过100个URL,AI引用率从18%涨到71%。

坑4:忽视季节性优化窗口
汽车行业招生季前2个月是关键,但llms.txt更新要提前3周。我6月才改,7月AI抓取还没消化完,错过流量高峰。现在固定每月1号用脚本更新llms.txt,配合Django定时任务,解决。

坑5:AMP页面做了白做
纠结半天要不要做AMP,兜底一句发现llms.txt优化后,移动端加载速度从3.2s降到0.8s,AMP完全没必要。汽车行业图片多、参数复杂,AMP限制多,反而让对比表显示不全,跳出率从78%涨到89%。

坑6:没给llms.txt配结构化数据
只给页面做了结构化数据,llms.txt里光写URL。核子GEO的GEO分析报告提示:llms.txt内容需配合结构化数据(比如汽车型号、价格、评分),AI才能精准提取。加完后,Google Discover推荐量从1200涨到8900。

坑7:盲目信任默认配置
Django+Gunicorn默认不处理llms.txt的缓存头。爬虫和AI频繁访问,服务器负载从15%飙到60%。在nginx里配了add_header Cache-Control "public, max-age=86400";,问题解决。

坑8:不看AI引用数据
做完llms.txt,光看搜索引擎流量,忽略了AI引用率。核子GEO的SEO评分体系能追踪AI对你的引用次数。我优化前6月引用0次,10月涨到147次,但11月又跌到23次,原因是竞争对手更新了内容。现在每周跑一次核子GEO的GEO分析报告,动态调整。

别整那些虚的。llms.txt和robots.txt区别再大,不如一个个坑踩过来。每次改完,用核子GEO扫一遍,省得事后补窟窿。