有时候网站可能会从一个框架迁移到另一个博客框架,而第三方引用的 url (如转载),或者搜索引擎收录的 url 已经固定了,无法进行修改
那只能在新的框架上,尽量迁移数据,并且保证url与原有的相同
但大多无法保证 100% 兼容
如何保证已有的 url 在迁移过后不会出现 404
失效的情况呢?
这时候就用到了 Nginx
的后端错误码拦截功能了,自定义错误处理方式: error_page
配置 Nginx
直接上一套我的 Nginx
配置供参考:
upstream blogserver {
server xxxxxxxx:xxxxxx;
keepalive 32;
}
server{
listen 80; listen 443 ssl http2;
server_name zwc365.com;
include conf.d/zwchttps.cfg;
location / {
proxy_pass http://blogserver;
proxy_intercept_errors on;
error_page 404 500 = @error_500;
}
location ~ /(api|admin) {proxy_pass http://blogserver;}
location @error_500 {
root /media/zhou-blog-release/;
try_files $uri $uri/index.html $uri/index.htm =404;
}
location ~ .*\.(gif|jpg|jpeg|png|css|js|woff|woff2|svg|svgz)(.*) {
access_log off;
proxy_pass http://blogserver;
proxy_intercept_errors on;
error_page 404 500 = @error_500;
expires 7d;
}
}
include conf.d/zwchttps.cfg;
里面是配置https
的,例如秘钥等之类的
分析
关键代码在两行
proxy_intercept_errors on;
error_page 404 500 = @error_500;
这两行的意思是指定由哪个 location
处理后端错误
来看 location / {}
配置块,在 Nginx 接收到请求时,会将请求转发到后端服务器 blogserver
定义这两行后,后端处理如果返回 404
或者 500
错误码时,会交由 location @error_500 {}
配置块处理
如果后端返回的是除 404 或者 500 以外的其它状态码,例如 200,则会直接将数据返回浏览器
在这份配置文件里,@error_500
配置的 /media/zhou-blog-release/
目录就是原有的静态博客文件,根据需要进行修改
下面的 location ~ .*\.(gif|jpg|jpeg|png|css|js|woff|woff2|svg|svgz)(.*) {}
同理,只是额外配置了静态文件有效时间
当访问一个 url时,如果这个 url 是新的博客框架的,那么会返回 200 状态码及内容。
而如果是来自第三方未完成迁移的旧链接(如转载或搜索引擎收录的旧链接),那么后端服务器显然会无法处理,返回错误码
此时 location @error_500 {}
就会返回原有的旧博客的文件内容,从而实现两套博客系统兼容共存。
保证不会丢失原有链接,只是两套系统可能主题风格不相同。
实例
例如博客迁移前有一篇文章:
这篇文章我不想迁移到新博客。但是如果不迁移,会导致url无法访问。如果有人从搜索引擎中点击进入这篇文章,就会出现 404
无法访问的情况。
经过上面的配置之后,这篇文章依旧可以访问。但是文章的主题样式却和目前我的博客主页不相同。
但确实避免了 404 的情况。如果想让主题风格也一样,还是规规矩矩一篇一篇的迁移到新博客系统吧
其它
error_page 功能还有另一用途:隐藏后端服务。
例如:有一个后端服务器,需要经过 http 的握手后才能建立正确的链接,否则会返回 400
错误码
这个正确的 http 握手当然是要专门的客户端的,为了向普通浏览器隐藏后端服务,可以通过 error_page 拦截 400
错误码
当使用 浏览器访问后端时,无法完成握手,返回400 错误码,被Nginx拦截后,返回一个自定义内容。
当使用 客户端访问后端时,能够完成握手,那么就进入正常的数据交互环节。