gitea源码

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212
  1. // Copyright 2016 The Gogs Authors. All rights reserved.
  2. // Copyright 2020 The Gitea Authors.
  3. // SPDX-License-Identifier: MIT
  4. package user
  5. import (
  6. "errors"
  7. "net/http"
  8. access_model "code.gitea.io/gitea/models/perm/access"
  9. repo_model "code.gitea.io/gitea/models/repo"
  10. user_model "code.gitea.io/gitea/models/user"
  11. api "code.gitea.io/gitea/modules/structs"
  12. "code.gitea.io/gitea/routers/api/v1/utils"
  13. "code.gitea.io/gitea/services/context"
  14. "code.gitea.io/gitea/services/convert"
  15. )
  16. // getStarredRepos returns the repos that the user with the specified userID has
  17. // starred
  18. func getStarredRepos(ctx *context.APIContext, user *user_model.User, private bool) ([]*api.Repository, error) {
  19. starredRepos, err := repo_model.GetStarredRepos(ctx, &repo_model.StarredReposOptions{
  20. ListOptions: utils.GetListOptions(ctx),
  21. StarrerID: user.ID,
  22. IncludePrivate: private,
  23. })
  24. if err != nil {
  25. return nil, err
  26. }
  27. repos := make([]*api.Repository, len(starredRepos))
  28. for i, starred := range starredRepos {
  29. permission, err := access_model.GetUserRepoPermission(ctx, starred, user)
  30. if err != nil {
  31. return nil, err
  32. }
  33. repos[i] = convert.ToRepo(ctx, starred, permission)
  34. }
  35. return repos, nil
  36. }
  37. // GetStarredRepos returns the repos that the given user has starred
  38. func GetStarredRepos(ctx *context.APIContext) {
  39. // swagger:operation GET /users/{username}/starred user userListStarred
  40. // ---
  41. // summary: The repos that the given user has starred
  42. // produces:
  43. // - application/json
  44. // parameters:
  45. // - name: username
  46. // in: path
  47. // description: username of the user whose starred repos are to be listed
  48. // type: string
  49. // required: true
  50. // - name: page
  51. // in: query
  52. // description: page number of results to return (1-based)
  53. // type: integer
  54. // - name: limit
  55. // in: query
  56. // description: page size of results
  57. // type: integer
  58. // responses:
  59. // "200":
  60. // "$ref": "#/responses/RepositoryList"
  61. // "404":
  62. // "$ref": "#/responses/notFound"
  63. // "403":
  64. // "$ref": "#/responses/forbidden"
  65. private := ctx.ContextUser.ID == ctx.Doer.ID
  66. repos, err := getStarredRepos(ctx, ctx.ContextUser, private)
  67. if err != nil {
  68. ctx.APIErrorInternal(err)
  69. return
  70. }
  71. ctx.SetTotalCountHeader(int64(ctx.ContextUser.NumStars))
  72. ctx.JSON(http.StatusOK, &repos)
  73. }
  74. // GetMyStarredRepos returns the repos that the authenticated user has starred
  75. func GetMyStarredRepos(ctx *context.APIContext) {
  76. // swagger:operation GET /user/starred user userCurrentListStarred
  77. // ---
  78. // summary: The repos that the authenticated user has starred
  79. // parameters:
  80. // - name: page
  81. // in: query
  82. // description: page number of results to return (1-based)
  83. // type: integer
  84. // - name: limit
  85. // in: query
  86. // description: page size of results
  87. // type: integer
  88. // produces:
  89. // - application/json
  90. // responses:
  91. // "200":
  92. // "$ref": "#/responses/RepositoryList"
  93. // "403":
  94. // "$ref": "#/responses/forbidden"
  95. repos, err := getStarredRepos(ctx, ctx.Doer, true)
  96. if err != nil {
  97. ctx.APIErrorInternal(err)
  98. }
  99. ctx.SetTotalCountHeader(int64(ctx.Doer.NumStars))
  100. ctx.JSON(http.StatusOK, &repos)
  101. }
  102. // IsStarring returns whether the authenticated is starring the repo
  103. func IsStarring(ctx *context.APIContext) {
  104. // swagger:operation GET /user/starred/{owner}/{repo} user userCurrentCheckStarring
  105. // ---
  106. // summary: Whether the authenticated is starring the repo
  107. // parameters:
  108. // - name: owner
  109. // in: path
  110. // description: owner of the repo
  111. // type: string
  112. // required: true
  113. // - name: repo
  114. // in: path
  115. // description: name of the repo
  116. // type: string
  117. // required: true
  118. // responses:
  119. // "204":
  120. // "$ref": "#/responses/empty"
  121. // "404":
  122. // "$ref": "#/responses/notFound"
  123. // "403":
  124. // "$ref": "#/responses/forbidden"
  125. if repo_model.IsStaring(ctx, ctx.Doer.ID, ctx.Repo.Repository.ID) {
  126. ctx.Status(http.StatusNoContent)
  127. } else {
  128. ctx.APIErrorNotFound()
  129. }
  130. }
  131. // Star the repo specified in the APIContext, as the authenticated user
  132. func Star(ctx *context.APIContext) {
  133. // swagger:operation PUT /user/starred/{owner}/{repo} user userCurrentPutStar
  134. // ---
  135. // summary: Star the given repo
  136. // parameters:
  137. // - name: owner
  138. // in: path
  139. // description: owner of the repo to star
  140. // type: string
  141. // required: true
  142. // - name: repo
  143. // in: path
  144. // description: name of the repo to star
  145. // type: string
  146. // required: true
  147. // responses:
  148. // "204":
  149. // "$ref": "#/responses/empty"
  150. // "403":
  151. // "$ref": "#/responses/forbidden"
  152. // "404":
  153. // "$ref": "#/responses/notFound"
  154. err := repo_model.StarRepo(ctx, ctx.Doer, ctx.Repo.Repository, true)
  155. if err != nil {
  156. if errors.Is(err, user_model.ErrBlockedUser) {
  157. ctx.APIError(http.StatusForbidden, err)
  158. } else {
  159. ctx.APIErrorInternal(err)
  160. }
  161. return
  162. }
  163. ctx.Status(http.StatusNoContent)
  164. }
  165. // Unstar the repo specified in the APIContext, as the authenticated user
  166. func Unstar(ctx *context.APIContext) {
  167. // swagger:operation DELETE /user/starred/{owner}/{repo} user userCurrentDeleteStar
  168. // ---
  169. // summary: Unstar the given repo
  170. // parameters:
  171. // - name: owner
  172. // in: path
  173. // description: owner of the repo to unstar
  174. // type: string
  175. // required: true
  176. // - name: repo
  177. // in: path
  178. // description: name of the repo to unstar
  179. // type: string
  180. // required: true
  181. // responses:
  182. // "204":
  183. // "$ref": "#/responses/empty"
  184. // "404":
  185. // "$ref": "#/responses/notFound"
  186. // "403":
  187. // "$ref": "#/responses/forbidden"
  188. err := repo_model.StarRepo(ctx, ctx.Doer, ctx.Repo.Repository, false)
  189. if err != nil {
  190. ctx.APIErrorInternal(err)
  191. return
  192. }
  193. ctx.Status(http.StatusNoContent)
  194. }