You can not select more than 25 topics Topics must start with a chinese character,a letter or number, can include dashes ('-') and can be up to 35 characters long.

temp.go 10 kB

1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393
  1. package http
  2. /*
  3. import (
  4. "net/http"
  5. "github.com/gin-gonic/gin"
  6. "github.com/samber/lo"
  7. "gitlink.org.cn/cloudream/common/consts/errorcode"
  8. "gitlink.org.cn/cloudream/common/pkgs/logger"
  9. cdssdk "gitlink.org.cn/cloudream/common/sdks/storage"
  10. )
  11. type TempService struct {
  12. *Server
  13. }
  14. func (s *Server) Temp() *TempService {
  15. return &TempService{
  16. Server: s,
  17. }
  18. }
  19. type TempListDetailsResp struct {
  20. Buckets []BucketDetail `json:"buckets"`
  21. }
  22. type BucketDetail struct {
  23. BucketID cdssdk.BucketID `json:"bucketID"`
  24. Name string `json:"name"`
  25. ObjectCount int `json:"objectCount"`
  26. }
  27. func (s *TempService) ListDetails(ctx *gin.Context) {
  28. log := logger.WithField("HTTP", "Bucket.ListBucketsDetails")
  29. bkts, err := s.svc.BucketSvc().GetUserBuckets(1)
  30. if err != nil {
  31. log.Warnf("getting user buckets: %s", err.Error())
  32. ctx.JSON(http.StatusOK, Failed(errorcode.OperationFailed, "get user buckets failed"))
  33. return
  34. }
  35. details := make([]BucketDetail, len(bkts))
  36. for i := range bkts {
  37. details[i].BucketID = bkts[i].BucketID
  38. details[i].Name = bkts[i].Name
  39. objs, err := s.getBucketObjects(bkts[i].BucketID)
  40. if err != nil {
  41. log.Warnf("getting bucket objects: %s", err.Error())
  42. ctx.JSON(http.StatusOK, Failed(errorcode.OperationFailed, "get bucket objects failed"))
  43. return
  44. }
  45. details[i].ObjectCount = len(objs)
  46. }
  47. ctx.JSON(http.StatusOK, OK(TempListDetailsResp{
  48. Buckets: details,
  49. }))
  50. }
  51. type TempGetObjects struct {
  52. BucketID cdssdk.BucketID `form:"bucketID"`
  53. }
  54. type BucketGetObjectsResp struct {
  55. Objects []cdssdk.Object `json:"objects"`
  56. }
  57. func (s *TempService) GetObjects(ctx *gin.Context) {
  58. log := logger.WithField("HTTP", "Bucket.ListBucketsDetails")
  59. var req TempGetObjects
  60. if err := ctx.ShouldBindQuery(&req); err != nil {
  61. log.Warnf("binding query: %s", err.Error())
  62. ctx.JSON(http.StatusBadRequest, Failed(errorcode.BadArgument, "missing argument or invalid argument"))
  63. return
  64. }
  65. objs, err := s.getBucketObjects(req.BucketID)
  66. if err != nil {
  67. log.Warnf("getting bucket objects: %s", err.Error())
  68. ctx.JSON(http.StatusOK, Failed(errorcode.OperationFailed, "get bucket objects failed"))
  69. return
  70. }
  71. ctx.JSON(http.StatusOK, OK(BucketGetObjectsResp{
  72. Objects: objs,
  73. }))
  74. }
  75. type TempGetObjectDetail struct {
  76. ObjectID cdssdk.ObjectID `form:"objectID"`
  77. }
  78. type TempGetObjectDetailResp struct {
  79. Blocks []ObjectBlockDetail `json:"blocks"`
  80. }
  81. type ObjectBlockDetail struct {
  82. ObjectID cdssdk.ObjectID `json:"objectID"`
  83. Type string `json:"type"`
  84. FileHash string `json:"fileHash"`
  85. LocationType string `json:"locationType"`
  86. LocationName string `json:"locationName"`
  87. }
  88. func (s *TempService) GetObjectDetail(ctx *gin.Context) {
  89. log := logger.WithField("HTTP", "Object.GetObjectDetail")
  90. var req TempGetObjectDetail
  91. if err := ctx.ShouldBindQuery(&req); err != nil {
  92. log.Warnf("binding query: %s", err.Error())
  93. ctx.JSON(http.StatusBadRequest, Failed(errorcode.BadArgument, "missing argument or invalid argument"))
  94. return
  95. }
  96. details, err := s.svc.ObjectSvc().GetObjectDetail(req.ObjectID)
  97. if err != nil {
  98. log.Warnf("getting object detail: %s", err.Error())
  99. ctx.JSON(http.StatusOK, Failed(errorcode.OperationFailed, "get object detail failed"))
  100. return
  101. }
  102. if details == nil {
  103. log.Warnf("object not found")
  104. ctx.JSON(http.StatusOK, Failed(errorcode.OperationFailed, "object not found"))
  105. return
  106. }
  107. loadedHubIDs, err := s.svc.PackageSvc().GetLoadedNodes(1, details.Object.PackageID)
  108. if err != nil {
  109. log.Warnf("getting loaded nodes: %s", err.Error())
  110. ctx.JSON(http.StatusOK, Failed(errorcode.OperationFailed, "get loaded nodes failed"))
  111. return
  112. }
  113. var allHubIDs []cdssdk.HubID
  114. allHubIDs = append(allHubIDs, details.PinnedAt...)
  115. for _, b := range details.Blocks {
  116. allHubIDs = append(allHubIDs, b.StorageID)
  117. }
  118. allHubIDs = append(allHubIDs, loadedHubIDs...)
  119. allHubIDs = lo.Uniq(allHubIDs)
  120. getNodes, err := s.svc.NodeSvc().GetNodes(allHubIDs)
  121. if err != nil {
  122. log.Warnf("getting nodes: %s", err.Error())
  123. ctx.JSON(http.StatusOK, Failed(errorcode.OperationFailed, "get nodes failed"))
  124. return
  125. }
  126. allNodes := make(map[cdssdk.HubID]*cdssdk.Node)
  127. for _, n := range getNodes {
  128. n2 := n
  129. allNodes[n.HubID] = &n2
  130. }
  131. var blocks []ObjectBlockDetail
  132. for _, hubID := range details.PinnedAt {
  133. blocks = append(blocks, ObjectBlockDetail{
  134. Type: "Rep",
  135. FileHash: details.Object.FileHash,
  136. LocationType: "Agent",
  137. LocationName: allNodes[hubID].Name,
  138. })
  139. }
  140. switch details.Object.Redundancy.(type) {
  141. case *cdssdk.NoneRedundancy:
  142. for _, blk := range details.Blocks {
  143. if !lo.Contains(details.PinnedAt, blk.StorageID) {
  144. blocks = append(blocks, ObjectBlockDetail{
  145. Type: "Rep",
  146. FileHash: blk.FileHash,
  147. LocationType: "Agent",
  148. LocationName: allNodes[blk.StorageID].Name,
  149. })
  150. }
  151. }
  152. case *cdssdk.RepRedundancy:
  153. for _, blk := range details.Blocks {
  154. if !lo.Contains(details.PinnedAt, blk.StorageID) {
  155. blocks = append(blocks, ObjectBlockDetail{
  156. Type: "Rep",
  157. FileHash: blk.FileHash,
  158. LocationType: "Agent",
  159. LocationName: allNodes[blk.StorageID].Name,
  160. })
  161. }
  162. }
  163. case *cdssdk.ECRedundancy:
  164. for _, blk := range details.Blocks {
  165. blocks = append(blocks, ObjectBlockDetail{
  166. Type: "Block",
  167. FileHash: blk.FileHash,
  168. LocationType: "Agent",
  169. LocationName: allNodes[blk.StorageID].Name,
  170. })
  171. }
  172. }
  173. for _, hubID := range loadedHubIDs {
  174. blocks = append(blocks, ObjectBlockDetail{
  175. Type: "Rep",
  176. FileHash: details.Object.FileHash,
  177. LocationType: "Storage",
  178. LocationName: allNodes[hubID].Name,
  179. })
  180. }
  181. ctx.JSON(http.StatusOK, OK(TempGetObjectDetailResp{
  182. Blocks: blocks,
  183. }))
  184. }
  185. func (s *TempService) getBucketObjects(bktID cdssdk.BucketID) ([]cdssdk.Object, error) {
  186. pkgs, err := s.svc.PackageSvc().GetBucketPackages(1, bktID)
  187. if err != nil {
  188. return nil, err
  189. }
  190. var allObjs []cdssdk.Object
  191. for _, pkg := range pkgs {
  192. objs, err := s.svc.ObjectSvc().GetPackageObjects(1, pkg.PackageID)
  193. if err != nil {
  194. return nil, err
  195. }
  196. allObjs = append(allObjs, objs...)
  197. }
  198. return allObjs, nil
  199. }
  200. type TempGetDatabaseAll struct {
  201. }
  202. type TempGetDatabaseAllResp struct {
  203. Buckets []BucketDetail `json:"buckets"`
  204. Objects []BucketObject `json:"objects"`
  205. Blocks []ObjectBlockDetail `json:"blocks"`
  206. }
  207. type BucketObject struct {
  208. cdssdk.Object
  209. BucketID cdssdk.BucketID `json:"bucketID"`
  210. }
  211. func (s *TempService) GetDatabaseAll(ctx *gin.Context) {
  212. log := logger.WithField("HTTP", "Temp.GetDatabaseAll")
  213. db, err := s.svc.ObjectSvc().GetDatabaseAll()
  214. if err != nil {
  215. log.Warnf("getting database all: %s", err.Error())
  216. ctx.JSON(http.StatusOK, Failed(errorcode.OperationFailed, "get database all failed"))
  217. return
  218. }
  219. nodes, err := s.svc.NodeSvc().GetNodes(nil)
  220. if err != nil {
  221. log.Warnf("getting nodes: %s", err.Error())
  222. ctx.JSON(http.StatusOK, Failed(errorcode.OperationFailed, "get nodes failed"))
  223. return
  224. }
  225. allNodes := make(map[cdssdk.HubID]cdssdk.Node)
  226. for _, n := range nodes {
  227. allNodes[n.HubID] = n
  228. }
  229. bkts := make(map[cdssdk.BucketID]*BucketDetail)
  230. for _, bkt := range db.Buckets {
  231. bkts[bkt.BucketID] = &BucketDetail{
  232. BucketID: bkt.BucketID,
  233. Name: bkt.Name,
  234. ObjectCount: 0,
  235. }
  236. }
  237. type PackageDetail struct {
  238. Package cdssdk.Package
  239. Loaded []cdssdk.Node
  240. }
  241. pkgs := make(map[cdssdk.PackageID]*PackageDetail)
  242. for _, pkg := range db.Packages {
  243. p := PackageDetail{
  244. Package: pkg,
  245. Loaded: make([]cdssdk.Node, 0),
  246. }
  247. loaded, err := s.svc.PackageSvc().GetLoadedNodes(1, pkg.PackageID)
  248. if err != nil {
  249. log.Warnf("getting loaded nodes: %s", err.Error())
  250. ctx.JSON(http.StatusOK, Failed(errorcode.OperationFailed, "get loaded nodes failed"))
  251. return
  252. }
  253. for _, hubID := range loaded {
  254. p.Loaded = append(p.Loaded, allNodes[hubID])
  255. }
  256. pkgs[pkg.PackageID] = &p
  257. }
  258. var objs []BucketObject
  259. for _, obj := range db.Objects {
  260. o := BucketObject{
  261. Object: obj.Object,
  262. BucketID: pkgs[obj.Object.PackageID].Package.BucketID,
  263. }
  264. objs = append(objs, o)
  265. }
  266. var blocks []ObjectBlockDetail
  267. for _, obj := range db.Objects {
  268. bkts[pkgs[obj.Object.PackageID].Package.BucketID].ObjectCount++
  269. for _, hubID := range obj.PinnedAt {
  270. blocks = append(blocks, ObjectBlockDetail{
  271. ObjectID: obj.Object.ObjectID,
  272. Type: "Rep",
  273. FileHash: obj.Object.FileHash,
  274. LocationType: "Agent",
  275. LocationName: allNodes[hubID].Name,
  276. })
  277. }
  278. switch obj.Object.Redundancy.(type) {
  279. case *cdssdk.NoneRedundancy:
  280. for _, blk := range obj.Blocks {
  281. if !lo.Contains(obj.PinnedAt, blk.StorageID) {
  282. blocks = append(blocks, ObjectBlockDetail{
  283. ObjectID: obj.Object.ObjectID,
  284. Type: "Rep",
  285. FileHash: blk.FileHash,
  286. LocationType: "Agent",
  287. LocationName: allNodes[blk.StorageID].Name,
  288. })
  289. }
  290. }
  291. case *cdssdk.RepRedundancy:
  292. for _, blk := range obj.Blocks {
  293. if !lo.Contains(obj.PinnedAt, blk.StorageID) {
  294. blocks = append(blocks, ObjectBlockDetail{
  295. ObjectID: obj.Object.ObjectID,
  296. Type: "Rep",
  297. FileHash: blk.FileHash,
  298. LocationType: "Agent",
  299. LocationName: allNodes[blk.StorageID].Name,
  300. })
  301. }
  302. }
  303. case *cdssdk.ECRedundancy:
  304. for _, blk := range obj.Blocks {
  305. blocks = append(blocks, ObjectBlockDetail{
  306. ObjectID: obj.Object.ObjectID,
  307. Type: "Block",
  308. FileHash: blk.FileHash,
  309. LocationType: "Agent",
  310. LocationName: allNodes[blk.StorageID].Name,
  311. })
  312. }
  313. }
  314. for _, node := range pkgs[obj.Object.PackageID].Loaded {
  315. blocks = append(blocks, ObjectBlockDetail{
  316. ObjectID: obj.Object.ObjectID,
  317. Type: "Rep",
  318. FileHash: obj.Object.FileHash,
  319. LocationType: "Storage",
  320. LocationName: allNodes[node.HubID].Name,
  321. })
  322. }
  323. }
  324. ctx.JSON(http.StatusOK, OK(TempGetDatabaseAllResp{
  325. Buckets: lo.Map(lo.Values(bkts), func(b *BucketDetail, _ int) BucketDetail { return *b }),
  326. Objects: objs,
  327. Blocks: blocks,
  328. }))
  329. }
  330. func initTemp(rt gin.IRoutes, s *Server) {
  331. rt.GET("/bucket/listDetails", s.Temp().ListDetails)
  332. rt.GET("/bucket/getObjects", s.Temp().GetObjects)
  333. rt.GET("/object/getDetail", s.Temp().GetObjectDetail)
  334. rt.GET("/temp/getDatabaseAll", s.Temp().GetDatabaseAll)
  335. }
  336. func auth(ctx *gin.Context) {
  337. token := ctx.Request.Header.Get("X-CDS-Auth")
  338. if token != "cloudream@123" {
  339. ctx.AbortWithStatus(http.StatusUnauthorized)
  340. }
  341. }
  342. */

本项目旨在将云际存储公共基础设施化,使个人及企业可低门槛使用高效的云际存储服务(安装开箱即用云际存储客户端即可,无需关注其他组件的部署),同时支持用户灵活便捷定制云际存储的功能细节。