aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorLunny Xiao <xiaolunwen@gmail.com>2024-11-29 09:53:49 -0800
committerGitHub <noreply@github.com>2024-11-29 17:53:49 +0000
commit1ed5f379b9f3e38b64cc9de9f418c164ce400be1 (patch)
treedee6e19dd5c3ae6e96df2c926f199bb3c1c1299b
parent93640993e3cca9d0e0261591ba38b84b0b99ab12 (diff)
downloadgitea-1ed5f379b9f3e38b64cc9de9f418c164ce400be1.tar.gz
gitea-1ed5f379b9f3e38b64cc9de9f418c164ce400be1.zip
Move GetFeeds to service layer (#32526)
Move GetFeeds from models to service layer, no code change.
-rw-r--r--models/activities/action.go54
-rw-r--r--models/activities/action_list.go52
-rw-r--r--models/activities/action_test.go149
-rw-r--r--models/activities/user_heatmap.go2
-rw-r--r--routers/api/v1/org/org.go3
-rw-r--r--routers/api/v1/org/team.go3
-rw-r--r--routers/api/v1/repo/repo.go3
-rw-r--r--routers/api/v1/user/user.go3
-rw-r--r--routers/web/feed/profile.go3
-rw-r--r--routers/web/feed/repo.go3
-rw-r--r--routers/web/user/home.go3
-rw-r--r--routers/web/user/profile.go3
-rw-r--r--services/feed/feed.go15
-rw-r--r--services/feed/feed_test.go165
-rw-r--r--services/feed/notifier.go (renamed from services/feed/action.go)0
-rw-r--r--services/feed/notifier_test.go (renamed from services/feed/action_test.go)0
16 files changed, 250 insertions, 211 deletions
diff --git a/models/activities/action.go b/models/activities/action.go
index 546d4340ae..65d95fbe66 100644
--- a/models/activities/action.go
+++ b/models/activities/action.go
@@ -448,65 +448,13 @@ type GetFeedsOptions struct {
Date string // the day we want activity for: YYYY-MM-DD
}
-// GetFeeds returns actions according to the provided options
-func GetFeeds(ctx context.Context, opts GetFeedsOptions) (ActionList, int64, error) {
- if opts.RequestedUser == nil && opts.RequestedTeam == nil && opts.RequestedRepo == nil {
- return nil, 0, fmt.Errorf("need at least one of these filters: RequestedUser, RequestedTeam, RequestedRepo")
- }
-
- cond, err := activityQueryCondition(ctx, opts)
- if err != nil {
- return nil, 0, err
- }
-
- actions := make([]*Action, 0, opts.PageSize)
- var count int64
- opts.SetDefaultValues()
-
- if opts.Page < 10 { // TODO: why it's 10 but other values? It's an experience value.
- sess := db.GetEngine(ctx).Where(cond)
- sess = db.SetSessionPagination(sess, &opts)
-
- count, err = sess.Desc("`action`.created_unix").FindAndCount(&actions)
- if err != nil {
- return nil, 0, fmt.Errorf("FindAndCount: %w", err)
- }
- } else {
- // First, only query which IDs are necessary, and only then query all actions to speed up the overall query
- sess := db.GetEngine(ctx).Where(cond).Select("`action`.id")
- sess = db.SetSessionPagination(sess, &opts)
-
- actionIDs := make([]int64, 0, opts.PageSize)
- if err := sess.Table("action").Desc("`action`.created_unix").Find(&actionIDs); err != nil {
- return nil, 0, fmt.Errorf("Find(actionsIDs): %w", err)
- }
-
- count, err = db.GetEngine(ctx).Where(cond).
- Table("action").
- Cols("`action`.id").Count()
- if err != nil {
- return nil, 0, fmt.Errorf("Count: %w", err)
- }
-
- if err := db.GetEngine(ctx).In("`action`.id", actionIDs).Desc("`action`.created_unix").Find(&actions); err != nil {
- return nil, 0, fmt.Errorf("Find: %w", err)
- }
- }
-
- if err := ActionList(actions).LoadAttributes(ctx); err != nil {
- return nil, 0, fmt.Errorf("LoadAttributes: %w", err)
- }
-
- return actions, count, nil
-}
-
// ActivityReadable return whether doer can read activities of user
func ActivityReadable(user, doer *user_model.User) bool {
return !user.KeepActivityPrivate ||
doer != nil && (doer.IsAdmin || user.ID == doer.ID)
}
-func activityQueryCondition(ctx context.Context, opts GetFeedsOptions) (builder.Cond, error) {
+func ActivityQueryCondition(ctx context.Context, opts GetFeedsOptions) (builder.Cond, error) {
cond := builder.NewCond()
if opts.RequestedTeam != nil && opts.RequestedUser == nil {
diff --git a/models/activities/action_list.go b/models/activities/action_list.go
index aafb7f8a26..5f9acb8f2a 100644
--- a/models/activities/action_list.go
+++ b/models/activities/action_list.go
@@ -201,3 +201,55 @@ func (actions ActionList) LoadIssues(ctx context.Context) error {
}
return nil
}
+
+// GetFeeds returns actions according to the provided options
+func GetFeeds(ctx context.Context, opts GetFeedsOptions) (ActionList, int64, error) {
+ if opts.RequestedUser == nil && opts.RequestedTeam == nil && opts.RequestedRepo == nil {
+ return nil, 0, fmt.Errorf("need at least one of these filters: RequestedUser, RequestedTeam, RequestedRepo")
+ }
+
+ cond, err := ActivityQueryCondition(ctx, opts)
+ if err != nil {
+ return nil, 0, err
+ }
+
+ actions := make([]*Action, 0, opts.PageSize)
+ var count int64
+ opts.SetDefaultValues()
+
+ if opts.Page < 10 { // TODO: why it's 10 but other values? It's an experience value.
+ sess := db.GetEngine(ctx).Where(cond)
+ sess = db.SetSessionPagination(sess, &opts)
+
+ count, err = sess.Desc("`action`.created_unix").FindAndCount(&actions)
+ if err != nil {
+ return nil, 0, fmt.Errorf("FindAndCount: %w", err)
+ }
+ } else {
+ // First, only query which IDs are necessary, and only then query all actions to speed up the overall query
+ sess := db.GetEngine(ctx).Where(cond).Select("`action`.id")
+ sess = db.SetSessionPagination(sess, &opts)
+
+ actionIDs := make([]int64, 0, opts.PageSize)
+ if err := sess.Table("action").Desc("`action`.created_unix").Find(&actionIDs); err != nil {
+ return nil, 0, fmt.Errorf("Find(actionsIDs): %w", err)
+ }
+
+ count, err = db.GetEngine(ctx).Where(cond).
+ Table("action").
+ Cols("`action`.id").Count()
+ if err != nil {
+ return nil, 0, fmt.Errorf("Count: %w", err)
+ }
+
+ if err := db.GetEngine(ctx).In("`action`.id", actionIDs).Desc("`action`.created_unix").Find(&actions); err != nil {
+ return nil, 0, fmt.Errorf("Find: %w", err)
+ }
+ }
+
+ if err := ActionList(actions).LoadAttributes(ctx); err != nil {
+ return nil, 0, fmt.Errorf("LoadAttributes: %w", err)
+ }
+
+ return actions, count, nil
+}
diff --git a/models/activities/action_test.go b/models/activities/action_test.go
index 64330ebbb3..9cfe981656 100644
--- a/models/activities/action_test.go
+++ b/models/activities/action_test.go
@@ -42,114 +42,6 @@ func TestAction_GetRepoLink(t *testing.T) {
assert.Equal(t, comment.HTMLURL(db.DefaultContext), action.GetCommentHTMLURL(db.DefaultContext))
}
-func TestGetFeeds(t *testing.T) {
- // test with an individual user
- assert.NoError(t, unittest.PrepareTestDatabase())
- user := unittest.AssertExistsAndLoadBean(t, &user_model.User{ID: 2})
-
- actions, count, err := activities_model.GetFeeds(db.DefaultContext, activities_model.GetFeedsOptions{
- RequestedUser: user,
- Actor: user,
- IncludePrivate: true,
- OnlyPerformedBy: false,
- IncludeDeleted: true,
- })
- assert.NoError(t, err)
- if assert.Len(t, actions, 1) {
- assert.EqualValues(t, 1, actions[0].ID)
- assert.EqualValues(t, user.ID, actions[0].UserID)
- }
- assert.Equal(t, int64(1), count)
-
- actions, count, err = activities_model.GetFeeds(db.DefaultContext, activities_model.GetFeedsOptions{
- RequestedUser: user,
- Actor: user,
- IncludePrivate: false,
- OnlyPerformedBy: false,
- })
- assert.NoError(t, err)
- assert.Len(t, actions, 0)
- assert.Equal(t, int64(0), count)
-}
-
-func TestGetFeedsForRepos(t *testing.T) {
- assert.NoError(t, unittest.PrepareTestDatabase())
- user := unittest.AssertExistsAndLoadBean(t, &user_model.User{ID: 2})
- privRepo := unittest.AssertExistsAndLoadBean(t, &repo_model.Repository{ID: 2})
- pubRepo := unittest.AssertExistsAndLoadBean(t, &repo_model.Repository{ID: 8})
-
- // private repo & no login
- actions, count, err := activities_model.GetFeeds(db.DefaultContext, activities_model.GetFeedsOptions{
- RequestedRepo: privRepo,
- IncludePrivate: true,
- })
- assert.NoError(t, err)
- assert.Len(t, actions, 0)
- assert.Equal(t, int64(0), count)
-
- // public repo & no login
- actions, count, err = activities_model.GetFeeds(db.DefaultContext, activities_model.GetFeedsOptions{
- RequestedRepo: pubRepo,
- IncludePrivate: true,
- })
- assert.NoError(t, err)
- assert.Len(t, actions, 1)
- assert.Equal(t, int64(1), count)
-
- // private repo and login
- actions, count, err = activities_model.GetFeeds(db.DefaultContext, activities_model.GetFeedsOptions{
- RequestedRepo: privRepo,
- IncludePrivate: true,
- Actor: user,
- })
- assert.NoError(t, err)
- assert.Len(t, actions, 1)
- assert.Equal(t, int64(1), count)
-
- // public repo & login
- actions, count, err = activities_model.GetFeeds(db.DefaultContext, activities_model.GetFeedsOptions{
- RequestedRepo: pubRepo,
- IncludePrivate: true,
- Actor: user,
- })
- assert.NoError(t, err)
- assert.Len(t, actions, 1)
- assert.Equal(t, int64(1), count)
-}
-
-func TestGetFeeds2(t *testing.T) {
- // test with an organization user
- assert.NoError(t, unittest.PrepareTestDatabase())
- org := unittest.AssertExistsAndLoadBean(t, &user_model.User{ID: 3})
- user := unittest.AssertExistsAndLoadBean(t, &user_model.User{ID: 2})
-
- actions, count, err := activities_model.GetFeeds(db.DefaultContext, activities_model.GetFeedsOptions{
- RequestedUser: org,
- Actor: user,
- IncludePrivate: true,
- OnlyPerformedBy: false,
- IncludeDeleted: true,
- })
- assert.NoError(t, err)
- assert.Len(t, actions, 1)
- if assert.Len(t, actions, 1) {
- assert.EqualValues(t, 2, actions[0].ID)
- assert.EqualValues(t, org.ID, actions[0].UserID)
- }
- assert.Equal(t, int64(1), count)
-
- actions, count, err = activities_model.GetFeeds(db.DefaultContext, activities_model.GetFeedsOptions{
- RequestedUser: org,
- Actor: user,
- IncludePrivate: false,
- OnlyPerformedBy: false,
- IncludeDeleted: true,
- })
- assert.NoError(t, err)
- assert.Len(t, actions, 0)
- assert.Equal(t, int64(0), count)
-}
-
func TestActivityReadable(t *testing.T) {
tt := []struct {
desc string
@@ -227,26 +119,6 @@ func TestNotifyWatchers(t *testing.T) {
})
}
-func TestGetFeedsCorrupted(t *testing.T) {
- // Now we will not check for corrupted data in the feeds
- // users should run doctor to fix their data
- assert.NoError(t, unittest.PrepareTestDatabase())
- user := unittest.AssertExistsAndLoadBean(t, &user_model.User{ID: 1})
- unittest.AssertExistsAndLoadBean(t, &activities_model.Action{
- ID: 8,
- RepoID: 1700,
- })
-
- actions, count, err := activities_model.GetFeeds(db.DefaultContext, activities_model.GetFeedsOptions{
- RequestedUser: user,
- Actor: user,
- IncludePrivate: true,
- })
- assert.NoError(t, err)
- assert.Len(t, actions, 1)
- assert.Equal(t, int64(1), count)
-}
-
func TestConsistencyUpdateAction(t *testing.T) {
if !setting.Database.Type.IsSQLite3() {
t.Skip("Test is only for SQLite database.")
@@ -322,24 +194,3 @@ func TestDeleteIssueActions(t *testing.T) {
assert.NoError(t, activities_model.DeleteIssueActions(db.DefaultContext, issue.RepoID, issue.ID, issue.Index))
unittest.AssertCount(t, &activities_model.Action{}, 0)
}
-
-func TestRepoActions(t *testing.T) {
- assert.NoError(t, unittest.PrepareTestDatabase())
- repo := unittest.AssertExistsAndLoadBean(t, &repo_model.Repository{ID: 1})
- _ = db.TruncateBeans(db.DefaultContext, &activities_model.Action{})
- for i := 0; i < 3; i++ {
- _ = db.Insert(db.DefaultContext, &activities_model.Action{
- UserID: 2 + int64(i),
- ActUserID: 2,
- RepoID: repo.ID,
- OpType: activities_model.ActionCommentIssue,
- })
- }
- count, _ := db.Count[activities_model.Action](db.DefaultContext, &db.ListOptions{})
- assert.EqualValues(t, 3, count)
- actions, _, err := activities_model.GetFeeds(db.DefaultContext, activities_model.GetFeedsOptions{
- RequestedRepo: repo,
- })
- assert.NoError(t, err)
- assert.Len(t, actions, 1)
-}
diff --git a/models/activities/user_heatmap.go b/models/activities/user_heatmap.go
index 78fcd76d43..1f8f0f590e 100644
--- a/models/activities/user_heatmap.go
+++ b/models/activities/user_heatmap.go
@@ -47,7 +47,7 @@ func getUserHeatmapData(ctx context.Context, user *user_model.User, team *organi
groupByName = groupBy
}
- cond, err := activityQueryCondition(ctx, GetFeedsOptions{
+ cond, err := ActivityQueryCondition(ctx, GetFeedsOptions{
RequestedUser: user,
RequestedTeam: team,
Actor: doer,
diff --git a/routers/api/v1/org/org.go b/routers/api/v1/org/org.go
index 9e58746272..3fb653bcb6 100644
--- a/routers/api/v1/org/org.go
+++ b/routers/api/v1/org/org.go
@@ -19,6 +19,7 @@ import (
"code.gitea.io/gitea/routers/api/v1/utils"
"code.gitea.io/gitea/services/context"
"code.gitea.io/gitea/services/convert"
+ feed_service "code.gitea.io/gitea/services/feed"
"code.gitea.io/gitea/services/org"
user_service "code.gitea.io/gitea/services/user"
)
@@ -447,7 +448,7 @@ func ListOrgActivityFeeds(ctx *context.APIContext) {
ListOptions: listOptions,
}
- feeds, count, err := activities_model.GetFeeds(ctx, opts)
+ feeds, count, err := feed_service.GetFeeds(ctx, opts)
if err != nil {
ctx.Error(http.StatusInternalServerError, "GetFeeds", err)
return
diff --git a/routers/api/v1/org/team.go b/routers/api/v1/org/team.go
index 20226b4d6b..bc50960b61 100644
--- a/routers/api/v1/org/team.go
+++ b/routers/api/v1/org/team.go
@@ -22,6 +22,7 @@ import (
"code.gitea.io/gitea/routers/api/v1/utils"
"code.gitea.io/gitea/services/context"
"code.gitea.io/gitea/services/convert"
+ feed_service "code.gitea.io/gitea/services/feed"
org_service "code.gitea.io/gitea/services/org"
repo_service "code.gitea.io/gitea/services/repository"
)
@@ -882,7 +883,7 @@ func ListTeamActivityFeeds(ctx *context.APIContext) {
ListOptions: listOptions,
}
- feeds, count, err := activities_model.GetFeeds(ctx, opts)
+ feeds, count, err := feed_service.GetFeeds(ctx, opts)
if err != nil {
ctx.Error(http.StatusInternalServerError, "GetFeeds", err)
return
diff --git a/routers/api/v1/repo/repo.go b/routers/api/v1/repo/repo.go
index 69a95dd5a5..40990a28cb 100644
--- a/routers/api/v1/repo/repo.go
+++ b/routers/api/v1/repo/repo.go
@@ -34,6 +34,7 @@ import (
actions_service "code.gitea.io/gitea/services/actions"
"code.gitea.io/gitea/services/context"
"code.gitea.io/gitea/services/convert"
+ feed_service "code.gitea.io/gitea/services/feed"
"code.gitea.io/gitea/services/issue"
repo_service "code.gitea.io/gitea/services/repository"
)
@@ -1313,7 +1314,7 @@ func ListRepoActivityFeeds(ctx *context.APIContext) {
ListOptions: listOptions,
}
- feeds, count, err := activities_model.GetFeeds(ctx, opts)
+ feeds, count, err := feed_service.GetFeeds(ctx, opts)
if err != nil {
ctx.Error(http.StatusInternalServerError, "GetFeeds", err)
return
diff --git a/routers/api/v1/user/user.go b/routers/api/v1/user/user.go
index a9011427fb..e668326861 100644
--- a/routers/api/v1/user/user.go
+++ b/routers/api/v1/user/user.go
@@ -13,6 +13,7 @@ import (
"code.gitea.io/gitea/routers/api/v1/utils"
"code.gitea.io/gitea/services/context"
"code.gitea.io/gitea/services/convert"
+ feed_service "code.gitea.io/gitea/services/feed"
)
// Search search users
@@ -214,7 +215,7 @@ func ListUserActivityFeeds(ctx *context.APIContext) {
ListOptions: listOptions,
}
- feeds, count, err := activities_model.GetFeeds(ctx, opts)
+ feeds, count, err := feed_service.GetFeeds(ctx, opts)
if err != nil {
ctx.Error(http.StatusInternalServerError, "GetFeeds", err)
return
diff --git a/routers/web/feed/profile.go b/routers/web/feed/profile.go
index 47de7c089d..4ec46e302a 100644
--- a/routers/web/feed/profile.go
+++ b/routers/web/feed/profile.go
@@ -10,6 +10,7 @@ import (
"code.gitea.io/gitea/models/renderhelper"
"code.gitea.io/gitea/modules/markup/markdown"
"code.gitea.io/gitea/services/context"
+ feed_service "code.gitea.io/gitea/services/feed"
"github.com/gorilla/feeds"
)
@@ -28,7 +29,7 @@ func ShowUserFeedAtom(ctx *context.Context) {
func showUserFeed(ctx *context.Context, formatType string) {
includePrivate := ctx.IsSigned && (ctx.Doer.IsAdmin || ctx.Doer.ID == ctx.ContextUser.ID)
- actions, _, err := activities_model.GetFeeds(ctx, activities_model.GetFeedsOptions{
+ actions, _, err := feed_service.GetFeeds(ctx, activities_model.GetFeedsOptions{
RequestedUser: ctx.ContextUser,
Actor: ctx.Doer,
IncludePrivate: includePrivate,
diff --git a/routers/web/feed/repo.go b/routers/web/feed/repo.go
index bfcc3a37d6..2e69fac758 100644
--- a/routers/web/feed/repo.go
+++ b/routers/web/feed/repo.go
@@ -9,13 +9,14 @@ import (
activities_model "code.gitea.io/gitea/models/activities"
repo_model "code.gitea.io/gitea/models/repo"
"code.gitea.io/gitea/services/context"
+ feed_service "code.gitea.io/gitea/services/feed"
"github.com/gorilla/feeds"
)
// ShowRepoFeed shows user activity on the repo as RSS / Atom feed
func ShowRepoFeed(ctx *context.Context, repo *repo_model.Repository, formatType string) {
- actions, _, err := activities_model.GetFeeds(ctx, activities_model.GetFeedsOptions{
+ actions, _, err := feed_service.GetFeeds(ctx, activities_model.GetFeedsOptions{
RequestedRepo: repo,
Actor: ctx.Doer,
IncludePrivate: true,
diff --git a/routers/web/user/home.go b/routers/web/user/home.go
index 6149ccb08d..0cf932ac03 100644
--- a/routers/web/user/home.go
+++ b/routers/web/user/home.go
@@ -33,6 +33,7 @@ import (
"code.gitea.io/gitea/modules/setting"
"code.gitea.io/gitea/routers/web/feed"
"code.gitea.io/gitea/services/context"
+ feed_service "code.gitea.io/gitea/services/feed"
issue_service "code.gitea.io/gitea/services/issue"
pull_service "code.gitea.io/gitea/services/pull"
@@ -113,7 +114,7 @@ func Dashboard(ctx *context.Context) {
ctx.Data["HeatmapTotalContributions"] = activities_model.GetTotalContributionsInHeatmap(data)
}
- feeds, count, err := activities_model.GetFeeds(ctx, activities_model.GetFeedsOptions{
+ feeds, count, err := feed_service.GetFeeds(ctx, activities_model.GetFeedsOptions{
RequestedUser: ctxUser,
RequestedTeam: ctx.Org.Team,
Actor: ctx.Doer,
diff --git a/routers/web/user/profile.go b/routers/web/user/profile.go
index 931af0a283..c41030a5e2 100644
--- a/routers/web/user/profile.go
+++ b/routers/web/user/profile.go
@@ -26,6 +26,7 @@ import (
"code.gitea.io/gitea/routers/web/org"
shared_user "code.gitea.io/gitea/routers/web/shared/user"
"code.gitea.io/gitea/services/context"
+ feed_service "code.gitea.io/gitea/services/feed"
)
const (
@@ -167,7 +168,7 @@ func prepareUserProfileTabData(ctx *context.Context, showPrivate bool, profileDb
case "activity":
date := ctx.FormString("date")
pagingNum = setting.UI.FeedPagingNum
- items, count, err := activities_model.GetFeeds(ctx, activities_model.GetFeedsOptions{
+ items, count, err := feed_service.GetFeeds(ctx, activities_model.GetFeedsOptions{
RequestedUser: ctx.ContextUser,
Actor: ctx.Doer,
IncludePrivate: showPrivate,
diff --git a/services/feed/feed.go b/services/feed/feed.go
new file mode 100644
index 0000000000..93bf875fd0
--- /dev/null
+++ b/services/feed/feed.go
@@ -0,0 +1,15 @@
+// Copyright 2024 The Gitea Authors. All rights reserved.
+// SPDX-License-Identifier: MIT
+
+package feed
+
+import (
+ "context"
+
+ activities_model "code.gitea.io/gitea/models/activities"
+)
+
+// GetFeeds returns actions according to the provided options
+func GetFeeds(ctx context.Context, opts activities_model.GetFeedsOptions) (activities_model.ActionList, int64, error) {
+ return activities_model.GetFeeds(ctx, opts)
+}
diff --git a/services/feed/feed_test.go b/services/feed/feed_test.go
new file mode 100644
index 0000000000..6f1cb9a969
--- /dev/null
+++ b/services/feed/feed_test.go
@@ -0,0 +1,165 @@
+// Copyright 2024 The Gitea Authors. All rights reserved.
+// SPDX-License-Identifier: MIT
+
+package feed
+
+import (
+ "testing"
+
+ activities_model "code.gitea.io/gitea/models/activities"
+ "code.gitea.io/gitea/models/db"
+ repo_model "code.gitea.io/gitea/models/repo"
+ "code.gitea.io/gitea/models/unittest"
+ user_model "code.gitea.io/gitea/models/user"
+
+ "github.com/stretchr/testify/assert"
+)
+
+func TestGetFeeds(t *testing.T) {
+ // test with an individual user
+ assert.NoError(t, unittest.PrepareTestDatabase())
+ user := unittest.AssertExistsAndLoadBean(t, &user_model.User{ID: 2})
+
+ actions, count, err := GetFeeds(db.DefaultContext, activities_model.GetFeedsOptions{
+ RequestedUser: user,
+ Actor: user,
+ IncludePrivate: true,
+ OnlyPerformedBy: false,
+ IncludeDeleted: true,
+ })
+ assert.NoError(t, err)
+ if assert.Len(t, actions, 1) {
+ assert.EqualValues(t, 1, actions[0].ID)
+ assert.EqualValues(t, user.ID, actions[0].UserID)
+ }
+ assert.Equal(t, int64(1), count)
+
+ actions, count, err = GetFeeds(db.DefaultContext, activities_model.GetFeedsOptions{
+ RequestedUser: user,
+ Actor: user,
+ IncludePrivate: false,
+ OnlyPerformedBy: false,
+ })
+ assert.NoError(t, err)
+ assert.Len(t, actions, 0)
+ assert.Equal(t, int64(0), count)
+}
+
+func TestGetFeedsForRepos(t *testing.T) {
+ assert.NoError(t, unittest.PrepareTestDatabase())
+ user := unittest.AssertExistsAndLoadBean(t, &user_model.User{ID: 2})
+ privRepo := unittest.AssertExistsAndLoadBean(t, &repo_model.Repository{ID: 2})
+ pubRepo := unittest.AssertExistsAndLoadBean(t, &repo_model.Repository{ID: 8})
+
+ // private repo & no login
+ actions, count, err := GetFeeds(db.DefaultContext, activities_model.GetFeedsOptions{
+ RequestedRepo: privRepo,
+ IncludePrivate: true,
+ })
+ assert.NoError(t, err)
+ assert.Len(t, actions, 0)
+ assert.Equal(t, int64(0), count)
+
+ // public repo & no login
+ actions, count, err = GetFeeds(db.DefaultContext, activities_model.GetFeedsOptions{
+ RequestedRepo: pubRepo,
+ IncludePrivate: true,
+ })
+ assert.NoError(t, err)
+ assert.Len(t, actions, 1)
+ assert.Equal(t, int64(1), count)
+
+ // private repo and login
+ actions, count, err = GetFeeds(db.DefaultContext, activities_model.GetFeedsOptions{
+ RequestedRepo: privRepo,
+ IncludePrivate: true,
+ Actor: user,
+ })
+ assert.NoError(t, err)
+ assert.Len(t, actions, 1)
+ assert.Equal(t, int64(1), count)
+
+ // public repo & login
+ actions, count, err = GetFeeds(db.DefaultContext, activities_model.GetFeedsOptions{
+ RequestedRepo: pubRepo,
+ IncludePrivate: true,
+ Actor: user,
+ })
+ assert.NoError(t, err)
+ assert.Len(t, actions, 1)
+ assert.Equal(t, int64(1), count)
+}
+
+func TestGetFeeds2(t *testing.T) {
+ // test with an organization user
+ assert.NoError(t, unittest.PrepareTestDatabase())
+ org := unittest.AssertExistsAndLoadBean(t, &user_model.User{ID: 3})
+ user := unittest.AssertExistsAndLoadBean(t, &user_model.User{ID: 2})
+
+ actions, count, err := GetFeeds(db.DefaultContext, activities_model.GetFeedsOptions{
+ RequestedUser: org,
+ Actor: user,
+ IncludePrivate: true,
+ OnlyPerformedBy: false,
+ IncludeDeleted: true,
+ })
+ assert.NoError(t, err)
+ assert.Len(t, actions, 1)
+ if assert.Len(t, actions, 1) {
+ assert.EqualValues(t, 2, actions[0].ID)
+ assert.EqualValues(t, org.ID, actions[0].UserID)
+ }
+ assert.Equal(t, int64(1), count)
+
+ actions, count, err = GetFeeds(db.DefaultContext, activities_model.GetFeedsOptions{
+ RequestedUser: org,
+ Actor: user,
+ IncludePrivate: false,
+ OnlyPerformedBy: false,
+ IncludeDeleted: true,
+ })
+ assert.NoError(t, err)
+ assert.Len(t, actions, 0)
+ assert.Equal(t, int64(0), count)
+}
+
+func TestGetFeedsCorrupted(t *testing.T) {
+ // Now we will not check for corrupted data in the feeds
+ // users should run doctor to fix their data
+ assert.NoError(t, unittest.PrepareTestDatabase())
+ user := unittest.AssertExistsAndLoadBean(t, &user_model.User{ID: 1})
+ unittest.AssertExistsAndLoadBean(t, &activities_model.Action{
+ ID: 8,
+ RepoID: 1700,
+ })
+
+ actions, count, err := GetFeeds(db.DefaultContext, activities_model.GetFeedsOptions{
+ RequestedUser: user,
+ Actor: user,
+ IncludePrivate: true,
+ })
+ assert.NoError(t, err)
+ assert.Len(t, actions, 1)
+ assert.Equal(t, int64(1), count)
+}
+
+func TestRepoActions(t *testing.T) {
+ assert.NoError(t, unittest.PrepareTestDatabase())
+ repo := unittest.AssertExistsAndLoadBean(t, &repo_model.Repository{ID: 1})
+ _ = db.TruncateBeans(db.DefaultContext, &activities_model.Action{})
+ for i := 0; i < 3; i++ {
+ _ = db.Insert(db.DefaultContext, &activities_model.Action{
+ UserID: 2 + int64(i),
+ ActUserID: 2,
+ RepoID: repo.ID,
+ OpType: activities_model.ActionCommentIssue,
+ })
+ }
+ count, _ := db.Count[activities_model.Action](db.DefaultContext, &db.ListOptions{})
+ assert.EqualValues(t, 3, count)
+ actions, _, err := GetFeeds(db.DefaultContext, activities_model.GetFeedsOptions{
+ RequestedRepo: repo,
+ })
+ assert.NoError(t, err)
+ assert.Len(t, actions, 1)
+}
diff --git a/services/feed/action.go b/services/feed/notifier.go
index a8820aeb77..a8820aeb77 100644
--- a/services/feed/action.go
+++ b/services/feed/notifier.go
diff --git a/services/feed/action_test.go b/services/feed/notifier_test.go
index 60cf7fbb49..60cf7fbb49 100644
--- a/services/feed/action_test.go
+++ b/services/feed/notifier_test.go