This commit is contained in:
Adam Majer 2024-07-26 16:53:09 +02:00
parent 18bfc87a1c
commit e47feaf5e8
12 changed files with 373 additions and 52 deletions

View File

@ -7,7 +7,7 @@ gitea-generated/client/gitea_api_client.go:: api.json
[ -d gitea-generated ] || mkdir gitea-generated
podman run --rm -v $$(pwd):/api ghcr.io/go-swagger/go-swagger generate client -f /api/api.json -t /api/gitea-generated
api: gitea-generated/client/gitea_api_client.go client.gen.go
api: gitea-generated/client/gitea_api_client.go
build: api
go build

View File

@ -10549,6 +10549,9 @@
},
"/repos/{owner}/{repo}/media/{filepath}": {
"get": {
"produces": [
"application/octet-stream"
],
"tags": [
"repository"
],
@ -10585,7 +10588,10 @@
],
"responses": {
"200": {
"description": "Returns raw file content."
"description": "Returns raw file content.",
"schema": {
"type": "file"
}
},
"404": {
"$ref": "#/responses/notFound"
@ -12621,14 +12627,13 @@
},
"/repos/{owner}/{repo}/raw/{filepath}": {
"get": {
"produces": [
"application/json"
],
"tags": [
"repository"
],
"summary": "Get a file from a repository",
"operationId": "repoGetRawFile",
"produces" : ["application/octet-stream"],
"consumes" : ["application/octet-stream"],
"parameters": [
{
"type": "string",
@ -12660,7 +12665,10 @@
],
"responses": {
"200": {
"description": "Returns raw file content."
"description": "Returns raw file content.",
"schema": {
"type": "file"
}
},
"404": {
"$ref": "#/responses/notFound"

View File

@ -3,7 +3,7 @@ package common
const (
GiteaTokenEnv = "GITEA_TOKEN"
ObsUserEnv = "OBS_USER"
ObsPasswordEnv = "OBS_PW"
ObsPasswordEnv = "OBS_PASSWORD"
DefaultGitPrj = "_ObsPrj"
GiteaRequestHeader = "X-Gitea-Event-Type"

View File

@ -174,6 +174,17 @@ func (f writeFunc) Write(data []byte) (int, error) {
return f(data)
}
func (h writeFunc) UnmarshalText(text []byte) error {
_, err := h.Write(text)
return err
}
func (h writeFunc) Close() error {
_, err := h.Write(nil)
return err
}
func (e *RequestHandler) GitExec(cwd string, params ...string) ExecStream {
if e.Error != nil {
return e
@ -436,6 +447,61 @@ func parseGitTree(data <-chan byte) (tree, error) {
return t, nil
}
func (e *RequestHandler) GitSubmoduleList(cwd, commitId string) map[string]string {
var done sync.Mutex
submoduleList := make(map[string]string)
done.Lock()
data_in, data_out := ChanIO{make(chan byte, 256)}, ChanIO{make(chan byte, 70)}
go func() {
defer done.Unlock()
defer close(data_out.ch)
data_out.Write([]byte(commitId))
data_out.ch <- '\x00'
c, err := parseGitCommit(data_in.ch)
if err != nil {
e.Error = err
e.LogError("Error parsing git commit: %v", err)
return
}
data_out.Write([]byte(c.Tree))
data_out.ch <- '\x00'
tree, err := parseGitTree(data_in.ch)
if err != nil {
e.Error = err
e.LogError("Error parsing git tree: %v", err)
return
}
for _, te := range tree.items {
if te.isSubmodule() {
submoduleList[te.name] = te.hash
}
}
}()
cmd := exec.Command("/usr/bin/git", "cat-file", "--batch", "-Z")
cmd.Env = []string{
"GIT_CEILING_DIRECTORIES=" + e.GitPath,
"GIT_CONFIG_GLOBAL=/dev/null",
}
cmd.Dir = filepath.Join(e.GitPath, cwd)
cmd.Stdout = &data_in
cmd.Stdin = &data_out
cmd.Stderr = writeFunc(func(data []byte) (int, error) {
e.Logger.LogError("%s", data)
return len(data), nil
})
e.Log("command run: %v", cmd.Args)
e.Error = cmd.Run()
done.Lock()
return submoduleList
}
func (e *RequestHandler) GitSubmoduleCommitId(cwd, packageName, commitId string) (string, bool) {
if e.Error != nil {
return "", false

View File

@ -7,6 +7,7 @@ package repository
import (
"fmt"
"io"
"github.com/go-openapi/runtime"
"github.com/go-openapi/strfmt"
@ -15,13 +16,14 @@ import (
// RepoGetRawFileOrLFSReader is a Reader for the RepoGetRawFileOrLFS structure.
type RepoGetRawFileOrLFSReader struct {
formats strfmt.Registry
writer io.Writer
}
// ReadResponse reads a server response into the received o.
func (o *RepoGetRawFileOrLFSReader) ReadResponse(response runtime.ClientResponse, consumer runtime.Consumer) (interface{}, error) {
switch response.Code() {
case 200:
result := NewRepoGetRawFileOrLFSOK()
result := NewRepoGetRawFileOrLFSOK(o.writer)
if err := result.readResponse(response, consumer, o.formats); err != nil {
return nil, err
}
@ -38,8 +40,11 @@ func (o *RepoGetRawFileOrLFSReader) ReadResponse(response runtime.ClientResponse
}
// NewRepoGetRawFileOrLFSOK creates a RepoGetRawFileOrLFSOK with default headers values
func NewRepoGetRawFileOrLFSOK() *RepoGetRawFileOrLFSOK {
return &RepoGetRawFileOrLFSOK{}
func NewRepoGetRawFileOrLFSOK(writer io.Writer) *RepoGetRawFileOrLFSOK {
return &RepoGetRawFileOrLFSOK{
Payload: writer,
}
}
/*
@ -48,6 +53,7 @@ RepoGetRawFileOrLFSOK describes a response with status code 200, with default he
Returns raw file content.
*/
type RepoGetRawFileOrLFSOK struct {
Payload io.Writer
}
// IsSuccess returns true when this repo get raw file or l f s o k response has a 2xx status code
@ -88,8 +94,17 @@ func (o *RepoGetRawFileOrLFSOK) String() string {
return fmt.Sprintf("[GET /repos/{owner}/{repo}/media/{filepath}][%d] repoGetRawFileOrLFSOK", 200)
}
func (o *RepoGetRawFileOrLFSOK) GetPayload() io.Writer {
return o.Payload
}
func (o *RepoGetRawFileOrLFSOK) readResponse(response runtime.ClientResponse, consumer runtime.Consumer, formats strfmt.Registry) error {
// response payload
if err := consumer.Consume(response.Body(), o.Payload); err != nil && err != io.EOF {
return err
}
return nil
}

View File

@ -7,6 +7,7 @@ package repository
import (
"fmt"
"io"
"github.com/go-openapi/runtime"
"github.com/go-openapi/strfmt"
@ -15,13 +16,14 @@ import (
// RepoGetRawFileReader is a Reader for the RepoGetRawFile structure.
type RepoGetRawFileReader struct {
formats strfmt.Registry
writer io.Writer
}
// ReadResponse reads a server response into the received o.
func (o *RepoGetRawFileReader) ReadResponse(response runtime.ClientResponse, consumer runtime.Consumer) (interface{}, error) {
switch response.Code() {
case 200:
result := NewRepoGetRawFileOK()
result := NewRepoGetRawFileOK(o.writer)
if err := result.readResponse(response, consumer, o.formats); err != nil {
return nil, err
}
@ -38,8 +40,11 @@ func (o *RepoGetRawFileReader) ReadResponse(response runtime.ClientResponse, con
}
// NewRepoGetRawFileOK creates a RepoGetRawFileOK with default headers values
func NewRepoGetRawFileOK() *RepoGetRawFileOK {
return &RepoGetRawFileOK{}
func NewRepoGetRawFileOK(writer io.Writer) *RepoGetRawFileOK {
return &RepoGetRawFileOK{
Payload: writer,
}
}
/*
@ -48,6 +53,7 @@ RepoGetRawFileOK describes a response with status code 200, with default header
Returns raw file content.
*/
type RepoGetRawFileOK struct {
Payload io.Writer
}
// IsSuccess returns true when this repo get raw file o k response has a 2xx status code
@ -88,8 +94,17 @@ func (o *RepoGetRawFileOK) String() string {
return fmt.Sprintf("[GET /repos/{owner}/{repo}/raw/{filepath}][%d] repoGetRawFileOK", 200)
}
func (o *RepoGetRawFileOK) GetPayload() io.Writer {
return o.Payload
}
func (o *RepoGetRawFileOK) readResponse(response runtime.ClientResponse, consumer runtime.Consumer, formats strfmt.Registry) error {
// response payload
if err := consumer.Consume(response.Body(), o.Payload); err != nil && err != io.EOF {
return err
}
return nil
}

View File

@ -7,6 +7,7 @@ package repository
import (
"fmt"
"io"
"github.com/go-openapi/runtime"
httptransport "github.com/go-openapi/runtime/client"
@ -103,6 +104,11 @@ func WithAcceptApplicationJSON(r *runtime.ClientOperation) {
r.ProducesMediaTypes = []string{"application/json"}
}
// WithAcceptApplicationOctetStream sets the Accept header to "application/octet-stream".
func WithAcceptApplicationOctetStream(r *runtime.ClientOperation) {
r.ProducesMediaTypes = []string{"application/octet-stream"}
}
// WithAcceptTextHTML sets the Accept header to "text/html".
func WithAcceptTextHTML(r *runtime.ClientOperation) {
r.ProducesMediaTypes = []string{"text/html"}
@ -303,9 +309,9 @@ type ClientService interface {
RepoGetPushMirrorByRemoteName(params *RepoGetPushMirrorByRemoteNameParams, authInfo runtime.ClientAuthInfoWriter, opts ...ClientOption) (*RepoGetPushMirrorByRemoteNameOK, error)
RepoGetRawFile(params *RepoGetRawFileParams, authInfo runtime.ClientAuthInfoWriter, opts ...ClientOption) (*RepoGetRawFileOK, error)
RepoGetRawFile(params *RepoGetRawFileParams, authInfo runtime.ClientAuthInfoWriter, writer io.Writer, opts ...ClientOption) (*RepoGetRawFileOK, error)
RepoGetRawFileOrLFS(params *RepoGetRawFileOrLFSParams, authInfo runtime.ClientAuthInfoWriter, opts ...ClientOption) (*RepoGetRawFileOrLFSOK, error)
RepoGetRawFileOrLFS(params *RepoGetRawFileOrLFSParams, authInfo runtime.ClientAuthInfoWriter, writer io.Writer, opts ...ClientOption) (*RepoGetRawFileOrLFSOK, error)
RepoGetRelease(params *RepoGetReleaseParams, authInfo runtime.ClientAuthInfoWriter, opts ...ClientOption) (*RepoGetReleaseOK, error)
@ -4103,7 +4109,7 @@ func (a *Client) RepoGetPushMirrorByRemoteName(params *RepoGetPushMirrorByRemote
/*
RepoGetRawFile gets a file from a repository
*/
func (a *Client) RepoGetRawFile(params *RepoGetRawFileParams, authInfo runtime.ClientAuthInfoWriter, opts ...ClientOption) (*RepoGetRawFileOK, error) {
func (a *Client) RepoGetRawFile(params *RepoGetRawFileParams, authInfo runtime.ClientAuthInfoWriter, writer io.Writer, opts ...ClientOption) (*RepoGetRawFileOK, error) {
// TODO: Validate the params before sending
if params == nil {
params = NewRepoGetRawFileParams()
@ -4112,11 +4118,11 @@ func (a *Client) RepoGetRawFile(params *RepoGetRawFileParams, authInfo runtime.C
ID: "repoGetRawFile",
Method: "GET",
PathPattern: "/repos/{owner}/{repo}/raw/{filepath}",
ProducesMediaTypes: []string{"application/json"},
ConsumesMediaTypes: []string{"application/json", "text/plain"},
ProducesMediaTypes: []string{"application/octet-stream"},
ConsumesMediaTypes: []string{"application/octet-stream"},
Schemes: []string{"http", "https"},
Params: params,
Reader: &RepoGetRawFileReader{formats: a.formats},
Reader: &RepoGetRawFileReader{formats: a.formats, writer: writer},
AuthInfo: authInfo,
Context: params.Context,
Client: params.HTTPClient,
@ -4142,7 +4148,7 @@ func (a *Client) RepoGetRawFile(params *RepoGetRawFileParams, authInfo runtime.C
/*
RepoGetRawFileOrLFS gets a file or it s l f s object from a repository
*/
func (a *Client) RepoGetRawFileOrLFS(params *RepoGetRawFileOrLFSParams, authInfo runtime.ClientAuthInfoWriter, opts ...ClientOption) (*RepoGetRawFileOrLFSOK, error) {
func (a *Client) RepoGetRawFileOrLFS(params *RepoGetRawFileOrLFSParams, authInfo runtime.ClientAuthInfoWriter, writer io.Writer, opts ...ClientOption) (*RepoGetRawFileOrLFSOK, error) {
// TODO: Validate the params before sending
if params == nil {
params = NewRepoGetRawFileOrLFSParams()
@ -4151,11 +4157,11 @@ func (a *Client) RepoGetRawFileOrLFS(params *RepoGetRawFileOrLFSParams, authInfo
ID: "repoGetRawFileOrLFS",
Method: "GET",
PathPattern: "/repos/{owner}/{repo}/media/{filepath}",
ProducesMediaTypes: []string{"application/json", "text/html"},
ProducesMediaTypes: []string{"application/octet-stream"},
ConsumesMediaTypes: []string{"application/json", "text/plain"},
Schemes: []string{"http", "https"},
Params: params,
Reader: &RepoGetRawFileOrLFSReader{formats: a.formats},
Reader: &RepoGetRawFileOrLFSReader{formats: a.formats, writer: writer},
AuthInfo: authInfo,
Context: params.Context,
Client: params.HTTPClient,

View File

@ -23,7 +23,7 @@ const PrPattern = "PR: %s/%s#%d"
func (h *RequestHandler) allocateGiteaTransport() (*transport.Runtime, *apiclient.GiteaAPI) {
r := transport.New("src.opensuse.org", apiclient.DefaultBasePath, [](string){"https"})
r.DefaultAuthentication = transport.BearerToken(giteaToken)
r.SetDebug(true)
// r.SetDebug(true)
return r, apiclient.New(r, nil)
}
@ -287,6 +287,56 @@ func (h *RequestHandler) RequestReviews(pr *models.PullRequest, reviewer string)
return review.GetPayload()
}
func (h *RequestHandler) AddReviewComment(pr *models.PullRequest, state models.ReviewStateType, comment string) (*models.PullReview, error) {
transport, client := h.allocateGiteaTransport()
h.Log("%#v", *pr)
c, err := client.Repository.RepoCreatePullReview(
repository.NewRepoCreatePullReviewParams().
WithDefaults().
WithOwner(pr.Base.Repo.Owner.UserName).
WithRepo(pr.Base.Repo.Name).
WithIndex(pr.Index).
WithBody(&models.CreatePullReviewOptions{
Event: state,
Body: comment,
}),
transport.DefaultAuthentication,
)
/*
c, err := client.Repository.RepoSubmitPullReview(
repository.NewRepoSubmitPullReviewParams().
WithDefaults().
WithOwner(pr.Base.Repo.Owner.UserName).
WithRepo(pr.Base.Repo.Name).
WithIndex(pr.Index).
WithID(review.ID).
WithBody(&models.SubmitPullReviewOptions{
Event: state,
Body: comment,
}),
transport.DefaultAuthentication,
)
*/
/* c, err := client.Issue.IssueCreateComment(
issue.NewIssueCreateCommentParams().
WithDefaults().
WithOwner(pr.Base.Repo.Owner.UserName).
WithRepo(pr.Base.Repo.Name).
WithIndex(pr.Index).
WithBody(&models.CreateIssueCommentOption{
Body: &comment,
}),
transport.DefaultAuthentication)
*/
if err != nil {
return nil, err
}
return c.Payload, nil
}
func (h *RequestHandler) GetAssociatedPrjGitPR(pr *PullRequestAction) *models.PullRequest {
if h.HasError() {
return nil
@ -335,20 +385,30 @@ func (h *RequestHandler) GetAssociatedPrjGitPR(pr *PullRequestAction) *models.Pu
return nil
}
func (h *RequestHandler) GetRepositoryFileContent(pr *models.PullRequest, path string) ([]byte, error) {
func (h *RequestHandler) GetRepositoryFileContent(repo *models.Repository, hash, path string) ([]byte, error) {
if h.HasError() {
return nil, h.Error
}
transport, client := h.allocateGiteaTransport()
repo := pr.Head.Repo
var retData []byte
dataOut := writeFunc(func(data []byte) (int, error) {
if len(data) == 0 {
return 0, nil
}
retData = data
return len(data), nil
})
file, err := client.Repository.RepoGetRawFile(
repository.NewRepoGetRawFileParams().
WithOwner(repo.Owner.UserName).
WithRepo(repo.Name).
WithFilepath(path).
WithRef(&pr.Head.Ref),
WithRef(&hash),
transport.DefaultAuthentication,
dataOut,
repository.WithContentTypeApplicationOctetStream,
)
if err != nil {
@ -359,6 +419,9 @@ func (h *RequestHandler) GetRepositoryFileContent(pr *models.PullRequest, path s
return nil, fmt.Errorf("Invalid response from server (%d): %s", file.Code(), file.Error())
}
return file.Body(), nil
return retData, nil
}
func (h *RequestHandler) GetPullRequestFileContent(pr *models.PullRequest, path string) ([]byte, error) {
return h.GetRepositoryFileContent(pr.Head.Repo, pr.Head.Sha, path)
}

View File

@ -44,7 +44,7 @@ func prepareMsg(time time.Duration, id uint, str string, params ...any) string {
}
func (s *StdoutLogging) LogPlainError(err error) (int, error) {
return s.Stderr.WriteString(prepareMsg(time.Since(s.Date), s.Id, "%#v\n", err))
return s.Stderr.WriteString(prepareMsg(time.Since(s.Date), s.Id, "%s\n", err.Error()))
}
func (s *StdoutLogging) LogError(str string, params ...any) (int, error) {

View File

@ -1,6 +1,7 @@
package common
import (
"bytes"
"encoding/xml"
"fmt"
"io"
@ -34,14 +35,15 @@ func NewObsClient(host string) (*ObsClient, error) {
}, nil
}
type RepositoryMeta struct {
Name string `xml:"name,attr"`
Arch []string `xml:"arch"`
Path []struct {
XMLName xml.Name `xml:"path"`
type RepositoryPathMeta struct {
Project string `xml:"project,attr"`
Repository string `xml:"repository,attr"`
}
type RepositoryMeta struct {
Name string `xml:"name,attr"`
Archs []string `xml:"arch"`
Paths []RepositoryPathMeta `xml:"path"`
}
type Flags struct {
@ -53,11 +55,13 @@ type ProjectMeta struct {
Name string `xml:"name,attr"`
Title string `xml:"title"`
Description string `xml:"description"`
ScmSync string `xml:"xmlsync"`
Repositories []Repository `xml:"repository"`
ScmSync string `xml:"scmsync"`
Repositories []RepositoryMeta `xml:"repository"`
BuildFlags Flags `xml:"build"`
PublicFlags Flags `xml:"publish"`
DebugFlags Flags `xml:"debuginfo"`
UseForBuild Flags `xml:"useforbuild"`
}
func parseProjectMeta(data []byte) (*ProjectMeta, error) {
@ -77,6 +81,8 @@ func (c *ObsClient) GetProjectMeta(project string) (*ProjectMeta, error) {
return nil, err
}
req.SetBasicAuth(c.user, c.password)
log.Printf("request: %#v", *req.URL)
log.Printf("headers: %#v", req.Header)
res, err := c.client.Do(req)
if err != nil {
@ -100,6 +106,57 @@ func (c *ObsClient) GetProjectMeta(project string) (*ProjectMeta, error) {
return parseProjectMeta(data)
}
func ObsSafeProjectName(prjname string) string {
if len(prjname) < 1 {
return prjname
} else if len(prjname) > 200 {
prjname = prjname[:199]
}
switch prjname[0] {
case '_', '.', ':':
prjname = "X" + prjname[1:]
// no UTF-8 in OBS :(
// prjname = "_" + prjname[1:]
// case ':':
// prjname = "" + prjname[1:]
// case '.':
// prjname = "" + prjname[1:]
}
return prjname
}
func (c *ObsClient) SetProjectMeta(meta *ProjectMeta) (error) {
req, err := http.NewRequest("PUT", c.baseUrl.JoinPath("source", meta.Name, "_meta").String(), nil)
if err != nil {
return err
}
req.SetBasicAuth(c.user, c.password)
xml, err := xml.Marshal(meta)
if err != nil {
return err
}
req.Body = io.NopCloser(bytes.NewReader(xml))
log.Printf("headers: %#v", req.Header)
log.Printf("xml: %s", xml)
res, err := c.client.Do(req)
if err != nil {
return err
}
switch res.StatusCode {
case 200:
break
default:
return fmt.Errorf("Unexpected return code: %d", res.StatusCode)
}
return nil
}
func (c *ObsClient) DeleteProject(project string) error {
req, err := http.NewRequest("DELETE", c.baseUrl.JoinPath("source", project).String(), nil)
if err != nil {

View File

@ -24,8 +24,8 @@ func RequireGiteaSecretToken() error {
}
func RequireObsSecretToken() error {
obsPassword = os.Getenv(ObsUserEnv)
obsUser = os.Getenv(ObsPasswordEnv)
obsUser = os.Getenv(ObsUserEnv)
obsPassword = os.Getenv(ObsPasswordEnv)
if len(obsPassword) < 10 || len(obsUser) < 2 {
return fmt.Errorf("Missing OBS authentication: %s %s", ObsUserEnv, ObsPasswordEnv)

View File

@ -1,10 +1,13 @@
package main
import (
"fmt"
"log"
"os"
"path"
"regexp"
"strconv"
"strings"
"src.opensuse.org/autogits/common"
"src.opensuse.org/autogits/common/gitea-generated/models"
@ -12,6 +15,7 @@ import (
const (
GitAuthor = "GiteaBot - Obs Staging"
BotName = "ObsStaging"
ObsBuildBot = "/obsbuild"
)
@ -24,14 +28,20 @@ func failOnError(err error, msg string) {
}
}
func allocateRequestHandler() *common.RequestHandler {
return &common.RequestHandler{
Logger: common.CreateStdoutLogger(os.Stdout, os.Stdout),
func fetchPrGit(h *common.RequestHandler, pr *models.PullRequest) error {
// clone PR head and base and return path
if _, err := os.Stat(path.Join(h.GitPath, pr.Head.Sha)); os.IsNotExist(err) {
h.GitExec("", "clone", "--depth", "1", pr.Head.Repo.CloneURL, pr.Head.Sha)
h.GitExec(pr.Head.Sha, "fetch", "--depth", "1", "origin", pr.Head.Sha, pr.Base.Sha)
} else if err != nil {
h.Error = err
}
return h.Error
}
func processPullNotification(h *common.RequestHandler, notification *models.NotificationSubject) {
rx := regexp.MustCompile(`^https://src\.(?:open)?suse\.org/api/v\d+/repos/(?<org>[a-zA-Z0-9]+)/(?<project>[_a-zA-Z0-9]+)/issues/(?<num>[0-9]+)$`)
rx := regexp.MustCompile(`^https://src\.(?:open)?suse\.(?:org|de)/api/v\d+/repos/(?<org>[a-zA-Z0-9]+)/(?<project>[_a-zA-Z0-9]+)/issues/(?<num>[0-9]+)$`)
match := rx.FindStringSubmatch(notification.URL)
if match == nil {
log.Panicf("Unexpected format of notification: %s", notification.URL)
@ -64,26 +74,89 @@ func processPullNotification(h *common.RequestHandler, notification *models.Noti
for _, review := range reviews {
h.Log("state: %s, body: %s, id:%d\n", string(review.State), review.Body, review.ID)
if *review.User.LoginName != "autogits_obs_staging_bot" {
if review.User.UserName != "autogits_obs_staging_bot" {
continue
}
switch review.State {
case common.ReviewStateUnknown, common.ReviewStateRequestReview:
err := fetchPrGit(h, pr)
if err != nil {
h.LogError("Cannot fetch PR git: %s", pr.URL)
return
}
dir := pr.Head.Sha
headSubmodules := h.GitSubmoduleList(dir, pr.Head.Sha)
baseSubmodules := h.GitSubmoduleList(dir, pr.Base.Sha)
// find modified submodules and new submodules -- build them
h.Log("processing state...")
switch review.State {
// create build project, if doesn't exist, and add it to pending requests
case common.ReviewStateUnknown, common.ReviewStateRequestReview:
h.Log("repo content fetching ...")
buildPrjBytes, err := h.GetPullRequestFileContent(pr, "project.build")
if err != nil {
h.LogPlainError(err)
_, err := h.AddReviewComment(pr, common.ReviewStateRequestChanges, "Cannot find reference project")
if err != nil {
h.LogPlainError(err)
}
return
}
buildPrj := strings.TrimSpace(string(buildPrjBytes))
meta, err := obsClient.GetProjectMeta(string(buildPrj))
if err != nil {
h.Log("error fetching project meta for %s: %v", buildPrj, err)
return
}
// generate new project with paths pointinig back to original repos
// disable publishing
// TODO: escape things here
meta.Name = fmt.Sprintf("%s:%s:%s:PR:%d",
obsClient.HomeProject,
common.ObsSafeProjectName(pr.Base.Repo.Owner.UserName),
common.ObsSafeProjectName(pr.Base.Repo.Name),
pr.Index,
)
meta.Description = fmt.Sprintf(`Pull request build job: %s%s PR#%d`,
"https://src.opensuse.org", pr.Base.Repo.Name, pr.Index)
// meta.ScmSync = pr.Head.Repo.CloneURL + "?" +
meta.Title = fmt.Sprintf("PR#%d to %s", pr.Index, pr.Base.Name)
meta.PublicFlags = common.Flags{Contents: "<disable/>"}
// set paths to parent project
for idx, r := range meta.Repositories {
meta.Repositories[idx].Paths = []common.RepositoryPathMeta{{
Project: buildPrj,
Repository: r.Name,
}}
}
h.Log("%#v", meta)
return
err = obsClient.SetProjectMeta(meta)
if err != nil {
h.LogError("cannot create meta project: %#v", err)
}
case common.ReviewStatePending:
// waiting for build results
case common.ReviewStateApproved:
// done, mark notification as read
case common.ReviewStateRequestChanges:
// build failures, mark notification as read
h.Log("processing request for failed request changes...")
// build failures, nothing to do here, mark notification as read
}
}
}
func pollWorkNotifications() {
h := allocateRequestHandler()
h := common.CreateRequestHandler(GitAuthor, BotName)
data, err := h.GetNotifications(nil)
if err != nil {
@ -117,7 +190,25 @@ func main() {
pollWorkNotifications()
/*
h := allocateRequestHandler()
//" autogits/_ObsPrj/raw/project.build?ref=9680b770855e4fc2e9d9cebbd87e6a0d119693c3e03db187494e3aeff727312f"
// https://src.opensuse.org/adamm/autogits/commit/8db4d8c3021fc21baa606b87eaad0e476bb7f624f76cb37b6a1819bdb5f04b43#diff-6e698c75c21cd4458440e8a71408c6301ba3a562
f, err := h.GetRepositoryFileContent(
&models.Repository{
Owner: &models.User{
UserName: "adamm",
},
Name: "autogits",
},
"54e418acaf960c5ed8be7f4a29616ae7b5eb75f797f7ed4d487f79485d056108",
"bots-common/obs/client.go")
if err != nil {
h.LogPlainError(err)
}
h.Log("len: %d", len(f))
*/
stuck := make(chan int)
<-stuck
}