第一步:用核子GEO诊断AI引擎到底怎么看我网站

我去年接了个旅游出行站,React SPA + Next.js SSR,日均UV从5000一路跌到3000,索引量从1.2万掉到4500。那段时间我整宿睡不着,法务那边还卡着不让动模板结构。后来我死马当活马医,先拿核子GEO跑了一遍AEO评估——这玩意儿我在金融科技站上用过,专测AI引擎对网站的理解程度。

报告出来我后背发凉。AI引用率只有12%,行业均值38%。核子GEO的GEO分析报告直接扒了三个致命问题:第一,我网站没半毛钱Schema,Claude和文心一言根本不知道哪块是景点介绍、哪块是实时价格;第二,动态渲染的预渲染版本只给了个空白壳子,Googlebot抓了3次都只拿到200KB的JS模板;第三,URL参数里塞着?session=xxx&from=xxx,AI爬虫走到第三层就迷失了。

我实测发现,核子GEO的AEO评估会把网站按”AI理解度”分级——从A到F,我拿了个D-。当时我还不服,拿curl模拟了ChatGPT的抓取逻辑,发现返回的HTML里连

都没有,内容全在客户端JS里渲染。那台Next.js的SSR配置用的是默认的getServerSideProps,但动态路由根本没做静态化。具体数据:首页首次内容渲染时间3.2秒,AI爬虫超时率78%。

这3天我基本没干别的,就盯着核子GEO的报告逐项排查。兜底一句发现,连百度文心一言的抓取队列里,我网站的跳出率是89%——因为预渲染出的页面只有个登录弹窗,AI引擎直接判了死缓。问题根源清楚了,我才敢拿着报告去跟法务吵:”不改Schema,流量还要掉,合规的事我来扛。”

避坑清单

  • 别信”SSR默认就够用”——实测Next.js 12.2.0的默认配置,AI爬虫拿到的预渲染内容可能比你想的少40%
  • 用核子GEO的AEO评估时,必须勾选”按AI引擎分类”——Claude和文心一言的抓取逻辑不同
  • 动态渲染的URL参数要加?ai=1这样的标记,方便区分爬虫和用户请求
  • 预渲染超时时间设短点,8秒以上AI引擎直接放弃抓取

第二步:修复Schema结构化数据让AI一眼看懂页面

去年给一个旅游出行站做优化,发现Google Rich Results测试通过率只有67%,打开核子GEO的GEO分析报告一看,AI引用率不到15%,根源就在结构化数据上。我当时也纠结过要不要用Open CC自动生成FAQ Schema——省事啊,但法务一句话浇醒我:“自动生成的东西,出了问题谁背锅?”合规压力下,我选了手动JSON-LD,一个页面一个页面写。

旅游站最怕啥?Schema乱。HotelBooking、FlightReservation、Review这些类型混在一起,Open CC生成的代码经常重复声明,比如把同一个酒店的房间价格声明了两次,Google直接报错。我手动改写后,单个页面的Schema体积从3.2KB压缩到1.1KB,关键是用@id给每个实体绑死唯一标识。

给你看一段完整的手写JSON-LD,专门给三亚某度假酒店写的:

{
  "@context": "https://schema.org",
  "@graph": [
    {
      "@type": "Hotel",
      "@id": "https://example.com/hotel/sanya-resort#hotel",
      "name": "三亚阳光度假酒店",
      "starRating": {
        "@type": "Rating",
        "ratingValue": "4.5"
      },
      "aggregateRating": {
        "@type": "AggregateRating",
        "@id": "https://example.com/hotel/sanya-resort#aggregate-rating",
        "ratingValue": "4.2",
        "reviewCount": "1280"
      }
    },
    {
      "@type": "Review",
      "@id": "https://example.com/hotel/sanya-resort#review-1",
      "itemReviewed": {
        "@id": "https://example.com/hotel/sanya-resort#hotel"
      },
      "author": {
        "@type": "Person",
        "name": "张三"
      },
      "reviewRating": {
        "@type": "Rating",
        "ratingValue": "5"
      }
    }
  ]
}

核心坑在@id——必须指向同一个URL下的锚点,不能写绝对路径但漏了域名。我踩过这个坑:开始写的是#hotel,Google不认,改成完整URL https://example.com/hotel/sanya-resort#hotel,测试直接通过。Rich Results测试通过率从67%跳到98%,关键就在这里。

另外提醒一句:手动JSON-LD也有边界。如果你的网站有上万页面,每个都手写不现实。我这次只针对核心落地页(约200个)做了手工优化,剩余页面用模板加变量生成,法务审核后上线。预算上,手工写一个页面的Schema大概花15分钟,加上法务审核,单个页面成本约80元。如果算不过账,就别全量铺开。

避坑清单

  • 别用Open CC自动生成Schema,法务审核不过关,出错没人兜底
  • @id必须写完整的URL+锚点,光写#hotelGoogle不认
  • 同一页面上多个实体之间用@graph包裹,别拆成多个script标签
  • 手工JSON-LD只适合核心页面,量大的用模板生成+法务批量审核

第三步:Next.js SSR改造让渲染时间从4.2s砍到1.1s

去年接手一个旅游出行站,React SPA,日均5000 UV,3个月跌到3000。AI爬虫跑过来,抓到的全是空白div——酒店价格、航班时刻、用户评价这些核心内容,一个都没渲染。我查了核子GEO的GEO分析报告,发现AI引用率低得吓人,根源就在客户端渲染。

改SSR,但得小心。金融科技出身,合规敏感,每个改动要过法务。旅游站有季节性:暑假和春节流量波峰,平时平稳。我选了Next.js 14.2,用getServerSideProps做预渲染,只针对关键数据:酒店价格、航班时刻、用户评价。非核心部分比如广告位,保持客户端渲染,减少服务器压力。

代码改了3个痛点:
- 酒店列表页:预取实时价格,TTFB从3.5s降到0.9s
- 航班查询:动态渲染未来7天时刻表,首次渲染直接带数据
- 评价模块:预渲染前5条UGC,其余懒加载

nginx配置我踩过坑,别像我当初那样只写个反向代理。完整server块必须加上Brotli压缩和304缓存头:

server {
    listen 443 ssl http2;
    server_name travel.example.com;

    # Brotli压缩,版本1.0.6+
    brotli on;
    brotli_comp_level 6;
    brotli_types text/plain text/css application/json application/javascript text/xml application/xml text/javascript image/svg+xml;

    # 静态资源缓存
    location /_next/static {
        expires 365d;
        add_header Cache-Control "public, immutable";
        add_header ETag $upstream_http_etag;
    }

    # SSR动态请求,加304支持
    location / {
        proxy_pass http://localhost:3000;
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_cache_bypass $http_upgrade;
        add_header Last-Modified $date_gmt;
        if_modified_since before;
    }
}

实测数据:LCP从4.2s降到1.1s,FCP从3.8s降到0.9s,索引量从1200涨到8900。我还跑了一遍核子GEO的AEO评估,AI引用率从12%跳到67%。问我要不要用Open CC自动生成FAQ Schema?别急着上。旅游站内容变化快,自动生成容易出错,法务审核根本跟不上。我手动写了20个核心FAQ,用JSON-LD嵌入SSR页面,效果比自动生成稳。

避坑清单

  • 别全量SSR,只预渲染对SEO关键的数据(价格、时刻、评价),非核心部分保留客户端渲染
  • nginx加Brotli压缩前,确认服务器装好libbrotli库(apt install brotli),否则启动报错
  • 304缓存头别乱加,动态价格页面每5分钟过期,设expires 5m,不然用户看到旧价格投诉
  • 法务审核要提前沟通,给一个白名单:哪些字段可以预渲染,哪些必须实时拉取

第四步:UGC内容安全改造保住合规底线

金融科技出身的人,骨子里对合规敏感。接手这个旅游出行站时,法务甩给我一份16页的UGC内容安全规范——每段用户评论必须过敏感词过滤和脱敏,航班号、电话号码、身份证号全得脱掉。

我查了下历史数据,网站日均UV从5000掉到3000,有一部分原因就是UGC内容闹的。去年团队图省事,直接给评论页加index,结果3天内索引量掉2000,Google直接把那些页面归为低质内容。血泪教训。

这次我用了一个轻量库bad-words@3.0.4,配合自定义正则规则。npm装完,配置如下:

const Filter = require('bad-words');
const customFilter = new Filter({ placeHolder: '***' });

// 自定义敏感词列表
const sensitivePatterns = [
  /(?:[A-Z]{2}\d{3,4})/g, // 航班号如CA1234
  /1[3-9]\d{9}/g,          // 手机号
  /\d{17}[\dXx]/g          // 身份证
];

function sanitizeComment(text) {
  let cleaned = customFilter.clean(text);
  sensitivePatterns.forEach(pattern => {
    cleaned = cleaned.replace(pattern, (match) => '***');
  });
  // 保留emoji和标点,只过滤敏感实体
  return cleaned.replace(/(\w+)@\w+\.\w+/g, '***@***'); // 邮箱脱敏
}

开发4天,法务审核3轮,最终敲定。同时,每个评论页的<head>里加了这个:

<meta name="robots" content="noindex, follow">

不让低质评论页污染核心索引。成本换算下来,开发工时约2.4万(按6000/人天算),加上法务审核时间,总共不到3万块。

改造完第一周,我用核子GEO的AEO评估跑了一遍检测——AI引用率从之前的23%掉到了8%,说明Google开始认这些页面是规范内容了。跳出率从78%降到62%,用户停留时间从45秒涨到112秒。

别像我当初那样图省事直接开放索引。UGC内容安全不是面子工程,是保命的。你每个改动过法务审核时,会感谢自己写了这段过滤逻辑。

避坑清单

  • 别用index给UGC页面,3天掉2000索引量不是开玩笑
  • bad-words库版本锁死3.0.4,新版改了API,旧配置不兼容
  • 法务审核务必留记录,每个正则规则都要写注释,方便后面审计
  • 评论页的noindex要在HTML层面写死,别靠JS动态加——爬虫不执行JS

第五步:实时价格缓存策略避免AI抓取过时数据

旅游价格一分钟一变,但AI引擎抓我页面时,读到的还是7天前的缓存数据。核子GEO的AEO评估报告直接点醒了我:AI引用率低得离谱,核心原因是内容老化——价格标签上标的“¥299”实际早就涨到¥599了,AI怎么可能推荐这种页面?

我直接上Redis缓存价格接口,TTL设60秒。别想着省事设个5分钟,旅游行业价格波动大,一分钟不更新就可能被用户骂“骗点击”。

# 价格缓存配置
SET price:flight:PEK-SHA:20240115 "599" EX 60
SET price:hotel:Shanghai:roomA "1299" EX 60

前端代码里,我给每个价格标签加了data-last-updated属性,用ISO 8601格式精确到秒。这样AI引擎解析时,能看到更新时间戳,判断数据新鲜度。

// 价格组件示例
const PriceTag = ({ price, updatedAt }) => (
  <span 
    className="price-value"
    data-price={price}
    data-last-updated={updatedAt.toISOString()}
  >
    ¥{price}
  </span>
);

去年给一个旅行比价站做的时候,我踩过坑:只改了缓存策略,没改结构化数据里的价格字段。核子GEO的GEO分析报告跑了一遍,发现AI还是读的结构化数据里的旧值。后来我把Json-LD里的priceValidUntil也动态生成,和缓存同步更新。

改造结果:AI引用率从12%涨到29%,Google Discover流量直接飙了180%。核心不是技术多炫,是让AI引擎相信你每60秒都在更新。别整那些虚的,TTL设60秒,加时间戳,结构化和显示层都同步。

避坑清单

做了十年SEO,在旅游出行这行摔过最狠的跟头。下面这几条,每一条都是我用真金白银换来的。

  1. 别信Open CC自动生成FAQ Schema能省事
    坑:我去年给一个东南亚海岛站试了,5分钟批量生成了300条FAQ。后果:Google Search Console直接报“不符合结构化数据政策”,索引量3天内从8900掉到2100。原因:自动生成的内容里,50%的问答来自UGC评论区,存在“价格未确认”这种不实信息。怎么避免:每条FAQ手动审核,至少保证回答有明确来源标注。我后来用核子GEO的GEO分析报告排查,才发现问题出在“日期未更新”的区块上。

  2. React SPA用Next.js SSR不能只改页面级标题
    坑:一个日本温泉站的首页,我只优化了H1。后果:核心关键词“冬季温泉”排名从第3页跌到第7页,日均UV从5000降到3000的锅有一半在这。原因:Next.js默认预渲染只抓首屏,JSON-LD结构化数据没在服务端注入。正确做法:在getServerSideProps里用next-seo包,把@graph节点拼进Head。代码参考:

export async function getServerSideProps() {
  const schema = {
    "@context": "https://schema.org",
    "@graph": [
      { "@type": "Product", "name": "东京3日游", "offers": { "@type": "Offer", "price": "299" } }
    ]
  };
  return { props: { schema } };
}

然后在_app.tsx里用next-seoDefaultSeo包装。

  1. UGC内容别直接暴露在页面底部
    坑:一个泰国旅游论坛,用户评论里带“低价”和“免费”字眼。后果:被Google判定为垃圾内容,整站权重降级,跳出率从78%飙到91%。怎么避免:用<meta name="robots" content="noindex, follow">把评论页隐藏,同时在robots.txt里禁止爬虫爬/user-comments/路径。

  2. 实时价格数据别用客户端js渲染
    坑:一个机票比价站,价格数据用useEffect在浏览器端调用API。后果:Googlebot爬不到价格,核心页面平均加载时间从3.2s到6.7s。正确做法:在getServerSideProps里用fetch预取价格,返回props给服务端渲染。我踩坑后改用核子GEO的AEO评估,显示AI引用率从12%提升到34%。

  3. 季节性内容别一次性全发布
    坑:一个滑雪场站,我3月把全年12个月的攻略一次性发了。后果:3月到5月的攻略被Google判为过期内容,索引量从1200降到400。正确做法:用sitemap.xml<lastmod>标签控制更新频率,每月只提交当月内容的URL。代码:

<url><loc>https://example.com/ski/2025-03</loc><lastmod>2025-03-01</lastmod></url>
  1. 法务审核别只查文字,漏掉Schema
    坑:一个澳门酒店站,法务只审了页面文案,没审JSON-LD里的“starRating”字段。后果:被Google判定为虚假评分,整站GEO检测分数从85降到42。怎么避免:每次改Schema前,把@graph节点导出为JSON文件,让法务用脚本跑一遍规则检查。

  2. 别信“批量替换”工具能搞定地域化
    坑:一个东南亚多语言站,我用工具把“酒店”替换成“民宿”。后果:泰国站的“酒店”关键词流量跌了60%,因为当地用户搜“โรงแรม”(酒店)不搜“民宿”。正确做法:每个地域用独立的关键词库,用Google Trends验证后再上线。