John Olheiser
5ecbcde518
Some checks reported errors
continuous-integration/drone/push Build encountered an error
Fix YAML New changes, generate docs, and add Drone for main Signed-off-by: jolheiser <john.olheiser@gmail.com> Merge branch 'master' of gitea.com:jolheiser/sip into vanity Change to vanity URL Signed-off-by: jolheiser <john.olheiser@gmail.com> Co-authored-by: jolheiser <john.olheiser@gmail.com> Reviewed-on: #37
152 lines
3.8 KiB
Go
152 lines
3.8 KiB
Go
package cmd
|
|
|
|
import (
|
|
"fmt"
|
|
"strings"
|
|
|
|
"go.jolheiser.com/sip/flag"
|
|
"go.jolheiser.com/sip/git"
|
|
"go.jolheiser.com/sip/markdown"
|
|
|
|
"code.gitea.io/sdk/gitea"
|
|
"github.com/AlecAivazis/survey/v2"
|
|
"github.com/urfave/cli/v2"
|
|
"go.jolheiser.com/beaver/color"
|
|
)
|
|
|
|
var PullsCreate = cli.Command{
|
|
Name: "create",
|
|
Aliases: []string{"new"},
|
|
Usage: "Create a new pull request",
|
|
Action: doPullCreate,
|
|
}
|
|
|
|
func doPullCreate(_ *cli.Context) error {
|
|
fmt.Println()
|
|
url := color.New(color.FgYellow).Format(flag.FullURL())
|
|
fmt.Println(color.New(color.FgCyan).Format("Creating a new pull request for"), url)
|
|
|
|
client, err := getClient(true)
|
|
if err != nil {
|
|
return err
|
|
}
|
|
|
|
repo, _, err := client.GetRepo(flag.Upstream.Owner, flag.Upstream.Repo)
|
|
if err != nil {
|
|
return err
|
|
}
|
|
|
|
upstreams, _, err := client.ListRepoBranches(flag.Upstream.Owner, flag.Upstream.Repo, gitea.ListRepoBranchesOptions{})
|
|
if err != nil {
|
|
return err
|
|
}
|
|
bases := make([]string, len(upstreams))
|
|
defUpstream := repo.DefaultBranch
|
|
for idx, upstream := range upstreams {
|
|
bases[idx] = upstream.Name
|
|
}
|
|
|
|
origins, _, err := client.ListRepoBranches(flag.Origin.Owner, flag.Origin.Repo, gitea.ListRepoBranchesOptions{})
|
|
if err != nil {
|
|
return err
|
|
}
|
|
heads := make([]string, len(origins))
|
|
defOrigin := origins[0].Name
|
|
for idx, origin := range origins {
|
|
originName := origin.Name
|
|
if flag.Owner != flag.Origin.Owner {
|
|
originName = flag.Origin.Owner + ":" + originName
|
|
}
|
|
if strings.EqualFold(origin.Name, git.Branch()) {
|
|
defOrigin = originName
|
|
}
|
|
heads[idx] = originName
|
|
}
|
|
|
|
var confirmed bool
|
|
var title, body string
|
|
base := defUpstream
|
|
head := defOrigin
|
|
|
|
for !confirmed {
|
|
questions := []*survey.Question{
|
|
{
|
|
Name: "title",
|
|
Prompt: &survey.Input{Message: "Title", Default: title},
|
|
Validate: survey.Required,
|
|
},
|
|
{
|
|
Name: "body",
|
|
Prompt: &survey.Multiline{Message: "Description", Default: body},
|
|
},
|
|
{
|
|
Name: "base",
|
|
Prompt: &survey.Select{Message: "Base target", Options: bases, Default: base},
|
|
Validate: survey.Required,
|
|
},
|
|
{
|
|
Name: "head",
|
|
Prompt: &survey.Select{Message: "Head target", Options: heads, Default: head},
|
|
Validate: survey.Required,
|
|
},
|
|
}
|
|
answers := struct {
|
|
Title string
|
|
Body string
|
|
Base string
|
|
Head string
|
|
}{}
|
|
|
|
if err := survey.Ask(questions, &answers); err != nil {
|
|
return err
|
|
}
|
|
title = answers.Title
|
|
body = answers.Body
|
|
base = answers.Base
|
|
head = answers.Head
|
|
|
|
preview, err := markdown.Render(body)
|
|
if err != nil {
|
|
return err
|
|
}
|
|
|
|
fmt.Printf("%s\n\n%s\n", title, preview)
|
|
confirm := &survey.Confirm{Message: "Preview above, enter to create or 'n' to edit", Default: true}
|
|
|
|
if err := survey.AskOne(confirm, &confirmed); err != nil {
|
|
return err
|
|
}
|
|
}
|
|
|
|
pull, _, err := client.CreatePullRequest(flag.Owner, flag.Repo, gitea.CreatePullRequestOption{Title: title, Body: body, Base: base, Head: head})
|
|
if err != nil {
|
|
if fmt.Sprint(err) == "409 Conflict" { // Hard-coded in the SDK
|
|
return existingPR(client, flag.Upstream.Owner, flag.Upstream.Repo, head, err)
|
|
}
|
|
return err
|
|
}
|
|
|
|
info := color.Info
|
|
cyan := color.New(color.FgCyan)
|
|
fmt.Println(info.Format("PR"), cyan.Format(fmt.Sprintf("#%d", pull.Index)), info.Format("created!"))
|
|
fmt.Println(cyan.Format(fmt.Sprintf("%s/pulls/%d", flag.FullURL(), pull.Index)))
|
|
return nil
|
|
}
|
|
|
|
func existingPR(client *gitea.Client, owner, repo, head string, pullErr error) error {
|
|
pulls, _, err := client.ListRepoPullRequests(owner, repo, gitea.ListPullRequestsOptions{State: "open"})
|
|
if err != nil {
|
|
return err
|
|
}
|
|
|
|
for _, pull := range pulls {
|
|
compare := fmt.Sprintf("%s:%s", pull.Head.Repository.Owner.UserName, pull.Head.Name)
|
|
if compare == head {
|
|
fmt.Println(color.New(color.FgCyan).Format("PR already exists at"), color.New(color.FgYellow).Format(pull.HTMLURL))
|
|
return nil
|
|
}
|
|
}
|
|
|
|
return pullErr
|
|
}
|