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.

278 lines
7.9 KiB

6 years ago
6 years ago
6 years ago
6 years ago
  1. package weed_server
  2. import (
  3. "context"
  4. "fmt"
  5. "github.com/chrislusf/seaweedfs/weed/pb"
  6. "github.com/chrislusf/seaweedfs/weed/pb/filer_pb"
  7. "github.com/chrislusf/seaweedfs/weed/pb/master_pb"
  8. "path/filepath"
  9. "github.com/chrislusf/seaweedfs/weed/glog"
  10. "github.com/chrislusf/seaweedfs/weed/pb/volume_server_pb"
  11. "github.com/chrislusf/seaweedfs/weed/stats"
  12. "github.com/chrislusf/seaweedfs/weed/storage/needle"
  13. "github.com/chrislusf/seaweedfs/weed/storage/super_block"
  14. "github.com/chrislusf/seaweedfs/weed/storage/types"
  15. )
  16. func (vs *VolumeServer) DeleteCollection(ctx context.Context, req *volume_server_pb.DeleteCollectionRequest) (*volume_server_pb.DeleteCollectionResponse, error) {
  17. resp := &volume_server_pb.DeleteCollectionResponse{}
  18. err := vs.store.DeleteCollection(req.Collection)
  19. if err != nil {
  20. glog.Errorf("delete collection %s: %v", req.Collection, err)
  21. } else {
  22. glog.V(2).Infof("delete collection %v", req)
  23. }
  24. return resp, err
  25. }
  26. func (vs *VolumeServer) AllocateVolume(ctx context.Context, req *volume_server_pb.AllocateVolumeRequest) (*volume_server_pb.AllocateVolumeResponse, error) {
  27. resp := &volume_server_pb.AllocateVolumeResponse{}
  28. err := vs.store.AddVolume(
  29. needle.VolumeId(req.VolumeId),
  30. req.Collection,
  31. vs.needleMapKind,
  32. req.Replication,
  33. req.Ttl,
  34. req.Preallocate,
  35. req.MemoryMapMaxSizeMb,
  36. types.ToDiskType(req.DiskType),
  37. )
  38. if err != nil {
  39. glog.Errorf("assign volume %v: %v", req, err)
  40. } else {
  41. glog.V(2).Infof("assign volume %v", req)
  42. }
  43. return resp, err
  44. }
  45. func (vs *VolumeServer) VolumeMount(ctx context.Context, req *volume_server_pb.VolumeMountRequest) (*volume_server_pb.VolumeMountResponse, error) {
  46. resp := &volume_server_pb.VolumeMountResponse{}
  47. err := vs.store.MountVolume(needle.VolumeId(req.VolumeId))
  48. if err != nil {
  49. glog.Errorf("volume mount %v: %v", req, err)
  50. } else {
  51. glog.V(2).Infof("volume mount %v", req)
  52. }
  53. return resp, err
  54. }
  55. func (vs *VolumeServer) VolumeUnmount(ctx context.Context, req *volume_server_pb.VolumeUnmountRequest) (*volume_server_pb.VolumeUnmountResponse, error) {
  56. resp := &volume_server_pb.VolumeUnmountResponse{}
  57. err := vs.store.UnmountVolume(needle.VolumeId(req.VolumeId))
  58. if err != nil {
  59. glog.Errorf("volume unmount %v: %v", req, err)
  60. } else {
  61. glog.V(2).Infof("volume unmount %v", req)
  62. }
  63. return resp, err
  64. }
  65. func (vs *VolumeServer) VolumeDelete(ctx context.Context, req *volume_server_pb.VolumeDeleteRequest) (*volume_server_pb.VolumeDeleteResponse, error) {
  66. resp := &volume_server_pb.VolumeDeleteResponse{}
  67. err := vs.store.DeleteVolume(needle.VolumeId(req.VolumeId))
  68. if err != nil {
  69. glog.Errorf("volume delete %v: %v", req, err)
  70. } else {
  71. glog.V(2).Infof("volume delete %v", req)
  72. }
  73. return resp, err
  74. }
  75. func (vs *VolumeServer) VolumeConfigure(ctx context.Context, req *volume_server_pb.VolumeConfigureRequest) (*volume_server_pb.VolumeConfigureResponse, error) {
  76. resp := &volume_server_pb.VolumeConfigureResponse{}
  77. // check replication format
  78. if _, err := super_block.NewReplicaPlacementFromString(req.Replication); err != nil {
  79. resp.Error = fmt.Sprintf("volume configure replication %v: %v", req, err)
  80. return resp, nil
  81. }
  82. // unmount
  83. if err := vs.store.UnmountVolume(needle.VolumeId(req.VolumeId)); err != nil {
  84. glog.Errorf("volume configure unmount %v: %v", req, err)
  85. resp.Error = fmt.Sprintf("volume configure unmount %v: %v", req, err)
  86. return resp, nil
  87. }
  88. // modify the volume info file
  89. if err := vs.store.ConfigureVolume(needle.VolumeId(req.VolumeId), req.Replication); err != nil {
  90. glog.Errorf("volume configure %v: %v", req, err)
  91. resp.Error = fmt.Sprintf("volume configure %v: %v", req, err)
  92. return resp, nil
  93. }
  94. // mount
  95. if err := vs.store.MountVolume(needle.VolumeId(req.VolumeId)); err != nil {
  96. glog.Errorf("volume configure mount %v: %v", req, err)
  97. resp.Error = fmt.Sprintf("volume configure mount %v: %v", req, err)
  98. return resp, nil
  99. }
  100. return resp, nil
  101. }
  102. func (vs *VolumeServer) VolumeMarkReadonly(ctx context.Context, req *volume_server_pb.VolumeMarkReadonlyRequest) (*volume_server_pb.VolumeMarkReadonlyResponse, error) {
  103. resp := &volume_server_pb.VolumeMarkReadonlyResponse{}
  104. err := vs.store.MarkVolumeReadonly(needle.VolumeId(req.VolumeId))
  105. if err != nil {
  106. glog.Errorf("volume mark readonly %v: %v", req, err)
  107. } else {
  108. glog.V(2).Infof("volume mark readonly %v", req)
  109. }
  110. return resp, err
  111. }
  112. func (vs *VolumeServer) VolumeMarkWritable(ctx context.Context, req *volume_server_pb.VolumeMarkWritableRequest) (*volume_server_pb.VolumeMarkWritableResponse, error) {
  113. resp := &volume_server_pb.VolumeMarkWritableResponse{}
  114. err := vs.store.MarkVolumeWritable(needle.VolumeId(req.VolumeId))
  115. if err != nil {
  116. glog.Errorf("volume mark writable %v: %v", req, err)
  117. } else {
  118. glog.V(2).Infof("volume mark writable %v", req)
  119. }
  120. return resp, err
  121. }
  122. func (vs *VolumeServer) VolumeStatus(ctx context.Context, req *volume_server_pb.VolumeStatusRequest) (*volume_server_pb.VolumeStatusResponse, error) {
  123. resp := &volume_server_pb.VolumeStatusResponse{}
  124. v := vs.store.GetVolume(needle.VolumeId(req.VolumeId))
  125. if v == nil {
  126. return nil, fmt.Errorf("not found volume id %d", req.VolumeId)
  127. }
  128. resp.IsReadOnly = v.IsReadOnly()
  129. return resp, nil
  130. }
  131. func (vs *VolumeServer) VolumeServerStatus(ctx context.Context, req *volume_server_pb.VolumeServerStatusRequest) (*volume_server_pb.VolumeServerStatusResponse, error) {
  132. resp := &volume_server_pb.VolumeServerStatusResponse{}
  133. for _, loc := range vs.store.Locations {
  134. if dir, e := filepath.Abs(loc.Directory); e == nil {
  135. resp.DiskStatuses = append(resp.DiskStatuses, stats.NewDiskStatus(dir))
  136. }
  137. }
  138. resp.MemoryStatus = stats.MemStat()
  139. return resp, nil
  140. }
  141. func (vs *VolumeServer) VolumeServerLeave(ctx context.Context, req *volume_server_pb.VolumeServerLeaveRequest) (*volume_server_pb.VolumeServerLeaveResponse, error) {
  142. resp := &volume_server_pb.VolumeServerLeaveResponse{}
  143. vs.StopHeartbeat()
  144. return resp, nil
  145. }
  146. func (vs *VolumeServer) VolumeNeedleStatus(ctx context.Context, req *volume_server_pb.VolumeNeedleStatusRequest) (*volume_server_pb.VolumeNeedleStatusResponse, error) {
  147. resp := &volume_server_pb.VolumeNeedleStatusResponse{}
  148. volumeId := needle.VolumeId(req.VolumeId)
  149. n := &needle.Needle{
  150. Id: types.NeedleId(req.NeedleId),
  151. }
  152. var count int
  153. var err error
  154. hasVolume := vs.store.HasVolume(volumeId)
  155. if !hasVolume {
  156. _, hasEcVolume := vs.store.FindEcVolume(volumeId)
  157. if !hasEcVolume {
  158. return nil, fmt.Errorf("volume not found %d", req.VolumeId)
  159. }
  160. count, err = vs.store.ReadEcShardNeedle(volumeId, n, nil)
  161. } else {
  162. count, err = vs.store.ReadVolumeNeedle(volumeId, n, nil, nil)
  163. }
  164. if err != nil {
  165. return nil, err
  166. }
  167. if count < 0 {
  168. return nil, fmt.Errorf("needle not found %d", n.Id)
  169. }
  170. resp.NeedleId = uint64(n.Id)
  171. resp.Cookie = uint32(n.Cookie)
  172. resp.Size = uint32(n.Size)
  173. resp.LastModified = n.LastModified
  174. resp.Crc = n.Checksum.Value()
  175. if n.HasTtl() {
  176. resp.Ttl = n.Ttl.String()
  177. }
  178. return resp, nil
  179. }
  180. func (vs *VolumeServer) Ping(ctx context.Context, req *volume_server_pb.PingRequest) (resp *volume_server_pb.PingResponse, pingErr error) {
  181. resp = &volume_server_pb.PingResponse{}
  182. if req.TargetType == "Filer" {
  183. pingErr = pb.WithFilerClient(false, pb.ServerAddress(req.Target), vs.grpcDialOption, func(client filer_pb.SeaweedFilerClient) error {
  184. _, err := client.Ping(ctx, &filer_pb.PingRequest{})
  185. return err
  186. })
  187. }
  188. if req.TargetType == "VolumeServer" {
  189. pingErr = pb.WithVolumeServerClient(false, pb.ServerAddress(req.Target), vs.grpcDialOption, func(client volume_server_pb.VolumeServerClient) error {
  190. _, err := client.Ping(ctx, &volume_server_pb.PingRequest{})
  191. return err
  192. })
  193. }
  194. if req.TargetType == "Master" {
  195. pingErr = pb.WithMasterClient(false, pb.ServerAddress(req.Target), vs.grpcDialOption, func(client master_pb.SeaweedClient) error {
  196. _, err := client.Ping(ctx, &master_pb.PingRequest{})
  197. return err
  198. })
  199. }
  200. if pingErr != nil {
  201. pingErr = fmt.Errorf("ping %s %s: %v", req.TargetType, req.Target, pingErr)
  202. }
  203. return
  204. }