Next js 中的 gridfs-stream 图像

问题描述

在“pages/api”中,尝试从客户端的 MongoDB 数据库中打印出 GridFS 图像。在(另一个)MERN-Stack 项目中工作,但似乎我在 Next.js 中遇到了问题。

pages/api/uploads/files/index.js 有效(我在客户端获取返回的文件):

    import Grid from 'gridfs-stream'
    Grid.mongo = mongoose.mongo;

    export default async function handler(req,res) {
        const { method } = req
    
        const conn = await mongoose.createConnection(db,{
            useNewUrlParser: true,useUnifiedTopology: true
        });
    
        switch (method) {
            case 'GET':
                try {
                    const files = await conn.db.collection("uploads.files").find().toArray()
                    if(!files || files.length === 0) {
                        return res.status(404).json({ err: 'No file exist' });
                    } else {
                        files.map(file => {
                            if (
                                file.contentType === 'image/jpeg' ||
                                file.contentType === 'image/jpg' ||
                                file.contentType === 'image/png'
                            ) {
                                file.isImage = true;
                            } else {
                                file.isImage = false;
                            }
                        });
                        return res.send(files);
                    }
                } catch (error) {
                    res.status(400).json({ itemnotfound: "No file found" })
                }
                break
            default:
                res.status(400).json({ itemnotfound: "No file" })
            break
        }
    }

pages/api/uploads/image/[filename].js 问题(记录“1 API / 3 API”)

import Grid from 'gridfs-stream'
Grid.mongo = mongoose.mongo;

export default async function handler(req,res) {        
    const {
      query: { filename },method,} = req
    
    const conn = await mongoose.createConnection(db,{
        useNewUrlParser: true,useUnifiedTopology: true
    });

    conn.once('open',() => {
        gfs = Grid(conn.db);
        gfs.collection('uploads');
    });

    switch (method) {
        case 'GET':
            try {
                const file = await conn.db.collection("uploads.files").findOne({ filename: filename })
                if(!file || file.length === 0){
                    return res.status(404).json({ err: "Could not find file" });
                } else if(
                    file.contentType === 'image/jpeg' ||
                    file.contentType === 'image/jpg' ||
                    file.contentType === 'image/png'
                ) {
                    console.log("1 API ",file) // gets printed out
                    const readstream = gfs.createReadStream(file.filename);
                    readstream.pipe(res);
                } else {
                    console.log("2 API")
                    res.status(404).json({ err: 'Not an image' });
                }
            } catch (error) {
                console.log("3 API")  // after "1 API",this gets called
                res.status(400).json({ itemnotfound: "No image found" })
            }
            break
        default:
            res.status(400).json({ itemnotfound: "No image" })
        break
    }
}

在客户端,我有一个等待图像的 img 标签

pages/index.js

<img key={f.uploadDate} src={`/api/uploads/image/${f.filename}`} alt={f.filename} width="50" height="50"></img>

这可能是 readstream.pipe(res) 的问题,因为 console.log 打印出“1 API”(和文件),然后打印出“3 API”,但我不知道是什么。

提前致谢!

解决方法

发现问题。以下行不起作用:

conn.once('open',() => {...})

显然,'open()' 已被弃用,您可以在此处找到更多信息: https://github.com/Automattic/mongoose/issues/5399

所以我只是删除了它,但保留了外部块中的行:

...
const conn = await mongoose.createConnection(db,{
    useNewUrlParser: true,useUnifiedTopology: true
});

gfs = Grid(conn.db);
gfs.collection('uploads');

switch (method) {
...