文件管理权限控制

This commit is contained in:
ryan
2026-06-11 13:58:45 +08:00
parent 312bc7d4d5
commit 5e0de01c4b
18 changed files with 993 additions and 337 deletions
+48
View File
@@ -5,10 +5,14 @@
package upload
import (
"encoding/json"
"errors"
"net/http"
"strconv"
"strings"
"github.com/Rain-kl/Wavelet/internal/apps/oauth"
"github.com/Rain-kl/Wavelet/internal/common"
"github.com/Rain-kl/Wavelet/internal/db"
"github.com/Rain-kl/Wavelet/internal/model"
"github.com/Rain-kl/Wavelet/internal/storage"
@@ -24,6 +28,7 @@ import (
// @Param id path string true "文件 ID"
// @Success 200 {file} file "成功获取文件内容"
// @Failure 400 {object} util.ResponseAny "文件 ID 格式错误"
// @Failure 401 {object} util.ResponseAny "未登录"
// @Failure 404 {object} util.ResponseAny "文件未找到"
// @Failure 500 {object} util.ResponseAny "服务内部错误"
// @Router /f/{id} [get]
@@ -50,6 +55,12 @@ func ServeFileByID(c *gin.Context) {
return
}
// 校验业务白名单与访问权限
if err := checkFileAccessPermission(c, upload.Type); err != nil {
c.AbortWithStatusJSON(http.StatusUnauthorized, gin.H{"error_msg": common.UnAuthorized, "data": nil})
return
}
if upload.StorageDriver == "local" || (upload.StorageDriver == "" && !storage.IsEnabled()) {
c.File(upload.FilePath)
return
@@ -74,3 +85,40 @@ func ServeFileByID(c *gin.Context) {
// Respond with the file content
c.DataFromReader(http.StatusOK, obj.ContentLength, obj.ContentType, obj.Body, nil)
}
// checkFileAccessPermission 校验文件是否可以被当前请求访问
func checkFileAccessPermission(c *gin.Context, uploadType string) error {
var sc model.SystemConfig
var whitelist []string
if err := sc.GetByKey(c.Request.Context(), model.ConfigKeyFileAccessWhitelist); err == nil && sc.Value != "" {
if err := json.Unmarshal([]byte(sc.Value), &whitelist); err != nil {
// 降级使用逗号分隔解析
parts := strings.Split(sc.Value, ",")
for _, p := range parts {
p = strings.TrimSpace(p)
if p != "" {
whitelist = append(whitelist, p)
}
}
}
} else {
// 默认兜底白名单为 avatar
whitelist = []string{"avatar"}
}
inWhitelist := false
for _, w := range whitelist {
if strings.EqualFold(w, uploadType) {
inWhitelist = true
break
}
}
if !inWhitelist {
// 必须进行鉴权
if _, err := oauth.GetUserFromRequest(c); err != nil {
return err
}
}
return nil
}