You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@answer.apache.org by li...@apache.org on 2024/01/30 08:16:22 UTC
(incubator-answer) 01/01: refactor(file): refactor file format check function
This is an automated email from the ASF dual-hosted git repository.
linkinstar pushed a commit to branch refactor/file
in repository https://gitbox.apache.org/repos/asf/incubator-answer.git
commit cf4e05fbc653e1888cd895e44fc4608af15a458f
Author: LinkinStars <li...@foxmail.com>
AuthorDate: Tue Jan 30 16:16:07 2024 +0800
refactor(file): refactor file format check function
---
internal/service/uploader/upload.go | 2 +-
pkg/checker/file_type.go | 77 +++++++++++++++++++++++++++++--------
2 files changed, 61 insertions(+), 18 deletions(-)
diff --git a/internal/service/uploader/upload.go b/internal/service/uploader/upload.go
index fb0b2af0..3619a6e1 100644
--- a/internal/service/uploader/upload.go
+++ b/internal/service/uploader/upload.go
@@ -244,7 +244,7 @@ func (us *uploaderService) uploadFile(ctx *gin.Context, file *multipart.FileHead
}
defer src.Close()
- if !checker.IsSupportedImageFile(src, filepath.Ext(fileSubPath)) {
+ if !checker.IsSupportedImageFile(filePath) {
return "", errors.BadRequest(reason.UploadFileUnsupportedFileFormat)
}
diff --git a/pkg/checker/file_type.go b/pkg/checker/file_type.go
index 3599270a..6c61dca2 100644
--- a/pkg/checker/file_type.go
+++ b/pkg/checker/file_type.go
@@ -20,13 +20,18 @@
package checker
import (
- "golang.org/x/image/webp"
+ "fmt"
"image"
_ "image/gif" // use init to support decode jpeg,jpg,png,gif
_ "image/jpeg"
_ "image/png"
"io"
+ "os"
+ "path/filepath"
"strings"
+
+ "github.com/segmentfault/pacman/log"
+ "golang.org/x/image/webp"
)
const (
@@ -35,47 +40,85 @@ const (
// IsSupportedImageFile currently answers support image type is
// `image/jpeg, image/jpg, image/png, image/gif, image/webp`
-func IsSupportedImageFile(file io.Reader, ext string) bool {
- ext = strings.ToLower(strings.TrimPrefix(ext, "."))
- var err error
+func IsSupportedImageFile(localFilePath string) bool {
+ ext := strings.ToLower(strings.TrimPrefix(filepath.Ext(localFilePath), "."))
switch ext {
case "jpg", "jpeg", "png", "gif": // only allow for `image/jpeg,image/jpg,image/png, image/gif`
- if !checkImageSize(file) {
+ if !decodeAndCheckImageFile(localFilePath, standardImageConfigCheck) {
+ return false
+ }
+ if !decodeAndCheckImageFile(localFilePath, standardImageCheck) {
return false
}
- _, _, err = image.Decode(file)
case "ico":
// TODO: There is currently no good Golang library to parse whether the image is in ico format.
return true
case "webp":
- if !checkWebpSize(file) {
+ if !decodeAndCheckImageFile(localFilePath, webpImageConfigCheck) {
+ return false
+ }
+ if !decodeAndCheckImageFile(localFilePath, webpImageCheck) {
return false
}
- _, err = webp.Decode(file)
default:
return false
}
- return err == nil
+ return true
}
-func checkImageSize(file io.Reader) bool {
- config, _, err := image.DecodeConfig(file)
+func decodeAndCheckImageFile(localFilePath string, checker func(io.Reader) error) bool {
+ file, err := os.Open(localFilePath)
if err != nil {
+ log.Errorf("open file error: %v", err)
return false
}
- if (config.Width * config.Height) > maxImageSize {
+ defer file.Close()
+
+ if err = checker(file); err != nil {
+ log.Errorf("check image format error: %v", err)
return false
}
return true
}
-func checkWebpSize(file io.Reader) bool {
+func standardImageConfigCheck(file io.Reader) error {
+ config, _, err := image.DecodeConfig(file)
+ if err != nil {
+ return fmt.Errorf("decode image config error: %v", err)
+ }
+ if imageSizeTooLarge(config) {
+ return fmt.Errorf("image size too large")
+ }
+ return nil
+}
+
+func standardImageCheck(file io.Reader) error {
+ _, _, err := image.Decode(file)
+ if err != nil {
+ return fmt.Errorf("decode image error: %v", err)
+ }
+ return nil
+}
+
+func webpImageConfigCheck(file io.Reader) error {
config, err := webp.DecodeConfig(file)
if err != nil {
- return false
+ return fmt.Errorf("decode webp image config error: %v", err)
}
- if (config.Width * config.Height) > maxImageSize {
- return false
+ if imageSizeTooLarge(config) {
+ return fmt.Errorf("image size too large")
}
- return true
+ return nil
+}
+
+func webpImageCheck(file io.Reader) error {
+ _, err := webp.Decode(file)
+ if err != nil {
+ return fmt.Errorf("decode webp image error: %v", err)
+ }
+ return nil
+}
+
+func imageSizeTooLarge(config image.Config) bool {
+ return config.Width*config.Height > maxImageSize
}