feat(package): gitea: index heatmap commits by author date
This commit is contained in:
@@ -0,0 +1,109 @@
|
||||
// Copyright 2026 The Gitea Authors. All rights reserved.
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
package repository
|
||||
|
||||
import (
|
||||
"context"
|
||||
"strings"
|
||||
|
||||
activities_model "code.gitea.io/gitea/models/activities"
|
||||
repo_model "code.gitea.io/gitea/models/repo"
|
||||
user_model "code.gitea.io/gitea/models/user"
|
||||
"code.gitea.io/gitea/modules/git"
|
||||
"code.gitea.io/gitea/modules/gitrepo"
|
||||
"code.gitea.io/gitea/modules/timeutil"
|
||||
)
|
||||
|
||||
const heatmapIndexCommitsPageSize = 100
|
||||
|
||||
// IndexDefaultBranchHeatmapContributions indexes commit author-date heatmap contributions reachable from repo's default branch.
|
||||
func IndexDefaultBranchHeatmapContributions(ctx context.Context, repo *repo_model.Repository) error {
|
||||
if repo == nil || repo.ID == 0 {
|
||||
return nil
|
||||
}
|
||||
if repo.DefaultBranch == "" || repo.IsEmpty {
|
||||
return activities_model.DeleteStaleHeatmapContributions(ctx, repo.ID, nil)
|
||||
}
|
||||
|
||||
gitRepo, closer, err := gitrepo.RepositoryFromContextOrOpen(ctx, repo)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
defer closer.Close()
|
||||
|
||||
head, err := gitRepo.GetBranchCommit(repo.DefaultBranch)
|
||||
if git.IsErrNotExist(err) {
|
||||
return activities_model.DeleteStaleHeatmapContributions(ctx, repo.ID, nil)
|
||||
}
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
currentIdentities := make([]activities_model.HeatmapContributionIdentity, 0)
|
||||
now := timeutil.TimeStampNow()
|
||||
for page := 1; ; page++ {
|
||||
commits, err := head.CommitsByRange(page, heatmapIndexCommitsPageSize, "", "", "")
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
if len(commits) == 0 {
|
||||
break
|
||||
}
|
||||
|
||||
for _, commit := range commits {
|
||||
commitSHA := commit.ID.String()
|
||||
if commit.Author == nil || commit.Author.Email == "" {
|
||||
continue
|
||||
}
|
||||
|
||||
authorUnix := timeutil.TimeStamp(commit.Author.When.Unix())
|
||||
if authorUnix > now {
|
||||
continue
|
||||
}
|
||||
|
||||
userID, ok, err := getHeatmapAuthorUserIDByEmail(ctx, commit.Author.Email)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
if !ok {
|
||||
continue
|
||||
}
|
||||
|
||||
if err := activities_model.UpsertHeatmapContribution(ctx, &activities_model.HeatmapContribution{
|
||||
UserID: userID,
|
||||
RepoID: repo.ID,
|
||||
CommitSHA: commitSHA,
|
||||
AuthorEmail: strings.ToLower(commit.Author.Email),
|
||||
AuthorUnix: authorUnix,
|
||||
}); err != nil {
|
||||
return err
|
||||
}
|
||||
currentIdentities = append(currentIdentities, activities_model.HeatmapContributionIdentity{
|
||||
RepoID: repo.ID,
|
||||
CommitSHA: commitSHA,
|
||||
UserID: userID,
|
||||
})
|
||||
}
|
||||
|
||||
if len(commits) < heatmapIndexCommitsPageSize {
|
||||
break
|
||||
}
|
||||
}
|
||||
|
||||
return activities_model.DeleteStaleHeatmapContributions(ctx, repo.ID, currentIdentities)
|
||||
}
|
||||
|
||||
func getHeatmapAuthorUserIDByEmail(ctx context.Context, email string) (int64, bool, error) {
|
||||
address, err := user_model.GetEmailAddressByEmail(ctx, email)
|
||||
if user_model.IsErrEmailAddressNotExist(err) {
|
||||
return 0, false, nil
|
||||
}
|
||||
if err != nil {
|
||||
return 0, false, err
|
||||
}
|
||||
if !address.IsActivated {
|
||||
return 0, false, nil
|
||||
}
|
||||
return address.UID, true, nil
|
||||
}
|
||||
Reference in New Issue
Block a user