代码之家  ›  专栏  ›  技术社区  ›  jsur

mongodb gridfs api返回corrupt.zip

  •  1
  • jsur  · 技术社区  · 6 年前

    上下文:

    node.js/loopback应用程序,该应用程序使用包含旧版企业CRM应用程序数据的.zip文件填充其数据库。我正在尝试将.zip文件的二进制文件存储到我的数据库中,以便进行生产调试,使用gridfs,因为该文件可以是>16MB,并使用管理端点随时检索该文件。

    问题:

    我可以用函数存储zip文件 storeLatestZipFile 在我的模块中,我可以使用该函数的端点来检索它。 createLatestZipEndpoint 创建。

    但是,我要返回的.zip文件比原始文件大(14.7MB对21.1MB),而且它也已损坏。

    我假设我没有对数据进行编码,或者只是没有正确地使用gridfs api。有没有人会发现我的代码中的错误/在用gridfs存储.zips方面有更多的经验?

    相关模块:

    const { pino } = require('amf-logger');
    const fs = require('fs');
    const mongo = require('mongodb');
    
    const log = pino({ name: 'bot-zip-upload-storage' });
    
    /**
     * @param {string} path Path to the zip file to be persisted.
     * @param {object} app Loopback application instance.
     */
    function storeLatestZipFile(path = './', app = {}) {
      log.info('**** Starting streaming current uploaded zip to DB ****');
      const zipReadStream = fs.createReadStream(path, { encoding: 'binary' });
      const { db } = app.dataSources.mongo.connector;
      const bucket = new mongo.GridFSBucket(db);
      bucket.delete('zipfile', () => {
        log.info('deleted old zipfile');
    
        const uploadStream = bucket.openUploadStreamWithId(
          'zipfile',
          `bot-data-${new Date().toISOString()}`,
          {
            contentType: 'application/zip'
          }
        );
    
        zipReadStream.pipe(uploadStream);
      });
    }
    
    /**
     * @param {object} app Loopback application instance.
     */
    async function createLatestZipEndpoint(app = {}) {
      if (!app.get) {
        log.error("app object does not have 'get' property.");
        return;
      }
    
      app.get('/api/admin/latestzip', async (req, res) => {
        if (!req.headers.latestfile || req.headers.latestfile !== process.env.ADMIN_LATESTFILE) {
          res.sendStatus(403);
          return;
        }
    
        try {
          const { db } = app.dataSources.mongo.connector;
          const bucket = new mongo.GridFSBucket(db);
          res.writeHead(200, { 'Content-Type': 'application/zip' });
          const downloadStream = bucket.openDownloadStream('zipfile');
          log.info('download stream opened, begin streaming');
          downloadStream.pipe(res);
        } catch (err) {
          log.error(`error getting zipfile: ${err}`);
          res.sendStatus(500);
        }
      });
    }
    
    module.exports = {
      storeLatestZipFile,
      createLatestZipEndpoint
    };
    1 回复  |  直到 6 年前
        1
  •  1
  •   Juha Lindstedt    6 年前

    createReadStream buffer

    const zipReadStream = fs.createReadStream(path);