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.

api_helper_for_declarative_test.go 11KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352
  1. // Copyright 2019 The Gitea Authors. All rights reserved.
  2. // Use of this source code is governed by a MIT-style
  3. // license that can be found in the LICENSE file.
  4. package integrations
  5. import (
  6. "encoding/json"
  7. "fmt"
  8. "io/ioutil"
  9. "net/http"
  10. "testing"
  11. "code.gitea.io/gitea/models"
  12. "code.gitea.io/gitea/modules/auth"
  13. api "code.gitea.io/gitea/modules/structs"
  14. "github.com/stretchr/testify/assert"
  15. )
  16. type APITestContext struct {
  17. Reponame string
  18. Session *TestSession
  19. Token string
  20. Username string
  21. ExpectedCode int
  22. }
  23. func NewAPITestContext(t *testing.T, username, reponame string) APITestContext {
  24. session := loginUser(t, username)
  25. token := getTokenForLoggedInUser(t, session)
  26. return APITestContext{
  27. Session: session,
  28. Token: token,
  29. Username: username,
  30. Reponame: reponame,
  31. }
  32. }
  33. func (ctx APITestContext) GitPath() string {
  34. return fmt.Sprintf("%s/%s.git", ctx.Username, ctx.Reponame)
  35. }
  36. func doAPICreateRepository(ctx APITestContext, empty bool, callback ...func(*testing.T, api.Repository)) func(*testing.T) {
  37. return func(t *testing.T) {
  38. createRepoOption := &api.CreateRepoOption{
  39. AutoInit: !empty,
  40. Description: "Temporary repo",
  41. Name: ctx.Reponame,
  42. Private: true,
  43. Template: true,
  44. Gitignores: "",
  45. License: "WTFPL",
  46. Readme: "Default",
  47. }
  48. req := NewRequestWithJSON(t, "POST", "/api/v1/user/repos?token="+ctx.Token, createRepoOption)
  49. if ctx.ExpectedCode != 0 {
  50. ctx.Session.MakeRequest(t, req, ctx.ExpectedCode)
  51. return
  52. }
  53. resp := ctx.Session.MakeRequest(t, req, http.StatusCreated)
  54. var repository api.Repository
  55. DecodeJSON(t, resp, &repository)
  56. if len(callback) > 0 {
  57. callback[0](t, repository)
  58. }
  59. }
  60. }
  61. func doAPIAddCollaborator(ctx APITestContext, username string, mode models.AccessMode) func(*testing.T) {
  62. return func(t *testing.T) {
  63. permission := "read"
  64. if mode == models.AccessModeAdmin {
  65. permission = "admin"
  66. } else if mode > models.AccessModeRead {
  67. permission = "write"
  68. }
  69. addCollaboratorOption := &api.AddCollaboratorOption{
  70. Permission: &permission,
  71. }
  72. req := NewRequestWithJSON(t, "PUT", fmt.Sprintf("/api/v1/repos/%s/%s/collaborators/%s?token=%s", ctx.Username, ctx.Reponame, username, ctx.Token), addCollaboratorOption)
  73. if ctx.ExpectedCode != 0 {
  74. ctx.Session.MakeRequest(t, req, ctx.ExpectedCode)
  75. return
  76. }
  77. ctx.Session.MakeRequest(t, req, http.StatusNoContent)
  78. }
  79. }
  80. func doAPIForkRepository(ctx APITestContext, username string, callback ...func(*testing.T, api.Repository)) func(*testing.T) {
  81. return func(t *testing.T) {
  82. createForkOption := &api.CreateForkOption{}
  83. req := NewRequestWithJSON(t, "POST", fmt.Sprintf("/api/v1/repos/%s/%s/forks?token=%s", username, ctx.Reponame, ctx.Token), createForkOption)
  84. if ctx.ExpectedCode != 0 {
  85. ctx.Session.MakeRequest(t, req, ctx.ExpectedCode)
  86. return
  87. }
  88. resp := ctx.Session.MakeRequest(t, req, http.StatusAccepted)
  89. var repository api.Repository
  90. DecodeJSON(t, resp, &repository)
  91. if len(callback) > 0 {
  92. callback[0](t, repository)
  93. }
  94. }
  95. }
  96. func doAPIGetRepository(ctx APITestContext, callback ...func(*testing.T, api.Repository)) func(*testing.T) {
  97. return func(t *testing.T) {
  98. urlStr := fmt.Sprintf("/api/v1/repos/%s/%s?token=%s", ctx.Username, ctx.Reponame, ctx.Token)
  99. req := NewRequest(t, "GET", urlStr)
  100. if ctx.ExpectedCode != 0 {
  101. ctx.Session.MakeRequest(t, req, ctx.ExpectedCode)
  102. return
  103. }
  104. resp := ctx.Session.MakeRequest(t, req, http.StatusOK)
  105. var repository api.Repository
  106. DecodeJSON(t, resp, &repository)
  107. if len(callback) > 0 {
  108. callback[0](t, repository)
  109. }
  110. }
  111. }
  112. func doAPIDeleteRepository(ctx APITestContext) func(*testing.T) {
  113. return func(t *testing.T) {
  114. urlStr := fmt.Sprintf("/api/v1/repos/%s/%s?token=%s", ctx.Username, ctx.Reponame, ctx.Token)
  115. req := NewRequest(t, "DELETE", urlStr)
  116. if ctx.ExpectedCode != 0 {
  117. ctx.Session.MakeRequest(t, req, ctx.ExpectedCode)
  118. return
  119. }
  120. ctx.Session.MakeRequest(t, req, http.StatusNoContent)
  121. }
  122. }
  123. func doAPICreateUserKey(ctx APITestContext, keyname, keyFile string, callback ...func(*testing.T, api.PublicKey)) func(*testing.T) {
  124. return func(t *testing.T) {
  125. urlStr := fmt.Sprintf("/api/v1/user/keys?token=%s", ctx.Token)
  126. dataPubKey, err := ioutil.ReadFile(keyFile + ".pub")
  127. assert.NoError(t, err)
  128. req := NewRequestWithJSON(t, "POST", urlStr, &api.CreateKeyOption{
  129. Title: keyname,
  130. Key: string(dataPubKey),
  131. })
  132. if ctx.ExpectedCode != 0 {
  133. ctx.Session.MakeRequest(t, req, ctx.ExpectedCode)
  134. return
  135. }
  136. resp := ctx.Session.MakeRequest(t, req, http.StatusCreated)
  137. var publicKey api.PublicKey
  138. DecodeJSON(t, resp, &publicKey)
  139. if len(callback) > 0 {
  140. callback[0](t, publicKey)
  141. }
  142. }
  143. }
  144. func doAPIDeleteUserKey(ctx APITestContext, keyID int64) func(*testing.T) {
  145. return func(t *testing.T) {
  146. urlStr := fmt.Sprintf("/api/v1/user/keys/%d?token=%s", keyID, ctx.Token)
  147. req := NewRequest(t, "DELETE", urlStr)
  148. if ctx.ExpectedCode != 0 {
  149. ctx.Session.MakeRequest(t, req, ctx.ExpectedCode)
  150. return
  151. }
  152. ctx.Session.MakeRequest(t, req, http.StatusNoContent)
  153. }
  154. }
  155. func doAPICreateDeployKey(ctx APITestContext, keyname, keyFile string, readOnly bool) func(*testing.T) {
  156. return func(t *testing.T) {
  157. urlStr := fmt.Sprintf("/api/v1/repos/%s/%s/keys?token=%s", ctx.Username, ctx.Reponame, ctx.Token)
  158. dataPubKey, err := ioutil.ReadFile(keyFile + ".pub")
  159. assert.NoError(t, err)
  160. req := NewRequestWithJSON(t, "POST", urlStr, api.CreateKeyOption{
  161. Title: keyname,
  162. Key: string(dataPubKey),
  163. ReadOnly: readOnly,
  164. })
  165. if ctx.ExpectedCode != 0 {
  166. ctx.Session.MakeRequest(t, req, ctx.ExpectedCode)
  167. return
  168. }
  169. ctx.Session.MakeRequest(t, req, http.StatusCreated)
  170. }
  171. }
  172. func doAPICreatePullRequest(ctx APITestContext, owner, repo, baseBranch, headBranch string) func(*testing.T) (api.PullRequest, error) {
  173. return func(t *testing.T) (api.PullRequest, error) {
  174. urlStr := fmt.Sprintf("/api/v1/repos/%s/%s/pulls?token=%s",
  175. owner, repo, ctx.Token)
  176. req := NewRequestWithJSON(t, http.MethodPost, urlStr, &api.CreatePullRequestOption{
  177. Head: headBranch,
  178. Base: baseBranch,
  179. Title: fmt.Sprintf("create a pr from %s to %s", headBranch, baseBranch),
  180. })
  181. expected := 201
  182. if ctx.ExpectedCode != 0 {
  183. expected = ctx.ExpectedCode
  184. }
  185. resp := ctx.Session.MakeRequest(t, req, expected)
  186. decoder := json.NewDecoder(resp.Body)
  187. pr := api.PullRequest{}
  188. err := decoder.Decode(&pr)
  189. return pr, err
  190. }
  191. }
  192. func doAPIMergePullRequest(ctx APITestContext, owner, repo string, index int64) func(*testing.T) {
  193. return func(t *testing.T) {
  194. urlStr := fmt.Sprintf("/api/v1/repos/%s/%s/pulls/%d/merge?token=%s",
  195. owner, repo, index, ctx.Token)
  196. req := NewRequestWithJSON(t, http.MethodPost, urlStr, &auth.MergePullRequestForm{
  197. MergeMessageField: "doAPIMergePullRequest Merge",
  198. Do: string(models.MergeStyleMerge),
  199. })
  200. if ctx.ExpectedCode != 0 {
  201. ctx.Session.MakeRequest(t, req, ctx.ExpectedCode)
  202. return
  203. }
  204. ctx.Session.MakeRequest(t, req, 200)
  205. }
  206. }
  207. func doAPIGetBranch(ctx APITestContext, branch string, callback ...func(*testing.T, api.Branch)) func(*testing.T) {
  208. return func(t *testing.T) {
  209. req := NewRequestf(t, "GET", "/api/v1/repos/%s/%s/branches/%s?token=%s", ctx.Username, ctx.Reponame, branch, ctx.Token)
  210. if ctx.ExpectedCode != 0 {
  211. ctx.Session.MakeRequest(t, req, ctx.ExpectedCode)
  212. return
  213. }
  214. resp := ctx.Session.MakeRequest(t, req, http.StatusOK)
  215. var branch api.Branch
  216. DecodeJSON(t, resp, &branch)
  217. if len(callback) > 0 {
  218. callback[0](t, branch)
  219. }
  220. }
  221. }
  222. func doAPICreateFile(ctx APITestContext, treepath string, options *api.CreateFileOptions, callback ...func(*testing.T, api.FileResponse)) func(*testing.T) {
  223. return func(t *testing.T) {
  224. url := fmt.Sprintf("/api/v1/repos/%s/%s/contents/%s?token=%s", ctx.Username, ctx.Reponame, treepath, ctx.Token)
  225. req := NewRequestWithJSON(t, "POST", url, &options)
  226. if ctx.ExpectedCode != 0 {
  227. ctx.Session.MakeRequest(t, req, ctx.ExpectedCode)
  228. return
  229. }
  230. resp := ctx.Session.MakeRequest(t, req, http.StatusCreated)
  231. var contents api.FileResponse
  232. DecodeJSON(t, resp, &contents)
  233. if len(callback) > 0 {
  234. callback[0](t, contents)
  235. }
  236. }
  237. }
  238. func doAPICreateOrganization(ctx APITestContext, options *api.CreateOrgOption, callback ...func(*testing.T, api.Organization)) func(t *testing.T) {
  239. return func(t *testing.T) {
  240. url := fmt.Sprintf("/api/v1/orgs?token=%s", ctx.Token)
  241. req := NewRequestWithJSON(t, "POST", url, &options)
  242. if ctx.ExpectedCode != 0 {
  243. ctx.Session.MakeRequest(t, req, ctx.ExpectedCode)
  244. return
  245. }
  246. resp := ctx.Session.MakeRequest(t, req, http.StatusCreated)
  247. var contents api.Organization
  248. DecodeJSON(t, resp, &contents)
  249. if len(callback) > 0 {
  250. callback[0](t, contents)
  251. }
  252. }
  253. }
  254. func doAPICreateOrganizationRepository(ctx APITestContext, orgName string, options *api.CreateRepoOption, callback ...func(*testing.T, api.Repository)) func(t *testing.T) {
  255. return func(t *testing.T) {
  256. url := fmt.Sprintf("/api/v1/orgs/%s/repos?token=%s", orgName, ctx.Token)
  257. req := NewRequestWithJSON(t, "POST", url, &options)
  258. if ctx.ExpectedCode != 0 {
  259. ctx.Session.MakeRequest(t, req, ctx.ExpectedCode)
  260. return
  261. }
  262. resp := ctx.Session.MakeRequest(t, req, http.StatusCreated)
  263. var contents api.Repository
  264. DecodeJSON(t, resp, &contents)
  265. if len(callback) > 0 {
  266. callback[0](t, contents)
  267. }
  268. }
  269. }
  270. func doAPICreateOrganizationTeam(ctx APITestContext, orgName string, options *api.CreateTeamOption, callback ...func(*testing.T, api.Team)) func(t *testing.T) {
  271. return func(t *testing.T) {
  272. url := fmt.Sprintf("/api/v1/orgs/%s/teams?token=%s", orgName, ctx.Token)
  273. req := NewRequestWithJSON(t, "POST", url, &options)
  274. if ctx.ExpectedCode != 0 {
  275. ctx.Session.MakeRequest(t, req, ctx.ExpectedCode)
  276. return
  277. }
  278. resp := ctx.Session.MakeRequest(t, req, http.StatusCreated)
  279. var contents api.Team
  280. DecodeJSON(t, resp, &contents)
  281. if len(callback) > 0 {
  282. callback[0](t, contents)
  283. }
  284. }
  285. }
  286. func doAPIAddUserToOrganizationTeam(ctx APITestContext, teamID int64, username string) func(t *testing.T) {
  287. return func(t *testing.T) {
  288. url := fmt.Sprintf("/api/v1/teams/%d/members/%s?token=%s", teamID, username, ctx.Token)
  289. req := NewRequest(t, "PUT", url)
  290. if ctx.ExpectedCode != 0 {
  291. ctx.Session.MakeRequest(t, req, ctx.ExpectedCode)
  292. return
  293. }
  294. ctx.Session.MakeRequest(t, req, http.StatusNoContent)
  295. }
  296. }
  297. func doAPIAddRepoToOrganizationTeam(ctx APITestContext, teamID int64, orgName, repoName string) func(t *testing.T) {
  298. return func(t *testing.T) {
  299. url := fmt.Sprintf("/api/v1/teams/%d/repos/%s/%s?token=%s", teamID, orgName, repoName, ctx.Token)
  300. req := NewRequest(t, "PUT", url)
  301. if ctx.ExpectedCode != 0 {
  302. ctx.Session.MakeRequest(t, req, ctx.ExpectedCode)
  303. return
  304. }
  305. ctx.Session.MakeRequest(t, req, http.StatusNoContent)
  306. }
  307. }