[MM-55053] Use request-specific logger in channels/app/file.go (#25037)

Этот коммит содержится в:
Ben Schumacher
2023-11-07 10:04:16 +01:00
коммит произвёл GitHub
родитель 45d6fb122f
Коммит b0bf5d0765
20 изменённых файлов: 334 добавлений и 325 удалений

Просмотреть файл

@@ -326,7 +326,7 @@ func (a *App) RemoveDirectory(path string) *model.AppError {
return nil
}
func (a *App) getInfoForFilename(post *model.Post, teamID, channelID, userID, oldId, filename string) *model.FileInfo {
func (a *App) getInfoForFilename(rctx request.CTX, post *model.Post, teamID, channelID, userID, oldId, filename string) *model.FileInfo {
name, _ := url.QueryUnescape(filename)
pathPrefix := fmt.Sprintf("teams/%s/channels/%s/users/%s/%s/", teamID, channelID, userID, oldId)
path := pathPrefix + name
@@ -334,7 +334,7 @@ func (a *App) getInfoForFilename(post *model.Post, teamID, channelID, userID, ol
// Open the file and populate the fields of the FileInfo
data, err := a.ReadFile(path)
if err != nil {
mlog.Error(
rctx.Logger().Error(
"File not found when migrating post to use FileInfos",
mlog.String("post_id", post.Id),
mlog.String("filename", filename),
@@ -346,7 +346,7 @@ func (a *App) getInfoForFilename(post *model.Post, teamID, channelID, userID, ol
info, err := getInfoForBytes(name, bytes.NewReader(data), len(data))
if err != nil {
mlog.Warn(
rctx.Logger().Warn(
"Unable to fully decode file info when migrating post to use FileInfos",
mlog.String("post_id", post.Id),
mlog.String("filename", filename),
@@ -372,13 +372,13 @@ func (a *App) getInfoForFilename(post *model.Post, teamID, channelID, userID, ol
return info
}
func (a *App) findTeamIdForFilename(post *model.Post, id, filename string) string {
func (a *App) findTeamIdForFilename(rctx request.CTX, post *model.Post, id, filename string) string {
name, _ := url.QueryUnescape(filename)
// This post is in a direct channel so we need to figure out what team the files are stored under.
teams, err := a.Srv().Store().Team().GetTeamsByUserId(post.UserId)
if err != nil {
mlog.Error("Unable to get teams when migrating post to use FileInfo", mlog.Err(err), mlog.String("post_id", post.Id))
rctx.Logger().Error("Unable to get teams when migrating post to use FileInfo", mlog.Err(err), mlog.String("post_id", post.Id))
return ""
}
@@ -402,18 +402,18 @@ var fileMigrationLock sync.Mutex
var oldFilenameMatchExp = regexp.MustCompile(`^\/([a-z\d]{26})\/([a-z\d]{26})\/([a-z\d]{26})\/([^\/]+)$`)
// Parse the path from the Filename of the form /{channelID}/{userID}/{uid}/{nameWithExtension}
func parseOldFilenames(filenames []string, channelID, userID string) [][]string {
func parseOldFilenames(rctx request.CTX, filenames []string, channelID, userID string) [][]string {
parsed := [][]string{}
for _, filename := range filenames {
matches := oldFilenameMatchExp.FindStringSubmatch(filename)
if len(matches) != 5 {
mlog.Error("Failed to parse old Filename", mlog.String("filename", filename))
rctx.Logger().Error("Failed to parse old Filename", mlog.String("filename", filename))
continue
}
if matches[1] != channelID {
mlog.Error("ChannelId in Filename does not match", mlog.String("channel_id", channelID), mlog.String("matched", matches[1]))
rctx.Logger().Error("ChannelId in Filename does not match", mlog.String("channel_id", channelID), mlog.String("matched", matches[1]))
} else if matches[2] != userID {
mlog.Error("UserId in Filename does not match", mlog.String("user_id", userID), mlog.String("matched", matches[2]))
rctx.Logger().Error("UserId in Filename does not match", mlog.String("user_id", userID), mlog.String("matched", matches[2]))
} else {
parsed = append(parsed, matches[1:])
}
@@ -422,9 +422,9 @@ func parseOldFilenames(filenames []string, channelID, userID string) [][]string
}
// Creates and stores FileInfos for a post created before the FileInfos table existed.
func (a *App) MigrateFilenamesToFileInfos(post *model.Post) []*model.FileInfo {
func (a *App) MigrateFilenamesToFileInfos(rctx request.CTX, post *model.Post) []*model.FileInfo {
if len(post.Filenames) == 0 {
mlog.Warn("Unable to migrate post to use FileInfos with an empty Filenames field", mlog.String("post_id", post.Id))
rctx.Logger().Warn("Unable to migrate post to use FileInfos with an empty Filenames field", mlog.String("post_id", post.Id))
return []*model.FileInfo{}
}
@@ -432,7 +432,7 @@ func (a *App) MigrateFilenamesToFileInfos(post *model.Post) []*model.FileInfo {
// There's a weird bug that rarely happens where a post ends up with duplicate Filenames so remove those
filenames := utils.RemoveDuplicatesFromStringArray(post.Filenames)
if errCh != nil {
mlog.Error(
rctx.Logger().Error(
"Unable to get channel when migrating post to use FileInfos",
mlog.String("post_id", post.Id),
mlog.String("channel_id", post.ChannelId),
@@ -442,10 +442,10 @@ func (a *App) MigrateFilenamesToFileInfos(post *model.Post) []*model.FileInfo {
}
// Parse and validate filenames before further processing
parsedFilenames := parseOldFilenames(filenames, post.ChannelId, post.UserId)
parsedFilenames := parseOldFilenames(rctx, filenames, post.ChannelId, post.UserId)
if len(parsedFilenames) == 0 {
mlog.Error("Unable to parse filenames")
rctx.Logger().Error("Unable to parse filenames")
return []*model.FileInfo{}
}
@@ -453,7 +453,7 @@ func (a *App) MigrateFilenamesToFileInfos(post *model.Post) []*model.FileInfo {
var teamID string
if channel.TeamId == "" {
// This post was made in a cross-team DM channel, so we need to find where its files were saved
teamID = a.findTeamIdForFilename(post, parsedFilenames[0][2], parsedFilenames[0][3])
teamID = a.findTeamIdForFilename(rctx, post, parsedFilenames[0][2], parsedFilenames[0][3])
} else {
teamID = channel.TeamId
}
@@ -461,14 +461,14 @@ func (a *App) MigrateFilenamesToFileInfos(post *model.Post) []*model.FileInfo {
// Create FileInfo objects for this post
infos := make([]*model.FileInfo, 0, len(filenames))
if teamID == "" {
mlog.Error(
rctx.Logger().Error(
"Unable to find team id for files when migrating post to use FileInfos",
mlog.String("filenames", strings.Join(filenames, ",")),
mlog.String("post_id", post.Id),
)
} else {
for _, parsed := range parsedFilenames {
info := a.getInfoForFilename(post, teamID, parsed[0], parsed[1], parsed[2], parsed[3])
info := a.getInfoForFilename(rctx, post, teamID, parsed[0], parsed[1], parsed[2], parsed[3])
if info == nil {
continue
}
@@ -483,7 +483,7 @@ func (a *App) MigrateFilenamesToFileInfos(post *model.Post) []*model.FileInfo {
result, nErr := a.Srv().Store().Post().Get(context.Background(), post.Id, model.GetPostsOptions{}, "", a.Config().GetSanitizeOptions())
if nErr != nil {
mlog.Error("Unable to get post when migrating post to use FileInfos", mlog.Err(nErr), mlog.String("post_id", post.Id))
rctx.Logger().Error("Unable to get post when migrating post to use FileInfos", mlog.Err(nErr), mlog.String("post_id", post.Id))
return []*model.FileInfo{}
}
@@ -492,21 +492,21 @@ func (a *App) MigrateFilenamesToFileInfos(post *model.Post) []*model.FileInfo {
var fileInfos []*model.FileInfo
fileInfos, nErr = a.Srv().Store().FileInfo().GetForPost(post.Id, true, false, false)
if nErr != nil {
mlog.Error("Unable to get FileInfos for migrated post", mlog.Err(nErr), mlog.String("post_id", post.Id))
rctx.Logger().Error("Unable to get FileInfos for migrated post", mlog.Err(nErr), mlog.String("post_id", post.Id))
return []*model.FileInfo{}
}
mlog.Debug("Post already migrated to use FileInfos", mlog.String("post_id", post.Id))
rctx.Logger().Debug("Post already migrated to use FileInfos", mlog.String("post_id", post.Id))
return fileInfos
}
mlog.Debug("Migrating post to use FileInfos", mlog.String("post_id", post.Id))
rctx.Logger().Debug("Migrating post to use FileInfos", mlog.String("post_id", post.Id))
savedInfos := make([]*model.FileInfo, 0, len(infos))
fileIDs := make([]string, 0, len(filenames))
for _, info := range infos {
if _, nErr = a.Srv().Store().FileInfo().Save(info); nErr != nil {
mlog.Error(
rctx.Logger().Error(
"Unable to save file info when migrating post to use FileInfos",
mlog.String("post_id", post.Id),
mlog.String("file_info_id", info.Id),
@@ -528,7 +528,7 @@ func (a *App) MigrateFilenamesToFileInfos(post *model.Post) []*model.FileInfo {
// Update Posts to clear Filenames and set FileIds
if _, nErr = a.Srv().Store().Post().Update(newPost, post); nErr != nil {
mlog.Error(
rctx.Logger().Error(
"Unable to save migrated post when migrating to use FileInfos",
mlog.String("new_file_ids", strings.Join(newPost.FileIds, ",")),
mlog.String("old_filenames", strings.Join(post.Filenames, ",")),
@@ -585,7 +585,7 @@ func (a *App) UploadFileForUserAndTeam(c request.CTX, data []byte, channelID str
thumbnailPathList := []string{info.ThumbnailPath}
imageDataList := [][]byte{data}
a.HandleImages(previewPathList, thumbnailPathList, imageDataList)
a.HandleImages(c, previewPathList, thumbnailPathList, imageDataList)
}
return info, nil
@@ -633,6 +633,8 @@ func UploadFileSetRaw() func(t *UploadFileTask) {
}
type UploadFileTask struct {
Logger mlog.LoggerIFace
// File name.
Name string
@@ -720,7 +722,12 @@ func (t *UploadFileTask) init(a *App) {
// contained the last "good" FileInfo before the execution of that plugin.
func (a *App) UploadFileX(c request.CTX, channelID, name string, input io.Reader,
opts ...func(*UploadFileTask)) (*model.FileInfo, *model.AppError) {
c.WithLogger(c.Logger().With(
mlog.String("file_name", name),
))
t := &UploadFileTask{
Logger: c.Logger(),
ChannelId: filepath.Base(channelID),
Name: filepath.Base(name),
Input: input,
@@ -812,7 +819,7 @@ func (t *UploadFileTask) preprocessImage() *model.AppError {
if t.fileinfo.IsSvg() {
svgInfo, err := imaging.ParseSVG(t.teeInput)
if err != nil {
mlog.Warn("Failed to parse SVG", mlog.Err(err))
t.Logger.Warn("Failed to parse SVG", mlog.Err(err))
}
if svgInfo.Width > 0 && svgInfo.Height > 0 {
t.fileinfo.Width = svgInfo.Width
@@ -876,7 +883,7 @@ func (t *UploadFileTask) postprocessImage(file io.Reader) {
var release func()
decoded, imgType, release, err = t.imgDecoder.DecodeMemBounded(file)
if err != nil {
mlog.Error("Unable to decode image", mlog.Err(err))
t.Logger.Error("Unable to decode image", mlog.Err(err))
return
}
defer release()
@@ -899,7 +906,7 @@ func (t *UploadFileTask) postprocessImage(file io.Reader) {
err = t.imgEncoder.EncodeJPEG(w, img, jpegEncQuality)
}
if err != nil {
mlog.Error("Unable to encode image as jpeg", mlog.String("path", path), mlog.Err(err))
t.Logger.Error("Unable to encode image as jpeg", mlog.String("path", path), mlog.Err(err))
w.CloseWithError(err)
} else {
w.Close()
@@ -907,7 +914,7 @@ func (t *UploadFileTask) postprocessImage(file io.Reader) {
}()
_, aerr := t.writeFile(r, path)
if aerr != nil {
mlog.Error("Unable to upload", mlog.String("path", path), mlog.Err(aerr))
t.Logger.Error("Unable to upload", mlog.String("path", path), mlog.Err(aerr))
r.CloseWithError(aerr) // always returns nil
return
}
@@ -932,7 +939,7 @@ func (t *UploadFileTask) postprocessImage(file io.Reader) {
if t.fileinfo.MiniPreview == nil {
if miniPreview, err := imaging.GenerateMiniPreviewImage(decoded,
miniPreviewImageWidth, miniPreviewImageHeight, jpegEncQuality); err != nil {
mlog.Info("Unable to generate mini preview image", mlog.Err(err))
t.Logger.Info("Unable to generate mini preview image", mlog.Err(err))
} else {
t.fileinfo.MiniPreview = &miniPreview
}
@@ -1058,24 +1065,24 @@ func (a *App) DoUploadFileExpectModification(c request.CTX, now time.Time, rawTe
return info, data, nil
}
func (a *App) HandleImages(previewPathList []string, thumbnailPathList []string, fileData [][]byte) {
func (a *App) HandleImages(rctx request.CTX, previewPathList []string, thumbnailPathList []string, fileData [][]byte) {
wg := new(sync.WaitGroup)
for i := range fileData {
img, imgType, release, err := prepareImage(a.ch.imgDecoder, bytes.NewReader(fileData[i]))
img, imgType, release, err := prepareImage(rctx, a.ch.imgDecoder, bytes.NewReader(fileData[i]))
if err != nil {
mlog.Debug("Failed to prepare image", mlog.Err(err))
rctx.Logger().Debug("Failed to prepare image", mlog.Err(err))
continue
}
wg.Add(2)
go func(img image.Image, imgType, path string) {
defer wg.Done()
a.generateThumbnailImage(img, imgType, path)
a.generateThumbnailImage(rctx, img, imgType, path)
}(img, imgType, thumbnailPathList[i])
go func(img image.Image, imgType, path string) {
defer wg.Done()
a.generatePreviewImage(img, imgType, path)
a.generatePreviewImage(rctx, img, imgType, path)
}(img, imgType, previewPathList[i])
wg.Wait()
@@ -1083,7 +1090,7 @@ func (a *App) HandleImages(previewPathList []string, thumbnailPathList []string,
}
}
func prepareImage(imgDecoder *imaging.Decoder, imgData io.ReadSeeker) (img image.Image, imgType string, release func(), err error) {
func prepareImage(rctx request.CTX, imgDecoder *imaging.Decoder, imgData io.ReadSeeker) (img image.Image, imgType string, release func(), err error) {
// Decode image bytes into Image object
img, imgType, release, err = imgDecoder.DecodeMemBounded(imgData)
if err != nil {
@@ -1094,70 +1101,70 @@ func prepareImage(imgDecoder *imaging.Decoder, imgData io.ReadSeeker) (img image
// Flip the image to be upright
orientation, err := imaging.GetImageOrientation(imgData)
if err != nil {
mlog.Debug("GetImageOrientation failed", mlog.Err(err))
rctx.Logger().Debug("GetImageOrientation failed", mlog.Err(err))
}
img = imaging.MakeImageUpright(img, orientation)
return img, imgType, release, nil
}
func (a *App) generateThumbnailImage(img image.Image, imgType, thumbnailPath string) {
func (a *App) generateThumbnailImage(rctx request.CTX, img image.Image, imgType, thumbnailPath string) {
var buf bytes.Buffer
thumb := imaging.GenerateThumbnail(img, imageThumbnailWidth, imageThumbnailHeight)
if imgType == "png" {
if err := a.ch.imgEncoder.EncodePNG(&buf, thumb); err != nil {
mlog.Error("Unable to encode image as png", mlog.String("path", thumbnailPath), mlog.Err(err))
rctx.Logger().Error("Unable to encode image as png", mlog.String("path", thumbnailPath), mlog.Err(err))
return
}
} else {
if err := a.ch.imgEncoder.EncodeJPEG(&buf, thumb, jpegEncQuality); err != nil {
mlog.Error("Unable to encode image as jpeg", mlog.String("path", thumbnailPath), mlog.Err(err))
rctx.Logger().Error("Unable to encode image as jpeg", mlog.String("path", thumbnailPath), mlog.Err(err))
return
}
}
if _, err := a.WriteFile(&buf, thumbnailPath); err != nil {
mlog.Error("Unable to upload thumbnail", mlog.String("path", thumbnailPath), mlog.Err(err))
rctx.Logger().Error("Unable to upload thumbnail", mlog.String("path", thumbnailPath), mlog.Err(err))
return
}
}
func (a *App) generatePreviewImage(img image.Image, imgType, previewPath string) {
func (a *App) generatePreviewImage(rctx request.CTX, img image.Image, imgType, previewPath string) {
var buf bytes.Buffer
preview := imaging.GeneratePreview(img, imagePreviewWidth)
if imgType == "png" {
if err := a.ch.imgEncoder.EncodePNG(&buf, preview); err != nil {
mlog.Error("Unable to encode image as preview png", mlog.Err(err), mlog.String("path", previewPath))
rctx.Logger().Error("Unable to encode image as preview png", mlog.Err(err), mlog.String("path", previewPath))
return
}
} else {
if err := a.ch.imgEncoder.EncodeJPEG(&buf, preview, jpegEncQuality); err != nil {
mlog.Error("Unable to encode image as preview jpg", mlog.Err(err), mlog.String("path", previewPath))
rctx.Logger().Error("Unable to encode image as preview jpg", mlog.Err(err), mlog.String("path", previewPath))
return
}
}
if _, err := a.WriteFile(&buf, previewPath); err != nil {
mlog.Error("Unable to upload preview", mlog.Err(err), mlog.String("path", previewPath))
rctx.Logger().Error("Unable to upload preview", mlog.Err(err), mlog.String("path", previewPath))
return
}
}
// generateMiniPreview updates mini preview if needed
// will save fileinfo with the preview added
func (a *App) generateMiniPreview(fi *model.FileInfo) {
func (a *App) generateMiniPreview(rctx request.CTX, fi *model.FileInfo) {
if fi.IsImage() && !fi.IsSvg() && fi.MiniPreview == nil {
file, appErr := a.FileReader(fi.Path)
if appErr != nil {
mlog.Debug("error reading image file", mlog.Err(appErr))
rctx.Logger().Debug("Error reading image file", mlog.Err(appErr))
return
}
defer file.Close()
img, _, release, err := prepareImage(a.ch.imgDecoder, file)
img, _, release, err := prepareImage(rctx, a.ch.imgDecoder, file)
if err != nil {
mlog.Debug("generateMiniPreview: prepareImage failed", mlog.Err(err),
rctx.Logger().Debug("generateMiniPreview: prepareImage failed", mlog.Err(err),
mlog.String("fileinfo_id", fi.Id), mlog.String("channel_id", fi.ChannelId),
mlog.String("creator_id", fi.CreatorId))
return
@@ -1166,26 +1173,26 @@ func (a *App) generateMiniPreview(fi *model.FileInfo) {
var miniPreview []byte
if miniPreview, err = imaging.GenerateMiniPreviewImage(img,
miniPreviewImageWidth, miniPreviewImageHeight, jpegEncQuality); err != nil {
mlog.Info("Unable to generate mini preview image", mlog.Err(err))
rctx.Logger().Info("Unable to generate mini preview image", mlog.Err(err))
} else {
fi.MiniPreview = &miniPreview
}
if _, err = a.Srv().Store().FileInfo().Upsert(fi); err != nil {
mlog.Debug("creating mini preview failed", mlog.Err(err))
rctx.Logger().Debug("Creating mini preview failed", mlog.Err(err))
} else {
a.Srv().Store().FileInfo().InvalidateFileInfosForPostCache(fi.PostId, false)
}
}
}
func (a *App) generateMiniPreviewForInfos(fileInfos []*model.FileInfo) {
func (a *App) generateMiniPreviewForInfos(rctx request.CTX, fileInfos []*model.FileInfo) {
wg := new(sync.WaitGroup)
wg.Add(len(fileInfos))
for _, fileInfo := range fileInfos {
go func(fi *model.FileInfo) {
defer wg.Done()
a.generateMiniPreview(fi)
a.generateMiniPreview(rctx, fi)
}(fileInfo)
}
wg.Wait()
@@ -1205,7 +1212,7 @@ func (s *Server) getFileInfo(fileID string) (*model.FileInfo, *model.AppError) {
return fileInfo, nil
}
func (a *App) GetFileInfo(fileID string) (*model.FileInfo, *model.AppError) {
func (a *App) GetFileInfo(rctx request.CTX, fileID string) (*model.FileInfo, *model.AppError) {
fileInfo, appErr := a.Srv().getFileInfo(fileID)
if appErr != nil {
return nil, appErr
@@ -1219,7 +1226,7 @@ func (a *App) GetFileInfo(fileID string) (*model.FileInfo, *model.AppError) {
return nil, model.NewAppError("GetFileInfo", "app.file.cloud.get.app_error", nil, "", http.StatusForbidden)
}
a.generateMiniPreview(fileInfo)
a.generateMiniPreview(rctx, fileInfo)
return fileInfo, appErr
}
@@ -1243,16 +1250,16 @@ func (a *App) SetFileSearchableContent(fileID string, data string) *model.AppErr
return nil
}
func (a *App) getFileInfoIgnoreCloudLimit(fileID string) (*model.FileInfo, *model.AppError) {
func (a *App) getFileInfoIgnoreCloudLimit(rctx request.CTX, fileID string) (*model.FileInfo, *model.AppError) {
fileInfo, appErr := a.Srv().getFileInfo(fileID)
if appErr == nil {
a.generateMiniPreview(fileInfo)
a.generateMiniPreview(rctx, fileInfo)
}
return fileInfo, appErr
}
func (a *App) GetFileInfos(page, perPage int, opt *model.GetFileInfosOptions) ([]*model.FileInfo, *model.AppError) {
func (a *App) GetFileInfos(rctx request.CTX, page, perPage int, opt *model.GetFileInfosOptions) ([]*model.FileInfo, *model.AppError) {
fileInfos, err := a.Srv().Store().FileInfo().GetWithOptions(page, perPage, opt)
if err != nil {
var invErr *store.ErrInvalidInput
@@ -1277,13 +1284,13 @@ func (a *App) GetFileInfos(page, perPage int, opt *model.GetFileInfosOptions) ([
return nil, appErr
}
a.generateMiniPreviewForInfos(fileInfos)
a.generateMiniPreviewForInfos(rctx, fileInfos)
return fileInfos, nil
}
func (a *App) GetFile(fileID string) ([]byte, *model.AppError) {
info, err := a.GetFileInfo(fileID)
func (a *App) GetFile(rctx request.CTX, fileID string) ([]byte, *model.AppError) {
info, err := a.GetFileInfo(rctx, fileID)
if err != nil {
return nil, err
}
@@ -1296,8 +1303,8 @@ func (a *App) GetFile(fileID string) ([]byte, *model.AppError) {
return data, nil
}
func (a *App) getFileIgnoreCloudLimit(fileID string) ([]byte, *model.AppError) {
info, err := a.getFileInfoIgnoreCloudLimit(fileID)
func (a *App) getFileIgnoreCloudLimit(rctx request.CTX, fileID string) ([]byte, *model.AppError) {
info, err := a.getFileInfoIgnoreCloudLimit(rctx, fileID)
if err != nil {
return nil, err
}
@@ -1473,7 +1480,7 @@ func (a *App) ExtractContentFromFileInfo(rctx request.CTX, fileInfo *model.FileI
}
reloadFileInfo, storeErr := a.Srv().Store().FileInfo().Get(fileInfo.Id)
if storeErr != nil {
mlog.Warn("Failed to invalidate the fileInfo cache.", mlog.Err(storeErr), mlog.String("file_info_id", fileInfo.Id))
rctx.Logger().Warn("Failed to invalidate the fileInfo cache.", mlog.Err(storeErr), mlog.String("file_info_id", fileInfo.Id))
} else {
a.Srv().Store().FileInfo().InvalidateFileInfosForPostCache(reloadFileInfo.PostId, false)
}