sortfile.go 2.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116
  1. package sortfile
  2. import (
  3. "encoding/json"
  4. "errors"
  5. "net/http"
  6. "os"
  7. "path/filepath"
  8. "sort"
  9. "strconv"
  10. "imuslab.com/arozos/mod/filesystem"
  11. user "imuslab.com/arozos/mod/user"
  12. )
  13. type LargeFileScanner struct {
  14. userHandler *user.UserHandler
  15. }
  16. func NewLargeFileScanner(u *user.UserHandler) *LargeFileScanner {
  17. return &LargeFileScanner{
  18. userHandler: u,
  19. }
  20. }
  21. func (s *LargeFileScanner) HandleLargeFileList(w http.ResponseWriter, r *http.Request) {
  22. userinfo, err := s.userHandler.GetUserInfoFromRequest(w, r)
  23. if err != nil {
  24. sendErrorResponse(w, err.Error())
  25. return
  26. }
  27. //Check if limit is set. If yes, use the limit in return
  28. limit, err := mv(r, "number", false)
  29. if err != nil {
  30. limit = "20"
  31. }
  32. //Try convert the limit to integer
  33. limitInt, err := strconv.Atoi(limit)
  34. if err != nil {
  35. limitInt = 20
  36. }
  37. //Get all the fshandler for this user
  38. fsHandlers := userinfo.GetAllFileSystemHandler()
  39. type FileObject struct {
  40. Filename string
  41. Filepath string
  42. Size int64
  43. IsOwner bool
  44. realpath string
  45. thisfsh *filesystem.FileSystemHandler
  46. }
  47. //Walk all filesystem handlers and buffer all files and their sizes
  48. fileList := []*FileObject{}
  49. for _, fsh := range fsHandlers {
  50. fsh.FileSystemAbstraction.Walk(fsh.Path, func(path string, info os.FileInfo, err error) error {
  51. if info == nil || err != nil {
  52. //Disk IO Error
  53. return errors.New("Disk IO Error: " + err.Error())
  54. }
  55. if info.IsDir() {
  56. return nil
  57. }
  58. //Push the current file into the filelist
  59. if info.Size() > 0 {
  60. vpath, _ := fsh.FileSystemAbstraction.RealPathToVirtualPath(path, userinfo.Username)
  61. fileList = append(fileList, &FileObject{
  62. Filename: filepath.Base(path),
  63. Filepath: vpath,
  64. realpath: path,
  65. thisfsh: fsh,
  66. Size: info.Size(),
  67. IsOwner: false,
  68. })
  69. }
  70. return nil
  71. })
  72. /*
  73. if err != nil {
  74. sendErrorResponse(w, "Failed to scan emulated storage device: "+fsh.Name)
  75. return
  76. }
  77. */
  78. }
  79. //Sort the fileList
  80. sort.Slice(fileList, func(i, j int) bool {
  81. return fileList[i].Size > fileList[j].Size
  82. })
  83. //Set the max filecount to prevent slice bounds out of range
  84. if len(fileList) < limitInt {
  85. limitInt = len(fileList)
  86. }
  87. //Only check ownership of those requested
  88. for _, file := range fileList[:limitInt] {
  89. if userinfo.IsOwnerOfFile(file.thisfsh, file.Filepath) {
  90. file.IsOwner = true
  91. } else {
  92. file.IsOwner = false
  93. }
  94. }
  95. //Format the results and return
  96. jsonString, _ := json.Marshal(fileList[:limitInt])
  97. sendJSONResponse(w, string(jsonString))
  98. }