1
mirror of https://github.com/rclone/rclone synced 2024-12-01 10:31:57 +01:00

fs: add Wrap feature for FS to identify their parent FS (#1884)

This commit is contained in:
remusb 2017-12-06 17:14:34 +02:00 committed by GitHub
parent ebd7780188
commit 25b073c767
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
3 changed files with 49 additions and 4 deletions

16
cache/cache.go vendored
View File

@ -206,6 +206,7 @@ type Storage interface {
// Fs represents a wrapped fs.Fs
type Fs struct {
fs.Fs
wrapper fs.Fs
name string
root string
@ -379,7 +380,9 @@ func NewFs(name, rpath string) (fs.Fs, error) {
PutStream: f.PutStream,
CleanUp: f.CleanUp,
UnWrap: f.UnWrap,
}).Fill(f).Mask(wrappedFs)
WrapFs: f.WrapFs,
SetWrapper: f.SetWrapper,
}).Fill(f).Mask(wrappedFs).WrapsFs(f, wrappedFs)
return f, wrapErr
}
@ -938,6 +941,16 @@ func (f *Fs) UnWrap() fs.Fs {
return f.Fs
}
// WrapFs returns the Fs that is wrapping this Fs
func (f *Fs) WrapFs() fs.Fs {
return f.wrapper
}
// SetWrapper sets the Fs that is wrapping this Fs
func (f *Fs) SetWrapper(wrapper fs.Fs) {
f.wrapper = wrapper
}
// DirCacheFlush flushes the dir cache
func (f *Fs) DirCacheFlush() {
_ = f.cache.RemoveDir("")
@ -963,5 +976,6 @@ var (
_ fs.PutStreamer = (*Fs)(nil)
_ fs.CleanUpper = (*Fs)(nil)
_ fs.UnWrapper = (*Fs)(nil)
_ fs.Wrapper = (*Fs)(nil)
_ fs.ListRer = (*Fs)(nil)
)

View File

@ -129,7 +129,7 @@ func NewFs(name, rpath string) (fs.Fs, error) {
WriteMimeType: false,
BucketBased: true,
CanHaveEmptyDirectories: true,
}).Fill(f).Mask(wrappedFs)
}).Fill(f).Mask(wrappedFs).WrapsFs(f, wrappedFs)
doDirChangeNotify := wrappedFs.Features().DirChangeNotify
if doDirChangeNotify != nil {

View File

@ -301,6 +301,12 @@ type Features struct {
// UnWrap returns the Fs that this Fs is wrapping
UnWrap func() Fs
// WrapFs returns the Fs that is wrapping this Fs
WrapFs func() Fs
// SetWrapper sets the Fs that is wrapping this Fs
SetWrapper func(f Fs)
// DirCacheFlush resets the directory cache - used in testing
// as an optional interface
DirCacheFlush func()
@ -413,6 +419,10 @@ func (ft *Features) Fill(f Fs) *Features {
if do, ok := f.(UnWrapper); ok {
ft.UnWrap = do.UnWrap
}
if do, ok := f.(Wrapper); ok {
ft.WrapFs = do.WrapFs
ft.SetWrapper = do.SetWrapper
}
if do, ok := f.(DirCacheFlusher); ok {
ft.DirCacheFlush = do.DirCacheFlush
}
@ -438,7 +448,7 @@ func (ft *Features) Fill(f Fs) *Features {
//
// Only optional features which are implemented in both the original
// Fs AND the one passed in will be advertised. Any features which
// aren't in both will be set to false/nil, except for UnWrap which
// aren't in both will be set to false/nil, except for UnWrap/Wrap which
// will be left untouched.
func (ft *Features) Mask(f Fs) *Features {
mask := f.Features()
@ -487,7 +497,7 @@ func (ft *Features) Mask(f Fs) *Features {
return ft.DisableList(Config.DisableFeatures)
}
// Wrap makes a Copy of the features passed in, overriding the UnWrap
// Wrap makes a Copy of the features passed in, overriding the UnWrap/Wrap
// method only if available in f.
func (ft *Features) Wrap(f Fs) *Features {
copy := new(Features)
@ -495,9 +505,22 @@ func (ft *Features) Wrap(f Fs) *Features {
if do, ok := f.(UnWrapper); ok {
copy.UnWrap = do.UnWrap
}
if do, ok := f.(Wrapper); ok {
copy.WrapFs = do.WrapFs
copy.SetWrapper = do.SetWrapper
}
return copy
}
// WrapsFs adds extra information between `f` which wraps `w`
func (ft *Features) WrapsFs(f Fs, w Fs) *Features {
wFeatures := w.Features()
if wFeatures.WrapFs != nil && wFeatures.SetWrapper != nil {
wFeatures.SetWrapper(f)
}
return ft
}
// Purger is an optional interfaces for Fs
type Purger interface {
// Purge all files in the root and the root directory
@ -564,6 +587,14 @@ type UnWrapper interface {
UnWrap() Fs
}
// Wrapper is an optional interfaces for Fs
type Wrapper interface {
// Wrap returns the Fs that is wrapping this Fs
WrapFs() Fs
// SetWrapper sets the Fs that is wrapping this Fs
SetWrapper(f Fs)
}
// DirCacheFlusher is an optional interface for Fs
type DirCacheFlusher interface {
// DirCacheFlush resets the directory cache - used in testing