前言

你是不是也有过这样的烦恼?辛辛苦苦给多语言站点生成了 sitemap.xml,结果丢到 Ahrefs 或者 Google Search Console 一检查,跳出一堆“重定向问题”的警告?尤其是那种不带语言的链接,下面咱们以我的另外一个站点( solomakerstudio.com),点进去一看,全都 301 重定向到默认语言(比如 solomakerstudio.com/en/)。这不仅看着烦,还可能让搜索引擎觉得你的站点不够“友好”,SEO 效果打折扣。

别慌!这篇文章就来手把手教你怎么优化多语言站点的 sitemap.xml,彻底解决重定向问题,还能让你的站点在搜索引擎里表现得更出色。咱们会讲得尽量简单、接地气,操作步骤也超级实用,哪怕你是 SEO 小白也能轻松上手!

为什么 sitemap.xml 会有重定向问题?

先来搞清楚问题根源。很多多语言站点(比如用 /en/zh 这种子目录结构)都会把不带语言的链接(solomakerstudio.com/)设置成自动重定向到默认语言(比如 /en/)。这在用户体验上没啥问题,但到了 sitemap.xml 就容易出幺蛾子:

  • 搜索引擎不爱重定向:你把 solomakerstudio.com/ 塞进 sitemap.xml,爬虫访问时发现它跳转到 /en/,这多了一步“跳转”,爬虫效率降低,还可能觉得你的 sitemap 不够“直接”。
  • SEO 工具报警:像 AhrefsSEMrush 这些工具,看到 sitemap 里的链接触发重定向,就会给你标个“问题”,看着就闹心。
  • 重复内容风险:如果 sitemap 里同时有 //en/,搜索引擎可能误以为这是两块内容,影响页面权重。

所以,解决问题的核心思路就是:让 sitemap.xml 里只放最终的、可直接访问的链接,别放那些会跳转的“中间页”。

ahrefs检测出来的404重定向

优化 sitemap.xml 的 4 个实用步骤

好了,废话不多说,咱们直接上干货!以下是优化多语言站点 sitemap.xml 的四个步骤,照着做,保证你的 sitemap 干净又高效。

步骤 1:只放带语言的链接

最重要的一招:sitemap.xml 里不要包含不带语言的链接(比如 solomakerstudio.com/)。只放那些带语言子目录的最终页面,比如:

1
2
3
4
5
6
7
8
9
10
11
12
<url>
<loc>https://solomakerstudio.com/en/</loc>
<lastmod>2025-04-17</lastmod>
<changefreq>weekly</changefreq>
<priority>0.8</priority>
</url>
<url>
<loc>https://solomakerstudio.com/zh/</loc>
<lastmod>2025-04-17</lastmod>
<changefreq>weekly</changefreq>
<priority>0.8</priority>
</url>

怎么做?

  • 如果你用 CMS(比如 WordPress),检查 sitemap 生成插件(像 Yoast SEO、Rank Math)的设置,确保它只生成带语言子目录的链接。
  • 如果是自定义脚本生成 sitemap,改下代码逻辑,过滤掉不带 /en//zh/ 的 URL这里咱们以我们的next.js项目为例子,需要在根目录中存放对应的sitemapt.tsx文件,在对应的代码中编辑如下的脚本:
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    import type { MetadataRoute } from 'next';
    import type { MetadataRoute } from 'next';
    import { appConfig } from '@/lib/appConfig';

    // 辅助函数:生成带有语言前缀的URL
    const getLocalizedUrl = (baseUrl: string, path: string, locale: string) => {
    const localePath = `/${locale}`;
    const routePath = path === '' ? '' : `/${path}`;
    return `${baseUrl}${localePath}${routePath}`;
    };

    export default async function sitemap(): Promise<MetadataRoute.Sitemap> {
    // 定义静态路由
    const staticRoutes = [
    {
    path: '',
    changeFrequency: 'daily' as const,
    priority: 1,
    },
    {
    path: 'tools',
    changeFrequency: 'daily' as const,
    priority: 0.9,
    },
    ]
    const sitemapData: MetadataRoute.Sitemap = [];
    // 获取项目中支持的语言列表
    const locales = appConfig.i18n.locales;
    // 然后便利对应的语言,来生成目标语言下的页面链接
    for (const locale of locales) {
    // 1. 处理静态路由
    staticRoutes.forEach(route => {
    sitemapData.push({
    url: getLocalizedUrl(BASE_URL, route.path, locale),
    lastModified: new Date(),
    changeFrequency: route.changeFrequency,
    priority: route.priority,
    });
    });
    }
    // 最终生成的链接均带有对应的语言前缀
    return sitemapData
    }

小贴士:首页也一样!如果 solomakerstudio.com/ 会跳转到 solomakerstudio.com/en/,那 sitemap 里就只放 solomakerstudio.com/en/

步骤 2:加个 hreflang 标签,告诉搜索引擎语言关系

多语言站点得让搜索引擎知道哪些页面是同一个内容的“不同语言版本”,这时候 hreflang 标签就派上用场了。你可以在 sitemap.xml 里给每个 URL 加 hreflang 标签,像这样:

1
2
3
4
5
6
7
8
9
10
11
12
<url>
<loc>https://solomakerstudio.com/en/</loc>
<xhtml:link rel="alternate" hreflang="en" href="https://solomakerstudio.com/en/" />
<xhtml:link rel="alternate" hreflang="zh" href="https://solomakerstudio.com/zh/" />
<lastmod>2025-04-17</lastmod>
</url>
<url>
<loc>https://solomakerstudio.com/zh/</loc>
<xhtml:link rel="alternate" hreflang="en" href="https://solomakerstudio.com/en/" />
<xhtml:link rel="alternate" hreflang="zh" href="https://solomakerstudio.com/zh/" />
<lastmod>2025-04-17</lastmod>
</url>

为什么要加?

  • 告诉 Google 哪个页面是英文版、哪个是中文版,避免被误判为重复内容。
  • 提高用户体验,搜索引擎会根据用户语言偏好推荐对应版本。
  • 搜索引擎爬取我们站点是需要消耗资源的,可以想象一下,整个互联网上有数不尽的站点需要等待搜索引擎来抓取,如果我们的程序不提供对应的“舒服”的方式来让搜索引擎快速抓取,我们的站点就不能很好的暴露给到搜索引擎了!

怎么加?

  • 如果用 WordPress,Yoast SEO 或者 Polylang 插件可以自动生成带 hreflang 的 sitemap。
  • 如果是手动写 sitemap,确保 XML 里包含 xmlns:xhtml="http://www.w3.org/1999/xhtml" 命名空间。如下所示:
    sitemap.xml

步骤 3:检查重定向用的是 301

不带语言的链接(比如 solomakerstudio.com/)既然会跳转,那得确保它用的是 301 永久重定向,而不是 302 临时重定向。为什么?301 告诉搜索引擎“这个页面永远搬到新地址了”,SEO 权重传递更顺畅。

怎么查?

  • 用浏览器的开发者工具(F12 -> 网络),访问 solomakerstudio.com/,看状态码是不是 301。
  • 或者用在线工具(比如 redirect-checker.org)测试一下。

怎么改?

  • 如果你在 Nginx/Apache 服务器上配置重定向,检查配置代码,确保是 301。
    比如 Nginx 配置:

    1
    rewrite ^/$ /en/ permanent;
  • 如果用 CMS,检查语言切换插件的设置,确保重定向类型是 301。\

  • 这里咱们以solomakerstudio.com为例子(部署在vercel上的,通过自定义的middleware.ts中间件来实现的)

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    import { NextRequest, NextResponse } from 'next/server';
    import { verifyToken } from './lib/auth';
    import createMiddleware from 'next-intl/middleware';
    import { appConfig } from './lib/appConfig';

    const intlMiddleware = createMiddleware({
    locales: appConfig.i18n.locales,
    defaultLocale: appConfig.i18n.defaultLocale,
    localePrefix: 'always',
    });

    export function middleware(request: NextRequest) {
    const { pathname, locale } = request.nextUrl;

    // Handle root path (/) for 301 redirect based on Accept-Language
    if (pathname === '/') {
    const acceptLanguage = request.headers.get('accept-language') || '';
    let targetLocale = ''; // Fallback to default locale
    // Match language based on Accept-Language header
    if (acceptLanguage.includes('zh')) {
    targetLocale = 'zh';
    } else if (acceptLanguage.includes('en')) {
    targetLocale = 'en';
    }else{
    targetLocale = appConfig.i18n.defaultLocale;
    }
    // Perform 301 redirect to the target locale
    const redirectUrl = new URL(`/${targetLocale}`, request.url);
    return NextResponse.redirect(redirectUrl, 301);
    }
    return intlMiddleware(request);
    }

    export const config = {
    matcher: [
    '/((?!api|_next|.*\\..*).*)',
    '/rss.xml',
    '/:locale/rss.xml',
    '/admin/:path*',
    ],
    };

步骤 4:验证你的 sitemap.xml

优化完 sitemap.xml,别急着提交,先验证一下,确保没问题。

怎么验证?

  1. 用 Google Search Console 的“站点地图”功能,提交你的 sitemap.xml,过几天看“覆盖率”报告,有没有错误。
  2. 用 Ahrefs 的 Site Audit 功能,检查 sitemap 里的链接有没有重定向警告。
  3. 本地测试:用 XML 验证工具(比如 xmlvalidation.com)检查 sitemap 文件格式是否正确。

小贴士:提交到 Google Search Console 后,记得点“重新提交”,让爬虫尽快抓取新版本。下面是咱们调整之后,丢到ahrefs上的抓取结果:
优化后ahrefs检测出来的结果

额外注意事项

优化 sitemap.xml 还有几个小细节,别忘了:

  • 动态生成 sitemap:如果你的站点页面很多,建议用脚本或插件自动生成 sitemap,省时省力。
  • 定期检查:站点更新后,sitemap 也要跟着更新,保持 <lastmod> 日期准确。
  • 多语言插件:如果用 WordPress,WPML、Polylang 这些插件对多语言 sitemap 支持很好,配置一下就能省不少事。

总结

搞定多语言站点的 sitemap.xml 其实没那么复杂,核心就是:别放会跳转的链接,明确语言版本,加好 hreflang,检查 301。照着这四个步骤走,你的 sitemap 就能干干净净,Ahrefs 再也挑不出毛病,Google 爬虫也会更喜欢你的站点。

试试看吧!如果有啥具体问题(比如你的 CMS 咋配置,或者代码咋写),随时告诉我,我再帮你细化!