dmitri.shuralyov.com/service/change/...

githubapi: Add support for bot actors.

Otherwise, they were showing up as ghost users.
dmitshur committed 6 years ago commit caf5deb01491616203ca0ed56937ef94650f29a0
Collapse all
githubapi/githubapi.go
@@ -218,11 +218,11 @@ func (s service) ListCommits(ctx context.Context, rs string, id uint64) ([]chang
	var commits []changes.Commit
	for _, c := range cs {
		commits = append(commits, changes.Commit{
			SHA:        *c.SHA,
			Message:    *c.Commit.Message,
			Author:     ghUser(c.Author),
			Author:     ghV3User(c.Author),
			AuthorTime: *c.Commit.Author.Date,
		})
	}
	return commits, nil
}
@@ -549,40 +549,59 @@ func ghRepoSpec(rs string) (repoSpec, error) {

type githubqlActor struct {
	User struct {
		DatabaseID uint64
	} `graphql:"...on User"`
	Bot struct {
		DatabaseID uint64
	} `graphql:"...on Bot"`
	Login     string
	AvatarURL string `graphql:"avatarUrl(size:96)"`
	URL       string
}

func ghActor(actor githubqlActor) users.User {
	if actor.User.DatabaseID == 0 {
		// Deleted user, replace with https://github.com/ghost.
		return users.User{
			UserSpec: users.UserSpec{
				ID:     10137,
				Domain: "github.com",
			},
			Login:     "ghost",
			AvatarURL: "https://avatars3.githubusercontent.com/u/10137?v=4",
			HTMLURL:   "https://github.com/ghost",
		}
	if actor.User.DatabaseID == 0 && actor.Bot.DatabaseID == 0 {
		return ghost // Deleted user, replace with https://github.com/ghost.
	}
	return users.User{
		UserSpec: users.UserSpec{
			ID:     actor.User.DatabaseID,
			ID:     actor.User.DatabaseID | actor.Bot.DatabaseID,
			Domain: "github.com",
		},
		Login:     actor.Login,
		AvatarURL: actor.AvatarURL,
		HTMLURL:   actor.URL,
	}
}

func ghUser(user *github.User) users.User {
type githubqlUser struct {
	DatabaseID uint64
	Login      string
	AvatarURL  string `graphql:"avatarUrl(size:96)"`
	URL        string
}

func ghUser(user githubqlUser) users.User {
	if user.DatabaseID == 0 {
		return ghost // Deleted user, replace with https://github.com/ghost.
	}
	return users.User{
		UserSpec: users.UserSpec{
			ID:     user.DatabaseID,
			Domain: "github.com",
		},
		Login:     user.Login,
		AvatarURL: user.AvatarURL,
		HTMLURL:   user.URL,
	}
}

func ghV3User(user *github.User) users.User {
	if *user.ID == 0 {
		return ghost // Deleted user, replace with https://github.com/ghost.
	}
	return users.User{
		UserSpec: users.UserSpec{
			ID:     uint64(*user.ID),
			Domain: "github.com",
		},
@@ -590,10 +609,21 @@ func ghUser(user *github.User) users.User {
		AvatarURL: *user.AvatarURL,
		HTMLURL:   *user.HTMLURL,
	}
}

// ghost is https://github.com/ghost, a replacement for deleted users.
var ghost = users.User{
	UserSpec: users.UserSpec{
		ID:     10137,
		Domain: "github.com",
	},
	Login:     "ghost",
	AvatarURL: "https://avatars3.githubusercontent.com/u/10137?v=4",
	HTMLURL:   "https://github.com/ghost",
}

// ghPRState converts a GitHub PullRequestState to changes.State.
func ghPRState(state githubql.PullRequestState) changes.State {
	switch state {
	case githubql.PullRequestStateOpen:
		return changes.OpenState
@@ -615,11 +645,11 @@ func ghColor(hex string) issues.RGB {
}

type reactionGroups []struct {
	Content githubql.ReactionContent
	Users   struct {
		Nodes      []githubqlActor
		Nodes      []githubqlUser
		TotalCount int
	} `graphql:"users(first:10)"`
	ViewerHasReacted bool
}

@@ -634,11 +664,11 @@ func (s service) reactions(rgs reactionGroups) ([]reactions.Reaction, error) {
		// Only return the details of first few users and authed user.
		var us []users.User
		addedAuthedUser := false
		for i := 0; i < rg.Users.TotalCount; i++ {
			if i < len(rg.Users.Nodes) {
				actor := ghActor(rg.Users.Nodes[i])
				actor := ghUser(rg.Users.Nodes[i])
				us = append(us, actor)
				if s.currentUser.ID != 0 && actor.UserSpec == s.currentUser.UserSpec {
					addedAuthedUser = true
				}
			} else if i == len(rg.Users.Nodes) {