blob: fd9021c0d354c4050c2e8455ad823e02e4d4773c [file] [log] [blame]
package monorailsource
import (
"context"
"fmt"
"time"
"github.com/spf13/viper"
"go.skia.org/infra/go/monorail/v1"
"go.skia.org/infra/go/skerr"
"go.skia.org/infra/go/sklog"
"go.skia.org/infra/hashtag/go/source"
)
const monorailTimeFormat = "2006-01-02T15:04:05"
// monorailSource implements source.Source.
type monorailSource struct {
m *monorail.Service
projectID string
linkFormat string
sort string
}
// New returns a new Source.
func New() (source.Source, error) {
m, err := monorail.NewService(context.Background())
if err != nil {
return nil, skerr.Wrapf(err, "Unable to create monorail service.")
}
return &monorailSource{
m: m,
projectID: viper.GetString("sources.monorail.projectID"),
linkFormat: viper.GetString("sources.monorail.linkFormat"),
sort: viper.GetString("sources.monorail.sort"),
}, nil
}
// addQuery extends the monorail IssuesListCall based on the source.Query.
func (m *monorailSource) addQuery(listCall *monorail.IssuesListCall, q source.Query) *monorail.IssuesListCall {
if q.Type == source.HashtagQuery {
listCall = listCall.Q(q.Value)
} else if q.Type == source.UserQuery {
listCall = listCall.Owner(q.Value)
}
if !q.Begin.IsZero() {
listCall = listCall.UpdatedMin(q.Begin.Unix())
}
if !q.End.IsZero() {
listCall = listCall.UpdatedMax(q.End.Unix())
}
return listCall
}
// See source.Source.
func (m *monorailSource) Search(ctx context.Context, q source.Query) <-chan source.Artifact {
ret := make(chan source.Artifact)
go func() {
defer close(ret)
listCall := m.m.Issues.List(m.projectID).Context(ctx).Sort(m.sort)
listCall = m.addQuery(listCall, q)
matchingIssues, err := listCall.Do()
if err != nil {
sklog.Errorf("Failed to build Monorail search: %s", err)
return
}
for _, issue := range matchingIssues.Items {
ts, err := time.Parse(monorailTimeFormat, issue.StatusModified)
if err != nil {
sklog.Errorf("Can't parse %q at time: %s", issue.StatusModified, err)
ts = time.Now()
}
ret <- source.Artifact{
Title: issue.Title,
URL: fmt.Sprintf(m.linkFormat, issue.Id),
LastModified: ts,
}
}
}()
return ret
}