add:grouping the branches and sort by time
This commit is contained in:
parent
fdfe572500
commit
71df4fdfa1
|
@ -30,8 +30,19 @@ func ToEmail(email *models.EmailAddress) *api.Email {
|
|||
}
|
||||
}
|
||||
|
||||
type BranchKind int
|
||||
const (
|
||||
|
||||
None BranchKind = iota
|
||||
DefaultBranch
|
||||
ProtectedBranch
|
||||
OtherBranch
|
||||
)
|
||||
|
||||
// ToBranch convert a git.Commit and git.Branch to an api.Branch
|
||||
func ToBranch(repo *models.Repository, b *git.Branch, c *git.Commit, bp *models.ProtectedBranch, user *models.User, isRepoAdmin bool) (*api.Branch, error) {
|
||||
|
||||
var branchKind BranchKind
|
||||
if bp == nil {
|
||||
var hasPerm bool
|
||||
var err error
|
||||
|
@ -41,9 +52,15 @@ func ToBranch(repo *models.Repository, b *git.Branch, c *git.Commit, bp *models.
|
|||
return nil, err
|
||||
}
|
||||
}
|
||||
if b.Name == repo.DefaultBranch{
|
||||
branchKind = DefaultBranch
|
||||
}else{
|
||||
branchKind = OtherBranch
|
||||
}
|
||||
|
||||
return &api.Branch{
|
||||
Name: b.Name,
|
||||
CommitID: c.ID.String(), //add configure
|
||||
Commit: ToCommit(repo, c),
|
||||
Protected: false,
|
||||
RequiredApprovals: 0,
|
||||
|
@ -51,16 +68,28 @@ func ToBranch(repo *models.Repository, b *git.Branch, c *git.Commit, bp *models.
|
|||
StatusCheckContexts: []string{},
|
||||
UserCanPush: hasPerm,
|
||||
UserCanMerge: hasPerm,
|
||||
CommitTime: c.Author.When.Format(time.RFC3339),
|
||||
DefaultBranch: repo.DefaultBranch,
|
||||
BranchKind: int(branchKind),
|
||||
}, nil
|
||||
}
|
||||
if b.Name == repo.DefaultBranch{
|
||||
branchKind = DefaultBranch
|
||||
}else{
|
||||
branchKind = ProtectedBranch
|
||||
}
|
||||
|
||||
branch := &api.Branch{
|
||||
Name: b.Name,
|
||||
CommitID: c.ID.String(), // add configure
|
||||
Commit: ToCommit(repo, c),
|
||||
Protected: true,
|
||||
RequiredApprovals: bp.RequiredApprovals,
|
||||
EnableStatusCheck: bp.EnableStatusCheck,
|
||||
StatusCheckContexts: bp.StatusCheckContexts,
|
||||
CommitTime: c.Author.When.Format(time.RFC3339),
|
||||
DefaultBranch: repo.DefaultBranch,
|
||||
BranchKind: int(branchKind),
|
||||
}
|
||||
|
||||
if isRepoAdmin {
|
||||
|
|
|
@ -5,7 +5,10 @@
|
|||
package convert
|
||||
|
||||
import (
|
||||
"strings"
|
||||
"code.gitea.io/gitea/modules/setting"
|
||||
"code.gitea.io/gitea/modules/structs"
|
||||
|
||||
)
|
||||
|
||||
// ToCorrectPageSize makes sure page size is in allowed range.
|
||||
|
@ -17,3 +20,36 @@ func ToCorrectPageSize(size int) int {
|
|||
}
|
||||
return size
|
||||
}
|
||||
|
||||
|
||||
|
||||
// ToGitServiceType return GitServiceType based on string
|
||||
func ToGitServiceType(value string) structs.GitServiceType {
|
||||
switch strings.ToLower(value) {
|
||||
case "github":
|
||||
return structs.GithubService
|
||||
case "gitea":
|
||||
return structs.GiteaService
|
||||
case "gitlab":
|
||||
return structs.GitlabService
|
||||
case "gogs":
|
||||
return structs.GogsService
|
||||
default:
|
||||
return structs.PlainGitService
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
func ToBranchType(index int) structs.BranchKind{
|
||||
switch(index){
|
||||
case 1:
|
||||
return structs.DefaultBranch
|
||||
case 2:
|
||||
return structs.ProtectedBranch
|
||||
case 3:
|
||||
return structs.OtherBranch
|
||||
default:
|
||||
return structs.None
|
||||
}
|
||||
}
|
|
@ -5,12 +5,14 @@
|
|||
package structs
|
||||
|
||||
import (
|
||||
"strings"
|
||||
"time"
|
||||
)
|
||||
|
||||
// Branch represents a repository branch
|
||||
type Branch struct {
|
||||
Name string `json:"name"`
|
||||
CommitID string `json:"commit_id"` // add configure
|
||||
Commit *PayloadCommit `json:"commit"`
|
||||
Protected bool `json:"protected"`
|
||||
RequiredApprovals int64 `json:"required_approvals"`
|
||||
|
@ -19,7 +21,56 @@ type Branch struct {
|
|||
UserCanPush bool `json:"user_can_push"`
|
||||
UserCanMerge bool `json:"user_can_merge"`
|
||||
EffectiveBranchProtectionName string `json:"effective_branch_protection_name"`
|
||||
CommitTime string `json:"commit_time"` // add configure
|
||||
DefaultBranch string `json:"default_branch"`
|
||||
BranchKind int `json:"branch_kind"`
|
||||
}
|
||||
type BranchKind int
|
||||
const (
|
||||
|
||||
None BranchKind = iota
|
||||
DefaultBranch
|
||||
ProtectedBranch
|
||||
OtherBranch
|
||||
)
|
||||
func (bk BranchKind) Name() string{
|
||||
return strings.ToLower(bk.Title())
|
||||
}
|
||||
func (bk BranchKind) Title() string {
|
||||
switch bk {
|
||||
case DefaultBranch:
|
||||
return "default"
|
||||
case ProtectedBranch:
|
||||
return "protected"
|
||||
case OtherBranch:
|
||||
return "other"
|
||||
}
|
||||
return ""
|
||||
}
|
||||
|
||||
type BranchesSlice struct {
|
||||
|
||||
BranchName string `json:"branch_name"`
|
||||
// BranchKind int `json:"branch_kind"`
|
||||
Branches []Branch `json:"branches"`
|
||||
}
|
||||
|
||||
// sort by branchkind
|
||||
type SortBranch []Branch
|
||||
func (s SortBranch) Len() int { return len(s) }
|
||||
func (s SortBranch) Swap(i, j int) { s[i], s[j] = s[j], s[i] }
|
||||
func (s SortBranch) Less(i, j int) bool { return s[i].BranchKind < s[j].BranchKind}
|
||||
|
||||
// sort by CommiTime of the branch
|
||||
type SortBranchTime []Branch
|
||||
func (s SortBranchTime) Len() int { return len(s) }
|
||||
func (s SortBranchTime) Swap(i, j int) { s[i], s[j] = s[j], s[i] }
|
||||
func (s SortBranchTime) Less(i, j int) bool { return s[i].CommitTime > s[j].CommitTime}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
// BranchProtection represents a branch protection for a repository
|
||||
type BranchProtection struct {
|
||||
|
|
|
@ -6,6 +6,10 @@
|
|||
package repo
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"net/http"
|
||||
"sort"
|
||||
|
||||
"code.gitea.io/gitea/models"
|
||||
"code.gitea.io/gitea/modules/context"
|
||||
"code.gitea.io/gitea/modules/convert"
|
||||
|
@ -14,8 +18,6 @@ import (
|
|||
"code.gitea.io/gitea/modules/repofiles"
|
||||
repo_module "code.gitea.io/gitea/modules/repository"
|
||||
api "code.gitea.io/gitea/modules/structs"
|
||||
"fmt"
|
||||
"net/http"
|
||||
)
|
||||
|
||||
// GetBranch get a branch of a repository
|
||||
|
@ -45,8 +47,6 @@ func GetBranch(ctx *context.APIContext) {
|
|||
// "200":
|
||||
// "$ref": "#/responses/Branch"
|
||||
|
||||
|
||||
|
||||
if ctx.Repo.TreePath != "" {
|
||||
// if TreePath != "", then URL contained extra slashes
|
||||
// (i.e. "master/subbranch" instead of "master"), so branch does
|
||||
|
@ -328,6 +328,92 @@ func ListBranches(ctx *context.APIContext) {
|
|||
ctx.JSON(http.StatusOK, &apiBranches)
|
||||
}
|
||||
|
||||
// ListBranches list all the branches of a repository
|
||||
func ListBranchesSlice(ctx *context.APIContext) {
|
||||
// swagger:operation GET /repos/{owner}/{repo}/branches/branches_slice repository repoListBranches
|
||||
// ---
|
||||
// summary: List a repository's branches, Group sort.
|
||||
// produces:
|
||||
// - application/json
|
||||
// parameters:
|
||||
// - name: owner
|
||||
// in: path
|
||||
// description: owner of the repo
|
||||
// type: string
|
||||
// required: true
|
||||
// - name: repo
|
||||
// in: path
|
||||
// description: name of the repo
|
||||
// type: string
|
||||
// required: true
|
||||
// responses:
|
||||
// "200":
|
||||
// "$ref": "#/responses/BranchList"
|
||||
|
||||
//start:=time.Now()
|
||||
branches, err := repo_module.GetBranches(ctx.Repo.Repository)
|
||||
if err != nil {
|
||||
ctx.Error(http.StatusInternalServerError, "GetBranches", err)
|
||||
return
|
||||
}
|
||||
//fmt.Println("***************** *GetBranches:",time.Now().Sub(start)," ",branches,len(branches))
|
||||
|
||||
apiBranches := make([]*api.Branch, len(branches))
|
||||
|
||||
// add configure
|
||||
apiBranchesList := []api.Branch{}
|
||||
for i := range branches {
|
||||
c, err := branches[i].GetCommit()
|
||||
if err != nil {
|
||||
ctx.Error(http.StatusInternalServerError, "GetCommit", err)
|
||||
return
|
||||
}
|
||||
//fmt.Println("****branches[i]:",branches[i])
|
||||
branchProtection, err := ctx.Repo.Repository.GetBranchProtection(branches[i].Name)
|
||||
if err != nil {
|
||||
ctx.Error(http.StatusInternalServerError, "GetBranchProtection", err)
|
||||
return
|
||||
}
|
||||
//fmt.Println("****branchProtection:",branchProtection)
|
||||
apiBranches[i], err = convert.ToBranch(ctx.Repo.Repository, branches[i], c, branchProtection, ctx.User, ctx.Repo.IsAdmin())
|
||||
if err != nil {
|
||||
ctx.Error(http.StatusInternalServerError, "convert.ToBranch", err)
|
||||
return
|
||||
}
|
||||
apiBranchesList = append(apiBranchesList, *apiBranches[i])
|
||||
//fmt.Println("****apiBranches[i]:",apiBranches[i])
|
||||
}
|
||||
|
||||
ctx.JSON(http.StatusOK, BranchesSliceByProtection(ctx, apiBranchesList))
|
||||
}
|
||||
|
||||
// branches slice. Group by protection
|
||||
|
||||
func BranchesSliceByProtection(ctx *context.APIContext, branchList []api.Branch) []api.BranchesSlice {
|
||||
// group by protection
|
||||
sort.Sort(api.SortBranch(branchList))
|
||||
branchSlice := make([]api.BranchesSlice, 0)
|
||||
i := 0
|
||||
var j int
|
||||
for {
|
||||
if i >= len(branchList) {
|
||||
break
|
||||
}
|
||||
for j = i + 1; j < len(branchList) && (branchList[i].BranchKind == branchList[j].BranchKind); j++ {
|
||||
}
|
||||
// get the same branches
|
||||
sameBranchSlice := branchList[i:j]
|
||||
// sort by time
|
||||
sort.Sort(api.SortBranchTime(sameBranchSlice))
|
||||
branchSlice = append(branchSlice, api.BranchesSlice{
|
||||
BranchName: convert.ToBranchType(branchList[i].BranchKind).Name(),
|
||||
Branches: sameBranchSlice,
|
||||
})
|
||||
i = j
|
||||
}
|
||||
return branchSlice
|
||||
}
|
||||
|
||||
// GetBranchProtection gets a branch protection
|
||||
func GetBranchProtection(ctx *context.APIContext) {
|
||||
// swagger:operation GET /repos/{owner}/{repo}/branch_protections/{name} repository repoGetBranchProtection
|
||||
|
|
Loading…
Reference in New Issue