WIP: Add admin function for unadopted repositories #490
|
@ -102,6 +102,12 @@ type DismissPullReviewOptions struct {
|
|||
Message string `json:"message"`
|
||||
}
|
||||
|
||||
// PullReviewRequestOptions are options to add or remove pull review requests
|
||||
type PullReviewRequestOptions struct {
|
||||
Reviewers []string `json:"reviewers"`
|
||||
TeamReviewers []string `json:"team_reviewers"`
|
||||
}
|
||||
|
||||
// ListPullReviewsOptions options for listing PullReviews
|
||||
type ListPullReviewsOptions struct {
|
||||
ListOptions
|
||||
|
@ -227,6 +233,38 @@ func (c *Client) SubmitPullReview(owner, repo string, index, id int64, opt Submi
|
|||
return r, resp, err
|
||||
}
|
||||
|
||||
// CreateReviewRequests create review requests to an pull request
|
||||
func (c *Client) CreateReviewRequests(owner, repo string, index int64, opt PullReviewRequestOptions) (*Response, error) {
|
||||
if err := c.checkServerVersionGreaterThanOrEqual(version1_14_0); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
body, err := json.Marshal(&opt)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
_, resp, err := c.getResponse("POST",
|
||||
fmt.Sprintf("/repos/%s/%s/pulls/%d/requested_reviewers", owner, repo, index),
|
||||
jsonHeader, bytes.NewReader(body))
|
||||
return resp, err
|
||||
}
|
||||
|
||||
// DeleteReviewRequests delete review requests to an pull request
|
||||
func (c *Client) DeleteReviewRequests(owner, repo string, index int64, opt PullReviewRequestOptions) (*Response, error) {
|
||||
if err := c.checkServerVersionGreaterThanOrEqual(version1_14_0); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
body, err := json.Marshal(&opt)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
_, resp, err := c.getResponse("DELETE",
|
||||
fmt.Sprintf("/repos/%s/%s/pulls/%d/requested_reviewers", owner, repo, index),
|
||||
jsonHeader, bytes.NewReader(body))
|
||||
return resp, err
|
||||
}
|
||||
|
||||
// DismissPullReview dismiss a review for a pull request
|
||||
func (c *Client) DismissPullReview(owner, repo string, index, id int64, opt DismissPullReviewOptions) (*Response, error) {
|
||||
if err := c.checkServerVersionGreaterThanOrEqual(version1_14_0); err != nil {
|
||||
|
|
|
@ -20,8 +20,6 @@ func TestPullReview(t *testing.T) {
|
|||
if !success {
|
||||
return
|
||||
}
|
||||
defer c.AdminDeleteUser(reviewer.UserName)
|
||||
defer c.AdminDeleteUser(submitter.UserName)
|
||||
|
||||
// CreatePullReview
|
||||
r1, _, err := c.CreatePullReview(repo.Owner.UserName, repo.Name, pull.Index, CreatePullReviewOptions{
|
||||
|
@ -64,9 +62,7 @@ func TestPullReview(t *testing.T) {
|
|||
// ListPullReviews
|
||||
c.SetSudo("")
|
||||
rl, _, err := c.ListPullReviews(repo.Owner.UserName, repo.Name, pull.Index, ListPullReviewsOptions{})
|
||||
if !assert.NoError(t, err) {
|
||||
return
|
||||
}
|
||||
assert.NoError(t, err)
|
||||
assert.Len(t, rl, 3)
|
||||
for i := range rl {
|
||||
assert.EqualValues(t, pull.HTMLURL, rl[i].HTMLPullURL)
|
||||
|
@ -155,6 +151,34 @@ func TestPullReview(t *testing.T) {
|
|||
}
|
||||
r, _, _ = c.GetPullReview(repo.Owner.UserName, repo.Name, pull.Index, r.ID)
|
||||
assert.False(t, r.Dismissed)
|
||||
|
||||
rl, _, err = c.ListPullReviews(repo.Owner.UserName, repo.Name, pull.Index, ListPullReviewsOptions{})
|
||||
assert.NoError(t, err)
|
||||
assert.Len(t, rl, 3)
|
||||
|
||||
c.SetSudo(submitter.UserName)
|
||||
resp, err = c.CreateReviewRequests(repo.Owner.UserName, repo.Name, pull.Index, PullReviewRequestOptions{Reviewers: []string{reviewer.UserName}})
|
||||
assert.NoError(t, err)
|
||||
assert.NotNil(t, resp)
|
||||
|
||||
rl, _, _ = c.ListPullReviews(repo.Owner.UserName, repo.Name, pull.Index, ListPullReviewsOptions{})
|
||||
if assert.Len(t, rl, 4) {
|
||||
assert.EqualValues(t, ReviewStateRequestReview, rl[3].State)
|
||||
}
|
||||
|
||||
c.SetSudo(reviewer.UserName)
|
||||
resp, err = c.DeleteReviewRequests(repo.Owner.UserName, repo.Name, pull.Index, PullReviewRequestOptions{Reviewers: []string{reviewer.UserName}})
|
||||
assert.NoError(t, err)
|
||||
assert.NotNil(t, resp)
|
||||
|
||||
rl, _, _ = c.ListPullReviews(repo.Owner.UserName, repo.Name, pull.Index, ListPullReviewsOptions{})
|
||||
assert.Len(t, rl, 3)
|
||||
|
||||
c.SetSudo("")
|
||||
_, err = c.AdminDeleteUser(reviewer.UserName)
|
||||
assert.NoError(t, err)
|
||||
_, err = c.AdminDeleteUser(submitter.UserName)
|
||||
assert.NoError(t, err)
|
||||
}
|
||||
|
||||
func preparePullReviewTest(t *testing.T, c *Client, repoName string) (*Repository, *PullRequest, *User, *User, bool) {
|
||||
|
|
|
@ -9,6 +9,7 @@ import (
|
|||
"bytes"
|
||||
"encoding/json"
|
||||
"fmt"
|
||||
"net/url"
|
||||
"strings"
|
||||
)
|
||||
|
||||
|
@ -115,32 +116,63 @@ type FileDeleteResponse struct {
|
|||
Verification *PayloadCommitVerification `json:"verification"`
|
||||
}
|
||||
|
||||
// pathEscapeSegments escapes segments of a path while not escaping forward slash
|
||||
func pathEscapeSegments(path string) string {
|
||||
slice := strings.Split(path, "/")
|
||||
for index := range slice {
|
||||
slice[index] = url.PathEscape(slice[index])
|
||||
}
|
||||
escapedPath := strings.Join(slice, "/")
|
||||
return escapedPath
|
||||
}
|
||||
|
||||
// GetFile downloads a file of repository, ref can be branch/tag/commit.
|
||||
// e.g.: ref -> master, tree -> macaron.go(no leading slash)
|
||||
func (c *Client) GetFile(user, repo, ref, tree string) ([]byte, *Response, error) {
|
||||
return c.getResponse("GET", fmt.Sprintf("/repos/%s/%s/raw/%s/%s", user, repo, ref, tree), nil, nil)
|
||||
// e.g.: ref -> master, filepath -> README.md (no leading slash)
|
||||
func (c *Client) GetFile(owner, repo, ref, filepath string) ([]byte, *Response, error) {
|
||||
filepath = pathEscapeSegments(filepath)
|
||||
if c.checkServerVersionGreaterThanOrEqual(version1_14_0) != nil {
|
||||
ref = pathEscapeSegments(ref)
|
||||
return c.getResponse("GET", fmt.Sprintf("/repos/%s/%s/raw/%s/%s", owner, repo, ref, filepath), nil, nil)
|
||||
}
|
||||
return c.getResponse("GET", fmt.Sprintf("/repos/%s/%s/raw/%s?ref=%s", owner, repo, filepath, url.QueryEscape(ref)), nil, nil)
|
||||
}
|
||||
|
||||
// GetContents get the metadata and contents of a file in a repository
|
||||
// ref is optional
|
||||
func (c *Client) GetContents(owner, repo, ref, filepath string) (*ContentsResponse, *Response, error) {
|
||||
data, resp, err := c.getDirOrFileContents(owner, repo, ref, filepath)
|
||||
if err != nil {
|
||||
return nil, resp, err
|
||||
}
|
||||
cr := new(ContentsResponse)
|
||||
filepath = strings.TrimPrefix(filepath, "/")
|
||||
resp, err := c.getParsedResponse("GET", fmt.Sprintf("/repos/%s/%s/contents/%s?ref=%s", owner, repo, filepath, ref), jsonHeader, nil, cr)
|
||||
if json.Unmarshal(data, &cr) != nil {
|
||||
return nil, resp, fmt.Errorf("expect file, got directory")
|
||||
}
|
||||
return cr, resp, err
|
||||
}
|
||||
|
||||
// ListContents gets a list of entries in a dir
|
||||
// ref is optional
|
||||
func (c *Client) ListContents(owner, repo, ref, filepath string) ([]*ContentsResponse, *Response, error) {
|
||||
cr := make([]*ContentsResponse, 0)
|
||||
filepath = strings.TrimPrefix(filepath, "/")
|
||||
resp, err := c.getParsedResponse("GET", fmt.Sprintf("/repos/%s/%s/contents/%s?ref=%s", owner, repo, filepath, ref), jsonHeader, nil, &cr)
|
||||
return cr, resp, err
|
||||
data, resp, err := c.getDirOrFileContents(owner, repo, ref, filepath)
|
||||
if err != nil {
|
||||
return nil, resp, err
|
||||
}
|
||||
crl := make([]*ContentsResponse, 0)
|
||||
if json.Unmarshal(data, &crl) != nil {
|
||||
return nil, resp, fmt.Errorf("expect directory, got file")
|
||||
}
|
||||
return crl, resp, err
|
||||
}
|
||||
|
||||
func (c *Client) getDirOrFileContents(owner, repo, ref, filepath string) ([]byte, *Response, error) {
|
||||
filepath = pathEscapeSegments(strings.TrimPrefix(filepath, "/"))
|
||||
return c.getResponse("GET", fmt.Sprintf("/repos/%s/%s/contents/%s?ref=%s", owner, repo, filepath, url.QueryEscape(ref)), jsonHeader, nil)
|
||||
}
|
||||
|
||||
// CreateFile create a file in a repository
|
||||
func (c *Client) CreateFile(owner, repo, filepath string, opt CreateFileOptions) (*FileResponse, *Response, error) {
|
||||
filepath = pathEscapeSegments(filepath)
|
||||
var err error
|
||||
if opt.BranchName, err = c.setDefaultBranchForOldVersions(owner, repo, opt.BranchName); err != nil {
|
||||
return nil, nil, err
|
||||
|
@ -157,6 +189,7 @@ func (c *Client) CreateFile(owner, repo, filepath string, opt CreateFileOptions)
|
|||
|
||||
// UpdateFile update a file in a repository
|
||||
func (c *Client) UpdateFile(owner, repo, filepath string, opt UpdateFileOptions) (*FileResponse, *Response, error) {
|
||||
filepath = pathEscapeSegments(filepath)
|
||||
var err error
|
||||
if opt.BranchName, err = c.setDefaultBranchForOldVersions(owner, repo, opt.BranchName); err != nil {
|
||||
return nil, nil, err
|
||||
|
@ -173,6 +206,7 @@ func (c *Client) UpdateFile(owner, repo, filepath string, opt UpdateFileOptions)
|
|||
|
||||
// DeleteFile delete a file from repository
|
||||
func (c *Client) DeleteFile(owner, repo, filepath string, opt DeleteFileOptions) (*Response, error) {
|
||||
filepath = pathEscapeSegments(filepath)
|
||||
var err error
|
||||
if opt.BranchName, err = c.setDefaultBranchForOldVersions(owner, repo, opt.BranchName); err != nil {
|
||||
return nil, err
|
||||
|
|
|
@ -5,6 +5,7 @@
|
|||
package gitea
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"encoding/base64"
|
||||
"log"
|
||||
"testing"
|
||||
|
@ -24,17 +25,18 @@ func TestFileCreateUpdateGet(t *testing.T) {
|
|||
assert.NoError(t, err)
|
||||
assert.EqualValues(t, "IyBDaGFuZ2VGaWxlcwoKQSB0ZXN0IFJlcG86IENoYW5nZUZpbGVz", base64.StdEncoding.EncodeToString(raw))
|
||||
|
||||
newFile, _, err := c.CreateFile(repo.Owner.UserName, repo.Name, "A", CreateFileOptions{
|
||||
testFileName := "A+#&ä"
|
||||
newFile, _, err := c.CreateFile(repo.Owner.UserName, repo.Name, testFileName, CreateFileOptions{
|
||||
FileOptions: FileOptions{
|
||||
Message: "create file A",
|
||||
Message: "create file " + testFileName,
|
||||
},
|
||||
Content: "ZmlsZUEK",
|
||||
})
|
||||
assert.NoError(t, err)
|
||||
raw, _, _ = c.GetFile(repo.Owner.UserName, repo.Name, "master", "A")
|
||||
raw, _, _ = c.GetFile(repo.Owner.UserName, repo.Name, "master", testFileName)
|
||||
assert.EqualValues(t, "ZmlsZUEK", base64.StdEncoding.EncodeToString(raw))
|
||||
|
||||
updatedFile, _, err := c.UpdateFile(repo.Owner.UserName, repo.Name, "A", UpdateFileOptions{
|
||||
updatedFile, _, err := c.UpdateFile(repo.Owner.UserName, repo.Name, testFileName, UpdateFileOptions{
|
||||
FileOptions: FileOptions{
|
||||
Message: "add a new line",
|
||||
},
|
||||
|
@ -44,18 +46,71 @@ func TestFileCreateUpdateGet(t *testing.T) {
|
|||
assert.NoError(t, err)
|
||||
assert.NotNil(t, updatedFile)
|
||||
|
||||
file, _, err := c.GetContents(repo.Owner.UserName, repo.Name, "master", "A")
|
||||
file, _, err := c.GetContents(repo.Owner.UserName, repo.Name, "master", testFileName)
|
||||
assert.NoError(t, err)
|
||||
assert.EqualValues(t, updatedFile.Content.SHA, file.SHA)
|
||||
assert.EqualValues(t, &updatedFile.Content.Content, &file.Content)
|
||||
|
||||
_, err = c.DeleteFile(repo.Owner.UserName, repo.Name, "A", DeleteFileOptions{
|
||||
_, err = c.DeleteFile(repo.Owner.UserName, repo.Name, testFileName, DeleteFileOptions{
|
||||
FileOptions: FileOptions{
|
||||
Message: "Delete File A",
|
||||
Message: "Delete File " + testFileName,
|
||||
},
|
||||
SHA: updatedFile.Content.SHA,
|
||||
})
|
||||
assert.NoError(t, err)
|
||||
_, _, err = c.GetFile(repo.Owner.UserName, repo.Name, "master", "A")
|
||||
assert.EqualValues(t, "404 Not Found", err.Error())
|
||||
_, resp, err := c.GetFile(repo.Owner.UserName, repo.Name, "master", testFileName)
|
||||
assert.Error(t, err)
|
||||
assert.EqualValues(t, 404, resp.StatusCode)
|
||||
|
||||
licence, _, err := c.GetContents(repo.Owner.UserName, repo.Name, "", "LICENSE")
|
||||
assert.NoError(t, err)
|
||||
licenceRaw, _, err := c.GetFile(repo.Owner.UserName, repo.Name, "", "LICENSE")
|
||||
testContent := "Tk9USElORyBJUyBIRVJFIEFOWU1PUkUKSUYgWU9VIExJS0UgVE8gRklORCBTT01FVEhJTkcKV0FJVCBGT1IgVEhFIEZVVFVSRQo="
|
||||
updatedFile, _, err = c.UpdateFile(repo.Owner.UserName, repo.Name, "LICENSE", UpdateFileOptions{
|
||||
FileOptions: FileOptions{
|
||||
Message: "Overwrite",
|
||||
BranchName: "master",
|
||||
NewBranchName: "overwrite-a+/&licence",
|
||||
},
|
||||
SHA: licence.SHA,
|
||||
Content: testContent,
|
||||
})
|
||||
assert.NoError(t, err)
|
||||
assert.NotNil(t, updatedFile)
|
||||
licenceRawNew, _, err := c.GetFile(repo.Owner.UserName, repo.Name, "overwrite-a+/&licence", "LICENSE")
|
||||
assert.NoError(t, err)
|
||||
assert.NotNil(t, licence)
|
||||
assert.False(t, bytes.Equal(licenceRaw, licenceRawNew))
|
||||
assert.EqualValues(t, testContent, base64.StdEncoding.EncodeToString(licenceRawNew))
|
||||
|
||||
// ListContents in root dir of default branch
|
||||
dir, resp, err := c.ListContents(repo.Owner.UserName, repo.Name, "", "")
|
||||
assert.NoError(t, err)
|
||||
assert.Len(t, dir, 3)
|
||||
assert.NotNil(t, resp)
|
||||
|
||||
// ListContents in not existing dir of default branch
|
||||
_, resp, err = c.ListContents(repo.Owner.UserName, repo.Name, "", "/hehe/")
|
||||
assert.Error(t, err)
|
||||
assert.EqualValues(t, 404, resp.StatusCode)
|
||||
// ListContents in root dir of not existing branch
|
||||
_, resp, err = c.ListContents(repo.Owner.UserName, repo.Name, "no-ref-at-all", "")
|
||||
assert.Error(t, err)
|
||||
assert.EqualValues(t, 404, resp.StatusCode)
|
||||
|
||||
// ListContents try to get file as dir
|
||||
dir, resp, err = c.ListContents(repo.Owner.UserName, repo.Name, "", "LICENSE")
|
||||
if assert.Error(t, err) {
|
||||
assert.EqualValues(t, "expect directory, got file", err.Error())
|
||||
}
|
||||
assert.Nil(t, dir)
|
||||
assert.EqualValues(t, 200, resp.StatusCode)
|
||||
|
||||
// GetContents try to get dir as file
|
||||
file, resp, err = c.GetContents(repo.Owner.UserName, repo.Name, "", "")
|
||||
if assert.Error(t, err) {
|
||||
assert.EqualValues(t, "expect file, got directory", err.Error())
|
||||
}
|
||||
assert.Nil(t, file)
|
||||
assert.EqualValues(t, 200, resp.StatusCode)
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue
Block a user