nodejs 实现文件拷贝

通过4中不通的方式实现对一个文件的拷贝

方式一:readFile 异步一次性读取文件再写入

//异步形式读取文件
function copyFile(url){
    const extName = path.extname(url)
    const fileName = path.basename(url)
    const dirName = path.dirname(url)
    fs.readFile(url, (err, data) => {
        fs.writeFile(`${dirName}/${fileName}_copy_1${extName}`, data , err => {
            if(err){
                console.log(`写入出现错误 ${err.toString()}`)
            }else{
                console.log('完成!')
            }
        })
    })
}

方式二:readFileSync 同步一次性读取文件再写入

//同步形式读取文件
function copySync(url){
    const extName = path.extname(url)
    const fileName = path.basename(url)
    const dirName = path.dirname(url)
    var data = fs.readFileSync(url)    
    fs.writeFileSync(`${dirName}/${fileName}_copy_1${extName}`,data)
    console.log('同步拷贝完成!')
}

方式三:使用流边读边写

const fs = require('fs')
const path = require('path')

// 使用流拷贝
function streamCopyFile(url){
    const extName = path.extname(url)
    const fileName = path.basename(url)
    const dirName = path.dirname(url)
    let options = {
        highWaterMark : 64 * 1024 //默认值,每个chunk的大小
    }
    const readable = fs.createReadStream(url, options)
    const writable = fs.createWriteStream(`${dirName}/${fileName}_copy${extName}`)
    var size = 0
    var totalSize = 0
    const stat = fs.stat(url, (err , stats) => {
        totalSize = stats.size
    })
    readable.on('open', () => {
        console.log('打开文件');
    })
    readable.on('data', data => {
        size = data.length + size
        console.log('已完成 ' + parseInt((size / totalSize) * 100) + '%');
        writable.write(data)
        readable.pause()
    })
    readable.on('end', () => {
        console.log('读取完成')
    })
    readable.on('error', err => {
        console.log(`读取时出现错误 ${err.toString()}`)
    })
    writable.on('error', err => {
        console.log(`写入时出现错误 ${err.toString()}`)
    })
    //将内存中数据全部写入文件后触发 drain 事件
    writable.on('drain', () => {
        readable.resume()
    })
    writable.on('finish', () => {
        console.error('写入完成');
    })
}

方式四:使用pipe

//通过管道的方式
function pipeCopyFile(url){
    const extName = path.extname(url)
    const fileName = path.basename(url)
    const dirName = path.dirname(url)
    const readable = fs.createReadStream(url)
    const writable = fs.createWriteStream(`${dirName}/${fileName}_copy_2${extName}`)
    var size = 0
    var totalSize = 0
    const stat = fs.stat(url, (err , stats) => {
        totalSize = stats.size
    })
    writable.on('pipe', (src) => {
        console.log('有数据正通过管道流入写入器')
    })
    writable.on('finish', () => {
        console.error('写入已完成')
    })
    readable.pipe(writable)
}

方法一和方法二使用起来简单,但是在操作大文件时对内存压力大,不推荐读取大文件使用

另外如果需要对文件制定块进行读取和写入请使用read 、write 两个方法

posted @ 2018-12-10 11:51  吃饭睡觉打豆豆o  阅读(572)  评论(0编辑  收藏  举报