1238 lines
34 KiB
Go
1238 lines
34 KiB
Go
package handlers
|
||
|
||
import (
|
||
"fmt"
|
||
"log"
|
||
"path/filepath"
|
||
"strconv"
|
||
|
||
"github.com/gin-gonic/gin"
|
||
"github.com/niangaodev/art-code/models"
|
||
"github.com/niangaodev/art-code/repositories"
|
||
"github.com/niangaodev/art-code/utils"
|
||
)
|
||
|
||
// AdminUploadAttachment 上传附件
|
||
func AdminUploadAttachment(c *gin.Context) {
|
||
// 获取文件
|
||
file, err := c.FormFile("file")
|
||
if err != nil {
|
||
utils.Error(c, 400, "No file uploaded")
|
||
return
|
||
}
|
||
|
||
// 获取分类ID(可选)
|
||
categoryIDStr := c.PostForm("categoryId")
|
||
var categoryID *uint
|
||
if categoryIDStr != "" {
|
||
if id, err := strconv.ParseUint(categoryIDStr, 10, 32); err == nil {
|
||
idUint := uint(id)
|
||
categoryID = &idUint
|
||
}
|
||
}
|
||
|
||
// 获取存储类型:Env 齐全时默认 aliyun
|
||
defaultStorage := "local"
|
||
if utils.HasAliyunEnvConfig() {
|
||
defaultStorage = "aliyun"
|
||
}
|
||
storageType := c.DefaultPostForm("storageType", defaultStorage)
|
||
|
||
// 打开文件
|
||
src, err := file.Open()
|
||
if err != nil {
|
||
utils.Error(c, 500, "Failed to open file")
|
||
return
|
||
}
|
||
defer src.Close()
|
||
|
||
// 创建OSS配置对象
|
||
config := &utils.OSSConfig{
|
||
StorageType: storageType,
|
||
}
|
||
|
||
var ossConfig *models.OSSConfig
|
||
usedEnvConfig := false
|
||
|
||
if storageType == "aliyun" {
|
||
if envCfg, ok := utils.LoadAliyunConfigFromEnv(); ok {
|
||
config = envCfg
|
||
usedEnvConfig = true
|
||
}
|
||
}
|
||
|
||
if !usedEnvConfig && storageType != "local" {
|
||
ossConfig, err = repositories.GetActiveOSSConfig(storageType)
|
||
if err != nil || ossConfig == nil {
|
||
utils.Error(c, 400, "OSS config not found or not active")
|
||
return
|
||
}
|
||
|
||
// 根据存储类型从专用字段或通用字段读取配置
|
||
var accessKey, secretKey, bucket, region, domain string
|
||
|
||
switch ossConfig.StorageType {
|
||
case "aliyun":
|
||
if ossConfig.OSSAccessKeyID != "" {
|
||
decrypted, err := utils.DecryptAES(ossConfig.OSSAccessKeyID)
|
||
if err == nil {
|
||
accessKey = decrypted
|
||
}
|
||
}
|
||
if ossConfig.OSSAccessKeySecret != "" {
|
||
decrypted, err := utils.DecryptAES(ossConfig.OSSAccessKeySecret)
|
||
if err == nil {
|
||
secretKey = decrypted
|
||
}
|
||
}
|
||
bucket = ossConfig.OSSBucket
|
||
domain = ossConfig.OSSDomain
|
||
if accessKey == "" && ossConfig.AccessKey != "" {
|
||
decrypted, err := utils.DecryptAES(ossConfig.AccessKey)
|
||
if err == nil {
|
||
accessKey = decrypted
|
||
}
|
||
}
|
||
if secretKey == "" && ossConfig.SecretKey != "" {
|
||
decrypted, err := utils.DecryptAES(ossConfig.SecretKey)
|
||
if err == nil {
|
||
secretKey = decrypted
|
||
}
|
||
}
|
||
if bucket == "" {
|
||
bucket = ossConfig.Bucket
|
||
}
|
||
if domain == "" {
|
||
domain = ossConfig.Domain
|
||
}
|
||
case "qcloud":
|
||
if ossConfig.QCloudSecretID != "" {
|
||
decrypted, err := utils.DecryptAES(ossConfig.QCloudSecretID)
|
||
if err == nil {
|
||
accessKey = decrypted
|
||
}
|
||
}
|
||
if ossConfig.QCloudSecretKey != "" {
|
||
decrypted, err := utils.DecryptAES(ossConfig.QCloudSecretKey)
|
||
if err == nil {
|
||
secretKey = decrypted
|
||
}
|
||
}
|
||
bucket = ossConfig.QCloudBucket
|
||
region = ossConfig.QCloudRegion
|
||
domain = ossConfig.QCloudDomain
|
||
if accessKey == "" && ossConfig.AccessKey != "" {
|
||
decrypted, err := utils.DecryptAES(ossConfig.AccessKey)
|
||
if err == nil {
|
||
accessKey = decrypted
|
||
}
|
||
}
|
||
if secretKey == "" && ossConfig.SecretKey != "" {
|
||
decrypted, err := utils.DecryptAES(ossConfig.SecretKey)
|
||
if err == nil {
|
||
secretKey = decrypted
|
||
}
|
||
}
|
||
if bucket == "" {
|
||
bucket = ossConfig.Bucket
|
||
}
|
||
if region == "" {
|
||
region = ossConfig.Region
|
||
}
|
||
if domain == "" {
|
||
domain = ossConfig.Domain
|
||
}
|
||
case "qiniu":
|
||
if ossConfig.QiniuAccessKey != "" {
|
||
decrypted, err := utils.DecryptAES(ossConfig.QiniuAccessKey)
|
||
if err == nil {
|
||
accessKey = decrypted
|
||
}
|
||
}
|
||
if ossConfig.QiniuSecretKey != "" {
|
||
decrypted, err := utils.DecryptAES(ossConfig.QiniuSecretKey)
|
||
if err == nil {
|
||
secretKey = decrypted
|
||
}
|
||
}
|
||
bucket = ossConfig.QiniuBucket
|
||
region = ossConfig.QiniuRegion
|
||
domain = ossConfig.QiniuDomain
|
||
if accessKey == "" && ossConfig.AccessKey != "" {
|
||
decrypted, err := utils.DecryptAES(ossConfig.AccessKey)
|
||
if err == nil {
|
||
accessKey = decrypted
|
||
}
|
||
}
|
||
if secretKey == "" && ossConfig.SecretKey != "" {
|
||
decrypted, err := utils.DecryptAES(ossConfig.SecretKey)
|
||
if err == nil {
|
||
secretKey = decrypted
|
||
}
|
||
}
|
||
if bucket == "" {
|
||
bucket = ossConfig.Bucket
|
||
}
|
||
if region == "" {
|
||
region = ossConfig.Region
|
||
}
|
||
if domain == "" {
|
||
domain = ossConfig.Domain
|
||
}
|
||
default:
|
||
if ossConfig.AccessKey != "" {
|
||
decrypted, err := utils.DecryptAES(ossConfig.AccessKey)
|
||
if err == nil {
|
||
accessKey = decrypted
|
||
}
|
||
}
|
||
if ossConfig.SecretKey != "" {
|
||
decrypted, err := utils.DecryptAES(ossConfig.SecretKey)
|
||
if err == nil {
|
||
secretKey = decrypted
|
||
}
|
||
}
|
||
bucket = ossConfig.Bucket
|
||
region = ossConfig.Region
|
||
domain = ossConfig.Domain
|
||
}
|
||
|
||
config.AccessKey = accessKey
|
||
config.SecretKey = secretKey
|
||
config.Bucket = bucket
|
||
config.Region = region
|
||
config.Domain = domain
|
||
|
||
switch ossConfig.StorageType {
|
||
case "aliyun":
|
||
config.OSSAccessKeyID = accessKey
|
||
config.OSSAccessKeySecret = secretKey
|
||
config.OSSEndpoint = ossConfig.OSSEndpoint
|
||
config.OSSBucket = bucket
|
||
config.OSSDomain = domain
|
||
case "qcloud":
|
||
config.QCloudSecretID = accessKey
|
||
config.QCloudSecretKey = secretKey
|
||
config.QCloudRegion = region
|
||
config.QCloudBucket = bucket
|
||
config.QCloudDomain = domain
|
||
case "qiniu":
|
||
config.QiniuAccessKey = accessKey
|
||
config.QiniuSecretKey = secretKey
|
||
config.QiniuBucket = bucket
|
||
config.QiniuRegion = region
|
||
config.QiniuDomain = domain
|
||
}
|
||
}
|
||
|
||
// 获取上传器
|
||
uploader, err := utils.GetOSSUploader(config)
|
||
if err != nil {
|
||
utils.Error(c, 500, err.Error())
|
||
return
|
||
}
|
||
|
||
// 上传文件
|
||
filePath, fileURL, err := uploader.Upload(src, file.Filename, file.Size)
|
||
if err != nil {
|
||
utils.Error(c, 500, "Failed to upload file: "+err.Error())
|
||
return
|
||
}
|
||
|
||
storedName := filepath.Base(filePath)
|
||
if storedName == "." || storedName == "/" || storedName == "" {
|
||
storedName = file.Filename
|
||
}
|
||
|
||
// 获取文件类型
|
||
fileType := utils.GetFileType(file.Header.Get("Content-Type"))
|
||
|
||
// 创建附件记录
|
||
attachment := &models.Attachment{
|
||
CategoryID: categoryID,
|
||
OriginalName: file.Filename,
|
||
StoredName: storedName,
|
||
FilePath: filePath,
|
||
FileURL: fileURL,
|
||
FileSize: file.Size,
|
||
FileType: fileType,
|
||
MimeType: file.Header.Get("Content-Type"),
|
||
StorageType: storageType,
|
||
}
|
||
|
||
if ossConfig != nil {
|
||
ossConfigID := ossConfig.ID
|
||
attachment.OSSConfigID = &ossConfigID
|
||
}
|
||
|
||
if err := repositories.CreateAttachment(attachment); err != nil {
|
||
uploader.Delete(filePath)
|
||
utils.ServerError(c, err)
|
||
return
|
||
}
|
||
|
||
utils.SuccessWithMsg(c, "File uploaded successfully", attachment)
|
||
}
|
||
|
||
// AdminGetAttachments 获取附件列表
|
||
func AdminGetAttachments(c *gin.Context) {
|
||
page, _ := strconv.Atoi(c.DefaultQuery("page", "1"))
|
||
pageSize, _ := strconv.Atoi(c.DefaultQuery("pageSize", "20"))
|
||
categoryIDStr := c.Query("categoryId")
|
||
fileType := c.Query("fileType")
|
||
keyword := c.Query("keyword")
|
||
|
||
var categoryID *uint
|
||
if categoryIDStr != "" {
|
||
if id, err := strconv.ParseUint(categoryIDStr, 10, 32); err == nil {
|
||
idUint := uint(id)
|
||
categoryID = &idUint
|
||
}
|
||
}
|
||
|
||
attachments, total, err := repositories.GetAttachments(page, pageSize, categoryID, fileType, keyword)
|
||
if err != nil {
|
||
utils.ServerError(c, err)
|
||
return
|
||
}
|
||
|
||
res := gin.H{
|
||
"list": attachments,
|
||
"total": total,
|
||
"page": page,
|
||
"size": pageSize,
|
||
}
|
||
|
||
utils.Success(c, res)
|
||
}
|
||
|
||
// AdminDeleteAttachment 删除附件
|
||
func AdminDeleteAttachment(c *gin.Context) {
|
||
idStr := c.Param("id")
|
||
parsedID, err := strconv.ParseUint(idStr, 10, 32)
|
||
if err != nil {
|
||
utils.Error(c, 400, "Invalid attachment ID")
|
||
return
|
||
}
|
||
id := uint(parsedID)
|
||
|
||
// 获取附件信息
|
||
attachment, err := repositories.GetAttachmentByID(id)
|
||
if err != nil || attachment == nil {
|
||
utils.Error(c, 404, "Attachment not found")
|
||
return
|
||
}
|
||
|
||
// 获取OSS配置并删除文件
|
||
if attachment.StorageType != "" {
|
||
var ossConfig *models.OSSConfig
|
||
if attachment.OSSConfigID != nil {
|
||
ossConfig, err = repositories.GetOSSConfigByID(*attachment.OSSConfigID)
|
||
} else {
|
||
ossConfig, err = repositories.GetActiveOSSConfig(attachment.StorageType)
|
||
}
|
||
|
||
if err == nil && ossConfig != nil {
|
||
config := &utils.OSSConfig{
|
||
StorageType: attachment.StorageType,
|
||
}
|
||
|
||
// 根据存储类型从专用字段或通用字段读取配置
|
||
var accessKey, secretKey, bucket, region, domain string
|
||
|
||
switch ossConfig.StorageType {
|
||
case "aliyun":
|
||
if ossConfig.OSSAccessKeyID != "" {
|
||
if decrypted, err := utils.DecryptAES(ossConfig.OSSAccessKeyID); err == nil {
|
||
accessKey = decrypted
|
||
}
|
||
}
|
||
if ossConfig.OSSAccessKeySecret != "" {
|
||
if decrypted, err := utils.DecryptAES(ossConfig.OSSAccessKeySecret); err == nil {
|
||
secretKey = decrypted
|
||
}
|
||
}
|
||
bucket = ossConfig.OSSBucket
|
||
domain = ossConfig.OSSDomain
|
||
// 向后兼容
|
||
if accessKey == "" && ossConfig.AccessKey != "" {
|
||
if decrypted, err := utils.DecryptAES(ossConfig.AccessKey); err == nil {
|
||
accessKey = decrypted
|
||
}
|
||
}
|
||
if secretKey == "" && ossConfig.SecretKey != "" {
|
||
if decrypted, err := utils.DecryptAES(ossConfig.SecretKey); err == nil {
|
||
secretKey = decrypted
|
||
}
|
||
}
|
||
if bucket == "" {
|
||
bucket = ossConfig.Bucket
|
||
}
|
||
if domain == "" {
|
||
domain = ossConfig.Domain
|
||
}
|
||
case "qcloud":
|
||
if ossConfig.QCloudSecretID != "" {
|
||
if decrypted, err := utils.DecryptAES(ossConfig.QCloudSecretID); err == nil {
|
||
accessKey = decrypted
|
||
}
|
||
}
|
||
if ossConfig.QCloudSecretKey != "" {
|
||
if decrypted, err := utils.DecryptAES(ossConfig.QCloudSecretKey); err == nil {
|
||
secretKey = decrypted
|
||
}
|
||
}
|
||
bucket = ossConfig.QCloudBucket
|
||
region = ossConfig.QCloudRegion
|
||
domain = ossConfig.QCloudDomain
|
||
// 向后兼容
|
||
if accessKey == "" && ossConfig.AccessKey != "" {
|
||
if decrypted, err := utils.DecryptAES(ossConfig.AccessKey); err == nil {
|
||
accessKey = decrypted
|
||
}
|
||
}
|
||
if secretKey == "" && ossConfig.SecretKey != "" {
|
||
if decrypted, err := utils.DecryptAES(ossConfig.SecretKey); err == nil {
|
||
secretKey = decrypted
|
||
}
|
||
}
|
||
if bucket == "" {
|
||
bucket = ossConfig.Bucket
|
||
}
|
||
if region == "" {
|
||
region = ossConfig.Region
|
||
}
|
||
if domain == "" {
|
||
domain = ossConfig.Domain
|
||
}
|
||
case "qiniu":
|
||
if ossConfig.QiniuAccessKey != "" {
|
||
if decrypted, err := utils.DecryptAES(ossConfig.QiniuAccessKey); err == nil {
|
||
accessKey = decrypted
|
||
}
|
||
}
|
||
if ossConfig.QiniuSecretKey != "" {
|
||
if decrypted, err := utils.DecryptAES(ossConfig.QiniuSecretKey); err == nil {
|
||
secretKey = decrypted
|
||
}
|
||
}
|
||
bucket = ossConfig.QiniuBucket
|
||
region = ossConfig.QiniuRegion
|
||
domain = ossConfig.QiniuDomain
|
||
// 向后兼容
|
||
if accessKey == "" && ossConfig.AccessKey != "" {
|
||
if decrypted, err := utils.DecryptAES(ossConfig.AccessKey); err == nil {
|
||
accessKey = decrypted
|
||
}
|
||
}
|
||
if secretKey == "" && ossConfig.SecretKey != "" {
|
||
if decrypted, err := utils.DecryptAES(ossConfig.SecretKey); err == nil {
|
||
secretKey = decrypted
|
||
}
|
||
}
|
||
if bucket == "" {
|
||
bucket = ossConfig.Bucket
|
||
}
|
||
if region == "" {
|
||
region = ossConfig.Region
|
||
}
|
||
if domain == "" {
|
||
domain = ossConfig.Domain
|
||
}
|
||
default:
|
||
if ossConfig.AccessKey != "" {
|
||
if decrypted, err := utils.DecryptAES(ossConfig.AccessKey); err == nil {
|
||
accessKey = decrypted
|
||
}
|
||
}
|
||
if ossConfig.SecretKey != "" {
|
||
if decrypted, err := utils.DecryptAES(ossConfig.SecretKey); err == nil {
|
||
secretKey = decrypted
|
||
}
|
||
}
|
||
bucket = ossConfig.Bucket
|
||
region = ossConfig.Region
|
||
domain = ossConfig.Domain
|
||
}
|
||
|
||
config.AccessKey = accessKey
|
||
config.SecretKey = secretKey
|
||
config.Bucket = bucket
|
||
config.Region = region
|
||
config.Domain = domain
|
||
|
||
uploader, err := utils.GetOSSUploader(config)
|
||
if err == nil {
|
||
uploader.Delete(attachment.FilePath)
|
||
}
|
||
}
|
||
}
|
||
|
||
// 删除数据库记录
|
||
if err := repositories.DeleteAttachment(id); err != nil {
|
||
utils.ServerError(c, err)
|
||
return
|
||
}
|
||
|
||
utils.SuccessWithMsg(c, "Attachment deleted successfully", nil)
|
||
}
|
||
|
||
// AdminUpdateAttachment 更新附件
|
||
func AdminUpdateAttachment(c *gin.Context) {
|
||
idStr := c.Param("id")
|
||
parsedID, err := strconv.ParseUint(idStr, 10, 32)
|
||
if err != nil {
|
||
utils.Error(c, 400, "Invalid attachment ID")
|
||
return
|
||
}
|
||
id := uint(parsedID)
|
||
|
||
// 获取现有附件
|
||
attachment, err := repositories.GetAttachmentByID(id)
|
||
if err != nil || attachment == nil {
|
||
utils.Error(c, 404, "Attachment not found")
|
||
return
|
||
}
|
||
|
||
// 解析请求体
|
||
var req struct {
|
||
CategoryID *uint `json:"categoryId"`
|
||
}
|
||
|
||
if err := c.ShouldBindJSON(&req); err != nil {
|
||
utils.Error(c, 400, "Invalid request")
|
||
return
|
||
}
|
||
|
||
// 更新分类ID
|
||
if req.CategoryID != nil {
|
||
if *req.CategoryID == 0 {
|
||
// 如果categoryId为0,设置为nil(无分类)
|
||
attachment.CategoryID = nil
|
||
} else {
|
||
attachment.CategoryID = req.CategoryID
|
||
}
|
||
}
|
||
|
||
// 更新附件
|
||
if err := repositories.UpdateAttachment(attachment); err != nil {
|
||
utils.ServerError(c, err)
|
||
return
|
||
}
|
||
|
||
// 重新获取更新后的附件(包含关联的分类信息)
|
||
updatedAttachment, err := repositories.GetAttachmentByID(id)
|
||
if err != nil {
|
||
utils.ServerError(c, err)
|
||
return
|
||
}
|
||
|
||
utils.SuccessWithMsg(c, "Attachment updated successfully", updatedAttachment)
|
||
}
|
||
|
||
// AdminGetAttachmentCategories 获取附件分类列表
|
||
func AdminGetAttachmentCategories(c *gin.Context) {
|
||
categories, err := repositories.GetAttachmentCategories()
|
||
if err != nil {
|
||
utils.ServerError(c, err)
|
||
return
|
||
}
|
||
|
||
utils.Success(c, categories)
|
||
}
|
||
|
||
// AdminCreateAttachmentCategory 创建附件分类
|
||
func AdminCreateAttachmentCategory(c *gin.Context) {
|
||
var category models.AttachmentCategory
|
||
if err := c.ShouldBindJSON(&category); err != nil {
|
||
utils.Error(c, 400, "Invalid request")
|
||
return
|
||
}
|
||
|
||
if err := repositories.CreateAttachmentCategory(&category); err != nil {
|
||
utils.ServerError(c, err)
|
||
return
|
||
}
|
||
|
||
utils.SuccessWithMsg(c, "Category created successfully", category)
|
||
}
|
||
|
||
// AdminUpdateAttachmentCategory 更新附件分类
|
||
func AdminUpdateAttachmentCategory(c *gin.Context) {
|
||
idStr := c.Param("id")
|
||
parsedID, err := strconv.ParseUint(idStr, 10, 32)
|
||
if err != nil {
|
||
utils.Error(c, 400, "Invalid category ID")
|
||
return
|
||
}
|
||
id := uint(parsedID)
|
||
|
||
var category models.AttachmentCategory
|
||
if err := c.ShouldBindJSON(&category); err != nil {
|
||
utils.Error(c, 400, "Invalid request")
|
||
return
|
||
}
|
||
|
||
category.ID = id
|
||
|
||
if err := repositories.UpdateAttachmentCategory(&category); err != nil {
|
||
utils.ServerError(c, err)
|
||
return
|
||
}
|
||
|
||
utils.SuccessWithMsg(c, "Category updated successfully", nil)
|
||
}
|
||
|
||
// AdminDeleteAttachmentCategory 删除附件分类
|
||
func AdminDeleteAttachmentCategory(c *gin.Context) {
|
||
idStr := c.Param("id")
|
||
parsedID, err := strconv.ParseUint(idStr, 10, 32)
|
||
if err != nil {
|
||
utils.Error(c, 400, "Invalid category ID")
|
||
return
|
||
}
|
||
id := uint(parsedID)
|
||
|
||
if err := repositories.DeleteAttachmentCategory(id); err != nil {
|
||
utils.ServerError(c, err)
|
||
return
|
||
}
|
||
|
||
utils.SuccessWithMsg(c, "Category deleted successfully", nil)
|
||
}
|
||
|
||
// AdminGetOSSConfigs 获取OSS配置列表
|
||
func AdminGetOSSConfigs(c *gin.Context) {
|
||
// 检查是否存在默认本地存储配置,如果不存在则创建
|
||
defaultConfig, err := repositories.GetDefaultLocalOSSConfig()
|
||
if err != nil {
|
||
log.Printf("Error checking default local OSS config: %v", err)
|
||
} else if defaultConfig == nil {
|
||
// 创建默认本地存储配置
|
||
// 本地存储不需要AccessKey和SecretKey,直接使用空字符串(不加密)
|
||
defaultOSSConfig := &models.OSSConfig{
|
||
Name: "本地存储",
|
||
StorageType: "local",
|
||
AccessKey: "", // 空字符串,不加密
|
||
SecretKey: "", // 空字符串,不加密
|
||
Bucket: "",
|
||
Region: "",
|
||
Domain: "",
|
||
IsActive: 1,
|
||
}
|
||
|
||
if err := repositories.CreateOSSConfig(defaultOSSConfig); err != nil {
|
||
log.Printf("Error creating default local OSS config: %v", err)
|
||
}
|
||
}
|
||
|
||
configs, err := repositories.GetOSSConfigs()
|
||
if err != nil {
|
||
utils.ServerError(c, err)
|
||
return
|
||
}
|
||
|
||
// 不返回加密的密钥
|
||
for i := range configs {
|
||
configs[i].AccessKey = "***"
|
||
configs[i].SecretKey = "***"
|
||
configs[i].OSSAccessKeyID = "***"
|
||
configs[i].OSSAccessKeySecret = "***"
|
||
configs[i].QCloudSecretID = "***"
|
||
configs[i].QCloudSecretKey = "***"
|
||
configs[i].QiniuAccessKey = "***"
|
||
configs[i].QiniuSecretKey = "***"
|
||
}
|
||
|
||
utils.Success(c, configs)
|
||
}
|
||
|
||
// AdminCreateOSSConfig 创建OSS配置
|
||
func AdminCreateOSSConfig(c *gin.Context) {
|
||
var req struct {
|
||
Name string `json:"name" binding:"required"`
|
||
StorageType string `json:"storageType" binding:"required"`
|
||
// 通用字段(向后兼容)
|
||
AccessKey string `json:"accessKey"`
|
||
SecretKey string `json:"secretKey"`
|
||
Bucket string `json:"bucket"`
|
||
Region string `json:"region"`
|
||
Domain string `json:"domain"`
|
||
// 阿里云OSS专用字段
|
||
OSSAccessKeyID string `json:"ossAccessKeyId"`
|
||
OSSAccessKeySecret string `json:"ossAccessKeySecret"`
|
||
OSSEndpoint string `json:"ossEndpoint"`
|
||
OSSBucket string `json:"ossBucket"`
|
||
OSSDomain string `json:"ossDomain"`
|
||
// 腾讯云COS专用字段
|
||
QCloudSecretID string `json:"qcloudSecretId"`
|
||
QCloudSecretKey string `json:"qcloudSecretKey"`
|
||
QCloudRegion string `json:"qcloudRegion"`
|
||
QCloudBucket string `json:"qcloudBucket"`
|
||
QCloudDomain string `json:"qcloudDomain"`
|
||
// 七牛云专用字段
|
||
QiniuAccessKey string `json:"qiniuAccessKey"`
|
||
QiniuSecretKey string `json:"qiniuSecretKey"`
|
||
QiniuBucket string `json:"qiniuBucket"`
|
||
QiniuRegion string `json:"qiniuRegion"`
|
||
QiniuDomain string `json:"qiniuDomain"`
|
||
IsActive int `json:"isActive"`
|
||
}
|
||
|
||
if err := c.ShouldBindJSON(&req); err != nil {
|
||
utils.Error(c, 400, "Invalid request")
|
||
return
|
||
}
|
||
|
||
// 加密函数
|
||
encryptKey := func(key string) (string, error) {
|
||
if key == "" {
|
||
return "", nil
|
||
}
|
||
return utils.EncryptAES(key)
|
||
}
|
||
|
||
// 加密通用密钥(向后兼容)
|
||
encryptedAccessKey, err := encryptKey(req.AccessKey)
|
||
if err != nil {
|
||
utils.Error(c, 500, "Failed to encrypt access key: "+err.Error())
|
||
return
|
||
}
|
||
encryptedSecretKey, err := encryptKey(req.SecretKey)
|
||
if err != nil {
|
||
utils.Error(c, 500, "Failed to encrypt secret key: "+err.Error())
|
||
return
|
||
}
|
||
|
||
// 加密阿里云密钥
|
||
encryptedOSSAccessKeyID, err := encryptKey(req.OSSAccessKeyID)
|
||
if err != nil {
|
||
utils.Error(c, 500, "Failed to encrypt OSS access key ID: "+err.Error())
|
||
return
|
||
}
|
||
encryptedOSSAccessKeySecret, err := encryptKey(req.OSSAccessKeySecret)
|
||
if err != nil {
|
||
utils.Error(c, 500, "Failed to encrypt OSS access key secret: "+err.Error())
|
||
return
|
||
}
|
||
|
||
// 加密腾讯云密钥
|
||
encryptedQCloudSecretID, err := encryptKey(req.QCloudSecretID)
|
||
if err != nil {
|
||
utils.Error(c, 500, "Failed to encrypt QCloud secret ID: "+err.Error())
|
||
return
|
||
}
|
||
encryptedQCloudSecretKey, err := encryptKey(req.QCloudSecretKey)
|
||
if err != nil {
|
||
utils.Error(c, 500, "Failed to encrypt QCloud secret key: "+err.Error())
|
||
return
|
||
}
|
||
|
||
// 加密七牛云密钥
|
||
encryptedQiniuAccessKey, err := encryptKey(req.QiniuAccessKey)
|
||
if err != nil {
|
||
utils.Error(c, 500, "Failed to encrypt Qiniu access key: "+err.Error())
|
||
return
|
||
}
|
||
encryptedQiniuSecretKey, err := encryptKey(req.QiniuSecretKey)
|
||
if err != nil {
|
||
utils.Error(c, 500, "Failed to encrypt Qiniu secret key: "+err.Error())
|
||
return
|
||
}
|
||
|
||
ossConfig := &models.OSSConfig{
|
||
Name: req.Name,
|
||
StorageType: req.StorageType,
|
||
// 通用字段(向后兼容)
|
||
AccessKey: encryptedAccessKey,
|
||
SecretKey: encryptedSecretKey,
|
||
Bucket: req.Bucket,
|
||
Region: req.Region,
|
||
Domain: req.Domain,
|
||
// 阿里云OSS专用字段
|
||
OSSAccessKeyID: encryptedOSSAccessKeyID,
|
||
OSSAccessKeySecret: encryptedOSSAccessKeySecret,
|
||
OSSEndpoint: req.OSSEndpoint,
|
||
OSSBucket: req.OSSBucket,
|
||
OSSDomain: req.OSSDomain,
|
||
// 腾讯云COS专用字段
|
||
QCloudSecretID: encryptedQCloudSecretID,
|
||
QCloudSecretKey: encryptedQCloudSecretKey,
|
||
QCloudRegion: req.QCloudRegion,
|
||
QCloudBucket: req.QCloudBucket,
|
||
QCloudDomain: req.QCloudDomain,
|
||
// 七牛云专用字段
|
||
QiniuAccessKey: encryptedQiniuAccessKey,
|
||
QiniuSecretKey: encryptedQiniuSecretKey,
|
||
QiniuBucket: req.QiniuBucket,
|
||
QiniuRegion: req.QiniuRegion,
|
||
QiniuDomain: req.QiniuDomain,
|
||
IsActive: req.IsActive,
|
||
}
|
||
|
||
if err := repositories.CreateOSSConfig(ossConfig); err != nil {
|
||
utils.ServerError(c, err)
|
||
return
|
||
}
|
||
|
||
// 不返回加密的密钥
|
||
ossConfig.AccessKey = "***"
|
||
ossConfig.SecretKey = "***"
|
||
ossConfig.OSSAccessKeyID = "***"
|
||
ossConfig.OSSAccessKeySecret = "***"
|
||
ossConfig.QCloudSecretID = "***"
|
||
ossConfig.QCloudSecretKey = "***"
|
||
ossConfig.QiniuAccessKey = "***"
|
||
ossConfig.QiniuSecretKey = "***"
|
||
|
||
utils.SuccessWithMsg(c, "OSS config created successfully", ossConfig)
|
||
}
|
||
|
||
// AdminUpdateOSSConfig 更新OSS配置
|
||
func AdminUpdateOSSConfig(c *gin.Context) {
|
||
idStr := c.Param("id")
|
||
parsedID, err := strconv.ParseUint(idStr, 10, 32)
|
||
if err != nil {
|
||
utils.Error(c, 400, "Invalid OSS config ID")
|
||
return
|
||
}
|
||
id := uint(parsedID)
|
||
|
||
var req struct {
|
||
Name string `json:"name"`
|
||
StorageType string `json:"storageType"`
|
||
// 通用字段(向后兼容)
|
||
AccessKey string `json:"accessKey"`
|
||
SecretKey string `json:"secretKey"`
|
||
Bucket string `json:"bucket"`
|
||
Region string `json:"region"`
|
||
Domain string `json:"domain"`
|
||
// 阿里云OSS专用字段
|
||
OSSAccessKeyID string `json:"ossAccessKeyId"`
|
||
OSSAccessKeySecret string `json:"ossAccessKeySecret"`
|
||
OSSEndpoint string `json:"ossEndpoint"`
|
||
OSSBucket string `json:"ossBucket"`
|
||
OSSDomain string `json:"ossDomain"`
|
||
// 腾讯云COS专用字段
|
||
QCloudSecretID string `json:"qcloudSecretId"`
|
||
QCloudSecretKey string `json:"qcloudSecretKey"`
|
||
QCloudRegion string `json:"qcloudRegion"`
|
||
QCloudBucket string `json:"qcloudBucket"`
|
||
QCloudDomain string `json:"qcloudDomain"`
|
||
// 七牛云专用字段
|
||
QiniuAccessKey string `json:"qiniuAccessKey"`
|
||
QiniuSecretKey string `json:"qiniuSecretKey"`
|
||
QiniuBucket string `json:"qiniuBucket"`
|
||
QiniuRegion string `json:"qiniuRegion"`
|
||
QiniuDomain string `json:"qiniuDomain"`
|
||
IsActive int `json:"isActive"`
|
||
}
|
||
|
||
if err := c.ShouldBindJSON(&req); err != nil {
|
||
utils.Error(c, 400, "Invalid request")
|
||
return
|
||
}
|
||
|
||
// 获取现有配置
|
||
existingConfig, err := repositories.GetOSSConfigByID(id)
|
||
if err != nil || existingConfig == nil {
|
||
utils.Error(c, 404, "OSS config not found")
|
||
return
|
||
}
|
||
|
||
storageType := existingConfig.StorageType
|
||
if req.StorageType != "" {
|
||
storageType = req.StorageType
|
||
}
|
||
|
||
// 启用非 local 配置前,按存储类型校验密钥(优先专用字段,兼容 legacy)
|
||
if req.IsActive == 1 && existingConfig.IsActive == 0 && storageType != "local" {
|
||
if errMsg := validateOSSCredentialsForEnable(storageType, existingConfig, req.AccessKey, req.SecretKey,
|
||
req.OSSAccessKeyID, req.OSSAccessKeySecret, req.OSSEndpoint, req.OSSBucket,
|
||
req.QCloudSecretID, req.QCloudSecretKey, req.QCloudRegion, req.QCloudBucket,
|
||
req.QiniuAccessKey, req.QiniuSecretKey, req.QiniuBucket); errMsg != "" {
|
||
utils.Error(c, 400, errMsg)
|
||
return
|
||
}
|
||
}
|
||
|
||
// 加密函数
|
||
encryptKey := func(key string) (string, error) {
|
||
if key == "" {
|
||
return "", nil
|
||
}
|
||
return utils.EncryptAES(key)
|
||
}
|
||
|
||
// 密钥字段:*** 或空表示不修改已有值
|
||
updateSecret := func(reqVal string, dest *string) error {
|
||
if reqVal == "***" || reqVal == "" {
|
||
return nil
|
||
}
|
||
encrypted, err := encryptKey(reqVal)
|
||
if err != nil {
|
||
return err
|
||
}
|
||
*dest = encrypted
|
||
return nil
|
||
}
|
||
|
||
// 更新字段
|
||
if req.Name != "" {
|
||
existingConfig.Name = req.Name
|
||
}
|
||
if req.StorageType != "" {
|
||
existingConfig.StorageType = req.StorageType
|
||
}
|
||
|
||
if err := updateSecret(req.AccessKey, &existingConfig.AccessKey); err != nil {
|
||
utils.Error(c, 500, "Failed to encrypt access key: "+err.Error())
|
||
return
|
||
}
|
||
if err := updateSecret(req.SecretKey, &existingConfig.SecretKey); err != nil {
|
||
utils.Error(c, 500, "Failed to encrypt secret key: "+err.Error())
|
||
return
|
||
}
|
||
|
||
existingConfig.Bucket = req.Bucket
|
||
existingConfig.Region = req.Region
|
||
existingConfig.Domain = req.Domain
|
||
|
||
if err := updateSecret(req.OSSAccessKeyID, &existingConfig.OSSAccessKeyID); err != nil {
|
||
utils.Error(c, 500, "Failed to encrypt OSS access key ID: "+err.Error())
|
||
return
|
||
}
|
||
if err := updateSecret(req.OSSAccessKeySecret, &existingConfig.OSSAccessKeySecret); err != nil {
|
||
utils.Error(c, 500, "Failed to encrypt OSS access key secret: "+err.Error())
|
||
return
|
||
}
|
||
existingConfig.OSSEndpoint = req.OSSEndpoint
|
||
existingConfig.OSSBucket = req.OSSBucket
|
||
existingConfig.OSSDomain = req.OSSDomain
|
||
|
||
if err := updateSecret(req.QCloudSecretID, &existingConfig.QCloudSecretID); err != nil {
|
||
utils.Error(c, 500, "Failed to encrypt QCloud secret ID: "+err.Error())
|
||
return
|
||
}
|
||
if err := updateSecret(req.QCloudSecretKey, &existingConfig.QCloudSecretKey); err != nil {
|
||
utils.Error(c, 500, "Failed to encrypt QCloud secret key: "+err.Error())
|
||
return
|
||
}
|
||
existingConfig.QCloudRegion = req.QCloudRegion
|
||
existingConfig.QCloudBucket = req.QCloudBucket
|
||
existingConfig.QCloudDomain = req.QCloudDomain
|
||
|
||
if err := updateSecret(req.QiniuAccessKey, &existingConfig.QiniuAccessKey); err != nil {
|
||
utils.Error(c, 500, "Failed to encrypt Qiniu access key: "+err.Error())
|
||
return
|
||
}
|
||
if err := updateSecret(req.QiniuSecretKey, &existingConfig.QiniuSecretKey); err != nil {
|
||
utils.Error(c, 500, "Failed to encrypt Qiniu secret key: "+err.Error())
|
||
return
|
||
}
|
||
existingConfig.QiniuBucket = req.QiniuBucket
|
||
existingConfig.QiniuRegion = req.QiniuRegion
|
||
existingConfig.QiniuDomain = req.QiniuDomain
|
||
|
||
existingConfig.IsActive = req.IsActive
|
||
|
||
if err := repositories.UpdateOSSConfig(existingConfig); err != nil {
|
||
utils.ServerError(c, err)
|
||
return
|
||
}
|
||
|
||
maskOSSSecrets(existingConfig)
|
||
utils.SuccessWithMsg(c, "OSS config updated successfully", existingConfig)
|
||
}
|
||
|
||
// AdminDeleteOSSConfig 删除OSS配置
|
||
func AdminDeleteOSSConfig(c *gin.Context) {
|
||
idStr := c.Param("id")
|
||
parsedID, err := strconv.ParseUint(idStr, 10, 32)
|
||
if err != nil {
|
||
utils.Error(c, 400, "Invalid OSS config ID")
|
||
return
|
||
}
|
||
id := uint(parsedID)
|
||
|
||
// 获取配置信息,检查是否为默认本地存储配置
|
||
ossConfig, err := repositories.GetOSSConfigByID(id)
|
||
if err != nil {
|
||
utils.ServerError(c, err)
|
||
return
|
||
}
|
||
|
||
if ossConfig == nil {
|
||
utils.Error(c, 404, "OSS config not found")
|
||
return
|
||
}
|
||
|
||
// 检查是否为默认本地存储配置,不允许删除
|
||
if ossConfig.Name == "本地存储" && ossConfig.StorageType == "local" {
|
||
utils.Error(c, 400, "默认本地存储配置不能删除")
|
||
return
|
||
}
|
||
|
||
if err := repositories.DeleteOSSConfig(id); err != nil {
|
||
utils.ServerError(c, err)
|
||
return
|
||
}
|
||
|
||
utils.SuccessWithMsg(c, "OSS config deleted successfully", nil)
|
||
}
|
||
|
||
// AdminTestOSSConfig 测试OSS配置连通性
|
||
func AdminTestOSSConfig(c *gin.Context) {
|
||
idStr := c.Param("id")
|
||
parsedID, err := strconv.ParseUint(idStr, 10, 32)
|
||
if err != nil {
|
||
utils.Error(c, 400, "Invalid OSS config ID")
|
||
return
|
||
}
|
||
id := uint(parsedID)
|
||
|
||
ossConfig, err := repositories.GetOSSConfigByID(id)
|
||
if err != nil || ossConfig == nil {
|
||
utils.Error(c, 404, "OSS config not found")
|
||
return
|
||
}
|
||
|
||
var runtimeCfg *utils.OSSConfig
|
||
if ossConfig.StorageType == "aliyun" {
|
||
if envCfg, ok := utils.LoadAliyunConfigFromEnv(); ok {
|
||
runtimeCfg = envCfg
|
||
}
|
||
}
|
||
if runtimeCfg == nil {
|
||
runtimeCfg, err = buildRuntimeOSSConfig(ossConfig)
|
||
if err != nil {
|
||
utils.Error(c, 400, err.Error())
|
||
return
|
||
}
|
||
}
|
||
|
||
if err := utils.TestOSSConnection(runtimeCfg); err != nil {
|
||
utils.Error(c, 400, "连接测试失败: "+err.Error())
|
||
return
|
||
}
|
||
|
||
source := "db"
|
||
if ossConfig.StorageType == "aliyun" && utils.HasAliyunEnvConfig() {
|
||
source = "env"
|
||
}
|
||
|
||
utils.SuccessWithMsg(c, "连接测试成功", gin.H{
|
||
"storageType": ossConfig.StorageType,
|
||
"name": ossConfig.Name,
|
||
"source": source,
|
||
})
|
||
}
|
||
|
||
func decryptOptional(encrypted string) string {
|
||
if encrypted == "" {
|
||
return ""
|
||
}
|
||
decrypted, err := utils.DecryptAES(encrypted)
|
||
if err != nil {
|
||
return ""
|
||
}
|
||
return decrypted
|
||
}
|
||
|
||
func pickCredential(reqVal, existingEncrypted string) string {
|
||
if reqVal != "" && reqVal != "***" {
|
||
return reqVal
|
||
}
|
||
return decryptOptional(existingEncrypted)
|
||
}
|
||
|
||
func validateOSSCredentialsForEnable(
|
||
storageType string,
|
||
existing *models.OSSConfig,
|
||
legacyAccessKey, legacySecretKey string,
|
||
ossAccessKeyID, ossAccessKeySecret, ossEndpoint, ossBucket string,
|
||
qcloudSecretID, qcloudSecretKey, qcloudRegion, qcloudBucket string,
|
||
qiniuAccessKey, qiniuSecretKey, qiniuBucket string,
|
||
) string {
|
||
switch storageType {
|
||
case "aliyun":
|
||
ak := pickCredential(ossAccessKeyID, existing.OSSAccessKeyID)
|
||
sk := pickCredential(ossAccessKeySecret, existing.OSSAccessKeySecret)
|
||
if ak == "" {
|
||
ak = pickCredential(legacyAccessKey, existing.AccessKey)
|
||
}
|
||
if sk == "" {
|
||
sk = pickCredential(legacySecretKey, existing.SecretKey)
|
||
}
|
||
endpoint := ossEndpoint
|
||
if endpoint == "" {
|
||
endpoint = existing.OSSEndpoint
|
||
}
|
||
if endpoint == "" {
|
||
endpoint = existing.Region
|
||
}
|
||
bucket := ossBucket
|
||
if bucket == "" {
|
||
bucket = existing.OSSBucket
|
||
}
|
||
if bucket == "" {
|
||
bucket = existing.Bucket
|
||
}
|
||
if ak == "" || sk == "" || endpoint == "" || bucket == "" {
|
||
return "启用阿里云OSS前必须填写 AccessKeyId、AccessKeySecret、Endpoint 和 Bucket"
|
||
}
|
||
case "qcloud":
|
||
id := pickCredential(qcloudSecretID, existing.QCloudSecretID)
|
||
key := pickCredential(qcloudSecretKey, existing.QCloudSecretKey)
|
||
if id == "" {
|
||
id = pickCredential(legacyAccessKey, existing.AccessKey)
|
||
}
|
||
if key == "" {
|
||
key = pickCredential(legacySecretKey, existing.SecretKey)
|
||
}
|
||
region := qcloudRegion
|
||
if region == "" {
|
||
region = existing.QCloudRegion
|
||
}
|
||
if region == "" {
|
||
region = existing.Region
|
||
}
|
||
bucket := qcloudBucket
|
||
if bucket == "" {
|
||
bucket = existing.QCloudBucket
|
||
}
|
||
if bucket == "" {
|
||
bucket = existing.Bucket
|
||
}
|
||
if id == "" || key == "" || region == "" || bucket == "" {
|
||
return "启用腾讯云COS前必须填写 SecretId、SecretKey、Region 和 Bucket"
|
||
}
|
||
case "qiniu":
|
||
ak := pickCredential(qiniuAccessKey, existing.QiniuAccessKey)
|
||
sk := pickCredential(qiniuSecretKey, existing.QiniuSecretKey)
|
||
if ak == "" {
|
||
ak = pickCredential(legacyAccessKey, existing.AccessKey)
|
||
}
|
||
if sk == "" {
|
||
sk = pickCredential(legacySecretKey, existing.SecretKey)
|
||
}
|
||
bucket := qiniuBucket
|
||
if bucket == "" {
|
||
bucket = existing.QiniuBucket
|
||
}
|
||
if bucket == "" {
|
||
bucket = existing.Bucket
|
||
}
|
||
if ak == "" || sk == "" || bucket == "" {
|
||
return "启用七牛云前必须填写 AccessKey、SecretKey 和 Bucket"
|
||
}
|
||
default:
|
||
ak := pickCredential(legacyAccessKey, existing.AccessKey)
|
||
sk := pickCredential(legacySecretKey, existing.SecretKey)
|
||
if ak == "" || sk == "" {
|
||
return "启用非本地存储配置前必须填写密钥"
|
||
}
|
||
}
|
||
return ""
|
||
}
|
||
|
||
func maskOSSSecrets(ossConfig *models.OSSConfig) {
|
||
ossConfig.AccessKey = "***"
|
||
ossConfig.SecretKey = "***"
|
||
ossConfig.OSSAccessKeyID = "***"
|
||
ossConfig.OSSAccessKeySecret = "***"
|
||
ossConfig.QCloudSecretID = "***"
|
||
ossConfig.QCloudSecretKey = "***"
|
||
ossConfig.QiniuAccessKey = "***"
|
||
ossConfig.QiniuSecretKey = "***"
|
||
}
|
||
|
||
func buildRuntimeOSSConfig(ossConfig *models.OSSConfig) (*utils.OSSConfig, error) {
|
||
cfg := &utils.OSSConfig{
|
||
StorageType: ossConfig.StorageType,
|
||
AccessKey: decryptOptional(ossConfig.AccessKey),
|
||
SecretKey: decryptOptional(ossConfig.SecretKey),
|
||
Bucket: ossConfig.Bucket,
|
||
Region: ossConfig.Region,
|
||
Domain: ossConfig.Domain,
|
||
}
|
||
|
||
switch ossConfig.StorageType {
|
||
case "aliyun":
|
||
cfg.OSSAccessKeyID = decryptOptional(ossConfig.OSSAccessKeyID)
|
||
cfg.OSSAccessKeySecret = decryptOptional(ossConfig.OSSAccessKeySecret)
|
||
cfg.OSSEndpoint = ossConfig.OSSEndpoint
|
||
cfg.OSSBucket = ossConfig.OSSBucket
|
||
cfg.OSSDomain = ossConfig.OSSDomain
|
||
if cfg.OSSAccessKeyID == "" {
|
||
cfg.OSSAccessKeyID = cfg.AccessKey
|
||
}
|
||
if cfg.OSSAccessKeySecret == "" {
|
||
cfg.OSSAccessKeySecret = cfg.SecretKey
|
||
}
|
||
if cfg.OSSBucket == "" {
|
||
cfg.OSSBucket = cfg.Bucket
|
||
}
|
||
if cfg.OSSDomain == "" {
|
||
cfg.OSSDomain = cfg.Domain
|
||
}
|
||
if cfg.OSSAccessKeyID == "" || cfg.OSSAccessKeySecret == "" || cfg.OSSBucket == "" {
|
||
return nil, fmt.Errorf("阿里云OSS配置不完整:需要 AccessKeyId、AccessKeySecret 和 Bucket")
|
||
}
|
||
if cfg.OSSEndpoint == "" && cfg.Region == "" {
|
||
return nil, fmt.Errorf("阿里云OSS配置不完整:需要 Endpoint 或 Region")
|
||
}
|
||
case "qcloud":
|
||
cfg.QCloudSecretID = decryptOptional(ossConfig.QCloudSecretID)
|
||
cfg.QCloudSecretKey = decryptOptional(ossConfig.QCloudSecretKey)
|
||
cfg.QCloudRegion = ossConfig.QCloudRegion
|
||
cfg.QCloudBucket = ossConfig.QCloudBucket
|
||
cfg.QCloudDomain = ossConfig.QCloudDomain
|
||
if cfg.QCloudSecretID == "" {
|
||
cfg.QCloudSecretID = cfg.AccessKey
|
||
}
|
||
if cfg.QCloudSecretKey == "" {
|
||
cfg.QCloudSecretKey = cfg.SecretKey
|
||
}
|
||
if cfg.QCloudRegion == "" {
|
||
cfg.QCloudRegion = cfg.Region
|
||
}
|
||
if cfg.QCloudBucket == "" {
|
||
cfg.QCloudBucket = cfg.Bucket
|
||
}
|
||
if cfg.QCloudDomain == "" {
|
||
cfg.QCloudDomain = cfg.Domain
|
||
}
|
||
if cfg.QCloudSecretID == "" || cfg.QCloudSecretKey == "" || cfg.QCloudBucket == "" || cfg.QCloudRegion == "" {
|
||
return nil, fmt.Errorf("腾讯云COS配置不完整:需要 SecretId、SecretKey、Bucket 和 Region")
|
||
}
|
||
case "qiniu":
|
||
cfg.QiniuAccessKey = decryptOptional(ossConfig.QiniuAccessKey)
|
||
cfg.QiniuSecretKey = decryptOptional(ossConfig.QiniuSecretKey)
|
||
cfg.QiniuBucket = ossConfig.QiniuBucket
|
||
cfg.QiniuRegion = ossConfig.QiniuRegion
|
||
cfg.QiniuDomain = ossConfig.QiniuDomain
|
||
if cfg.QiniuAccessKey == "" {
|
||
cfg.QiniuAccessKey = cfg.AccessKey
|
||
}
|
||
if cfg.QiniuSecretKey == "" {
|
||
cfg.QiniuSecretKey = cfg.SecretKey
|
||
}
|
||
if cfg.QiniuBucket == "" {
|
||
cfg.QiniuBucket = cfg.Bucket
|
||
}
|
||
if cfg.QiniuDomain == "" {
|
||
cfg.QiniuDomain = cfg.Domain
|
||
}
|
||
if cfg.QiniuAccessKey == "" || cfg.QiniuSecretKey == "" || cfg.QiniuBucket == "" {
|
||
return nil, fmt.Errorf("七牛云配置不完整:需要 AccessKey、SecretKey 和 Bucket")
|
||
}
|
||
case "local":
|
||
// no credentials required
|
||
default:
|
||
return nil, fmt.Errorf("不支持的存储类型: %s", ossConfig.StorageType)
|
||
}
|
||
|
||
return cfg, nil
|
||
}
|