首页 > 代码库 > [前端]代理知识入门介绍
[前端]代理知识入门介绍
主要目的是帮助我们了解代理和反向代理,以及熟悉它们的工作原理,帮助我们更好的在开发过程中进行使用,提高工作效率。
本内容主要围绕Http反向代理进行介绍,其他不常用的代理大家可自行了解。
什么是代理?代理有哪些类型?
代理(英语:Proxy),也称网络代理,是一种特殊的网络服务,允许一个网络终端(一般为客户端)通过这个服务与另一个网络终端(一般为服务器)进行非直接的连接。
协议
- HTTP RFC 7230 - HTTP/1.1: Message Syntax and Routing
- SOCKET Tunneling TCP based protocols through Web proxy servers
功能
- 提高访问速度: 通常代理服务器都设置一个较大的缓冲区,当有外界的信息通过时,同时也将其保存到缓冲区中,当其他用户再访问相同的信息时, 则直接由缓冲区中取出信息,传给用户,以提高访问速度。
- 隐藏真实IP(网络安全)。
- FQ:允许一个网络终端(一般为客户端)通过这个服务与另一个网络终端(一般为服务器)进行非直接的连接。
- 负载均衡。
种类
根据协议区分
FTP代理服务器、HTTP代理服务器、SSL/TLS代理、RTSP代理、Telnet代理、POP3/SMTP代理、SOCKS代理
根据类型区分
正向代理、反向代理、透明代理、分布式代理等
什么是反向代理?
反向代理是代理服务器的一种。它根据客户端的请求,从后端的服务器(如Web服务器)上获取资源,然后再将这些资源返回给客户端。
功能
- 加密和SSL加速
- 负载平衡
- 缓存静态内容
- 压缩
- 安全
- 隔离内外网
和正向代理的区别
- 正向代理需要客户端进行设置,在网络请求中设置代理地址;而反向代理不需要客户端进行任何设置。
- 客户端向代理发送一个请求并指定目标(原始服务器),然后代理向原始服务器转交请求并将获得的内容返回给客户端;反向代理正好相反,对于客户端而言它就像是原始服务器。客户端向反向代理 的命名空间(name-space)中的内容发送普通请求,接着反向代理将判断向何处(原始服务器)转交请求,并将获得的内容返回给客户端,就像这些内容 原本就是它自己的一样。
- 正向代理允许客户端通过它访问任意网站并且隐藏客户端自身;反向代理对外都是透明的,访问者并不知道自己访问的是一个代理。
常见的反向代理
由于代理本身只是一种网络通信模式,所以只要遵循相应的协议规则,任何人都可以开发属于自己的反向代理服务;目前常用的功能完善的反向代理服务主要有nginx、apache httpd、Squid等。
Nginx 反向代理设置
轻量级,目前使用最广泛,Mac需要安装Nginx才可使用。
注:仅介绍反向代理相关内容,不研究nginx
proxy_pass http://127.0.0.1:88; # 核心配置 proxy_redirect off; # 后端的Web服务器可以通过X-Forwarded-For获取用户真实IP proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; # 以下是一些反向代理的配置,可选。 proxy_set_header Host $host; client_max_body_size 10m; #允许客户端请求的最大单文件字节数 client_body_buffer_size 128k; #缓冲区代理缓冲用户端请求的最大字节数, proxy_connect_timeout 90; #nginx跟后端服务器连接超时时间(代理连接超时) proxy_send_timeout 90; #后端服务器数据回传时间(代理发送超时) proxy_read_timeout 90; #连接成功后,后端服务器响应时间(代理接收超时) proxy_buffer_size 4k; #设置代理服务器(nginx)保存用户头信息的缓冲区大小 proxy_buffers 4 32k; #proxy_buffers缓冲区,网页平均在32k以下的设置 proxy_busy_buffers_size 64k; #高负荷下缓冲大小(proxy_buffers*2) proxy_temp_file_write_size 64k; #设定缓存文件夹大小,大于这个值,将从upstream服务器传 |
Apache 反向代理设置
重量级,功能强大,历史悠久,但Mac自带Apache服务,启动就好!
MAC中的目录:/etc/apache2
启动命令:sudo apachectl start 或 sudo apachectl restart
#off表示开启反向代理,on表示开启正向代理ProxyRequests Off ProxyMaxForwards 100 ProxyPreserveHost On ProxyPass / http://www.junjunfudao.com/ ProxyPassReverse / http://www.junjunfudao.com/ |
前端与反向代理
前端开发本来并不关心反向代理问题,但如果为了提高前端代码的运行效率和开发体验。非常有必要加深对服务器端web容器配置的了解。而反向代理的应用对于提高前端工程的开发效率有很大帮助。
JS如何实现代理
-
正向代理实现方式
/** * 正向代理示例 */ var http = require(‘http‘); var url = require(‘url‘); function request(cReq, cRes) { var u = url.parse(cReq.url); var options = { hostname: ‘http://www.junjunfudao.com‘, port: u.port || 80, path: u.path, method: cReq.method, headers: cReq.headers }; var pReq = http.request(options, function(pRes) { cRes.writeHead(pRes.statusCode, pRes.headers); pRes.pipe(cRes); }).on(‘error‘, function(e) { cRes.end(); }); cReq.pipe(pReq); } http.createServer().on(‘request‘, request).listen(8080, ‘0.0.0.0‘);
-
反向代理实现方式(使用http-proxy包来实现)
/** * 反向代理示例 */ var http = require(‘http‘), httpProxy = require(‘http-proxy‘), //http-proxy proxy = httpProxy.createProxyServer({}), fs = require(‘fs‘), path = require(‘path‘) var getConType = function (ext) { switch(ext){ case ‘.html‘: return ‘text/html‘; case ‘.js‘: return ‘text/javascript‘; case ‘.css‘: return ‘text/css‘; case ‘.gif‘: return ‘image/gif‘; case ‘.jpg‘: return ‘image/jpeg‘; case ‘.png‘: return ‘image/png‘; case ‘.ico‘: return ‘image/icon‘; default: return ‘application/octet-stream‘; } }; var server = http.createServer(function(req, res) { var _url = req.url; //获取请求的url var _file = _url.replace(/\?.*/ig,‘‘); var _localPath, _localFile, _stream; var _ext = path.extname(_file); // 文件扩展 if(_ext){ // 如果是静态资源文件,则总本地读取 //转换成本地路径 _localPath = ‘/Users/yangyang.zhang/Work/wenba/fudao_activity/static/‘; _localFile = _localPath+_file; //判断文件是否存在 if(fs.existsSync(_localFile)){//如果文件存在 res.writeHead(200, {‘Content-Type‘: getConType(_ext) }); _stream = fs.createReadStream(_localFile, {flags : ‘r‘, encoding : null});//只读模式 读取文件内容 _stream.on(‘error‘,function(){//如果读取错误 返回404 res.writeHead(404, {‘Content-Type‘: ‘text/html‘}); res.end(‘<h1>404 Read Error</h1>‘); }); _stream.pipe(res);//连接文件流和http返回流的管道,用于返回实际Web内容 _stream.on(‘end‘,function(){ _stream = null; }) }else{//返回404错误 res.writeHead(404, {‘Content-Type‘: ‘text/html‘}); res.end(‘<h1>404 Not Found</h1>‘); } }else{ proxy.web(req, res, {target: ‘http://www.junjunfudao.com‘}); } }); console.log(‘listening on port 8080‘) server.listen(8080);
-
反向代理实现 (使用request模块来实现)
/** * 反向代理示例:使用request模块来实现反向代理 */ var nodeStatic = require(‘node-static‘).Server; var request = require("request"); var fs = require(‘fs‘); var fileServer = new nodeStatic(fs.realpathSync("/Users/yangyang.zhang/Work/wenba/fudao_activity/static/")); var http = require("http"); var httpServer = http.createServer(function(req, res) { var body =‘‘; req.addListener(‘data‘, function(chunk){ body += chunk; }) req.addListener(‘end‘, function() { fileServer.serve(req, res, function(err, result) { if (err && (err.status === 404)) { var p = ‘http://qa01-activity.xuebadev.com‘+req.url; req.headers[‘Host‘] = ‘qa01-activity.xuebadev.com‘; request({ method: req.method, url: p, headers: req.headers, body: body }).pipe(res); } }); }).resume(); }); httpServer.listen(8080); console.log(‘proxy listen in 8080‘);
参考文献
- 代理服务器-维基百科
- 正向代理与反向代理的区别
- NodeJS实现反向代理
- Nodejs实现一个http反向代理
- 用 nodejs 做反向代理服务器
- Nginx 配置介绍
[前端]代理知识入门介绍