nodejs实现递归遍历多层目录,并分组获取目录中的文件名称

需求:
递归遍历多层结构的目录,在其他位置创建响应结构的目录。
遍历目录的时候当目录中有文件时,获取该目录中所有的文件名称,并在创建新目录的时候在该目录对应的目录中创建一个txt文件用来保存响应的文件名称
问题:
现在可以创建目录,也可以获取文件名,但不能把文件名分组存放到响应的目录中,不能实现一一对应

示例:
源目录结构

目录1
    子目录1
        孙子目录1
            文件1、文件2、文件3
目录2
    子目录2
        孙子目录2
            文件1、文件2、文件3

希望实现

目录1
    子目录1
        孙子目录1
            文件1(这个文件里存放源对应目录中的文件名称)
            
目录2
    子目录2
        孙子目录2
            文件2(这个文件里存放源对应目录中的文件名称)
const fs = require('fs')
const path = require('path')
const join = require('path').join
const mkdirp = require('mkdirp')

let arr = []
function getImageFiles(imageFolder) {
    // 递归
    function findImages(imageFolder) {
        fs.readdir(imageFolder, (err, files) => { // 读取目录
            files.forEach((item, index) => { // item: 目录和文件名称
                // console.log(item);
                let filesPath = path.resolve(imageFolder, item) // 绝对路径:e:\wirteImgSrc\image
                fs.stat(filesPath, (err, stats) => { // 检测类型
                    if (err) throw err
                    if (stats.isDirectory()) {
                        let txtFolderPath = filesPath.replace('image', 'txt')
                        mkdirp(txtFolderPath, (err) => { // 批量创建目录
                            if (err) throw err
                        })
                        findImages(filesPath)
                    }
                    if (stats.isFile()) {
                        console.log(filesPath);
                        arr.push(item)
                        // console.log(arr);
                        //     setTimeout(function () {
                        //         let imageUrl = filesPath.split(path.sep).join('/') // 扶正反斜杠
                        //         imageUrl = imageUrl.replace(__dirname.split(path.sep).join('/'), '').replace('image/', '')
                        //         arr.push(imageUrl)
                        //         let createTxt = path.resolve(__dirname, imageFolder).replace('image', 'txt') + '/html.txt'
                        //         let txtContent = arr
                        //         fs.writeFile(createTxt, txtContent, 'utf-8', err => {
                        //             if (err) throw err
                        //         })
                        //     }, 1000)
                    }
                })
            })
        })
    }
    findImages(imageFolder)
}

getImageFiles("image")
阅读 4.8k
2 个回答

自己搞定了,记录一下~
还有很多优化空间,目前暂时理清楚了思路

const fs = require('fs')
const path = require('path')
const { sep } = path
const mkdirp = require('mkdirp')

let srcArr = [] // 初始化源文件名称空数组

// 递归文件目录、文件名
let readDir = function (rootFolder) {
    let exists = fs.existsSync(rootFolder),
        stat = fs.statSync(rootFolder)

    if (exists && stat) { //判断文件、目录是否存在
        if (stat.isFile() && srcArr.length === 0) { // 当数组为空时,表示还没有读取过文件
            let fpath = rootFolder.split(sep) // 路径按 \ 分割成数组
            // let fileName = fpath[fpath.length - 1] // 获取文件名
            let folderName = fpath[fpath.length - 2] // 获取有文件的目录名称

            fpath.length = fpath.length - 1 // 删除文件名
            let hasFileFolderName = fpath.join('/') // 有文件的目录路径
            srcArr = fs.readdirSync(hasFileFolderName) // 读取文件

            let htmlContent = initHtml(hasFileFolderName.replace('image', ''), srcArr) // 需要写入文件的内容

            fpath.length = fpath.length - 1 // 删除有文件的目录名称
            let targetFileNama = path.resolve(fpath.join('/').replace('image', 'txt') + '/' + folderName + '.txt') // 需要写入的文件名

            setTimeout(function () { // 等待目录生成后执行
                fs.writeFileSync(targetFileNama, htmlContent, 'utf-8') // 创建新文件
            }, 1000);
        } else if (stat.isDirectory()) {
            srcArr = [] // 清空一下数组
            let fpath = rootFolder.split(sep)
            fpath.length = fpath.length - 1 // 删除最后一层目录
            let targetFolder = fpath.join('/').replace('image', 'txt') // 需要生成的目标目录
            mkdirp(targetFolder, err => { // 生成新目录
                if (err) throw err
            })
            // console.info('====' + fpath + fpath[fpath.length - 1])
            let files = fs.readdirSync(rootFolder)
            if (files && files.length > 0) {
                files.forEach(function (file) {
                    readDir(rootFolder + sep + file) //递归
                })
            }
        }
    } else {
        console.info('根目录不存在.')
    }
}

// 初始化 HTML
let initHtml = (readFilePath, html) => {
    let reg = /^.*\.(jpg|jpeg|gif|png)$/i
    html = html.filter(item => reg.test(item)) // 过滤不是图片的文件
    readFilePath = encodeURI(readFilePath).replace(/\+/g, '%2B') // encodeURI 转码
    let img = ''
    html.forEach((item) => {
        item = encodeURI(item).replace(/\+/g, '%2B') // encodeURI 转码
        img += `\n<img src="http:www.xxy5.com${readFilePath}/${item}">`
    })
    html = `<div id="products_desc"  style="width: 100%; ">${img}\n</div>`
    return html
}

readDir('image')

不知道你在问什么 。。。。

撰写回答
你尚未登录,登录后可以
  • 和开发者交流问题的细节
  • 关注并接收问题和回答的更新提醒
  • 参与内容的编辑和改进,让解决方法与时俱进
推荐问题