net,http,https net模块 创建客户端 响应头和响应体应该使用两个换行隔开
createConnection(options,callback); 1 2 3 4 5 6 7 8 9 const net = require ('net' );const socket = net.createConnection({ host : 'xyq135.com' , port : 80 }, () => { console .log('连接成功!' ) })
参数 options:配置参数
callback:监听函数
callback:处理函数
返回值 返回值为:socket,是一个特殊的文件, 在node中变现为双工流 对象:通过向流写入内容来发送数据,通过监听流的内容获取数据
创建服务端 net.createServer() 1 2 3 4 5 6 7 8 9 10 11 12 13 14 const net = require ('net' );const server = net.createServer();server.listen(9527 ); server.on('listening' , () => { console .log('server正在监听9527' ) }) server.on('connection' , socket => { console .log('有客户端连接!' ) })
返回值 server对象。
server.listen(port) 监听每个端口
server.on(‘listening’,()=>{}) 开始监听端口后触发的事件
server.on(‘connection’,socket=>{}) 某个连接到来时触发该事件。 事件监听函数会获得socket对象
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 const net = require ('net' );const server = net.createServer();server.listen(9527 ); server.on('listening' , () => { console .log('server正在监听9527' ) }) server.on('connection' , socket => { console .log('有客户端连接!' ) socket.on('data' , chunk => { console .log('客户端请求:' , chunk.toString('utf-8' )); }) socket.write(`HTTP/1.1 200 OK <html> <head><title>404 Not Found</title></head> <body> <center><h1>404 Not Found</h1></center> <hr><center>nginx</center> </body> </html> <!-- a padding to disable MSIE and Chrome friendly error page --> <!-- a padding to disable MSIE and Chrome friendly error page --> <!-- a padding to disable MSIE and Chrome friendly error page --> <!-- a padding to disable MSIE and Chrome friendly error page --> <!-- a padding to disable MSIE and Chrome friendly error page --> <!-- a padding to disable MSIE and Chrome friendly error page --> ` ) socket.end(); })
http模块 发送请求
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 const http = require ('http' );const request = http.request("http://nodejs.cn/api/http.html#httprequestoptions-callback" , { method : 'GET' , }, resp => { console .log('状态码:' , resp.statusCode); console .log('响应头:' , resp.headers); let result = '' ; resp.on('data' , chunk => { result += chunk.toString('utf-8' ); }) resp.on('end' , () => { console .log('响应体:' ) console .log(result); }) }) request.end();
方法返回结果为可写流,需要使用request.write()写入请求体,使用request.end()结束写入。
创建服务器
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 const http = require ('http' );const url = require ('url' );const server = http.createServer((req, res ) => { console .log('有请求来了!' ) console .log('请求地址:' , req.url); console .log('请求方法:' , req.method); console .log('请求头:' , req.headers); let body = '' ; req.on('data' , chunk => { body += chunk.toString('utf-8' ) }) req.on('end' , () => { console .log('请求体:' ); console .log(body); }) res.setHeader('name' , 'xyq' ); res.setHeader('lover' , 'hsz' ); res.statusCode = 404 ; res.write('I love you!' ); res.end(); }) server.listen(8080 ) server.on('listening' , () => { console .log('正在监听8080' ) })
客户端:
服务端
静态资源服务器(使用简单的readFile读取文件)
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 const http = require ('http' );const path = require ('path' );const fs = require ('fs' );const url = require ('url' );const server = http.createServer(handleServer);server.listen(9000 ); server.on('listening' , () => { console .log('server listening 9000!' ); }) async function handleServer (req, res ) { const requestUrl = req.url; const fileContent = await getFileContent(requestUrl); if (!fileContent) { res.write(fileContent) } else { res.statusCode = 404 ; res.write('sources is not exit!' ); } res.end(); } async function getState (filename ) { try { return await fs.promises.stat(filename) } catch { return null ; } } async function getFileContent (requestUrl ) { const urlObj = url.parse(requestUrl); let filename; filename = path.resolve(__dirname, 'public' , urlObj.pathname.substr(1 )); let stat = await getState(filename); if (stat) { return null ; } else if (stat.isDirectory()) { filename = path.resolve(__dirname, 'public' , urlObj.pathname.substr(1 ), 'index.html' ); stat = await getState(filename); if (!stat) { return null ; } else { return await fs.promises.readFile(filename); } } else { return await fs.promises.readFile(filename); } }
搭建静态资源服务器(通过流来读取)
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 const http = require ('http' );const path = require ('path' );const fs = require ('fs' );const url = require ('url' );const server = http.createServer(handleServer);server.listen(9000 ); server.on('listening' , () => { console .log('server listening 9000!' ); }) async function handleServer (req, res ) { const requestUrl = req.url; const fileContent = await getFileContent(requestUrl, res); if (!fileContent) { res.statusCode = 404 ; res.write('sources is not exit!' ); res.end(); } } async function getState (filename ) { try { return await fs.promises.stat(filename) } catch { return null ; } } async function getFileContent (requestUrl, res ) { const urlObj = url.parse(requestUrl); let filename; filename = path.resolve(__dirname, 'public' , urlObj.pathname.substr(1 )); let stat = await getState(filename); if (!stat) { return null ; } else if (stat.isDirectory()) { filename = path.resolve(__dirname, 'public' , urlObj.pathname.substr(1 ), 'index.html' ); stat = await getState(filename); if (!stat) { return null ; } else { readFileStream(filename, res); return true ; } } else { readFileStream(filename, res); return true ; } } function readFileStream (filename, res ) { const rs = fs.createReadStream(filename); rs.on('data' , chunk => { const flag = res.write(chunk); if (!flag) { rs.pause(); } }) res.on('drain' , () => { rs.resume(); }) rs.on('end' , () => { res.end(); }) }
https协议 https协议保证数据在传输过程中不被窃取或篡改。
加密 对称加密 产生一个秘钥,既可以加密,又可以解密。
常用算法:DE3、3DES、AES、Blowfish
非对称加密 产生一堆秘钥,一个用于加密,一个用于解密。 一个公钥,一个私钥。
常用算法:RSA、Elgamal、Rabin、D-H、ECC。
https的默认端口是443。
https模块