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.

73 lines
1.9 KiB

5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
5 years ago
  1. package filer
  2. import (
  3. "context"
  4. "fmt"
  5. "os"
  6. "time"
  7. "github.com/chrislusf/seaweedfs/weed/operation"
  8. "github.com/chrislusf/seaweedfs/weed/pb/filer_pb"
  9. "github.com/chrislusf/seaweedfs/weed/util"
  10. )
  11. func (f *Filer) appendToFile(targetFile string, data []byte) error {
  12. assignResult, uploadResult, err2 := f.assignAndUpload(data)
  13. if err2 != nil {
  14. return err2
  15. }
  16. // find out existing entry
  17. fullpath := util.FullPath(targetFile)
  18. entry, err := f.FindEntry(context.Background(), fullpath)
  19. var offset int64 = 0
  20. if err == filer_pb.ErrNotFound {
  21. entry = &Entry{
  22. FullPath: fullpath,
  23. Attr: Attr{
  24. Crtime: time.Now(),
  25. Mtime: time.Now(),
  26. Mode: os.FileMode(0644),
  27. Uid: OS_UID,
  28. Gid: OS_GID,
  29. },
  30. }
  31. } else {
  32. offset = int64(TotalSize(entry.Chunks))
  33. }
  34. // append to existing chunks
  35. entry.Chunks = append(entry.Chunks, uploadResult.ToPbFileChunk(assignResult.Fid, offset))
  36. // update the entry
  37. err = f.CreateEntry(context.Background(), entry, false, false, nil)
  38. return err
  39. }
  40. func (f *Filer) assignAndUpload(data []byte) (*operation.AssignResult, *operation.UploadResult, error) {
  41. // assign a volume location
  42. assignRequest := &operation.VolumeAssignRequest{
  43. Count: 1,
  44. Collection: f.metaLogCollection,
  45. Replication: f.metaLogReplication,
  46. WritableVolumeCount: 1,
  47. }
  48. assignResult, err := operation.Assign(f.GetMaster(), f.GrpcDialOption, assignRequest)
  49. if err != nil {
  50. return nil, nil, fmt.Errorf("AssignVolume: %v", err)
  51. }
  52. if assignResult.Error != "" {
  53. return nil, nil, fmt.Errorf("AssignVolume error: %v", assignResult.Error)
  54. }
  55. // upload data
  56. targetUrl := "http://" + assignResult.Url + "/" + assignResult.Fid
  57. uploadResult, err := operation.UploadData(targetUrl, "", f.Cipher, data, false, "", nil, assignResult.Auth)
  58. if err != nil {
  59. return nil, nil, fmt.Errorf("upload data %s: %v", targetUrl, err)
  60. }
  61. // println("uploaded to", targetUrl)
  62. return assignResult, uploadResult, nil
  63. }