Невозможно извлечь содержимое файла из вложенного каталога с помощью Node.js

#node.js #fs

#node.js #fs

Вопрос:

Я пытаюсь прочитать содержимое файлов из каталога, используя node.js . Но в этой папке снова может быть какой-то вложенный каталог, поэтому мне нужно прочитать каждый файл, присутствующий внутри корневого каталога. Я объясняю свой код ниже.

 checkDirectory = async (path) => {
    let fileArr = [];
    let flag = 0;

    if (!_.isEmpty(path)) {
        fs.readdirSync(`${path}`).forEach(f1 => {
            fs.lstat(`${path}/${f1}`, (err, stat) => {
                if (!err) {
                    if (stat.isFile()) {
                        flag = 1;
                        let rawdata = fs.readFileSync(`${path}/${f1}`, {
                            encoding: 'utf8',
                            flag: 'r'
                        });
                        fileArr.push({
                            rawContent: rawdata,
                            fileName: f1
                        });
                    }
                    if (stat.isDirectory()) {
                        flag = 0;
                        const fullPath = `${path}/${f1}`;
                        checkDirectory(fullPath);
                    }
                }
            })
        })
    }
    if (falg === 1) {
        return fileArr;
    }
}
let dataArr = [];
fs.readdirSync(`${process.env['root_dir']}/uploads}`).forEach(f => {
    fs.lstat(`${process.env['root_dir']}/uploads/${f}`, (err, stat) => {
        if (!err) {
            if (stat.isFile()) {
                let outputObj = {};
                let rawdata = fs.readFileSync(`${process.env['root_dir']}/uploads/${f}`, {
                    encoding: 'utf8',
                    flag: 'r'
                });
                if (!_.isEmpty(rawdata)) {
                    const contentToBase64 = Buffer.from(rawdata, "utf8").toString('base64');
                    outputObj = {
                        fileName: f,
                        fileData: contentToBase64
                    }
                    dataArr.push(outputObj);
                }
            }
            if (stat.isDirectory()) {
                const fullPath = `${process.env['root_dir']}/uploads/${f}`;
                let fileContentArr = checkDirectory(fullPath);
                for (let e of fileContentArr) {
                    if (!_.isEmpty(e.rawContent)) {
                        const contentToBase64 = Buffer.from(e.rawContent, "utf8").toString('base64');
                        outputObj = {
                            fileName: e.fileName,
                            fileData: contentToBase64
                        }
                        dataArr.push(outputObj);
                    }
                }
            }
        }
    });
})
}
console.log('dataArr', dataArr);
 

Здесь я пытаюсь прочитать содержимое файла из uploads папки. Когда я выполняю этот код, он выдает следующую ошибку.

Ошибка:

 dataArr []
/app/controller/usecaseWorkflowCtrl.js:135
                                    for(let e of fileContentArr) {
                                                 ^

TypeError: fileContentArr is not iterable
 

Здесь также я проверяю, присутствует ли какая-либо вложенная папка внутри uploads папки, и считываю все файлы из этих вложенных каталогов. checkDirectory метод используется для чтения файлов из вложенного каталога.

Мне нужно прочитать все файлы из uploads каталога и отправить их dataArr . После прочтения всех файлов затем console.log('dataArr', dataArr); следует выполнить. Согласно моему текущему коду, это консольное сообщение выполняется с самого начала и выдает некоторую ошибку. Пожалуйста, помогите мне устранить эту ошибку и выполнить скрипт в соответствии с моим ожидаемым результатом.

Комментарии:

1. Почему нет возврата checkDirectory(fullPath); ? Не должно ли это быть return checkDirectory(fullPath);

Ответ №1:

Дождитесь CheckDirectory, прежде чем использовать его. Вы можете выполнить это, превратив функцию в обещание. https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Promise . У вас может быть что-то вроде этого:

 checkDirectory = (path) => {
    return new Promise((resolve, reject) => {
        let fileArr = [];
        let flag = 0;

        if (!_.isEmpty(path)) {
            fs.readdirSync(`${path}`).forEach(f1 => {
                fs.lstat(`${path}/${f1}`, (err, stat) => {
                    if (!err) {
                        if (stat.isFile()) {
                            flag = 1;
                            let rawdata = fs.readFileSync(`${path}/${f1}`, {
                                encoding: 'utf8',
                                flag: 'r'
                            });
                            fileArr.push({
                                rawContent: rawdata,
                                fileName: f1
                            });
                        }
                        if (stat.isDirectory()) {
                            flag = 0;
                            const fullPath = `${path}/${f1}`;
                            checkDirectory(fullPath);
                        }
                    }
                })
            })
        }
        if (falg === 1) { // why do you need this
            return resolve(fileArr);
        }
    });
}
 

Затем используйте его как:

 let fileContentArr = await checkDirectory(fullPath);