diff --git a/agent/app/service/file.go b/agent/app/service/file.go index e9a25ae00..a375129b8 100644 --- a/agent/app/service/file.go +++ b/agent/app/service/file.go @@ -720,6 +720,9 @@ func (f *FileService) GetPreviewContent(op request.FileContentReq) (response.Fil return response.FileInfo{}, err } + if files.IsBinaryPreviewFile(info.MimeType, info.Extension) { + return response.FileInfo{}, buserr.New("ErrFileCanNotRead") + } if files.IsBlockDevice(info.FileMode) { return response.FileInfo{FileInfo: *info}, nil } @@ -932,6 +935,9 @@ func readEditableFileHistoryContent(filePath string) ([]byte, os.FileMode, bool) if mode.IsDir() || mode&os.ModeSymlink != 0 || !mode.IsRegular() || files.IsBlockDevice(mode) || info.Size() > fileHistorySnapshotMaxSize { return nil, mode, false } + if files.IsBinaryPreviewFile(files.GetMimeType(filePath), filepath.Ext(info.Name())) { + return nil, mode, false + } file, err := os.Open(filePath) if err != nil { return nil, mode, false diff --git a/agent/utils/files/fileinfo.go b/agent/utils/files/fileinfo.go index 0ab23fb23..25c5380e0 100644 --- a/agent/utils/files/fileinfo.go +++ b/agent/utils/files/fileinfo.go @@ -21,6 +21,76 @@ import ( "github.com/spf13/afero" ) +var binaryPreviewMimeTypes = map[string]struct{}{ + "application/pdf": {}, + "application/zip": {}, + "application/gzip": {}, + "application/x-gzip": {}, + "application/x-7z-compressed": {}, + "application/x-rar-compressed": {}, + "application/x-bzip2": {}, + "application/x-xz": {}, + "application/x-tar": {}, + "application/java-archive": {}, + "application/msword": {}, + "application/vnd.ms-excel": {}, + "application/vnd.ms-powerpoint": {}, + "application/vnd.openxmlformats-officedocument.wordprocessingml.document": {}, + "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet": {}, + "application/vnd.openxmlformats-officedocument.presentationml.presentation": {}, +} + +var binaryPreviewMimePrefixes = []string{ + "image/", + "audio/", + "video/", + "application/vnd.ms-", + "application/vnd.openxmlformats-officedocument.", + "application/vnd.oasis.opendocument.", +} + +var binaryPreviewExtensions = map[string]struct{}{ + ".pdf": {}, + ".zip": {}, + ".gz": {}, + ".bz2": {}, + ".xz": {}, + ".tar": {}, + ".tgz": {}, + ".rar": {}, + ".7z": {}, + ".war": {}, + ".doc": {}, + ".docx": {}, + ".xls": {}, + ".xlsx": {}, + ".ppt": {}, + ".pptx": {}, + ".jpg": {}, + ".jpeg": {}, + ".png": {}, + ".bmp": {}, + ".gif": {}, + ".tiff": {}, + ".ico": {}, + ".webp": {}, + ".svg": {}, + ".mp3": {}, + ".wav": {}, + ".wma": {}, + ".ape": {}, + ".acc": {}, + ".ogg": {}, + ".flac": {}, + ".mp4": {}, + ".webm": {}, + ".mov": {}, + ".wmv": {}, + ".mkv": {}, + ".avi": {}, + ".flv": {}, +} + type FileInfo struct { Fs afero.Fs `json:"-"` Path string `json:"path"` @@ -418,6 +488,9 @@ func (f *FileInfo) getContent() error { if f.Size > 10*1024*1024 { return buserr.New("ErrFileToLarge") } + if IsBinaryPreviewFile(f.MimeType, f.Extension) { + return buserr.New("ErrFileCanNotRead") + } afs := &afero.Afero{Fs: f.Fs} cByte, err := afs.ReadFile(f.Path) if err != nil { @@ -430,8 +503,39 @@ func (f *FileInfo) getContent() error { return nil } +func IsBinaryPreviewFile(mimeType, extension string) bool { + mimeType = strings.ToLower(strings.TrimSpace(mimeType)) + extension = strings.ToLower(strings.TrimSpace(extension)) + + if mimeType == "" || mimeType == "application/octet-stream" { + _, ok := binaryPreviewExtensions[extension] + return ok + } + + if strings.HasPrefix(mimeType, "text/") { + return false + } + + for _, prefix := range binaryPreviewMimePrefixes { + if strings.HasPrefix(mimeType, prefix) { + return true + } + } + + _, ok := binaryPreviewMimeTypes[mimeType] + if ok { + return true + } + + _, ok = binaryPreviewExtensions[extension] + return ok +} + func DetectBinary(buf []byte) bool { mimeType := http.DetectContentType(buf) + if IsBinaryPreviewFile(mimeType, "") { + return true + } if !strings.HasPrefix(mimeType, "text/") { whiteByte := 0 n := min(1024, len(buf)) @@ -445,7 +549,6 @@ func DetectBinary(buf []byte) bool { return whiteByte < 1 } return false - } func min(x, y int) int { diff --git a/frontend/src/views/host/file-management/code-editor/index.vue b/frontend/src/views/host/file-management/code-editor/index.vue index 8ca62da52..832b9639c 100644 --- a/frontend/src/views/host/file-management/code-editor/index.vue +++ b/frontend/src/views/host/file-management/code-editor/index.vue @@ -105,7 +105,7 @@ class="monaco-editor sm:w-48 w-1/3 monaco-editor-background border-0 tree-container" v-if="isShow" > -