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

120 lines
2.9 KiB

  1. package memdb
  2. import (
  3. "github.com/chrislusf/seaweedfs/weed/filer2"
  4. "github.com/google/btree"
  5. "strings"
  6. "fmt"
  7. "time"
  8. "github.com/spf13/viper"
  9. )
  10. func init() {
  11. filer2.Stores = append(filer2.Stores, &MemDbStore{})
  12. }
  13. type MemDbStore struct {
  14. tree *btree.BTree
  15. }
  16. type entryItem struct {
  17. *filer2.Entry
  18. }
  19. func (a entryItem) Less(b btree.Item) bool {
  20. return strings.Compare(string(a.FullPath), string(b.(entryItem).FullPath)) < 0
  21. }
  22. func (store *MemDbStore) GetName() string {
  23. return "memory"
  24. }
  25. func (store *MemDbStore) Initialize(viper *viper.Viper) (err error) {
  26. store.tree = btree.New(8)
  27. return nil
  28. }
  29. func (store *MemDbStore) InsertEntry(entry *filer2.Entry) (err error) {
  30. // println("inserting", entry.FullPath)
  31. entry.Crtime = time.Now()
  32. store.tree.ReplaceOrInsert(entryItem{entry})
  33. return nil
  34. }
  35. func (store *MemDbStore) UpdateEntry(entry *filer2.Entry) (err error) {
  36. if _, err = store.FindEntry(entry.FullPath); err != nil {
  37. return fmt.Errorf("no such file %s : %v", entry.FullPath, err)
  38. }
  39. entry.Mtime = time.Now()
  40. store.tree.ReplaceOrInsert(entryItem{entry})
  41. return nil
  42. }
  43. func (store *MemDbStore) FindEntry(fullpath filer2.FullPath) (entry *filer2.Entry, err error) {
  44. item := store.tree.Get(entryItem{&filer2.Entry{FullPath: fullpath}})
  45. if item == nil {
  46. return nil, nil
  47. }
  48. entry = item.(entryItem).Entry
  49. return entry, nil
  50. }
  51. func (store *MemDbStore) DeleteEntry(fullpath filer2.FullPath) (entry *filer2.Entry, err error) {
  52. item := store.tree.Delete(entryItem{&filer2.Entry{FullPath: fullpath}})
  53. if item == nil {
  54. return nil, nil
  55. }
  56. entry = item.(entryItem).Entry
  57. return entry, nil
  58. }
  59. func (store *MemDbStore) ListDirectoryEntries(fullpath filer2.FullPath, startFileName string, inclusive bool, limit int) (entries []*filer2.Entry, err error) {
  60. startFrom := string(fullpath)
  61. if startFileName != "" {
  62. startFrom = startFrom + "/" + startFileName
  63. }
  64. store.tree.AscendGreaterOrEqual(entryItem{&filer2.Entry{FullPath: filer2.FullPath(startFrom)}},
  65. func(item btree.Item) bool {
  66. if limit <= 0 {
  67. return false
  68. }
  69. entry := item.(entryItem).Entry
  70. // println("checking", entry.FullPath)
  71. if entry.FullPath == fullpath {
  72. // skipping the current directory
  73. // println("skipping the folder", entry.FullPath)
  74. return true
  75. }
  76. dir, name := entry.FullPath.DirAndName()
  77. if name == startFileName {
  78. if inclusive {
  79. limit--
  80. entries = append(entries, entry)
  81. }
  82. return true
  83. }
  84. // only iterate the same prefix
  85. if !strings.HasPrefix(string(entry.FullPath), string(fullpath)) {
  86. // println("breaking from", entry.FullPath)
  87. return false
  88. }
  89. if dir != string(fullpath) {
  90. // this could be items in deeper directories
  91. // println("skipping deeper folder", entry.FullPath)
  92. return true
  93. }
  94. // now process the directory items
  95. // println("adding entry", entry.FullPath)
  96. limit--
  97. entries = append(entries, entry)
  98. return true
  99. },
  100. )
  101. return entries, nil
  102. }