You can not select more than 25 topics Topics must start with a chinese character,a letter or number, can include dashes ('-') and can be up to 35 characters long.

dir_reader.go 2.6 kB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129
  1. package rclone
  2. import (
  3. "context"
  4. "io"
  5. "github.com/rclone/rclone/fs"
  6. stgtypes "gitlink.org.cn/cloudream/jcs-pub/common/pkgs/storage/types"
  7. jcstypes "gitlink.org.cn/cloudream/jcs-pub/common/types"
  8. )
  9. type DirReader struct {
  10. fs fs.Fs
  11. rootPath string
  12. // ReadDir函数传递进来的path参数
  13. rootJPath jcstypes.JPath
  14. init bool
  15. curEntries []DirEntry
  16. }
  17. func NewDirReader(fs fs.Fs, rootPath string, rootJPath jcstypes.JPath) *DirReader {
  18. return &DirReader{
  19. fs: fs,
  20. rootPath: rootPath,
  21. rootJPath: rootJPath,
  22. }
  23. }
  24. func (r *DirReader) Next() (stgtypes.DirEntry, error) {
  25. e, err := r.NextRaw()
  26. if err != nil {
  27. return stgtypes.DirEntry{}, err
  28. }
  29. eFullJPath := r.rootJPath.ConcatNew(e.Dir)
  30. // 如果根路径就是一个文件,那么Name就为空
  31. if e.Name != "" {
  32. eFullJPath.Push(e.Name)
  33. }
  34. switch e2 := e.Entry.(type) {
  35. case fs.Object:
  36. return stgtypes.DirEntry{
  37. Path: eFullJPath,
  38. Size: e2.Size(),
  39. ModTime: e2.ModTime(context.Background()),
  40. IsDir: false,
  41. }, nil
  42. default:
  43. return stgtypes.DirEntry{
  44. Path: eFullJPath,
  45. Size: 0,
  46. ModTime: e2.ModTime(context.Background()),
  47. IsDir: true,
  48. }, nil
  49. }
  50. }
  51. func (r *DirReader) NextRaw() (DirEntry, error) {
  52. if !r.init {
  53. info, err := r.fs.NewObject(context.Background(), r.rootPath)
  54. if err == nil {
  55. r.init = true
  56. return DirEntry{
  57. Dir: jcstypes.JPath{},
  58. Entry: info,
  59. Name: "",
  60. }, nil
  61. }
  62. if err != fs.ErrorIsDir {
  63. return DirEntry{}, err
  64. }
  65. es, err := r.fs.List(context.Background(), r.rootPath)
  66. if err != nil {
  67. return DirEntry{}, err
  68. }
  69. for _, e := range es {
  70. r.curEntries = append(r.curEntries, DirEntry{
  71. Dir: jcstypes.JPath{},
  72. Entry: e,
  73. Name: BaseName(e.Remote()),
  74. })
  75. }
  76. r.init = true
  77. }
  78. if len(r.curEntries) == 0 {
  79. return DirEntry{}, io.EOF
  80. }
  81. entry := r.curEntries[0]
  82. r.curEntries = r.curEntries[1:]
  83. _, isDir := entry.Entry.(fs.Directory)
  84. if isDir {
  85. dirPath := Join(r.rootPath, entry.Dir.String(), entry.Name)
  86. es, err := r.fs.List(context.Background(), dirPath)
  87. if err != nil {
  88. return DirEntry{}, err
  89. }
  90. // 多个entry对象共享同一个JPath对象,但因为不会修改JPath,所以没问题
  91. dir := entry.Dir.Clone()
  92. dir.Push(entry.Name)
  93. for _, e := range es {
  94. r.curEntries = append(r.curEntries, DirEntry{
  95. Dir: dir,
  96. Entry: e,
  97. Name: BaseName(e.Remote()),
  98. })
  99. }
  100. }
  101. return entry, nil
  102. }
  103. func (r *DirReader) Close() {
  104. }
  105. type DirEntry struct {
  106. Dir jcstypes.JPath
  107. Entry fs.DirEntry
  108. Name string
  109. }

本项目旨在将云际存储公共基础设施化,使个人及企业可低门槛使用高效的云际存储服务(安装开箱即用云际存储客户端即可,无需关注其他组件的部署),同时支持用户灵活便捷定制云际存储的功能细节。