filer_server.go 8.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247
  1. package weed_server
  2. import (
  3. "context"
  4. "fmt"
  5. "net/http"
  6. "os"
  7. "strings"
  8. "sync"
  9. "sync/atomic"
  10. "time"
  11. "github.com/seaweedfs/seaweedfs/weed/stats"
  12. "google.golang.org/grpc"
  13. "github.com/seaweedfs/seaweedfs/weed/util/grace"
  14. "github.com/seaweedfs/seaweedfs/weed/operation"
  15. "github.com/seaweedfs/seaweedfs/weed/pb"
  16. "github.com/seaweedfs/seaweedfs/weed/pb/filer_pb"
  17. "github.com/seaweedfs/seaweedfs/weed/pb/master_pb"
  18. "github.com/seaweedfs/seaweedfs/weed/util"
  19. "github.com/seaweedfs/seaweedfs/weed/filer"
  20. _ "github.com/seaweedfs/seaweedfs/weed/filer/arangodb"
  21. _ "github.com/seaweedfs/seaweedfs/weed/filer/cassandra"
  22. _ "github.com/seaweedfs/seaweedfs/weed/filer/elastic/v7"
  23. _ "github.com/seaweedfs/seaweedfs/weed/filer/etcd"
  24. _ "github.com/seaweedfs/seaweedfs/weed/filer/hbase"
  25. _ "github.com/seaweedfs/seaweedfs/weed/filer/leveldb"
  26. _ "github.com/seaweedfs/seaweedfs/weed/filer/leveldb2"
  27. _ "github.com/seaweedfs/seaweedfs/weed/filer/leveldb3"
  28. _ "github.com/seaweedfs/seaweedfs/weed/filer/mongodb"
  29. _ "github.com/seaweedfs/seaweedfs/weed/filer/mysql"
  30. _ "github.com/seaweedfs/seaweedfs/weed/filer/mysql2"
  31. _ "github.com/seaweedfs/seaweedfs/weed/filer/postgres"
  32. _ "github.com/seaweedfs/seaweedfs/weed/filer/postgres2"
  33. _ "github.com/seaweedfs/seaweedfs/weed/filer/redis"
  34. _ "github.com/seaweedfs/seaweedfs/weed/filer/redis2"
  35. _ "github.com/seaweedfs/seaweedfs/weed/filer/redis3"
  36. _ "github.com/seaweedfs/seaweedfs/weed/filer/sqlite"
  37. _ "github.com/seaweedfs/seaweedfs/weed/filer/ydb"
  38. "github.com/seaweedfs/seaweedfs/weed/glog"
  39. "github.com/seaweedfs/seaweedfs/weed/notification"
  40. _ "github.com/seaweedfs/seaweedfs/weed/notification/aws_sqs"
  41. _ "github.com/seaweedfs/seaweedfs/weed/notification/gocdk_pub_sub"
  42. _ "github.com/seaweedfs/seaweedfs/weed/notification/google_pub_sub"
  43. _ "github.com/seaweedfs/seaweedfs/weed/notification/kafka"
  44. _ "github.com/seaweedfs/seaweedfs/weed/notification/log"
  45. "github.com/seaweedfs/seaweedfs/weed/security"
  46. )
  47. type FilerOption struct {
  48. Masters *pb.ServerDiscovery
  49. FilerGroup string
  50. Collection string
  51. DefaultReplication string
  52. DisableDirListing bool
  53. MaxMB int
  54. DirListingLimit int
  55. DataCenter string
  56. Rack string
  57. DataNode string
  58. DefaultLevelDbDir string
  59. DisableHttp bool
  60. Host pb.ServerAddress
  61. recursiveDelete bool
  62. Cipher bool
  63. SaveToFilerLimit int64
  64. ConcurrentUploadLimit int64
  65. ShowUIDirectoryDelete bool
  66. DownloadMaxBytesPs int64
  67. DiskType string
  68. AllowedOrigins []string
  69. ExposeDirectoryData bool
  70. JoinExistingFiler bool
  71. }
  72. type FilerServer struct {
  73. inFlightDataSize int64
  74. listenersWaits int64
  75. // notifying clients
  76. listenersLock sync.Mutex
  77. listenersCond *sync.Cond
  78. inFlightDataLimitCond *sync.Cond
  79. filer_pb.UnimplementedSeaweedFilerServer
  80. option *FilerOption
  81. secret security.SigningKey
  82. filer *filer.Filer
  83. filerGuard *security.Guard
  84. volumeGuard *security.Guard
  85. grpcDialOption grpc.DialOption
  86. // metrics read from the master
  87. metricsAddress string
  88. metricsIntervalSec int
  89. // track known metadata listeners
  90. knownListenersLock sync.Mutex
  91. knownListeners map[int32]int32
  92. }
  93. func NewFilerServer(defaultMux, readonlyMux *http.ServeMux, option *FilerOption) (fs *FilerServer, err error) {
  94. v := util.GetViper()
  95. signingKey := v.GetString("jwt.filer_signing.key")
  96. v.SetDefault("jwt.filer_signing.expires_after_seconds", 10)
  97. expiresAfterSec := v.GetInt("jwt.filer_signing.expires_after_seconds")
  98. readSigningKey := v.GetString("jwt.filer_signing.read.key")
  99. v.SetDefault("jwt.filer_signing.read.expires_after_seconds", 60)
  100. readExpiresAfterSec := v.GetInt("jwt.filer_signing.read.expires_after_seconds")
  101. volumeSigningKey := v.GetString("jwt.signing.key")
  102. v.SetDefault("jwt.signing.expires_after_seconds", 10)
  103. volumeExpiresAfterSec := v.GetInt("jwt.signing.expires_after_seconds")
  104. volumeReadSigningKey := v.GetString("jwt.signing.read.key")
  105. v.SetDefault("jwt.signing.read.expires_after_seconds", 60)
  106. volumeReadExpiresAfterSec := v.GetInt("jwt.signing.read.expires_after_seconds")
  107. v.SetDefault("cors.allowed_origins.values", "*")
  108. allowedOrigins := v.GetString("cors.allowed_origins.values")
  109. domains := strings.Split(allowedOrigins, ",")
  110. option.AllowedOrigins = domains
  111. v.SetDefault("filer.expose_directory_metadata.enabled", true)
  112. returnDirMetadata := v.GetBool("filer.expose_directory_metadata.enabled")
  113. option.ExposeDirectoryData = returnDirMetadata
  114. fs = &FilerServer{
  115. option: option,
  116. grpcDialOption: security.LoadClientTLS(util.GetViper(), "grpc.filer"),
  117. knownListeners: make(map[int32]int32),
  118. inFlightDataLimitCond: sync.NewCond(new(sync.Mutex)),
  119. }
  120. fs.listenersCond = sync.NewCond(&fs.listenersLock)
  121. option.Masters.RefreshBySrvIfAvailable()
  122. if len(option.Masters.GetInstances()) == 0 {
  123. glog.Fatal("master list is required!")
  124. }
  125. v.SetDefault("filer.options.max_file_name_length", 255)
  126. maxFilenameLength := v.GetUint32("filer.options.max_file_name_length")
  127. fs.filer = filer.NewFiler(*option.Masters, fs.grpcDialOption, option.Host, option.FilerGroup, option.Collection, option.DefaultReplication, option.DataCenter, maxFilenameLength, func() {
  128. if atomic.LoadInt64(&fs.listenersWaits) > 0 {
  129. fs.listenersCond.Broadcast()
  130. }
  131. })
  132. fs.filer.Cipher = option.Cipher
  133. // we do not support IP whitelist right now
  134. fs.filerGuard = security.NewGuard([]string{}, signingKey, expiresAfterSec, readSigningKey, readExpiresAfterSec)
  135. fs.volumeGuard = security.NewGuard([]string{}, volumeSigningKey, volumeExpiresAfterSec, volumeReadSigningKey, volumeReadExpiresAfterSec)
  136. fs.checkWithMaster()
  137. go stats.LoopPushingMetric("filer", string(fs.option.Host), fs.metricsAddress, fs.metricsIntervalSec)
  138. go fs.filer.KeepMasterClientConnected(context.Background())
  139. if !util.LoadConfiguration("filer", false) {
  140. v.SetDefault("leveldb2.enabled", true)
  141. v.SetDefault("leveldb2.dir", option.DefaultLevelDbDir)
  142. _, err := os.Stat(option.DefaultLevelDbDir)
  143. if os.IsNotExist(err) {
  144. os.MkdirAll(option.DefaultLevelDbDir, 0755)
  145. }
  146. glog.V(0).Infof("default to create filer store dir in %s", option.DefaultLevelDbDir)
  147. } else {
  148. glog.Warningf("skipping default store dir in %s", option.DefaultLevelDbDir)
  149. }
  150. util.LoadConfiguration("notification", false)
  151. fs.option.recursiveDelete = v.GetBool("filer.options.recursive_delete")
  152. v.SetDefault("filer.options.buckets_folder", "/buckets")
  153. fs.filer.DirBucketsPath = v.GetString("filer.options.buckets_folder")
  154. // TODO deprecated, will be removed after 2020-12-31
  155. // replaced by https://github.com/seaweedfs/seaweedfs/wiki/Path-Specific-Configuration
  156. // fs.filer.FsyncBuckets = v.GetStringSlice("filer.options.buckets_fsync")
  157. isFresh := fs.filer.LoadConfiguration(v)
  158. notification.LoadConfiguration(v, "notification.")
  159. handleStaticResources(defaultMux)
  160. if !option.DisableHttp {
  161. defaultMux.HandleFunc("/healthz", fs.filerHealthzHandler)
  162. defaultMux.HandleFunc("/", fs.filerHandler)
  163. }
  164. if defaultMux != readonlyMux {
  165. handleStaticResources(readonlyMux)
  166. readonlyMux.HandleFunc("/healthz", fs.filerHealthzHandler)
  167. readonlyMux.HandleFunc("/", fs.readonlyFilerHandler)
  168. }
  169. existingNodes := fs.filer.ListExistingPeerUpdates(context.Background())
  170. startFromTime := time.Now().Add(-filer.LogFlushInterval)
  171. if option.JoinExistingFiler {
  172. startFromTime = time.Time{}
  173. }
  174. if isFresh {
  175. glog.V(0).Infof("%s bootstrap from peers %+v", option.Host, existingNodes)
  176. if err := fs.filer.MaybeBootstrapFromPeers(option.Host, existingNodes, startFromTime); err != nil {
  177. glog.Fatalf("%s bootstrap from %+v: %v", option.Host, existingNodes, err)
  178. }
  179. }
  180. fs.filer.AggregateFromPeers(option.Host, existingNodes, startFromTime)
  181. fs.filer.LoadFilerConf()
  182. fs.filer.LoadRemoteStorageConfAndMapping()
  183. grace.OnInterrupt(func() {
  184. fs.filer.Shutdown()
  185. })
  186. fs.filer.Dlm.LockRing.SetTakeSnapshotCallback(fs.OnDlmChangeSnapshot)
  187. return fs, nil
  188. }
  189. func (fs *FilerServer) checkWithMaster() {
  190. isConnected := false
  191. for !isConnected {
  192. fs.option.Masters.RefreshBySrvIfAvailable()
  193. for _, master := range fs.option.Masters.GetInstances() {
  194. readErr := operation.WithMasterServerClient(false, master, fs.grpcDialOption, func(masterClient master_pb.SeaweedClient) error {
  195. resp, err := masterClient.GetMasterConfiguration(context.Background(), &master_pb.GetMasterConfigurationRequest{})
  196. if err != nil {
  197. return fmt.Errorf("get master %s configuration: %v", master, err)
  198. }
  199. fs.metricsAddress, fs.metricsIntervalSec = resp.MetricsAddress, int(resp.MetricsIntervalSeconds)
  200. return nil
  201. })
  202. if readErr == nil {
  203. isConnected = true
  204. } else {
  205. time.Sleep(7 * time.Second)
  206. }
  207. }
  208. }
  209. }