You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用Go上传PNG图片到MinIO时报no such file or directory错误如何解决

错误原因

触发报错的核心原因是FPutObject参数逻辑传递错误,同时没有正确处理Gin框架上传的临时文件:

  • minio.FPutObject的第四个参数要求填写本地待上传文件的路径,你传递的是期望存到MinIO侧的路径/sensors/xxx.png,本地服务器不存在该路径,直接触发找不到文件的错误。
  • 你当前通过c.FormFile仅拿到了上传文件的元数据,没有将用户上传的文件存储到本地磁盘,就算填对本地路径也会找不到对应文件。
  • 额外参数错误:你当前FPutObject第三个参数(MinIO侧存储的对象名)仅填了原始文件名,没有带sensors/前缀,就算上传成功文件也不会存入你提前创建的sensors目录下。
  • 隐藏bug:原有代码上传成功后使用了utilities.Info.Panicf打印结果,会直接触发panic终止程序,需要修改为普通日志打印方法。
修复方案

推荐直接使用PutObject方法读取文件流上传,无需额外将文件存到本地磁盘,修改fileNormalIcon != nil分支内的逻辑即可:

if fileNormalIcon != nil {
    // 打开上传的文件流
    src, err := fileNormalIcon.Open()
    if err != nil {
        utilities.Error.Printf("Open upload file error: %s", err)
        response[config.MESSAGE_RESPONSE_INDEX] = fmt.Sprintf("err: %s", err.Error())
        c.JSON(http.StatusInternalServerError, response)
        return
    }
    defer src.Close()

    // 拼接MinIO侧的存储路径,存入sensors目录
    objectName := "sensors/" + fileNormalIcon.Filename
    // 调用PutObject上传流,无需本地存储文件
    output, err := minioClient.PutObject(ctx, bucketName, objectName, src, fileNormalIcon.Size, minio.PutObjectOptions{ContentType: contentType})
    if err != nil {
        utilities.Error.Printf("Error upload image to bucket: %s", err)
        response[config.MESSAGE_RESPONSE_INDEX] = fmt.Sprintf("err: %s", err.Error())
        c.JSON(http.StatusInternalServerError, response)
        return
    }

    utilities.Info.Printf("upload result: %+v", output)
    data["normal_icon"] = objectName
    dataUpdateExist = true
}
可选方案(坚持使用FPutObject的场景)

如果需要先将文件存到本地再上传,可以先将Gin上传的文件保存到本地临时目录,再调用FPutObject:

import "os"

// ... 其他原有代码不变
if fileNormalIcon != nil {
    // 先创建本地临时存储目录(如果不存在)
    if err := os.MkdirAll("./temp", 0755); err != nil {
        utilities.Error.Printf("Create temp dir error: %s", err)
        response[config.MESSAGE_RESPONSE_INDEX] = fmt.Sprintf("err: %s", err.Error())
        c.JSON(http.StatusInternalServerError, response)
        return
    }
    // 自定义本地临时存储路径
    localTempPath := "./temp/" + fileNormalIcon.Filename
    // 保存上传的文件到本地
    if err := c.SaveUploadedFile(fileNormalIcon, localTempPath); err != nil {
        utilities.Error.Printf("Save upload file to local error: %s", err)
        response[config.MESSAGE_RESPONSE_INDEX] = fmt.Sprintf("err: %s", err.Error())
        c.JSON(http.StatusInternalServerError, response)
        return
    }
    // 拼接MinIO侧的存储路径
    objectName := "sensors/" + fileNormalIcon.Filename
    // 调用FPutObject上传本地文件
    output, err := minioClient.FPutObject(ctx, bucketName, objectName, localTempPath, minio.PutObjectOptions{ContentType: contentType})
    if err != nil {
        utilities.Error.Printf("Error upload image to bucket: %s", err)
        response[config.MESSAGE_RESPONSE_INDEX] = fmt.Sprintf("err: %s", err.Error())
        c.JSON(http.StatusInternalServerError, response)
        return
    }
    // 上传完成后可以选择删除本地临时文件释放磁盘
    _ = os.Remove(localTempPath)

    utilities.Info.Printf("upload result: %+v", output)
    data["normal_icon"] = objectName
    dataUpdateExist = true
}

内容的提问来源于stack exchange,提问作者Titanio Yudista

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.03 06:24:04