详解node如何让一个端口同时支持https与http


Posted in Javascript onJuly 04, 2017

众所周知node是一个高性能的web服务器,使用它可以很简单的创建一个http或https的服务器。

比如一个很简单的http服务器:

var http = require('http');
var https = require('https');

var httpPort = 3345;

var server = http.createServer(function(req, res){
 res.writeHead(200, {'Content-Type': 'text/plain'});
 res.end('hello world!');
}).listen(httpPort);

https服务器需要生成证书,详情请看这篇文章:HTTPS 的原理和 NodeJS 的实现。这里我们直接看最终成果,附件证书。

var https = require('https');
var fs = require('fs');

var httpsPort = 3346;

var options = {
 key: fs.readFileSync('./cakey.pem'),
 cert: fs.readFileSync('./cacert.pem')
};

var sserver = https.createServer(options, function(req, res){
 res.writeHead(200, {'Content-Type': 'text/plain'});
 res.end('secured hello world');
}).listen(httpsPort);

从上文我们可以看出,node生成的每个服务器必须分配一个端口。那么如果我们在工作中遇到一个需求:让同一个端口或地址既支持http协议又支持https协议,这时候我们该怎么办,有的同学很可能想到用nginx做反向代理,这不失为一个解决方案,但这也同样意味着增加了产品的复杂度,用户并不想去折腾ngnix。

办法是有的,原理就要搬出OSI的七层模型:

详解node如何让一个端口同时支持https与http

HTTP与HTTPS都属于应用层协议,所以只要我们在底层协议中进行反向代理,就可以解决这个问题! 刚好node可以让我们很方便的创建一个tcp服务器!

所以我们的核心代码如下:

var net = require('net');
var http = require('http');
var https = require('https');
var fs = require('fs');

var httpPort = 3345;
var httpsPort = 3346;

var server = http.createServer(function(req, res){
 res.writeHead(200, {'Content-Type': 'text/plain'});
 res.end('hello world!');
}).listen(httpPort);

var options = {
 key: fs.readFileSync('./cakey.pem'),
 cert: fs.readFileSync('./cacert.pem')
};

var sserver = https.createServer(options, function(req, res){
 res.writeHead(200, {'Content-Type': 'text/plain'});
 res.end('secured hello world');
}).listen(httpsPort);

net.createServer(function(socket){
 socket.once('data', function(buf){
  console.log(buf[0]);
  // https数据流的第一位是十六进制“16”,转换成十进制就是22
  var address = buf[0] === 22 ? httpsPort : httpPort;
  //创建一个指向https或http服务器的链接
  var proxy = net.createConnection(address, function() {
   proxy.write(buf);
   //反向代理的过程,tcp接受的数据交给代理链接,代理链接服务器端返回数据交由socket返回给客户端
   socket.pipe(proxy).pipe(socket);
  });
  
  
  proxy.on('error', function(err) {
   console.log(err);
  });
 });
 
 socket.on('error', function(err) {
  console.log(err);
 });
}).listen(3344);

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
ExtJS 2.0实用简明教程之应用ExtJS
Apr 29 Javascript
javascript中IE浏览器不支持NEW DATE()带参数的解决方法
Mar 01 Javascript
jquery和javascript的区别(常用方法比较)
Jul 04 Javascript
html页面显示年月日时分秒和星期几的两种方式
Aug 20 Javascript
JavaScript学习笔记之Function对象
Jan 22 Javascript
AngularJs ng-route路由详解及实例代码
Sep 14 Javascript
微信小程序 缓存(本地缓存、异步缓存、同步缓存)详解
Jan 17 Javascript
vue.js学习之UI组件开发教程
Jul 03 Javascript
jQuery实现文字超过1行、2行或规定的行数时自动加省略号的方法
Mar 28 jQuery
LayUI表格批量删除方法
Aug 15 Javascript
详解js删除数组中的指定元素
Oct 31 Javascript
JavaScript canvas仿代码流瀑布
Feb 10 Javascript
Angular 2父子组件之间共享服务通信的实现
Jul 04 #Javascript
jQuery实现动态给table赋值的方法示例
Jul 04 #jQuery
Angular 2父子组件数据传递之局部变量获取子组件其他成员
Jul 04 #Javascript
Angular 4.X开发实践中的踩坑小结
Jul 04 #Javascript
jQuery操作DOM_动力节点Java学院整理
Jul 04 #jQuery
jQuery层级选择器_动力节点节点Java学院整理
Jul 04 #jQuery
jQuery简介_动力节点Java学院整理
Jul 04 #jQuery
You might like
这部番真是良心,画质好到像风景区,剧情让人跟着小公会热血沸腾
2020/03/10 日漫
php下使用无限生命期Session的方法
2007/03/16 PHP
PHP与MySQL开发中页面出现乱码的一种解决方法
2007/07/29 PHP
PHP 日期加减的类,很不错
2009/10/10 PHP
PHP如何抛出异常处理错误
2011/03/02 PHP
PHP常用技巧总结(附函数代码)
2012/02/04 PHP
PHP的一个完美GIF等比缩放类,附带去除缩放黑背景
2014/04/01 PHP
Symfony2实现在controller中获取url的方法
2016/03/18 PHP
php求数组全排列,元素所有组合的方法
2016/05/05 PHP
PHP用户验证和标签推荐的简单使用
2016/10/31 PHP
php实现网页上一页下一页翻页过程详解
2019/06/28 PHP
基于canvas实现的绚丽圆圈效果完整实例
2016/01/26 Javascript
JavaScript面向对象编写购物车功能
2016/08/19 Javascript
js遍历map javaScript遍历map的简单实现
2016/08/26 Javascript
详解微信小程序——自定义圆形进度条
2016/12/29 Javascript
javascript+html5+css3自定义提示窗口
2017/06/21 Javascript
electron demo项目npm install安装失败的解决方法
2018/02/06 Javascript
Vue 框架之键盘事件、健值修饰符、双向数据绑定
2018/11/14 Javascript
在vue中获取微信支付code及code被占用问题的解决方法
2019/04/16 Javascript
聊聊Vue 中 title 的动态修改问题
2019/06/11 Javascript
python实现的用于搜索文件并进行内容替换的类实例
2015/06/28 Python
Python正则表达式教程之一:基础篇
2017/03/02 Python
python3实现钉钉消息推送的方法示例
2019/03/14 Python
Python函数定义及传参方式详解(4种)
2019/03/18 Python
python读取当前目录下的CSV文件数据
2020/03/11 Python
python3.5的包存放的具体路径
2020/08/16 Python
软件测试常见笔试题
2012/02/04 面试题
儿媳婚宴答谢词
2014/01/14 职场文书
行政管理专业求职信
2014/07/06 职场文书
镇副书记专题民主生活会对照检查材料思想汇报
2014/10/02 职场文书
起诉书范文
2015/05/20 职场文书
2015年教务处干事工作总结
2015/07/22 职场文书
班主任寄语2016
2015/12/04 职场文书
房屋转让协议书(标准范本)
2016/03/21 职场文书
如何解决.cuda()加载用时很长的问题
2021/05/24 Python
Mysql数据库值的添加、修改、删除及清空操作实例
2021/06/20 MySQL