> 技术文档 > 请谈谈 HTTP 中的重定向,如何处理 301 和 302 重定向?_302重定向怎么实现

请谈谈 HTTP 中的重定向,如何处理 301 和 302 重定向?_302重定向怎么实现


HTTP重定向深度解析:301与302的正确使用姿势

一、重定向本质解析

重定向就像快递员送快递时发现地址变更,新地址会写在包裹单的\"改派地址\"栏。

浏览器收到3xx状态码时,会自动前往Location头指定的新地址。

常用状态码对比:

  • 301 Moved Permanently(永久迁移)
  • 302 Found(临时转移,原称Moved Temporarily)
  • 307 Temporary Redirect(严格临时重定向)
  • 308 Permanent Redirect(严格永久重定向)
二、服务端实现示例
// Express基础示例const express = require(\'express\');const app = express();// 301永久重定向(SEO权重转移)app.get(\'/old-page\', (req, res) => { res.redirect(301, \'/new-page\'); // 必须显式指定301});// 302临时重定向(默认行为)app.get(\'/temp-redirect\', (req, res) => { res.redirect(\'/new-location\'); // 默认302});// 307/308精准重定向(保持请求方法)app.get(\'/strict-redirect\', (req, res) => { res.status(307).header(\'Location\', \'/new-location\').send();});
三、前端处理机制

现代浏览器默认自动跟随重定向,但特殊场景需要手动处理:

// Fetch API手动处理重定向fetch(\'/api/data\', { redirect: \'manual\' }) .then(response => { if (response.status === 301 || response.status === 302) { const newUrl = response.headers.get(\'Location\'); window.location.href = newUrl; // 需处理相对路径 } else { return response.json(); } }) .catch(error => console.error(\'Redirect failed:\', error));
四、核心差异与使用场景

301永久重定向

  • 适用场景:域名更换、网站改版、URL标准化
  • 浏览器行为:更新书签,下次直接访问新地址
  • SEO影响:权重转移至新地址

302临时重定向

  • 适用场景:A/B测试、临时活动页、登录跳转
  • 浏览器行为:每次访问原地址都重新请求
  • SEO风险:可能被搜索引擎视为作弊
五、实战避坑指南
  1. 路径解析陷阱
// 错误:未处理相对路径const newUrl = \'/new-path\'; // 如果原地址是 /old/path// 正确应解析为绝对路径function resolveRedirect(base, path) { return new URL(path, base).href;}// 示例用法const absoluteUrl = resolveRedirect(\'https://example.com/old/\', \'../new\');// 输出: https://example.com/new
  1. 重定向循环检测
// 服务端防止循环重定向const MAX_REDIRECTS = 5;app.use((req, res, next) => { const redirectHistory = req.session.redirectHistory || []; if (redirectHistory.length >= MAX_REDIRECTS) { return res.status(508).send(\'Loop Detected\'); } res.redirect = function(url, status = 302) { redirectHistory.push(req.originalUrl); req.session.redirectHistory = redirectHistory; res.status(status).set(\'Location\', url).end(); }; next();});
  1. POST请求保护
// 307重定向保持请求方法app.post(\'/submit-form\', (req, res) => { if (needsRedirect(req.body)) { res.status(307) .set(\'Location\', \'/new-submit-url\') .send(); } else { // 正常处理逻辑 }});
六、性能优化技巧
  1. CDN缓存策略
# Nginx配置301缓存location /legacy-url { return 301 /new-url; add_header Cache-Control \"public, max-age=31536000\"; # 缓存1年}
  1. 客户端缓存控制
  1. 负载均衡优化
// 分布式环境下同步重定向规则const redis = require(\'redis\');const client = redis.createClient();app.get(\'/dynamic-redirect/:id\', async (req, res) => { const target = await client.get(`redirect:${req.params.id}`); target ? res.redirect(302, target) : res.sendStatus(404);});
七、安全防护要点
  1. 开放重定向防护
// 校验目标URL合法性const allowedDomains = [\'example.com\', \'trusted-site.org\'];function isValidRedirect(url) { try { const parsed = new URL(url); return allowedDomains.includes(parsed.hostname); } catch { return false; }}app.get(\'/redirect\', (req, res) => { const target = req.query.url; if (isValidRedirect(target)) { res.redirect(302, target); } else { res.status(400).send(\'Invalid redirect target\'); }});
  1. 敏感参数处理
// 删除敏感信息再重定向app.use(\'/auth-callback\', (req, res) => { const cleanUrl = new URL(req.originalUrl); cleanUrl.searchParams.delete(\'token\'); res.redirect(cleanUrl.toString());});
八、调试与监控
  1. cURL调试命令
# 查看完整重定向过程curl -Lv http://example.com/old-url# 限制最大重定向次数curl --max-redirs 3 http://example.com# 保持POST方法测试(-X POST -d参数)curl -X POST -d \"param=value\" -Lv http://example.com/submit
  1. 前端监控实现
// 捕获重定向错误window.addEventListener(\'error\', (event) => { if (event.message.includes(\'redirect\')) { trackError(\'Redirect Error\', { url: window.location.href, destination: event.filename }); }});// 性能监控重定向耗时const navigationTiming = performance.getEntriesByType(\'navigation\')[0];if (navigationTiming.redirectCount > 0) { reportMetrics({ redirectCount: navigationTiming.redirectCount, totalTime: navigationTiming.redirectEnd - navigationTiming.startTime });}
九、最佳实践总结
  1. 状态码选择原则
  • 永久迁移用301,临时跳转用302
  • 涉及POST请求时优先使用307/308
  • 单页应用内部路由避免使用HTTP重定向
  1. 性能优化要点
  • 对301设置长期缓存
  • 避免超过2次重定向链
  • 使用CDN加速重定向响应
  1. 安全防护必须
  • 永远不要信任用户提供的重定向地址
  • 对敏感操作使用一次性Token
  • 定期审计重定向规则
  1. 异常处理规范
  • 客户端设置最大重试次数
  • 服务端记录重定向日志
  • 监控平台配置重定向告警
// 终极防御:全链路重定向处理const fetchWithGuard = async (url, options = {}) => { let redirectCount = 0; const controller = new AbortController(); const fetchData = async (url) => { if (redirectCount >= 5) throw new Error(\'Too many redirects\'); const response = await fetch(url, { ...options, signal: controller.signal, redirect: \'manual\' }); if ([301, 302, 307, 308].includes(response.status)) { redirectCount++; const newUrl = response.headers.get(\'Location\'); return fetchData(new URL(newUrl, url).href); } return response; }; return fetchData(url);};

正确运用重定向技术可以实现:

  • 无缝迁移网站资源
  • 智能流量引导
  • 灵活的业务流程控制
  • 增强的用户体验

但需时刻警惕:

  • 避免形成重定向黑洞
  • 防止成为网络攻击跳板
  • 控制性能损耗在合理范围