GoFiber 从零系列(四):腾讯云cos实现文件上传

858 阅读1分钟

GitHub项目地址

GoFiber 从零系列(一):项目创建&配置文件&gorm-mysql

GoFiber 从零系列(二):热加载/热更新 && 日志系统 && 验证入参

GoFiber 从零系列(三):JWT注册,登录

GoFiber 从零系列(四):腾讯云cos实现文件上传

GoFiber 从零系列(五):腾讯云SMS && goredis && 简单的短信登录功能

安装插件

go get -u github.com/tencentyun/cos-go-sdk-v5

修改app.ini配置文件

...
# 添加
[tencent_cos]
SECRET_ID = 腾讯云SECRET_ID
SECRET_KEY = 腾讯云SECRET_KEY
BUCKET = 腾讯云桶名
COS_URL = 腾讯云cos地址

修改setting.go

package setting

import (
	"time"

	"github.com/go-ini/ini"
	"github.com/jinpikaFE/go_fiber/pkg/logging"
)

var (
	Cfg *ini.File

	RunMode string

	HTTPPort     int
	ReadTimeout  time.Duration
	WriteTimeout time.Duration

	PageSize  int
	JwtSecret string

	SecretId  string
	SecretKey string
	CosUrl    string
)

func init() {
	var err error
	Cfg, err = ini.Load("conf/app.ini")
	if err != nil {
		logging.Fatal("Fail to parse 'conf/app.ini': %v", err)
	}

	LoadBase()
	LoadServer()
	LoadApp()
	LoadTenCentCos()
}

func LoadBase() {
	RunMode = Cfg.Section("").Key("RUN_MODE").MustString("dev")
}

func LoadServer() {
	sec, err := Cfg.GetSection("server")
	if err != nil {
		logging.Fatal("Fail to get section 'server': %v", err)
	}

	HTTPPort = sec.Key("HTTP_PORT").MustInt(8000)
	ReadTimeout = time.Duration(sec.Key("READ_TIMEOUT").MustInt(60)) * time.Second
	WriteTimeout = time.Duration(sec.Key("WRITE_TIMEOUT").MustInt(60)) * time.Second
}

func LoadApp() {
	sec, err := Cfg.GetSection("app")
	if err != nil {
		logging.Fatal("Fail to get section 'app': %v", err)
	}

	JwtSecret = sec.Key("JWT_SECRET").MustString("!@)*#)!@U#@*!@!)")
	PageSize = sec.Key("PAGE_SIZE").MustInt(10)
}

func LoadTenCentCos() {
	sec, err := Cfg.GetSection("tencent_cos")
	if err != nil {
		logging.Fatal("Fail to get section 'tencent_cos': %v", err)
	}

	SecretId = sec.Key("SECRET_ID").MustString("")
	SecretKey = sec.Key("SECRET_KEY").MustString("")
	CosUrl = sec.Key("COS_URL").MustString("")
}

新建pkg/tencentcos/tencentcos.go

package tencentcos

import (
	"fmt"
	"net/http"
	"net/url"

	"github.com/jinpikaFE/go_fiber/pkg/setting"
	"github.com/tencentyun/cos-go-sdk-v5"
)

var (
	Client *cos.Client
)

func init() {
	u, _ := url.Parse(setting.CosUrl)
	b := &cos.BaseURL{BucketURL: u}
	Client = cos.NewClient(b, &http.Client{
		Transport: &cos.AuthorizationTransport{
			SecretID:  fmt.Sprintf("%s", setting.SecretId),  // 替换为用户的 SecretId,请登录访问管理控制台进行查看和管理,https://console.cloud.tencent.com/cam/capi
			SecretKey: fmt.Sprintf("%s", setting.SecretKey), // 替换为用户的 SecretKey,请登录访问管理控制台进行查看和管理,https://console.cloud.tencent.com/cam/capi
		},
	})
}

新建models/upload.go

package models

import (
	"context"
	"io"

	"github.com/jinpikaFE/go_fiber/pkg/logging"
	"github.com/jinpikaFE/go_fiber/pkg/tencentcos"
)

func UploadFile(file io.Reader, filePath string) bool {
	_, err := tencentcos.Client.Object.Put(context.Background(), filePath, file, nil)
	if err != nil {
		logging.Error(err)
		return false
	}
	return true
}

新建controllers/upload.go

package controller

import (
	"fmt"
	"strings"
	"time"

	"github.com/gofiber/fiber/v2"
	"github.com/jinpikaFE/go_fiber/pkg/logging"
	"github.com/jinpikaFE/go_fiber/pkg/setting"

	"github.com/jinpikaFE/go_fiber/models"
)

func Upload(c *fiber.Ctx) error {
	file, err := c.FormFile("file")
	message := "SUCCESS"
	if err != nil {
		logging.Error((err))
		return c.Status(fiber.StatusBadRequest).JSON(fiber.Map{
			"code":    fiber.StatusBadRequest,
			"message": "file为空",
			"data":    nil,
		})
	}

	// //大小限制2Mb
	// if file.Size > (2 << 20) {
	// 	return c.Status(fiber.StatusBadRequest).JSON(fiber.Map{
	// 		"code":    fiber.StatusBadRequest,
	// 		"message": "文件过大 超过2m",
	// 		"data":    nil,
	// 	})
	// }

	relFile, err := file.Open()

	filePath := "/file/" + fmt.Sprintf("%d", time.Now().Unix()) + "." + strings.Split(file.Filename, `.`)[1]

	if err != nil {
		message = "ERROR"
		logging.Error(err)
	}

	res := models.UploadFile(relFile, filePath)

	if !res {
		message = "上传失败"
	}

	url := setting.CosUrl + filePath

	return c.Status(fiber.StatusOK).JSON(fiber.Map{
		"code":    "code",
		"message": message,
		"data":    url,
	})
}

修改router.go

// 添加/upload路由
{
        apiv1.Post("/upload", controller.Upload)
}

image.png