Skip to content

Commit

Permalink
Add file extsnsion check to media uploads.
Browse files Browse the repository at this point in the history
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.
  • Loading branch information
knadh committed May 23, 2021
1 parent 69f84c9 commit dba47bc
Show file tree
Hide file tree
Showing 2 changed files with 22 additions and 26 deletions.
26 changes: 16 additions & 10 deletions cmd/media.go
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ import (
"bytes"
"mime/multipart"
"net/http"
"path/filepath"
"strconv"

"github.com/disintegration/imaging"
Expand All @@ -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 {
Expand All @@ -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))
}
Expand Down
22 changes: 6 additions & 16 deletions cmd/utils.go
Original file line number Diff line number Diff line change
Expand Up @@ -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.
Expand Down

0 comments on commit dba47bc

Please sign in to comment.