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.

109 lines
3.0 KiB

5 years ago
  1. package broker
  2. import (
  3. "context"
  4. "fmt"
  5. "io"
  6. "github.com/chrislusf/seaweedfs/weed/glog"
  7. "github.com/chrislusf/seaweedfs/weed/operation"
  8. "github.com/chrislusf/seaweedfs/weed/pb"
  9. "github.com/chrislusf/seaweedfs/weed/pb/filer_pb"
  10. "github.com/chrislusf/seaweedfs/weed/pb/messaging_pb"
  11. "github.com/chrislusf/seaweedfs/weed/security"
  12. "github.com/chrislusf/seaweedfs/weed/util"
  13. )
  14. func (broker *MessageBroker) appendToFile(targetFile string, topicConfig *messaging_pb.TopicConfiguration, data []byte) error {
  15. assignResult, uploadResult, err2 := broker.assignAndUpload(topicConfig, data)
  16. if err2 != nil {
  17. return err2
  18. }
  19. dir, name := util.FullPath(targetFile).DirAndName()
  20. // append the chunk
  21. if err := broker.WithFilerClient(func(client filer_pb.SeaweedFilerClient) error {
  22. request := &filer_pb.AppendToEntryRequest{
  23. Directory: dir,
  24. EntryName: name,
  25. Chunks: []*filer_pb.FileChunk{uploadResult.ToPbFileChunk(assignResult.Fid, 0)},
  26. }
  27. _, err := client.AppendToEntry(context.Background(), request)
  28. if err != nil {
  29. glog.V(0).Infof("append to file %v: %v", request, err)
  30. return err
  31. }
  32. return nil
  33. }); err != nil {
  34. return fmt.Errorf("append to file %v: %v", targetFile, err)
  35. }
  36. return nil
  37. }
  38. func (broker *MessageBroker) assignAndUpload(topicConfig *messaging_pb.TopicConfiguration, data []byte) (*operation.AssignResult, *operation.UploadResult, error) {
  39. var assignResult = &operation.AssignResult{}
  40. // assign a volume location
  41. if err := broker.WithFilerClient(func(client filer_pb.SeaweedFilerClient) error {
  42. request := &filer_pb.AssignVolumeRequest{
  43. Count: 1,
  44. Replication: topicConfig.Replication,
  45. Collection: topicConfig.Collection,
  46. }
  47. resp, err := client.AssignVolume(context.Background(), request)
  48. if err != nil {
  49. glog.V(0).Infof("assign volume failure %v: %v", request, err)
  50. return err
  51. }
  52. if resp.Error != "" {
  53. return fmt.Errorf("assign volume failure %v: %v", request, resp.Error)
  54. }
  55. assignResult.Auth = security.EncodedJwt(resp.Auth)
  56. assignResult.Fid = resp.FileId
  57. assignResult.Url = resp.Url
  58. assignResult.PublicUrl = resp.PublicUrl
  59. assignResult.Count = uint64(resp.Count)
  60. return nil
  61. }); err != nil {
  62. return nil, nil, err
  63. }
  64. // upload data
  65. targetUrl := fmt.Sprintf("http://%s/%s", assignResult.Url, assignResult.Fid)
  66. uploadResult, err := operation.UploadData(targetUrl, "", broker.option.Cipher, data, false, "", nil, assignResult.Auth)
  67. if err != nil {
  68. return nil, nil, fmt.Errorf("upload data %s: %v", targetUrl, err)
  69. }
  70. // println("uploaded to", targetUrl)
  71. return assignResult, uploadResult, nil
  72. }
  73. var _ = filer_pb.FilerClient(&MessageBroker{})
  74. func (broker *MessageBroker) WithFilerClient(fn func(filer_pb.SeaweedFilerClient) error) (err error) {
  75. for _, filer := range broker.option.Filers {
  76. if err = pb.WithFilerClient(filer, broker.grpcDialOption, fn); err != nil {
  77. if err == io.EOF {
  78. return
  79. }
  80. glog.V(0).Infof("fail to connect to %s: %v", filer, err)
  81. } else {
  82. break
  83. }
  84. }
  85. return
  86. }