refactor: add endpoint to delete file parts

This commit is contained in:
divyam234 2024-05-26 01:56:05 +05:30
parent 44a91ee180
commit 5fa2a064fb
7 changed files with 97 additions and 32 deletions

View file

@ -28,6 +28,7 @@ func InitRouter(r *gin.Engine, c *controller.Controller, cnf *config.Config) *gi
files.PATCH(":fileID", authmiddleware, c.UpdateFile)
files.HEAD(":fileID/stream/:fileName", c.GetFileStream)
files.GET(":fileID/stream/:fileName", c.GetFileStream)
files.DELETE(":fileID/parts", authmiddleware, c.DeleteFileParts)
files.GET("/category/stats", authmiddleware, c.GetCategoryStats)
files.POST("/move", authmiddleware, c.MoveFiles)
files.POST("/directories", authmiddleware, c.MakeDirectory)

View file

@ -3,6 +3,7 @@ package controller
import (
"net/http"
"github.com/divyam234/teldrive/internal/cache"
"github.com/divyam234/teldrive/pkg/httputil"
"github.com/divyam234/teldrive/pkg/logging"
"github.com/divyam234/teldrive/pkg/schemas"
@ -43,7 +44,7 @@ func (fc *Controller) UpdateFile(c *gin.Context) {
httputil.NewError(c, http.StatusBadRequest, err)
return
}
res, err := fc.FileService.UpdateFile(c.Param("fileID"), userId, &fileUpdate)
res, err := fc.FileService.UpdateFile(c.Param("fileID"), userId, &fileUpdate, cache.FromContext(c))
if err != nil {
httputil.NewError(c, err.Code, err.Error)
return
@ -151,6 +152,17 @@ func (fc *Controller) DeleteFiles(c *gin.Context) {
c.JSON(http.StatusOK, res)
}
func (fc *Controller) DeleteFileParts(c *gin.Context) {
res, err := fc.FileService.DeleteFileParts(c, c.Param("fileID"))
if err != nil {
httputil.NewError(c, err.Code, err.Error)
return
}
c.JSON(http.StatusOK, res)
}
func (fc *Controller) MoveDirectory(c *gin.Context) {
userId, _ := services.GetUserAuth(c)

View file

@ -4,16 +4,13 @@ import (
"context"
"database/sql/driver"
"encoding/json"
"strconv"
"time"
"github.com/divyam234/teldrive/internal/config"
"github.com/divyam234/teldrive/internal/tgc"
"github.com/divyam234/teldrive/pkg/logging"
"github.com/divyam234/teldrive/pkg/models"
"github.com/divyam234/teldrive/pkg/services"
"github.com/go-co-op/gocron"
"github.com/gotd/td/tg"
"go.uber.org/zap"
"gorm.io/gorm"
)
@ -114,7 +111,7 @@ func (c *CronService) CleanFiles(ctx context.Context) {
}
}
err := deleteTGMessages(ctx, c.cnf, row.Session, row.ChannelId, row.UserId, ids)
err := services.DeleteTGMessages(ctx, &c.cnf.TG, row.Session, row.ChannelId, row.UserId, ids)
if err != nil {
c.logger.Errorw("failed to clean files", err)
}
@ -142,7 +139,7 @@ func (c *CronService) CleanUploads(ctx context.Context) {
if result.Session == "" {
break
}
err := deleteTGMessages(ctx, c.cnf, result.Session, result.ChannelId, result.UserId, result.Parts)
err := services.DeleteTGMessages(ctx, &c.cnf.TG, result.Session, result.ChannelId, result.UserId, result.Parts)
c.logger.Errorw("failed to delete messages", err)
parts := []int{}
for _, id := range result.Parts {
@ -158,26 +155,3 @@ func (c *CronService) CleanUploads(ctx context.Context) {
func (c *CronService) UpdateFolderSize() {
c.db.Exec("call teldrive.update_size();")
}
func deleteTGMessages(ctx context.Context, cnf *config.Config, session string, channelId, userId int64, ids []int) error {
client, _ := tgc.AuthClient(ctx, &cnf.TG, session)
err := tgc.RunWithAuth(ctx, client, "", func(ctx context.Context) error {
channel, err := services.GetChannelById(ctx, client, channelId, strconv.FormatInt(userId, 10))
if err != nil {
return err
}
messageDeleteRequest := tg.ChannelsDeleteMessagesRequest{Channel: channel, ID: ids}
_, err = client.API().ChannelsDeleteMessages(ctx, &messageDeleteRequest)
if err != nil {
return err
}
return nil
})
return err
}

View file

@ -67,6 +67,7 @@ type FileUpdate struct {
ParentID string `json:"parentId,omitempty"`
UpdatedAt time.Time `json:"updatedAt,omitempty"`
Parts []Part `json:"parts,omitempty"`
Size *int64 `json:"size,omitempty"`
}
type FileResponse struct {

View file

@ -334,3 +334,26 @@ func getSessionByHash(db *gorm.DB, cache *cache.Cache, hash string) (*models.Ses
return &session, nil
}
func DeleteTGMessages(ctx context.Context, cnf *config.TGConfig, session string, channelId, userId int64, ids []int) error {
client, _ := tgc.AuthClient(ctx, cnf, session)
err := tgc.RunWithAuth(ctx, client, "", func(ctx context.Context) error {
channel, err := GetChannelById(ctx, client, channelId, strconv.FormatInt(userId, 10))
if err != nil {
return err
}
messageDeleteRequest := tg.ChannelsDeleteMessagesRequest{Channel: channel, ID: ids}
_, err = client.API().ChannelsDeleteMessages(ctx, &messageDeleteRequest)
if err != nil {
return err
}
return nil
})
return err
}

View file

@ -110,7 +110,7 @@ func (fs *FileService) CreateFile(c *gin.Context, userId int64, fileIn *schemas.
return res, nil
}
func (fs *FileService) UpdateFile(id string, userId int64, update *schemas.FileUpdate) (*schemas.FileOut, *types.AppError) {
func (fs *FileService) UpdateFile(id string, userId int64, update *schemas.FileUpdate, cache *cache.Cache) (*schemas.FileOut, *types.AppError) {
var (
files []models.File
chain *gorm.DB
@ -118,7 +118,35 @@ func (fs *FileService) UpdateFile(id string, userId int64, update *schemas.FileU
if update.Type == "folder" && update.Name != "" {
chain = fs.db.Raw("select * from teldrive.update_folder(?, ?, ?)", id, update.Name, userId).Scan(&files)
} else {
chain = fs.db.Model(&files).Clauses(clause.Returning{}).Where("id = ?", id).Updates(update)
updateDb := models.File{
Name: update.Name,
ParentID: update.ParentID,
UpdatedAt: update.UpdatedAt,
Path: update.Path,
Size: update.Size,
}
if update.Starred != nil {
updateDb.Starred = *update.Starred
}
if len(update.Parts) > 0 {
parts := models.Parts{}
for _, part := range update.Parts {
parts = append(parts, models.Part{
ID: part.ID,
Salt: part.Salt,
})
}
updateDb.Parts = &parts
}
chain = fs.db.Model(&files).Clauses(clause.Returning{}).Where("id = ?", id).Updates(updateDb)
cache.Delete(fmt.Sprintf("files:%s", id))
}
if chain.Error != nil {
@ -267,6 +295,32 @@ func (fs *FileService) DeleteFiles(userId int64, payload *schemas.FileOperation)
return &schemas.Message{Message: "files deleted"}, nil
}
func (fs *FileService) DeleteFileParts(c *gin.Context, id string) (*schemas.Message, *types.AppError) {
var file models.File
if err := fs.db.Where("id = ?", id).First(&file).Error; err != nil {
if database.IsRecordNotFoundErr(err) {
return nil, &types.AppError{Error: database.ErrNotFound, Code: http.StatusNotFound}
}
return nil, &types.AppError{Error: err}
}
userId, session := GetUserAuth(c)
ids := []int{}
for _, part := range *file.Parts {
ids = append(ids, int(part.ID))
}
err := DeleteTGMessages(c, fs.cnf, session, *file.ChannelID, userId, ids)
if err != nil {
return nil, &types.AppError{Error: err}
}
return &schemas.Message{Message: "file parts deleted"}, nil
}
func (fs *FileService) MoveDirectory(userId int64, payload *schemas.DirMove) (*schemas.Message, *types.AppError) {
if err := fs.db.Exec("select * from teldrive.move_directory(? , ? , ?)", payload.Source,

View file

@ -83,7 +83,7 @@ func (s *FileServiceSuite) Test_Update() {
Path: "/dwkd",
Type: "file",
}
r, err := s.srv.UpdateFile(res.ID, 123456, data)
r, err := s.srv.UpdateFile(res.ID, 123456, data, nil)
s.NoError(err.Error)
s.Equal(r.Name, data.Name)
s.Equal(r.Path, data.Path)