diff --git a/weed/filesys/dir.go b/weed/filesys/dir.go index 79fc10442..33d9248ab 100644 --- a/weed/filesys/dir.go +++ b/weed/filesys/dir.go @@ -176,7 +176,7 @@ func (dir *Dir) Create(ctx context.Context, req *fuse.CreateRequest, }, } file.dirtyMetadata = true - fh := dir.wfs.AcquireHandle(file, req.Uid, req.Gid) + fh := dir.wfs.AcquireHandle(file, req.Uid, req.Gid, req.Flags & fuse.OpenWriteOnly > 0) return file, fh, nil } diff --git a/weed/filesys/dirty_page.go b/weed/filesys/dirty_page.go index 8888cff96..1719d68e6 100644 --- a/weed/filesys/dirty_page.go +++ b/weed/filesys/dirty_page.go @@ -13,6 +13,7 @@ import ( type ContinuousDirtyPages struct { intervals *ContinuousIntervals f *File + fh *FileHandle writeWaitGroup sync.WaitGroup chunkAddLock sync.Mutex lastErr error @@ -94,7 +95,7 @@ func (pages *ContinuousDirtyPages) saveToStorage(reader io.Reader, offset int64, defer pages.writeWaitGroup.Done() reader = io.LimitReader(reader, size) - chunk, collection, replication, err := pages.f.wfs.saveDataAsChunk(pages.f.fullpath())(reader, pages.f.Name, offset) + chunk, collection, replication, err := pages.f.wfs.saveDataAsChunk(pages.f.fullpath(), pages.fh.writeOnly)(reader, pages.f.Name, offset) if err != nil { glog.V(0).Infof("%s saveToStorage [%d,%d): %v", pages.f.fullpath(), offset, offset+size, err) pages.lastErr = err diff --git a/weed/filesys/file.go b/weed/filesys/file.go index bb57988cd..80905a967 100644 --- a/weed/filesys/file.go +++ b/weed/filesys/file.go @@ -97,7 +97,7 @@ func (file *File) Open(ctx context.Context, req *fuse.OpenRequest, resp *fuse.Op glog.V(4).Infof("file %v open %+v", file.fullpath(), req) - handle := file.wfs.AcquireHandle(file, req.Uid, req.Gid) + handle := file.wfs.AcquireHandle(file, req.Uid, req.Gid, req.Flags&fuse.OpenWriteOnly > 0) resp.Handle = fuse.HandleID(handle.handle) diff --git a/weed/filesys/filehandle.go b/weed/filesys/filehandle.go index 27ffab6e1..8cbaf6fd2 100644 --- a/weed/filesys/filehandle.go +++ b/weed/filesys/filehandle.go @@ -32,7 +32,7 @@ type FileHandle struct { NodeId fuse.NodeID // file or directory the request is about Uid uint32 // user ID of process making request Gid uint32 // group ID of process making request - + writeOnly bool } func newFileHandle(file *File, uid, gid uint32) *FileHandle { @@ -42,6 +42,7 @@ func newFileHandle(file *File, uid, gid uint32) *FileHandle { Uid: uid, Gid: gid, } + fh.dirtyPages.fh = fh entry := fh.f.getEntry() if entry != nil { entry.Attributes.FileSize = filer.FileSize(entry) @@ -289,7 +290,7 @@ func (fh *FileHandle) doFlush(ctx context.Context, header fuse.Header) error { manifestChunks, nonManifestChunks := filer.SeparateManifestChunks(entry.Chunks) chunks, _ := filer.CompactFileChunks(fh.f.wfs.LookupFn(), nonManifestChunks) - chunks, manifestErr := filer.MaybeManifestize(fh.f.wfs.saveDataAsChunk(fh.f.fullpath()), chunks) + chunks, manifestErr := filer.MaybeManifestize(fh.f.wfs.saveDataAsChunk(fh.f.fullpath(), fh.writeOnly), chunks) if manifestErr != nil { // not good, but should be ok glog.V(0).Infof("MaybeManifestize: %v", manifestErr) diff --git a/weed/filesys/wfs.go b/weed/filesys/wfs.go index 832925bc1..7757e4285 100644 --- a/weed/filesys/wfs.go +++ b/weed/filesys/wfs.go @@ -138,7 +138,7 @@ func (wfs *WFS) Root() (fs.Node, error) { return wfs.root, nil } -func (wfs *WFS) AcquireHandle(file *File, uid, gid uint32) (fileHandle *FileHandle) { +func (wfs *WFS) AcquireHandle(file *File, uid, gid uint32, writeOnly bool) (fileHandle *FileHandle) { fullpath := file.fullpath() glog.V(4).Infof("AcquireHandle %s uid=%d gid=%d", fullpath, uid, gid) @@ -150,6 +150,9 @@ func (wfs *WFS) AcquireHandle(file *File, uid, gid uint32) (fileHandle *FileHand wfs.handlesLock.Unlock() if found && existingHandle != nil { existingHandle.f.isOpen++ + if existingHandle.writeOnly { + existingHandle.writeOnly = writeOnly + } glog.V(4).Infof("Acquired Handle %s open %d", fullpath, existingHandle.f.isOpen) return existingHandle } @@ -157,6 +160,7 @@ func (wfs *WFS) AcquireHandle(file *File, uid, gid uint32) (fileHandle *FileHand entry, _ := file.maybeLoadEntry(context.Background()) file.entry = entry fileHandle = newFileHandle(file, uid, gid) + fileHandle.writeOnly = writeOnly file.isOpen++ wfs.handlesLock.Lock() diff --git a/weed/filesys/wfs_write.go b/weed/filesys/wfs_write.go index dbec3bebc..9d2ce26ec 100644 --- a/weed/filesys/wfs_write.go +++ b/weed/filesys/wfs_write.go @@ -13,7 +13,7 @@ import ( "github.com/chrislusf/seaweedfs/weed/util" ) -func (wfs *WFS) saveDataAsChunk(fullPath util.FullPath) filer.SaveDataAsChunkFunctionType { +func (wfs *WFS) saveDataAsChunk(fullPath util.FullPath, writeOnly bool) filer.SaveDataAsChunkFunctionType { return func(reader io.Reader, filename string, offset int64) (chunk *filer_pb.FileChunk, collection, replication string, err error) { var fileId, host string @@ -67,7 +67,9 @@ func (wfs *WFS) saveDataAsChunk(fullPath util.FullPath) filer.SaveDataAsChunkFun return nil, "", "", fmt.Errorf("upload result: %v", uploadResult.Error) } - wfs.chunkCache.SetChunk(fileId, data) + if !writeOnly { + wfs.chunkCache.SetChunk(fileId, data) + } chunk = uploadResult.ToPbFileChunk(fileId, offset) return chunk, collection, replication, nil