github.com/gfleury/gobbs@v0.0.0-20200831213239-44ca2b94c1a1/pullrequests/merge.go (about)

     1  package pullrequests
     2  
     3  import (
     4  	"context"
     5  	"errors"
     6  	"fmt"
     7  	"net"
     8  	"net/http"
     9  	"strconv"
    10  	"time"
    11  
    12  	"github.com/gfleury/gobbs/common"
    13  	"github.com/gfleury/gobbs/common/log"
    14  
    15  	bitbucketv1 "github.com/gfleury/go-bitbucket-v1"
    16  	"github.com/spf13/cobra"
    17  )
    18  
    19  // Merge is the cmd implementation for Merging Pull Requests
    20  var Merge = &cobra.Command{
    21  	Use:     "merge pullRequestID",
    22  	Aliases: []string{"mer"},
    23  	Short:   "Merge pull requests for repository",
    24  	Args:    cobra.MinimumNArgs(1),
    25  	RunE: func(cmd *cobra.Command, args []string) error {
    26  		prID, err := strconv.Atoi(args[0])
    27  		if err != nil {
    28  			log.Critical("Argument must be a pull request ID. Err: %s", err.Error())
    29  			return err
    30  		}
    31  
    32  		apiClient, cancel, err := common.APIClient(cmd)
    33  		defer cancel()
    34  
    35  		if err != nil {
    36  			return err
    37  		}
    38  
    39  		stashInfo := cmd.Context().Value(common.StashInfoKey).(*common.StashInfo)
    40  		err = mustHaveProjectRepo(stashInfo)
    41  		if err != nil {
    42  			return err
    43  		}
    44  
    45  		opts := map[string]interface{}{
    46  			"version": int32(*prVersion),
    47  		}
    48  
    49  		response, err := apiClient.DefaultApi.Merge(*stashInfo.Project(), *stashInfo.Repo(), prID, opts, nil, []string{"application/json"})
    50  
    51  		if netError, ok := err.(net.Error); (!ok || (ok && !netError.Timeout())) &&
    52  			!errors.Is(err, context.Canceled) &&
    53  			!errors.Is(err, context.DeadlineExceeded) &&
    54  			response != nil && response.Response != nil &&
    55  			response.Response.StatusCode >= http.StatusMultipleChoices {
    56  			common.PrintApiError(response.Values)
    57  			cmd.SilenceUsage = true
    58  			log.Debugf(err.Error())
    59  			return fmt.Errorf("Unable to process request, API Error")
    60  		} else if err != nil {
    61  			cmd.SilenceUsage = true
    62  			return err
    63  		}
    64  
    65  		if response.StatusCode == http.StatusNoContent {
    66  			log.Infof("Pull request ID: %v sucessfully MERGED.", prID)
    67  		}
    68  
    69  		pr, err := bitbucketv1.GetPullRequestResponse(response)
    70  		if err != nil {
    71  			log.Critical("Argument must be a pull request ID. Err: %s", err.Error())
    72  			return err
    73  		}
    74  
    75  		header := []string{"ID", "State", "Updated", "Result", "Tasks Resolv. / Done", "Short Desc.", "Reviewers"}
    76  		table := common.Table(header)
    77  
    78  		table.Append([]string{
    79  			fmt.Sprintf("%d", pr.ID),
    80  			pr.State,
    81  			fmt.Sprint(time.Unix(pr.UpdatedDate/1000, 0).Format("2006-01-02T15:04:05-0700")),
    82  			pr.Properties.MergeResult.Outcome,
    83  			fmt.Sprintf("%d / %d", pr.Properties.OpenTaskCount, pr.Properties.ResolvedTaskCount),
    84  			fmt.Sprintf("[%s -> %s] %s", pr.FromRef.DisplayID, pr.ToRef.DisplayID, pr.Title),
    85  			func() (r string) {
    86  				for _, reviewer := range pr.Reviewers {
    87  					r = fmt.Sprintf("%s%s %s\n", r, reviewer.User.Name,
    88  						func() string {
    89  							if reviewer.Approved {
    90  								return "(A)"
    91  							}
    92  							return "( )"
    93  						}())
    94  				}
    95  				return
    96  			}(),
    97  		})
    98  		table.Render()
    99  
   100  		return nil
   101  	},
   102  }