HTTP 转发(Forward)与重定向(Redirect)的核心区别
| 特性 | 转发(Forward) | 重定向(Redirect) |
|---|---|---|
| 发生位置 | 服务器内部 | 客户端(浏览器) |
| HTTP 状态码 | 无(或 200) | 301、302、307、308 等 |
| 浏览器地址栏 | 不变 | 变更为新 URL |
| 请求次数 | 1 次 | 至少 2 次(原始请求 + 重定向请求) |
| 数据携带 | 可以共享原始请求的 Request/Response 数据 | 不能直接共享,需通过 URL 参数或 Session |
| 效率 | 高(无额外往返) | 低(多一次网络往返) |
详细说明
1. 转发(Forward)
-
定义:服务器内部将请求从一个资源转交给另一个资源(如 Servlet 到 JSP)。
-
示例(Java):
javarequest.getRequestDispatcher("/target.jsp").forward(request, response); -
特点:
-
对客户端透明,浏览器不知道发生了转发。
-
共享同一个 HTTP 请求和响应对象。
-
只能转发到同一应用内的资源(不能跨域)。
-
2. 重定向(Redirect)
-
定义:服务器返回一个特殊响应(状态码 3xx + Location 头),让客户端重新发起请求到新地址。
-
示例(Java):
javaresponse.sendRedirect("/new-location"); -
常见状态码:
-
301 Moved Permanently:永久重定向(缓存) -
302 Found:临时重定向(默认) -
307 Temporary Redirect:保持原始请求方法
-
-
特点:
-
浏览器地址栏更新。
-
新的请求与原始请求完全独立(丢失原始请求的 Body、参数等,除非手动传递)。
-
可以跨域、跨应用重定向。
-
使用场景
| 场景 | 推荐方式 | 原因 |
|---|---|---|
| 用户登录后跳转到主页 | 重定向 | 避免刷新页面时重复提交表单 |
| 后台 MVC 控制器转到 JSP 渲染 | 转发 | 效率高,数据共享方便 |
| 外部支付成功后回调跳转 | 重定向 | 需要跨域,且浏览器地址变化 |
| 处理 POST 请求后避免重复提交 | 重定向(Post/Redirect/Get 模式) | 刷新页面不会重复 POST |
| 内部权限检查后展示错误页面 | 转发 | 保留原始请求数据,便于展示错误信息 |
直观对比图
bash
转发:
Client → Server (请求资源A)
↓
资源A 内部转发给 资源B
↓
Client ← Server (返回资源B的内容)
地址栏:仍然是资源A的URL
重定向:
Client → Server (请求资源A)
↓
Server ← 返回 302 + Location: 资源B
↓
Client → Server (新请求 资源B)
↓
Client ← Server (返回资源B的内容)
地址栏:变为资源B的URL
总结
-
转发:服务器内部跳转,客户端无感知,一次请求,高效。
-
重定向:客户端再次请求,地址栏变化,两次请求,适用于跨域、避免重复提交等场景。