Как извлечь файлы .zip в каталог с лямбда-функцией - PullRequest
0 голосов
/ 04 марта 2020

Проблема, с которой я сталкиваюсь, заключается в том, что, когда я проверяю функцию на файл .zip, когда функция попадает в fs.createReadStream & Zip, функция не выполняется или не возвращает ошибку, и я хотел бы получить представление о том, что Я делаю неправильно и как будет выглядеть правильное решение.

const AWS = require('aws-sdk');
const fs = require('fs');
const mkdirp = require('mkdirp');
const unzipper = require('unzipper');

exports.handler = async (event, context) => {

    // Variables for bucket init
    let sourceBucket = 'am-doc-mgmt-s3-dev-landing';
    let storageBucket = 'am-doc-mgmt-s3-dev';

    // Variables for folder init and Buffer config
    const localZippedFolder = '/tmp/ZippedStudentData/';
    const localUnzippedFolder = '/tmp/UnzippedStudentData/';

    const ZipBuffer = Buffer.from(localZippedFolder, 'base64');
    const UnzippedBuffer = Buffer.from(localUnzippedFolder, 'base64');

    // Inits AWS s3 Bucket and DynamoDB
    let s3 = new AWS.S3();
    let docClient = new AWS.DynamoDB.DocumentClient({ region: 'us-east-1' });

    // Gets the file bucket and file name of the s3 object from context
    let fileBucket = event.Records[0].s3.bucket.name;
    let fileName = event.Records[0].s3.object.key;
    let params = {
        Bucket: fileBucket,
        Key: fileName
    };

    // Creates temporary variables
    let tempFile = localZippedFolder + fileBucket;
    let tempUnzippedFile = localUnzippedFolder + fileBucket;

    // Make Directories for Zipped and Unzipped files
    try {
        const zipDirFolder = await mkdirp(localZippedFolder, { recursive: true })
        const unZipDirFolder = await mkdirp(localUnzippedFolder, { recursive: true });
        console.log('SUCCESS: unzipped directory created!');
        console.log('SUCCESS: zipped directory create!')

    // Download files from s3 Bucket
        let newFolder = await s3.getObject(params).promise()
        .then(data => {
            console.log(data);
            return data;
        });

    // Extract files from zipped folder and store them in a local directory
       fs.createReadStream(params.Key)
        .pipe(unzipper.Extract({path: unZipDirFolder}))
        .on('finish', () => {
             fs.readdir(unZipDirFolder);
        }).on('error', (err) => {
             // error handling here
             console.log(err);
    });

    }   
     catch (error) {
        console.log(error);
    }
};

ошибка: ничего не возвращается из функции fs.createReadStream. Как будто он просто пропускает функцию.

1 Ответ

1 голос
/ 04 марта 2020

Честно говоря, трудно понять, какую проблему вы на самом деле пытаетесь решить, поскольку вы просто не очень конкретно c об этом. Если вы хотите, чтобы содержащаяся функция async не разрешала свое обещание до тех пор, пока не будет выполнено разархивирование, вы можете обернуть поток в обещание следующим образом:

const AWS = require('aws-sdk');
const fs = require('fs');
const mkdirp = require('mkdirp');
const unzipper = require('unzipper');

exports.handler = async (event, context) => {

    // Variables for bucket init
    let sourceBucket = 'am-doc-mgmt-s3-dev-landing';
    let storageBucket = 'am-doc-mgmt-s3-dev';

    // Variables for folder init and Buffer config
    const localZippedFolder = '/tmp/ZippedStudentData/';
    const localUnzippedFolder = '/tmp/UnzippedStudentData/';

    const ZipBuffer = Buffer.from(localZippedFolder, 'base64');
    const UnzippedBuffer = Buffer.from(localUnzippedFolder, 'base64');

    // Inits AWS s3 Bucket and DynamoDB
    let s3 = new AWS.S3();
    let docClient = new AWS.DynamoDB.DocumentClient({ region: 'us-east-1' });

    // Gets the file bucket and file name of the s3 object from context
    let fileBucket = event.Records[0].s3.bucket.name;
    let fileName = event.Records[0].s3.object.key;
    let params = {
        Bucket: fileBucket,
        Key: fileName
    };

    // Creates temporary variables
    let tempFile = localZippedFolder + fileBucket;
    let tempUnzippedFile = localUnzippedFolder + fileBucket;

    // Make Directories for Zipped and Unzipped files
    try {
        const zipDirFolder = await mkdirp(localZippedFolder, { recursive: true })
        const unZipDirFolder = await mkdirp(localUnzippedFolder, { recursive: true });
        console.log('SUCCESS: unzipped directory created!');
        console.log('SUCCESS: zipped directory create!')

        // Download files from s3 Bucket
        let newFolder = await s3.getObject(params).promise();

        await new Promise((resolve, reject) => {
            // Extract files from zipped folder and store them in a local directory
           fs.createReadStream(params.Key)
                .pipe(unzipper.Extract({path: unZipDirFolder}))
                .on('finish', resolve);
                .on('error', reject);
        });

    } catch (error) {
        console.log(error);
        // rethrow error so caller sees the error
        throw error;
    }
};

И ваш абонент, использующий эту экспортированную функцию, будет иметь использовать .then() или await в возвращенном обещании, чтобы знать, когда это будет сделано. И используйте .catch() или try/catch вокруг await, чтобы ловить ошибки.

...