164 lines
4.2 KiB
Go
164 lines
4.2 KiB
Go
package storageService
|
|
|
|
import (
|
|
"mime/multipart"
|
|
"os"
|
|
"path/filepath"
|
|
"strings"
|
|
|
|
"git.ma-al.com/goc_daniel/b2b/app/model"
|
|
"git.ma-al.com/goc_daniel/b2b/app/repos/storageRepo"
|
|
"git.ma-al.com/goc_daniel/b2b/app/utils/responseErrors"
|
|
"github.com/gofiber/fiber/v3"
|
|
)
|
|
|
|
type StorageService struct {
|
|
storageRepo storageRepo.UIStorageRepo
|
|
}
|
|
|
|
func New() *StorageService {
|
|
return &StorageService{
|
|
storageRepo: storageRepo.New(),
|
|
}
|
|
}
|
|
|
|
func (s *StorageService) ListContent(abs_path string) (*[]model.EntryInList, error) {
|
|
info, err := s.storageRepo.EntryInfo(abs_path)
|
|
if err != nil || !info.IsDir() {
|
|
return nil, responseErrors.ErrFolderDoesNotExist
|
|
}
|
|
|
|
entries_in_list, err := s.storageRepo.ListContent(abs_path)
|
|
return entries_in_list, err
|
|
}
|
|
|
|
func (s *StorageService) DownloadFilePrep(abs_path string) (*os.File, string, int64, error) {
|
|
info, err := s.storageRepo.EntryInfo(abs_path)
|
|
if err != nil || info.IsDir() {
|
|
return nil, "", 0, responseErrors.ErrFileDoesNotExist
|
|
}
|
|
|
|
f, err := s.storageRepo.OpenFile(abs_path)
|
|
if err != nil {
|
|
return nil, "", 0, err
|
|
}
|
|
|
|
return f, filepath.Base(abs_path), info.Size(), nil
|
|
}
|
|
|
|
func (s *StorageService) Move(src_abs_path string, dest_abs_path string) error {
|
|
_, err := s.storageRepo.EntryInfo(src_abs_path)
|
|
if err != nil {
|
|
return responseErrors.ErrFileDoesNotExist
|
|
}
|
|
|
|
_, err = s.storageRepo.EntryInfo(dest_abs_path)
|
|
if err == nil {
|
|
return responseErrors.ErrNameTaken
|
|
} else if os.IsNotExist(err) {
|
|
return s.storageRepo.Move(src_abs_path, dest_abs_path)
|
|
} else {
|
|
return err
|
|
}
|
|
}
|
|
func (s *StorageService) Copy(src_abs_path string, dest_abs_path string) error {
|
|
_, err := s.storageRepo.EntryInfo(src_abs_path)
|
|
if err != nil {
|
|
return responseErrors.ErrFileDoesNotExist
|
|
}
|
|
|
|
_, err = s.storageRepo.EntryInfo(dest_abs_path)
|
|
if err == nil {
|
|
return responseErrors.ErrNameTaken
|
|
} else if os.IsNotExist(err) {
|
|
return s.storageRepo.Copy(src_abs_path, dest_abs_path)
|
|
} else {
|
|
return err
|
|
}
|
|
}
|
|
|
|
func (s *StorageService) UploadFile(c fiber.Ctx, abs_path string, f *multipart.FileHeader) error {
|
|
info, err := s.storageRepo.EntryInfo(abs_path)
|
|
if err != nil || !info.IsDir() {
|
|
return responseErrors.ErrFolderDoesNotExist
|
|
}
|
|
|
|
name := f.Filename
|
|
if name == "" || name == "." || name == ".." || filepath.Base(name) != name {
|
|
return responseErrors.ErrBadAttribute
|
|
}
|
|
abs_file_path, err := s.AbsPath(abs_path, name)
|
|
if err != nil {
|
|
return err
|
|
}
|
|
if abs_file_path == abs_path {
|
|
return responseErrors.ErrBadAttribute
|
|
}
|
|
|
|
info, err = s.storageRepo.EntryInfo(abs_file_path)
|
|
if err == nil {
|
|
return responseErrors.ErrNameTaken
|
|
} else if os.IsNotExist(err) {
|
|
return s.storageRepo.UploadFile(c, abs_file_path, f)
|
|
} else {
|
|
return err
|
|
}
|
|
}
|
|
|
|
func (s *StorageService) CreateFolder(abs_path string, name string) error {
|
|
info, err := s.storageRepo.EntryInfo(abs_path)
|
|
if err != nil || !info.IsDir() {
|
|
return responseErrors.ErrFolderDoesNotExist
|
|
}
|
|
|
|
if name == "" || name == "." || name == ".." || filepath.Base(name) != name {
|
|
return responseErrors.ErrBadAttribute
|
|
}
|
|
abs_folder_path, err := s.AbsPath(abs_path, name)
|
|
if err != nil {
|
|
return err
|
|
}
|
|
if abs_folder_path == abs_path {
|
|
return responseErrors.ErrBadAttribute
|
|
}
|
|
|
|
info, err = s.storageRepo.EntryInfo(abs_folder_path)
|
|
if err == nil {
|
|
return responseErrors.ErrNameTaken
|
|
} else if os.IsNotExist(err) {
|
|
return s.storageRepo.CreateFolder(abs_folder_path)
|
|
} else {
|
|
return err
|
|
}
|
|
}
|
|
|
|
func (s *StorageService) DeleteFile(abs_path string) error {
|
|
info, err := s.storageRepo.EntryInfo(abs_path)
|
|
if err != nil || info.IsDir() {
|
|
return responseErrors.ErrFileDoesNotExist
|
|
}
|
|
|
|
return s.storageRepo.DeleteFile(abs_path)
|
|
}
|
|
|
|
func (s *StorageService) DeleteFolder(abs_path string) error {
|
|
info, err := s.storageRepo.EntryInfo(abs_path)
|
|
if err != nil || !info.IsDir() {
|
|
return responseErrors.ErrFolderDoesNotExist
|
|
}
|
|
|
|
return s.storageRepo.DeleteFolder(abs_path)
|
|
}
|
|
|
|
// AbsPath extracts an absolute path and validates it
|
|
func (s *StorageService) AbsPath(root string, relativePath string) (string, error) {
|
|
clean_name := filepath.Clean(relativePath)
|
|
full_path := filepath.Join(root, clean_name)
|
|
|
|
if full_path != root && !strings.HasPrefix(full_path, root+string(os.PathSeparator)) {
|
|
return "", responseErrors.ErrAccessDenied
|
|
}
|
|
|
|
return full_path, nil
|
|
}
|