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) } }