修复数据类型错误
This commit is contained in:
@@ -24,12 +24,12 @@ user:
|
|||||||
file:
|
file:
|
||||||
max_size: 52428800
|
max_size: 52428800
|
||||||
pahts:
|
pahts:
|
||||||
- "./data/avatar/"
|
avatar: "./data/avatar/"
|
||||||
- "./data/upload/image/"
|
image: "./data/upload/image/"
|
||||||
- "./data/upload/video/"
|
video: "./data/upload/video/"
|
||||||
- "./data/upload/music/"
|
music: "./data/upload/music/"
|
||||||
- "./data/upload/pdf/"
|
pdf: "./data/upload/pdf/"
|
||||||
- "./data/upload/other/"
|
other: "./data/upload/other/"
|
||||||
|
|
||||||
allow_image_mime:
|
allow_image_mime:
|
||||||
image/jpeg: true
|
image/jpeg: true
|
||||||
|
|||||||
+1
-1
@@ -77,7 +77,7 @@ func main() {
|
|||||||
r.Static("/dist/", "./static/dist/")
|
r.Static("/dist/", "./static/dist/")
|
||||||
|
|
||||||
//静态用户上传的文件
|
//静态用户上传的文件
|
||||||
r.Static("/avatar/", models.Configs_file.Pahts[0])
|
r.Static("/avatar/", models.Configs_file.Pahts["avatar"])
|
||||||
//store := cookie.NewStore([]byte("secret"))
|
//store := cookie.NewStore([]byte("secret"))
|
||||||
|
|
||||||
// 自定义 404 页面(需要提前加载模板)
|
// 自定义 404 页面(需要提前加载模板)
|
||||||
|
|||||||
@@ -15,16 +15,7 @@ var Configs_file Configs_file_t
|
|||||||
|
|
||||||
var Database_configs map[string]interface{}
|
var Database_configs map[string]interface{}
|
||||||
|
|
||||||
var Allowed_avatar_ext = map[string]bool{
|
|
||||||
".jpg": true,
|
|
||||||
".jpeg": true,
|
|
||||||
".png": true,
|
|
||||||
}
|
|
||||||
|
|
||||||
var Allowed_avatar_mime = map[string]bool{
|
|
||||||
"image/jpeg": true,
|
|
||||||
"image/png": true,
|
|
||||||
}
|
|
||||||
|
|
||||||
func init() {
|
func init() {
|
||||||
|
|
||||||
|
|||||||
@@ -1,5 +1,27 @@
|
|||||||
package models
|
package models
|
||||||
|
|
||||||
|
//mime信息转换位拓展名
|
||||||
|
var Mime_to_extname = map[string]string{
|
||||||
|
|
||||||
|
"image/jpeg": ".jpeg",
|
||||||
|
"image/png": ".png",
|
||||||
|
"image/gif": ".gif",
|
||||||
|
"image/bmp": ".bmp",
|
||||||
|
|
||||||
|
"video/mp4": ".mp4",
|
||||||
|
"video/x-msvideo": ".",
|
||||||
|
"video/quicktime": ".",
|
||||||
|
"video/x-flv": ".flv",
|
||||||
|
"video/mpeg": ".mpeg",
|
||||||
|
|
||||||
|
"audio/mpeg": ".mp3",
|
||||||
|
"audio/aac": ".acc",
|
||||||
|
"audio/wav": ".wav",
|
||||||
|
"audio/flac": ".flac",
|
||||||
|
|
||||||
|
"application/pdf": ".pdf",
|
||||||
|
}
|
||||||
|
|
||||||
type Configs_web_t struct {
|
type Configs_web_t struct {
|
||||||
Host string `mapstructure:"host"`
|
Host string `mapstructure:"host"`
|
||||||
Port string `mapstructure:"port"`
|
Port string `mapstructure:"port"`
|
||||||
@@ -18,7 +40,7 @@ type Configs_user_t struct {
|
|||||||
|
|
||||||
type Configs_file_t struct {
|
type Configs_file_t struct {
|
||||||
Max_size uint64 `mapstructure:"max_size"`
|
Max_size uint64 `mapstructure:"max_size"`
|
||||||
Pahts []string `mapstructure:"pahts"`
|
Pahts map[string]string `mapstructure:"pahts"`
|
||||||
Allow_image_mime map[string]bool `mapstructure:"allow_image_mime"`
|
Allow_image_mime map[string]bool `mapstructure:"allow_image_mime"`
|
||||||
Allow_video_mime map[string]bool `mapstructure:"allow_video_mime"`
|
Allow_video_mime map[string]bool `mapstructure:"allow_video_mime"`
|
||||||
Allow_music_mime map[string]bool `mapstructure:"allow_music_mime"`
|
Allow_music_mime map[string]bool `mapstructure:"allow_music_mime"`
|
||||||
|
|||||||
@@ -2,14 +2,8 @@ package routers
|
|||||||
|
|
||||||
import (
|
import (
|
||||||
"bytes"
|
"bytes"
|
||||||
"crypto/sha256"
|
|
||||||
"encoding/hex"
|
|
||||||
"fmt"
|
"fmt"
|
||||||
"io"
|
"io"
|
||||||
"net/http"
|
|
||||||
"path"
|
|
||||||
"path/filepath"
|
|
||||||
"saas/models"
|
|
||||||
"time"
|
"time"
|
||||||
|
|
||||||
"github.com/gin-gonic/gin"
|
"github.com/gin-gonic/gin"
|
||||||
@@ -94,118 +88,6 @@ func V1_file_api(r *gin.RouterGroup) {
|
|||||||
|
|
||||||
//接收头像的接口,
|
//接收头像的接口,
|
||||||
r.POST("/avatar", func(ctx *gin.Context) {
|
r.POST("/avatar", func(ctx *gin.Context) {
|
||||||
//返回前端的数据
|
|
||||||
err_msg := "user_api_error"
|
|
||||||
err_code := Error_code[err_msg]
|
|
||||||
data := map[string]interface{}{}
|
|
||||||
|
|
||||||
//判断权限是否可以接收
|
|
||||||
//先判断是否已经登录
|
|
||||||
//获取中间件处理的结果
|
|
||||||
is_login, _ := ctx.Get("is_login")
|
|
||||||
if is_login == true {
|
|
||||||
//读取用户id信息
|
|
||||||
user, _ := ctx.Get("user")
|
|
||||||
//保存这个头像
|
|
||||||
file, err := ctx.FormFile("file")
|
|
||||||
if err == nil {
|
|
||||||
//限制文件大小
|
|
||||||
if file.Size > 512 {
|
|
||||||
if file.Size < 1024000 {
|
|
||||||
// 2. 安全获取文件名并处理路径问题
|
|
||||||
filename := filepath.Base(file.Filename) // 防御性处理路径分隔符
|
|
||||||
// 3. 获取标准后缀名(含点)
|
|
||||||
extWithDot := filepath.Ext(filename)
|
|
||||||
//判断后缀名类型是否是允许的
|
|
||||||
if models.Allowed_avatar_ext[extWithDot] {
|
|
||||||
//判断文件mime是否合法
|
|
||||||
// 打开文件流
|
|
||||||
src_mime, _ := file.Open()
|
|
||||||
defer src_mime.Close()
|
|
||||||
// 读取前512字节用于MIME检测
|
|
||||||
buffer := make([]byte, 512)
|
|
||||||
io.ReadFull(src_mime, buffer)
|
|
||||||
// 检测MIME类型
|
|
||||||
mimeType := http.DetectContentType(buffer)
|
|
||||||
if models.Allowed_avatar_mime[mimeType] {
|
|
||||||
// 打开文件流
|
|
||||||
src, _ := file.Open()
|
|
||||||
defer src.Close()
|
|
||||||
// 创建SHA256哈希器
|
|
||||||
hasher := sha256.New()
|
|
||||||
|
|
||||||
// 计算哈希值
|
|
||||||
io.Copy(hasher, src)
|
|
||||||
// 获取哈希结果
|
|
||||||
hashBytes := hasher.Sum(nil)
|
|
||||||
hashString := hex.EncodeToString(hashBytes)
|
|
||||||
|
|
||||||
new_filename := fmt.Sprintf("%d_%s%s", user.(*models.User).ID, hashString, extWithDot)
|
|
||||||
file.Filename = new_filename
|
|
||||||
|
|
||||||
//这是上传的真实路径
|
|
||||||
dst := path.Join("./data/avatar", file.Filename)
|
|
||||||
|
|
||||||
//这是经过gin路由的路径
|
|
||||||
gin_dat := path.Join("/avatar", file.Filename)
|
|
||||||
|
|
||||||
//判断文件是否存在避免重复保存
|
|
||||||
if models.File_exists(dst) {
|
|
||||||
//fmt.Println("文件存在")
|
|
||||||
err_msg = "api_ok"
|
|
||||||
err_code = Error_code[err_msg]
|
|
||||||
//返回gin路由的路径
|
|
||||||
data["path"] = gin_dat
|
|
||||||
data["new_path"] = false
|
|
||||||
} else {
|
|
||||||
//fmt.Println("文件no存在")
|
|
||||||
ferr := ctx.SaveUploadedFile(file, dst)
|
|
||||||
if ferr == nil {
|
|
||||||
//文件保存成功
|
|
||||||
err_msg = "api_ok"
|
|
||||||
err_code = Error_code[err_msg]
|
|
||||||
//返回gin路由的路径
|
|
||||||
data["path"] = gin_dat
|
|
||||||
data["new_path"] = true
|
|
||||||
|
|
||||||
} else {
|
|
||||||
err_msg = "file_save_err"
|
|
||||||
err_code = Error_code[err_msg]
|
|
||||||
fmt.Println(ferr)
|
|
||||||
data["err"] = ferr
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
err_msg = "file_mime_err"
|
|
||||||
err_code = Error_code[err_msg]
|
|
||||||
}
|
|
||||||
|
|
||||||
} else {
|
|
||||||
err_msg = "file_type_err"
|
|
||||||
err_code = Error_code[err_msg]
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
err_msg = "file_size_err"
|
|
||||||
err_code = Error_code[err_msg]
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
err_msg = "file_size_err"
|
|
||||||
err_code = Error_code[err_msg]
|
|
||||||
}
|
|
||||||
|
|
||||||
} else {
|
|
||||||
err_msg = "file_get_err"
|
|
||||||
err_code = Error_code[err_msg]
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
err_msg = "user_no_sign"
|
|
||||||
err_code = Error_code[err_msg]
|
|
||||||
}
|
|
||||||
ctx.JSON(200, map[string]interface{}{
|
|
||||||
"api": "ok",
|
|
||||||
"err_code": err_code,
|
|
||||||
"err_msg": err_msg,
|
|
||||||
"data": data,
|
|
||||||
})
|
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -41,7 +41,7 @@ func Router_file(r *gin.RouterGroup) {
|
|||||||
//先判断有没有登录
|
//先判断有没有登录
|
||||||
user_info_any, is_login := ctx.Get("user_info") //因为需要读取user_info,避免重复调用 这一步就不在中间件操作了
|
user_info_any, is_login := ctx.Get("user_info") //因为需要读取user_info,避免重复调用 这一步就不在中间件操作了
|
||||||
if is_login {
|
if is_login {
|
||||||
user_info := user_info_any.(models.User_info) //直接断言类型,这个值是从数据库直接读取的 理论不会出错
|
user_info := user_info_any.(*models.User_info) //直接断言类型,这个值是从数据库直接读取的 理论不会出错
|
||||||
file, err := ctx.FormFile("file")
|
file, err := ctx.FormFile("file")
|
||||||
if err == nil {
|
if err == nil {
|
||||||
|
|
||||||
@@ -75,11 +75,13 @@ func Router_file(r *gin.RouterGroup) {
|
|||||||
hashBytes := hasher.Sum(nil)
|
hashBytes := hasher.Sum(nil)
|
||||||
hashString := hex.EncodeToString(hashBytes)
|
hashString := hex.EncodeToString(hashBytes)
|
||||||
|
|
||||||
new_filename := fmt.Sprintf("%d_%s", user_info.UserID, hashString)
|
new_filename := fmt.Sprintf("%s", hashString)
|
||||||
file.Filename = new_filename
|
file.Filename = new_filename
|
||||||
|
|
||||||
|
fmt.Println(user_info)
|
||||||
|
|
||||||
//这是上传的真实路径
|
//这是上传的真实路径
|
||||||
dst := path.Join("./data/avatar", file.Filename)
|
dst := path.Join(models.Configs_file.Pahts["image"], file.Filename)
|
||||||
|
|
||||||
//判断文件是否存在避免重复保存
|
//判断文件是否存在避免重复保存
|
||||||
if models.File_exists(dst) {
|
if models.File_exists(dst) {
|
||||||
|
|||||||
Reference in New Issue
Block a user