Browse Source

增加LockRequestBuilder

pull/1/head
Sydonian 2 years ago
parent
commit
13c85ff6b6
8 changed files with 291 additions and 16 deletions
  1. +7
    -0
      pkg/distlock/const.go
  2. +18
    -1
      pkg/distlock/lockprovider/string_lock_target.go
  3. +73
    -0
      pkg/distlock/reqbuilder/ipfs.go
  4. +16
    -0
      pkg/distlock/reqbuilder/lock_request_builder.go
  5. +75
    -0
      pkg/distlock/reqbuilder/metadata.go
  6. +82
    -0
      pkg/distlock/reqbuilder/storage.go
  7. +16
    -15
      pkg/distlock/service/init_providers.go
  8. +4
    -0
      utils/lo/lo.go

+ 7
- 0
pkg/distlock/const.go View File

@@ -0,0 +1,7 @@
package distlock

const (
METADATA_LOCK_PATH_PREFIX = "Metadata"
IPFS_LOCK_PATH_PREFIX = "IPFS"
STORAGE_LOCK_PATH_PREFIX = "Storage"
)

+ 18
- 1
pkg/distlock/lockprovider/string_lock_target.go View File

@@ -1,11 +1,28 @@
package lockprovider

import "gitlink.org.cn/cloudream/common/utils/serder"
import (
"fmt"

"github.com/samber/lo"
"gitlink.org.cn/cloudream/common/utils/serder"
)

type StringLockTarget struct {
Components []StringLockTargetComponet `json:"components"`
}

func NewStringLockTarget() *StringLockTarget {
return &StringLockTarget{}
}

func (t *StringLockTarget) AddComponent(values ...any) *StringLockTarget {
t.Components = append(t.Components, StringLockTargetComponet{
Values: lo.Map(values, func(val any, index int) string { return fmt.Sprintf("%v", val) }),
})

return t
}

// IsConflict 判断两个锁对象是否冲突。注:只有相同的结构的Target才有意义
func (t *StringLockTarget) IsConflict(other *StringLockTarget) bool {
if len(t.Components) != len(other.Components) {


+ 73
- 0
pkg/distlock/reqbuilder/ipfs.go View File

@@ -0,0 +1,73 @@
package reqbuilder

import (
"strconv"

"gitlink.org.cn/cloudream/common/pkg/distlock"
"gitlink.org.cn/cloudream/common/pkg/distlock/lockprovider"
)

type IPFSLockReqBuilder struct {
*LockRequestBuilder
}

func (b *LockRequestBuilder) IPFS() *IPFSLockReqBuilder {
return &IPFSLockReqBuilder{LockRequestBuilder: b}
}

func (b *MetadataLockReqBuilder) IPFS() *IPFSLockReqBuilder {
return &IPFSLockReqBuilder{LockRequestBuilder: b.LockRequestBuilder}
}

func (b *StorageLockReqBuilder) IPFS() *IPFSLockReqBuilder {
return &IPFSLockReqBuilder{LockRequestBuilder: b.LockRequestBuilder}
}

func (b *IPFSLockReqBuilder) ReadOneRep(nodeID int, fileHash string) *IPFSLockReqBuilder {
b.locks = append(b.locks, distlock.Lock{
Path: b.makePath(nodeID),
Name: lockprovider.IPFS_ELEMENT_READ_LOCK,
Target: *lockprovider.NewStringLockTarget().AddComponent(fileHash),
})
return b
}

func (b *IPFSLockReqBuilder) WriteOneRep(nodeID int, fileHash string) *IPFSLockReqBuilder {
b.locks = append(b.locks, distlock.Lock{
Path: b.makePath(nodeID),
Name: lockprovider.IPFS_ELEMENT_WRITE_LOCK,
Target: *lockprovider.NewStringLockTarget().AddComponent(fileHash),
})
return b
}

func (b *IPFSLockReqBuilder) ReadAnyRep(nodeID int) *IPFSLockReqBuilder {
b.locks = append(b.locks, distlock.Lock{
Path: b.makePath(nodeID),
Name: lockprovider.IPFS_SET_READ_LOCK,
Target: *lockprovider.NewStringLockTarget(),
})
return b
}

func (b *IPFSLockReqBuilder) WriteAnyRep(nodeID int) *IPFSLockReqBuilder {
b.locks = append(b.locks, distlock.Lock{
Path: b.makePath(nodeID),
Name: lockprovider.IPFS_SET_WRITE_LOCK,
Target: *lockprovider.NewStringLockTarget(),
})
return b
}

func (b *IPFSLockReqBuilder) CreateAnyRep(nodeID int) *IPFSLockReqBuilder {
b.locks = append(b.locks, distlock.Lock{
Path: b.makePath(nodeID),
Name: lockprovider.IPFS_SET_CREATE_LOCK,
Target: *lockprovider.NewStringLockTarget(),
})
return b
}

func (b *IPFSLockReqBuilder) makePath(nodeID int) []string {
return []string{distlock.IPFS_LOCK_PATH_PREFIX, strconv.Itoa(nodeID)}
}

+ 16
- 0
pkg/distlock/reqbuilder/lock_request_builder.go View File

@@ -0,0 +1,16 @@
package reqbuilder

import (
"gitlink.org.cn/cloudream/common/pkg/distlock"
mylo "gitlink.org.cn/cloudream/common/utils/lo"
)

type LockRequestBuilder struct {
locks []distlock.Lock
}

func (b *LockRequestBuilder) Build() distlock.LockRequest {
return distlock.LockRequest{
Locks: mylo.ArrayClone(b.locks),
}
}

+ 75
- 0
pkg/distlock/reqbuilder/metadata.go View File

@@ -0,0 +1,75 @@
package reqbuilder

import (
"gitlink.org.cn/cloudream/common/pkg/distlock"
"gitlink.org.cn/cloudream/common/pkg/distlock/lockprovider"
)

type MetadataLockReqBuilder struct {
*LockRequestBuilder
}

func (b *LockRequestBuilder) Metadata() *MetadataLockReqBuilder {
return &MetadataLockReqBuilder{LockRequestBuilder: b}
}

func (b *IPFSLockReqBuilder) Metadata() *MetadataLockReqBuilder {
return &MetadataLockReqBuilder{LockRequestBuilder: b.LockRequestBuilder}
}

func (b *StorageLockReqBuilder) Metadata() *MetadataLockReqBuilder {
return &MetadataLockReqBuilder{LockRequestBuilder: b.LockRequestBuilder}
}

func (b *MetadataLockReqBuilder) ReadOneNode(nodeID int) *MetadataLockReqBuilder {
b.locks = append(b.locks, distlock.Lock{
Path: b.makePath("Node"),
Name: lockprovider.METADATA_ELEMENT_READ_LOCK,
Target: *lockprovider.NewStringLockTarget().AddComponent(nodeID),
})
return b
}
func (b *MetadataLockReqBuilder) WriteOneNode(nodeID int) *MetadataLockReqBuilder {
b.locks = append(b.locks, distlock.Lock{
Path: b.makePath("Node"),
Name: lockprovider.METADATA_ELEMENT_WRITE_LOCK,
Target: *lockprovider.NewStringLockTarget().AddComponent(nodeID),
})
return b
}
func (b *MetadataLockReqBuilder) CreateOneNode() *MetadataLockReqBuilder {
b.locks = append(b.locks, distlock.Lock{
Path: b.makePath("Node"),
Name: lockprovider.METADATA_ELEMENT_CREATE_LOCK,
Target: *lockprovider.NewStringLockTarget(),
})
return b
}
func (b *MetadataLockReqBuilder) ReadAnyNode() *MetadataLockReqBuilder {
b.locks = append(b.locks, distlock.Lock{
Path: b.makePath("Node"),
Name: lockprovider.METADATA_SET_READ_LOCK,
Target: *lockprovider.NewStringLockTarget(),
})
return b
}
func (b *MetadataLockReqBuilder) WriteAnyNode(nodeID int) *MetadataLockReqBuilder {
b.locks = append(b.locks, distlock.Lock{
Path: b.makePath("Node"),
Name: lockprovider.METADATA_SET_WRITE_LOCK,
Target: *lockprovider.NewStringLockTarget(),
})
return b
}
func (b *MetadataLockReqBuilder) CreateAnyNode() *MetadataLockReqBuilder {
b.locks = append(b.locks, distlock.Lock{
Path: b.makePath("Node"),
Name: lockprovider.METADATA_SET_CREATE_LOCK,
Target: *lockprovider.NewStringLockTarget(),
})
return b
}

func (b *MetadataLockReqBuilder) makePath(tableName string) []string {
return []string{distlock.METADATA_LOCK_PATH_PREFIX, tableName}
}

+ 82
- 0
pkg/distlock/reqbuilder/storage.go View File

@@ -0,0 +1,82 @@
package reqbuilder

import (
"strconv"

"gitlink.org.cn/cloudream/common/pkg/distlock"
"gitlink.org.cn/cloudream/common/pkg/distlock/lockprovider"
)

type StorageLockReqBuilder struct {
*LockRequestBuilder
}

func (b *LockRequestBuilder) Storage() *StorageLockReqBuilder {
return &StorageLockReqBuilder{LockRequestBuilder: b}
}

func (b *MetadataLockReqBuilder) Storage() *StorageLockReqBuilder {
return &StorageLockReqBuilder{LockRequestBuilder: b.LockRequestBuilder}
}

func (b *IPFSLockReqBuilder) Storage() *StorageLockReqBuilder {
return &StorageLockReqBuilder{LockRequestBuilder: b.LockRequestBuilder}
}

func (b *StorageLockReqBuilder) ReadOneObject(storageID int, fileHash string) *StorageLockReqBuilder {
b.locks = append(b.locks, distlock.Lock{
Path: b.makePath(storageID),
Name: lockprovider.STORAGE_ELEMENT_READ_LOCK,
Target: *lockprovider.NewStringLockTarget().AddComponent(fileHash),
})
return b
}

func (b *StorageLockReqBuilder) WriteOneObject(storageID int, fileHash string) *StorageLockReqBuilder {
b.locks = append(b.locks, distlock.Lock{
Path: b.makePath(storageID),
Name: lockprovider.STORAGE_ELEMENT_WRITE_LOCK,
Target: *lockprovider.NewStringLockTarget().AddComponent(fileHash),
})
return b
}

func (b *StorageLockReqBuilder) CreateOneObject(storageID int, fileHash string) *StorageLockReqBuilder {
b.locks = append(b.locks, distlock.Lock{
Path: b.makePath(storageID),
Name: lockprovider.STORAGE_ELEMENT_WRITE_LOCK,
Target: *lockprovider.NewStringLockTarget().AddComponent(fileHash),
})
return b
}

func (b *StorageLockReqBuilder) ReadAnyObject(storageID int) *StorageLockReqBuilder {
b.locks = append(b.locks, distlock.Lock{
Path: b.makePath(storageID),
Name: lockprovider.STORAGE_SET_READ_LOCK,
Target: *lockprovider.NewStringLockTarget(),
})
return b
}

func (b *StorageLockReqBuilder) WriteAnyObject(storageID int) *StorageLockReqBuilder {
b.locks = append(b.locks, distlock.Lock{
Path: b.makePath(storageID),
Name: lockprovider.STORAGE_SET_WRITE_LOCK,
Target: *lockprovider.NewStringLockTarget(),
})
return b
}

func (b *StorageLockReqBuilder) CreateAnyObject(storageID int) *StorageLockReqBuilder {
b.locks = append(b.locks, distlock.Lock{
Path: b.makePath(storageID),
Name: lockprovider.STORAGE_SET_CREATE_LOCK,
Target: *lockprovider.NewStringLockTarget(),
})
return b
}

func (b *StorageLockReqBuilder) makePath(storageID int) []string {
return []string{distlock.STORAGE_LOCK_PATH_PREFIX, strconv.Itoa(storageID)}
}

+ 16
- 15
pkg/distlock/service/init_providers.go View File

@@ -1,6 +1,7 @@
package service

import (
"gitlink.org.cn/cloudream/common/pkg/distlock"
"gitlink.org.cn/cloudream/common/pkg/distlock/lockprovider"
"gitlink.org.cn/cloudream/common/pkg/distlock/service/internal"
"gitlink.org.cn/cloudream/common/pkg/trie"
@@ -15,25 +16,25 @@ func initProviders(providers *internal.ProvidersActor) {
}

func initMetadataLockProviders(providers *internal.ProvidersActor) {
providers.AddProvider(lockprovider.NewMetadataLock(), "Metadata", "Node")
providers.AddProvider(lockprovider.NewMetadataLock(), "Metadata", "Storage")
providers.AddProvider(lockprovider.NewMetadataLock(), "Metadata", "User")
providers.AddProvider(lockprovider.NewMetadataLock(), "Metadata", "UserBucket")
providers.AddProvider(lockprovider.NewMetadataLock(), "Metadata", "UserNode")
providers.AddProvider(lockprovider.NewMetadataLock(), "Metadata", "UserStorage")
providers.AddProvider(lockprovider.NewMetadataLock(), "Metadata", "Bucket")
providers.AddProvider(lockprovider.NewMetadataLock(), "Metadata", "Object")
providers.AddProvider(lockprovider.NewMetadataLock(), "Metadata", "ObjectRep")
providers.AddProvider(lockprovider.NewMetadataLock(), "Metadata", "ObjectBlock")
providers.AddProvider(lockprovider.NewMetadataLock(), "Metadata", "Cache")
providers.AddProvider(lockprovider.NewMetadataLock(), "Metadata", "StorageObject")
providers.AddProvider(lockprovider.NewMetadataLock(), "Metadata", "Location")
providers.AddProvider(lockprovider.NewMetadataLock(), distlock.METADATA_LOCK_PATH_PREFIX, "Node")
providers.AddProvider(lockprovider.NewMetadataLock(), distlock.METADATA_LOCK_PATH_PREFIX, "Storage")
providers.AddProvider(lockprovider.NewMetadataLock(), distlock.METADATA_LOCK_PATH_PREFIX, "User")
providers.AddProvider(lockprovider.NewMetadataLock(), distlock.METADATA_LOCK_PATH_PREFIX, "UserBucket")
providers.AddProvider(lockprovider.NewMetadataLock(), distlock.METADATA_LOCK_PATH_PREFIX, "UserNode")
providers.AddProvider(lockprovider.NewMetadataLock(), distlock.METADATA_LOCK_PATH_PREFIX, "UserStorage")
providers.AddProvider(lockprovider.NewMetadataLock(), distlock.METADATA_LOCK_PATH_PREFIX, "Bucket")
providers.AddProvider(lockprovider.NewMetadataLock(), distlock.METADATA_LOCK_PATH_PREFIX, "Object")
providers.AddProvider(lockprovider.NewMetadataLock(), distlock.METADATA_LOCK_PATH_PREFIX, "ObjectRep")
providers.AddProvider(lockprovider.NewMetadataLock(), distlock.METADATA_LOCK_PATH_PREFIX, "ObjectBlock")
providers.AddProvider(lockprovider.NewMetadataLock(), distlock.METADATA_LOCK_PATH_PREFIX, "Cache")
providers.AddProvider(lockprovider.NewMetadataLock(), distlock.METADATA_LOCK_PATH_PREFIX, "StorageObject")
providers.AddProvider(lockprovider.NewMetadataLock(), distlock.METADATA_LOCK_PATH_PREFIX, "Location")
}

func initIPFSLockProviders(providers *internal.ProvidersActor) {
providers.AddProvider(lockprovider.NewIPFSLock(), "IPFS", trie.WORD_ANY)
providers.AddProvider(lockprovider.NewIPFSLock(), distlock.IPFS_LOCK_PATH_PREFIX, trie.WORD_ANY)
}

func initStorageLockProviders(providers *internal.ProvidersActor) {
providers.AddProvider(lockprovider.NewStorageLock(), "Storage", trie.WORD_ANY)
providers.AddProvider(lockprovider.NewStorageLock(), distlock.STORAGE_LOCK_PATH_PREFIX, trie.WORD_ANY)
}

+ 4
- 0
utils/lo/lo.go View File

@@ -18,3 +18,7 @@ func RemoveAt[T any](arr []T, index int) []T {

return append(arr[:index], arr[:index+1]...)
}

func ArrayClone[T any](arr []T) []T {
return append([]T{}, arr...)
}

Loading…
Cancel
Save