Skip to content

Commit

Permalink
Only call GitHub APIs when needed (#918)
Browse files Browse the repository at this point in the history
Co-authored-by: Azeem Shaikh <azeems@google.com>
  • Loading branch information
azeemshaikh38 and azeemsgoogle committed Aug 26, 2021
1 parent c9a617b commit fe54c51
Show file tree
Hide file tree
Showing 3 changed files with 103 additions and 56 deletions.
8 changes: 2 additions & 6 deletions clients/githubrepo/client.go
Original file line number Diff line number Diff line change
Expand Up @@ -57,14 +57,10 @@ func (client *Client) InitRepo(owner, repoName string) error {
}

// Setup GraphQL.
if err := client.graphClient.init(client.ctx, client.owner, client.repoName); err != nil {
return fmt.Errorf("error during graphqlHandler.init: %w", err)
}
client.graphClient.init(client.ctx, client.owner, client.repoName)

// Setup contributors.
if err := client.contributors.init(client.ctx, client.owner, client.repoName); err != nil {
return fmt.Errorf("error during contributorsHandler.init: %w", err)
}
client.contributors.init(client.ctx, client.owner, client.repoName)

// Setup Search.
client.search.init(client.ctx, client.owner, client.repoName)
Expand Down
79 changes: 50 additions & 29 deletions clients/githubrepo/contributors.go
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ package githubrepo
import (
"context"
"fmt"
"sync"

"github.com/google/go-github/v38/github"

Expand All @@ -25,44 +26,64 @@ import (

type contributorsHandler struct {
ghClient *github.Client
once *sync.Once
ctx context.Context
errSetup error
owner string
repo string
contributors []clients.Contributor
}

func (handler *contributorsHandler) init(ctx context.Context, owner, repo string) error {
contribs, _, err := handler.ghClient.Repositories.ListContributors(ctx, owner, repo, &github.ListContributorsOptions{})
if err != nil {
return fmt.Errorf("error during ListContributors: %w", err)
}
func (handler *contributorsHandler) init(ctx context.Context, owner, repo string) {
handler.ctx = ctx
handler.owner = owner
handler.repo = repo
handler.errSetup = nil
handler.once = new(sync.Once)
}

for _, contrib := range contribs {
if contrib.GetLogin() == "" {
continue
}
contributor := clients.Contributor{
NumContributions: contrib.GetContributions(),
User: clients.User{
Login: contrib.GetLogin(),
},
func (handler *contributorsHandler) setup() error {
handler.once.Do(func() {
contribs, _, err := handler.ghClient.Repositories.ListContributors(
handler.ctx, handler.owner, handler.repo, &github.ListContributorsOptions{})
if err != nil {
handler.errSetup = fmt.Errorf("error during ListContributors: %w", err)
}
orgs, _, err := handler.ghClient.Organizations.List(ctx, contrib.GetLogin(), nil)
// This call can fail due to token scopes. So ignore error.
if err == nil {
for _, org := range orgs {
contributor.Organizations = append(contributor.Organizations, clients.User{
Login: org.GetLogin(),
})

for _, contrib := range contribs {
if contrib.GetLogin() == "" {
continue
}
contributor := clients.Contributor{
NumContributions: contrib.GetContributions(),
User: clients.User{
Login: contrib.GetLogin(),
},
}
orgs, _, err := handler.ghClient.Organizations.List(handler.ctx, contrib.GetLogin(), nil)
// This call can fail due to token scopes. So ignore error.
if err == nil {
for _, org := range orgs {
contributor.Organizations = append(contributor.Organizations, clients.User{
Login: org.GetLogin(),
})
}
}
user, _, err := handler.ghClient.Users.Get(handler.ctx, contrib.GetLogin())
if err != nil {
handler.errSetup = fmt.Errorf("error during Users.Get: %w", err)
}
contributor.Company = user.GetCompany()
handler.contributors = append(handler.contributors, contributor)
}
user, _, err := handler.ghClient.Users.Get(ctx, contrib.GetLogin())
if err != nil {
return fmt.Errorf("error during Users.Get: %w", err)
}
contributor.Company = user.GetCompany()
handler.contributors = append(handler.contributors, contributor)
}
return nil
handler.errSetup = nil
})
return handler.errSetup
}

func (handler *contributorsHandler) getContributors() ([]clients.Contributor, error) {
if err := handler.setup(); err != nil {
return nil, fmt.Errorf("error during contributorsHandler.setup: %w", err)
}
return handler.contributors, nil
}
72 changes: 51 additions & 21 deletions clients/githubrepo/graphql.go
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ package githubrepo
import (
"context"
"fmt"
"sync"

"github.com/shurcooL/githubv4"

Expand Down Expand Up @@ -96,54 +97,83 @@ type graphqlData struct {
type graphqlHandler struct {
client *githubv4.Client
data *graphqlData
once *sync.Once
ctx context.Context
errSetup error
owner string
repo string
prs []clients.PullRequest
commits []clients.Commit
releases []clients.Release
defaultBranchRef clients.BranchRef
archived bool
}

func (handler *graphqlHandler) init(ctx context.Context, owner, repo string) error {
vars := map[string]interface{}{
"owner": githubv4.String(owner),
"name": githubv4.String(repo),
"pullRequestsToAnalyze": githubv4.Int(pullRequestsToAnalyze),
"reviewsToAnalyze": githubv4.Int(reviewsToAnalyze),
"labelsToAnalyze": githubv4.Int(labelsToAnalyze),
"commitsToAnalyze": githubv4.Int(commitsToAnalyze),
"releasesToAnalyze": githubv4.Int(releasesToAnalyze),
"releaseAssetsToAnalyze": githubv4.Int(releaseAssetsToAnalyze),
}
func (handler *graphqlHandler) init(ctx context.Context, owner, repo string) {
handler.ctx = ctx
handler.owner = owner
handler.repo = repo
handler.data = new(graphqlData)
if err := handler.client.Query(ctx, handler.data, vars); err != nil {
// nolint: wrapcheck
return sce.Create(sce.ErrScorecardInternal, fmt.Sprintf("githubv4.Query: %v", err))
}
handler.archived = bool(handler.data.Repository.IsArchived)
handler.prs = pullRequestsFrom(handler.data)
handler.releases = releasesFrom(handler.data)
handler.defaultBranchRef = defaultBranchRefFrom(handler.data)
handler.commits = commitsFrom(handler.data)
return nil
handler.errSetup = nil
handler.once = new(sync.Once)
}

func (handler *graphqlHandler) setup() error {
handler.once.Do(func() {
vars := map[string]interface{}{
"owner": githubv4.String(handler.owner),
"name": githubv4.String(handler.repo),
"pullRequestsToAnalyze": githubv4.Int(pullRequestsToAnalyze),
"reviewsToAnalyze": githubv4.Int(reviewsToAnalyze),
"labelsToAnalyze": githubv4.Int(labelsToAnalyze),
"commitsToAnalyze": githubv4.Int(commitsToAnalyze),
"releasesToAnalyze": githubv4.Int(releasesToAnalyze),
"releaseAssetsToAnalyze": githubv4.Int(releaseAssetsToAnalyze),
}
if err := handler.client.Query(handler.ctx, handler.data, vars); err != nil {
handler.errSetup = sce.Create(sce.ErrScorecardInternal, fmt.Sprintf("githubv4.Query: %v", err))
}
handler.archived = bool(handler.data.Repository.IsArchived)
handler.prs = pullRequestsFrom(handler.data)
handler.releases = releasesFrom(handler.data)
handler.defaultBranchRef = defaultBranchRefFrom(handler.data)
handler.commits = commitsFrom(handler.data)
})
return handler.errSetup
}

func (handler *graphqlHandler) getMergedPRs() ([]clients.PullRequest, error) {
if err := handler.setup(); err != nil {
return nil, fmt.Errorf("error during graphqlHandler.setup: %w", err)
}
return handler.prs, nil
}

func (handler *graphqlHandler) getDefaultBranch() (clients.BranchRef, error) {
if err := handler.setup(); err != nil {
return clients.BranchRef{}, fmt.Errorf("error during graphqlHandler.setup: %w", err)
}
return handler.defaultBranchRef, nil
}

func (handler *graphqlHandler) getCommits() ([]clients.Commit, error) {
if err := handler.setup(); err != nil {
return nil, fmt.Errorf("error during graphqlHandler.setup: %w", err)
}
return handler.commits, nil
}

func (handler *graphqlHandler) getReleases() ([]clients.Release, error) {
if err := handler.setup(); err != nil {
return nil, fmt.Errorf("error during graphqlHandler.setup: %w", err)
}
return handler.releases, nil
}

func (handler *graphqlHandler) isArchived() (bool, error) {
if err := handler.setup(); err != nil {
return false, fmt.Errorf("error during graphqlHandler.setup: %w", err)
}
return handler.archived, nil
}

Expand Down

0 comments on commit fe54c51

Please sign in to comment.