当前位置: 首页 > 后端技术 > Node.js

搭建自己的服务器

时间:2023-04-03 19:53:19 Node.js

什么是服务器?在开始搭建自己的服务器之前,我们先明确一下服务器的定义:管理资源并为用户提供服务的计算机软件。服务器按功能分为两种:静态web服务器,如常见的nginx、apache等;动态web服务器,如常见的tomcat、jboss、resin等。动态和静态服务器的区别一般是阅读静态服务器的资源,然后返回给浏览器;动态服务器是指返回给浏览器的文件是通过逻辑处理动态生成的。服务端的功能特性,nginx和tomcat,之前都用过和研究过,所以就拿这两个来举例,但是现在用的很少了,基本都是和node相关的,所以最后搭建的serve会基于节点。nginx的特点Nginx配置简单灵活(只有一个主配置文件nginx.conf)支持高并发(静态小文件)占用资源相对少(2w并发,开启10个线程,内存消耗只有几百M)并且具有多种功能(例如proxy、cache、Log、Gzip等)nginx应用场景静态服务器(image、js、css等)server{listen8080;服务器名称本地主机;位置/{根html;indexindex.htmlindex.htm;}}上面解释的是nginx配置,指定访问根目录和默认主页,以及监听端口?~clear?~curl-ihttp://127.0.0.1:8080HTTP/1.1200OKServer:nginx/1.12.2//服务器类型和版本Date:Fri,02Mar201808:49:44GMTContent-Type:text/htmlContent-Length:11Last-Modified:Fri,02Mar201808:46:27GMT//支持Last-Modified缓存mechanismConnection:keep-alive//支持长连接ETag:"5a990f63-b"//支持ETag缓存机制Accept-Ranges:bytes//支持断点resumehellojsdt%//响应体说明上面是本地测试request,从responseheader可以看到支持很多功能性的反向代理,上面负载均衡的描述是上游的实验结果jsdt.com{server127.0.0.1:8083max_fails=3fail_timeout=30sweight=1;服务器47.97.xxx.xxx:8084max_fails=3fail_timeout=30sweight=2;//为了安全隐藏真实ip地址}server{listen8080;服务器名称本地主机;位置/{根html;#索引index.htmlindex.htm;proxy_passhttp://jsdt.com;proxy_redirect默认;}error_page500502503504/50x.html;location=/50x.html{根html;}}说明我把上面配置的关键部分提取出来,采用了轮训+权值算法。其他包括ip_hash、url_hash等算法的真正应用,需要考虑的问题很多,比如集群会话同步。记得大学实习的时候,公司用的是cookie+memcache的集群方案。tomcattomcat特点tomcat运行在jvm上,跨平台,是一个servlet容器(可以运行servlet,编译jsp),实现了http请求响应处理中需要的http接口相关的实现类。此外,它还支持虚拟主机、session共享、静态文件处理等,只是没有那么专业。tomcat应用场景描述如上图。我们可以在页面中加入动态的处理逻辑,返回的数据可以根据用户自定义(相比静态服务器的优势)。最后,.jsp通过tomcat编译成.java,再通过javac编译成.java的普通字节码文件,最终运行在jvm上。如何实现自己的服务器在实现自己的服务器之前,我们先搞清楚服务器的本质。server属于应用层的协议,基于tcp的封装,tcp的应用实现是基于socket(node和java都有socket)封装。socket监听某个端口,获取面向流的data数据。我们服务器需要做的就是对数据进行解析封装,使其符合http规范。接下来实现自己的静态服务器因为有http模块,所以在node中实现一个基本的服务器非常简单。但是如果你添加了额外的功能,比如压缩、缓存、断点续传、反向代理等,就需要自己添加了。接下来,先看看项目结构。bin目录主要和启动脚本有关。主要逻辑在app.js中,然后根据功能将代码拆分到不同的模块中。templatet目录包含编译后的原始模板。|____斌||____.DS_Store||____deamon.js||____开始||____yargsConfig.js|____node_modules|____package-lock.json|____package.json|____readme.md|____src||____.DS_Store|____资产||____cacheSupport.js||____config.js||____picGuard.js||____模板||____util.js服务器运行之前,首先我们通过yargs模块获取解析后的命令行参数。如下if(argv.D){letsp=cp.spawn(process.execPath,['deamon.js'],{cwd:__dirname,stdio:['ignore','ignore','ignore'],env:argv,detached:true//http://nodejs.cn/api/child_process.html#child_process_child_process_spawn_command_args_options})sp.unref()}else{letconfig=Object.assign({},defautConfig,argv)letserver=新服务器(配置);服务器.start();console.log('serveralreadystarted')}表示如果开启了deamon模式,服务会通过子进程在后台运行,否则在启动时直接启动服务器实例,在服务器启动后接受并处理请求。下面以resume功能模块为例res.setHeader('Accept-Range','bytes')res.statusCode=206//部分内容letresult=range.match(/bytes=(\d*)-(\d*)/);如果(结果){开始=isNaN(结果[1])?开始:parseInt(结果[1]);结束=isNaN(结果[2]])?结束:parseInt(结果[2])-1;}}returnfs.createReadStream(filepath,{start,end})}module.exports={byteRangeStream}使用说明在主模块app.js中,导入以上模块,如代码所示,先判断客户端是否支持断点续传传输,根据range请求头,如果有请求范围,直接返回请求范围内的数据,否则全部读取返回,依赖浏览器和服务器的协商机制,需要双方的支持才能完成整个过程。更多功能模块可以参考我的github。欢迎加星。总结写这篇文章,总结了服务器的相关知识,参考了之前大学做的笔记,看了之前做的记录,回忆了当时在学校学习和在公司实习的经历,充满了感慨。时光飞逝,做你自己。