浏览代码

Add file extsnsion check to media uploads.

While file content (MIME) check already existed, the lack of file
extension check allowed arbitrary extensions to be uploaded and
then accessed via the static file server. For instance, a .html file
with JPG content intersperesed with Javascript.

This commit adds a file extension check on top of the MIME type check.
Kailash Nadh 4 年之前
父节点
当前提交
dba47bca28
共有 2 个文件被更改,包括 22 次插入26 次删除
  1. 16 10
      cmd/media.go
  2. 6 16
      cmd/utils.go

+ 16 - 10
cmd/media.go

@@ -4,6 +4,7 @@ import (
 	"bytes"
 	"mime/multipart"
 	"net/http"
+	"path/filepath"
 	"strconv"
 
 	"github.com/disintegration/imaging"
@@ -17,13 +18,11 @@ const (
 	thumbnailSize = 90
 )
 
-// imageMimes is the list of image types allowed to be uploaded.
-var imageMimes = []string{
-	"image/jpg",
-	"image/jpeg",
-	"image/png",
-	"image/svg",
-	"image/gif"}
+// validMimes is the list of image types allowed to be uploaded.
+var (
+	validMimes = []string{"image/jpg", "image/jpeg", "image/png", "image/gif"}
+	validExts  = []string{".jpg", ".jpeg", ".png", ".gif"}
+)
 
 // handleUploadMedia handles media file uploads.
 func handleUploadMedia(c echo.Context) error {
@@ -37,9 +36,16 @@ func handleUploadMedia(c echo.Context) error {
 			app.i18n.Ts("media.invalidFile", "error", err.Error()))
 	}
 
-	// Validate MIME type with the list of allowed types.
-	var typ = file.Header.Get("Content-type")
-	if ok := validateMIME(typ, imageMimes); !ok {
+	// Validate file extension.
+	ext := filepath.Ext(file.Filename)
+	if ok := inArray(ext, validExts); !ok {
+		return echo.NewHTTPError(http.StatusBadRequest,
+			app.i18n.Ts("media.unsupportedFileType", "type", ext))
+	}
+
+	// Validate file's mime.
+	typ := file.Header.Get("Content-type")
+	if ok := inArray(typ, validMimes); !ok {
 		return echo.NewHTTPError(http.StatusBadRequest,
 			app.i18n.Ts("media.unsupportedFileType", "type", typ))
 	}

+ 6 - 16
cmd/utils.go

@@ -15,24 +15,14 @@ var (
 	tagRegexpSpaces = regexp.MustCompile(`[\s]+`)
 )
 
-// validateMIME is a helper function to validate uploaded file's MIME type
-// against the slice of MIME types is given.
-func validateMIME(typ string, mimes []string) (ok bool) {
-	if len(mimes) > 0 {
-		var (
-			ok = false
-		)
-		for _, m := range mimes {
-			if typ == m {
-				ok = true
-				break
-			}
-		}
-		if !ok {
-			return false
+// inArray checks if a string is present in a list of strings.
+func inArray(val string, vals []string) (ok bool) {
+	for _, v := range vals {
+		if v == val {
+			return true
 		}
 	}
-	return true
+	return false
 }
 
 // generateFileName appends the incoming file's name with a small random hash.