frag-review/src/cmd/patch.go

120 lines
2.9 KiB
Go
Raw Normal View History

package cmd
import (
"bufio"
"bytes"
"errors"
"fmt"
"os"
"os/exec"
"strings"
"code.gitea.io/sdk/gitea"
"github.com/spf13/cobra"
"git.mfocko.xyz/mfocko/frag-review/core"
)
var (
prID int64
branch string
patchCmd = &cobra.Command{
Use: "patch",
Short: "Patches the source files with comments from PR review.",
PreRun: InitializeConfig,
Run: func(cmd *cobra.Command, args []string) {
client, err := gitea.NewClient(config.Gitea.InstanceURL, gitea.SetToken(config.Gitea.Token))
core.ExitOnError("Couldn't create gitea client", err)
err = GetPrID(client, &prID)
core.ExitOnError("Couldn't get PR ID", err)
comments := core.GetComments(&config, client, prID)
core.ProcessComments(&config, &comments)
PatchFiles(comments)
},
}
)
func init() {
patchCmd.Flags().Int64VarP(&prID, "prID", "p", -1, "specifies ID of pull request containing changes")
patchCmd.Flags().StringVarP(&branch, "branch", "b", "", "specifies branch where the review is present")
}
func GetPrID(client *gitea.Client, prID *int64) error {
if *prID != -1 {
return nil
}
if branch == "" {
gitCmd := exec.Command("git", "branch", "--show-current")
var capturedOutput bytes.Buffer
gitCmd.Stdout = &capturedOutput
err := gitCmd.Run()
core.ExitOnError("Couldn't list git branches", err)
branch = strings.TrimSpace(capturedOutput.String())
}
prs, _, err := client.ListRepoPullRequests(
config.Gitea.Owner, config.Gitea.Repository, gitea.ListPullRequestsOptions{},
)
core.ExitOnError("Couldn't list pull requests", err)
for _, pr := range prs {
if pr.Head.Name == branch {
*prID = pr.ID
return nil
}
}
return errors.New("no pull request has been found")
}
func WriteCommentsInFile(
outputFile *os.File,
lineNum uint64,
comments []*gitea.PullReviewComment,
nextComment, commentsLength int,
) int {
for (nextComment < commentsLength) && comments[nextComment].LineNum == lineNum {
comment := comments[nextComment].Body
fmt.Fprint(outputFile, comment)
fmt.Printf("L%04d:\n%s\n", comments[nextComment].LineNum, comment)
nextComment++
}
return nextComment
}
func ProcessFile(filepath string, comments []*gitea.PullReviewComment) {
fmt.Printf("FILE: %s\n", filepath)
core.BackUpSource(filepath)
inputFile, err := os.Open(filepath + ".bck")
core.ExitOnError("Couldn't open backup file", err)
defer inputFile.Close()
outputFile, err := os.Create(filepath)
core.ExitOnError("Couldn't overwrite original file", err)
defer outputFile.Close()
var i uint64 = 1
nextComment, commentsLength := 0, len(comments)
scanner := bufio.NewScanner(inputFile)
for scanner.Scan() {
nextComment = WriteCommentsInFile(outputFile, i, comments, nextComment, commentsLength)
fmt.Fprintln(outputFile, scanner.Text())
i++
}
}
func PatchFiles(commentsByFile map[string]([]*gitea.PullReviewComment)) {
for filepath, comments := range commentsByFile {
ProcessFile(filepath, comments)
}
}