node中有一组流api,它们可以像处理网络流一样处理文件。流api用起来非常方便,本节学习介绍文件处理基础和流的概念。
处理文件路径需要用到一个核心模块(path),path模块可以规范化、连接、解析路径,还可以将绝对路径转换为相对路径,提取路径的组成以及判断路径是否存在。
在存储和使用路径前最好能够将其进行规范化,这里使用path模块的normalize()函数
1 //规范化路径 2 var path=require('path'); 3 path.normalize('/pathstudy//path1') 4 // =>'/pathstudy/path1'
通过path.join()函数可以连接多个路径字符串,如下所示:
1 //连接路径 2 var path=require('path'); 3 path.join('/pathstudy','path1','test'); 4 // => '/pathstudy/path1/test'
使用path.resolve()函数将多个路径解析为一个规范化的路径
1 //解析路径 2 var path=require('path'); 3 path.resolve('/foo/bar','./dd'); 4 // =>/foo/bar/dd使用path.exists()函数判断路径是否存在,0.8版本以后使用fs.exists()函数代替,只需将导入模块替换为fs即可。
1 //判断路径是否存在 2 var path=require('path'); 3 path.exists('/foo/bar/dd',function(exists){ 4 console.log('是否存在:',exists); 5 })fs核心模块内置查询文件信息和打开/读写/关闭文件操作
使用fs.stat()函数查询文件特征,例如大小、创建时间、权限等
//查询文件信息 var fs=require('fs'); fs.stat('/foo/bar/dd',function(stats){ console.log(stats);//打印出文件信息 stats.isFile();//判断是否文件 stats.isDirectory();//判断是否目录 stats.isSocket();//判断是否UNIX套接字 //... });文件模式类型:
r——数据流的位置从起始处打开文件读取
r+——数据流的位置从起始处打开文件读写
w——如果文件存在则清零,不存在则创建文件并写入数据,数据流的位置从文件起始处
w+——打开文件进行读写,如果文件存在则清零,不存在则创建文件并写入数据,数据流的位置从文件起始处
a——打开文件写入数据,如果文件存在则清零,不存在则创建文件,数据流的位置从文件结尾处,写操作都将追加到文件后面
a+——打开文件读写数据,如果文件存在则清零,不存在则创建文件,数据流的位置从文件结尾处,写操作都将追加到文件后面
需要注意,在读写文件操作回调函数执行之后,不要使用提供的缓冲区,不然可能会导致读写数据不完整。
流是由几个node对象实现的抽象概念,创建或读取流的方式取决于使用流的类型,流的特性包含可读流和可写流,通过监听data事件,在流每次提交数据时,都能够得到通知。
可以指定createReadStream和createWriteStream函数的第二个参数,用来设置文件的起始结束位置、编码格式等等,参数选项如下所示:
encoding——data事件发送的编码格式fd——如果已经有一个打开文件描述符则可以传入该参数选项bufferSize——要被读取的每个文件块大小,单位是字节,默认64kbstart——设置文件中第一个被读取的字节位置,用来限制读取数据范围end——与start相反flags——表示用于打开文件的模式类型mode——指定要打开文件的权限当客户端的网络连接速度较慢时,可写流也就慢速,可读流会快速产生data事件并监听,数据被发送到可写流,导致node不得不缓存数据导致缓冲区被快速填满。
一般情况可以通过暂停数据生产者来避免这个问题:
1 var http=require('http'); 2 var fs=require('fs'); 3 http.createServer(function(req,res){ 4 var rs= fs.createReadStream('/foo/bar/file'); 5 6 rs.on('data',function(data){ 7 if(!res.write(data)){ 8 rs.pause();//暂停可读流 9 } 10 }); 11 12 rs.on('drain',function(){ 13 rs.resume();//恢复可读流 14 }); 15 16 rs.on('end',function(){ 17 res.end();//结束操作 18 }); 19 20 }).listen('8080'); View Code扩展:使用pipe函数操作上述暂停/恢复操作
1 var http=require('http'); 2 var fs=require('fs'); 3 http.createServer(function(req,res){ 4 var rs= fs.createReadStream('/foo/bar/file'); 5 rs.pipe(res);//由传输源调用并接受目标可写流作为参数 6 }).listen('8080'); 7 8 http.createServer(function(req,res){ 9 var rs= fs.createReadStream('/foo/bar/file'); 10 //默认情况下end()在可读流结束时在可写流上被调用,设置第二个参数end选项为false表示不让pipe函数进行end操作 11 rs.pipe(res,{end:false}); 12 13 rs.on('end',function(){ 14 res.write('endend~~'); 15 res.end();//结束操作 16 }); 17 }).listen('8080'); View Code对于流我表示比较懵逼,对概念理解的还不是很透彻。。
转载于:https://www.cnblogs.com/flypig-322/p/10269589.html
