【问题标题】:How should attached files be saved?附件应该如何保存?
【发布时间】:2021-07-18 23:29:40
【问题描述】:

我目前正在使用 Multer 这样做,但我不确定最佳做法是什么。

文件保存在files 文件夹中,命名约定如下:uid-filename

例如。 pdMNjRYIJTn9vw84tPCF-some_file_name.jpg.

使用 UID 的原因是允许保存具有相同名称的文件。下载的文件名称中没有 UID。

这是一个好方法吗?有什么可以改进的?

表格

id recordId originalName uid fileName extension path size userId created
1 6 some_file_name.jpg pdMNjRYIJTn9vw84tPCF pdMNjRYIJTn9vw84tPCF-some_file_name.jpg jpg /uploads/pdMNjRYIJTn9vw84tPCF-some_file_name.jpg 76463 1 2021-04-25 11:53:17

客户

async function uploadFile(file) {
    let formData = new FormData();

    formData.append("file", file);
    formData.append("recordUid", recordUid);

    let res = await fetchPostFile("/api/files", formData);
}

服务器

const storage = multer.diskStorage({
    destination: filesFolderPath,
    filename: (req, file, cb) => {
        let uid = generateUid();
        cb(null, `${uid}-${file.originalName}`);
    },
});

const upload = multer({
    storage: storage,
    limits: { fileSize: 1024 * 1024 * 10 }, // 10 mb
});

router.post("/api/files", upload.single("file"), async (req, res, next) => {
    try {
        let { recordUid } = req.body;
        let { originalName, filename, path, size } = req.file;

        let parts = originalName.split(".");
        let extension = parts[parts.length - 1];
        let uid = filename.substring(0, 20);

        let query = `
            insert into file
                (
                    recordId, 
                    originalName, 
                    uid, 
                    fileName, 
                    extension, 
                    path, 
                    size, 
                    userId, 
                    created
                )
            values
                (
                    (select id from record where uid = ?), 
                    ?, 
                    ?, 
                    ?, 
                    ?, 
                    ?, 
                    ?, 
                    ?, 
                    now()
                );
        `;

        let rows = await req.asyncQuery(query, [recordUid, originalName, uid, filename, extension, path, size, req.userId]);

        res.status(200).send({ success: true });
    } catch (err) {
        next(err);
    } finally {
        req.connection.release();
    }
});

【问题讨论】:

    标签: javascript mysql linux filesystems multer


    【解决方案1】:

    您的方法很干净,尽管我个人不会使用 32 位 UUID,而是将用户(进行上传)的 ID 与当前时间戳一起混淆。简而言之,只有时间戳应该这样做,因为传入的文件都有不同的名称,所以如果它们都具有相同的时间戳是有意义的。这更像你已经拥有的,但我的(文件名)会更短。所以尽量保守一点。

    您提到下载的文件中没有 uid。使用我上面解释的方法,在将文件提供给客户端之前,您不必担心截断 uuid。这与我们的设备(手机、笔记本电脑等)用于保存文件的约定相同。附加时间戳。

    这只是我的意见。

    【讨论】:

    • 截断uuid是什么意思?
    • 在发送回客户端之前剥离 uid。
    • 这是您第二次询问截断,所以我假设您不知道这意味着什么。截断仅仅意味着根据牛津词典缩短持续时间或范围。
    • 我设法重构了代码,因此名称中不再包含 UID。这些文件以 UID 作为名称保存在磁盘上,没有扩展名。如果有人想下载它,我重命名文件并添加扩展名。
    【解决方案2】:

    原始文件名应在磁盘上被截断但保存在数据库中以供参考。只需通过 (U)UID 识别磁盘文件。

    【讨论】:

    • 您能解释一下在磁盘上截断是什么意思吗?
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2019-03-11
    • 1970-01-01
    • 1970-01-01
    • 2018-07-02
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多