@@ -13,16 +13,23 @@ import (
1313 "strings"
1414
1515 activities_model "code.gitea.io/gitea/models/activities"
16+ "code.gitea.io/gitea/models/db"
17+ issues_model "code.gitea.io/gitea/models/issues"
18+ repo_model "code.gitea.io/gitea/models/repo"
1619 "code.gitea.io/gitea/modules/base"
1720 "code.gitea.io/gitea/modules/context"
1821 "code.gitea.io/gitea/modules/log"
1922 "code.gitea.io/gitea/modules/setting"
2023 "code.gitea.io/gitea/modules/structs"
24+ "code.gitea.io/gitea/modules/util"
25+ issue_service "code.gitea.io/gitea/services/issue"
26+ pull_service "code.gitea.io/gitea/services/pull"
2127)
2228
2329const (
24- tplNotification base.TplName = "user/notification/notification"
25- tplNotificationDiv base.TplName = "user/notification/notification_div"
30+ tplNotification base.TplName = "user/notification/notification"
31+ tplNotificationDiv base.TplName = "user/notification/notification_div"
32+ tplNotificationSubscriptions base.TplName = "user/notification/notification_subscriptions"
2633)
2734
2835// GetNotificationCount is the middleware that sets the notification count in the context
@@ -197,6 +204,208 @@ func NotificationPurgePost(c *context.Context) {
197204 c .Redirect (setting .AppSubURL + "/notifications" , http .StatusSeeOther )
198205}
199206
207+ // NotificationSubscriptions returns the list of subscribed issues
208+ func NotificationSubscriptions (c * context.Context ) {
209+ page := c .FormInt ("page" )
210+ if page < 1 {
211+ page = 1
212+ }
213+
214+ sortType := c .FormString ("sort" )
215+ c .Data ["SortType" ] = sortType
216+
217+ state := c .FormString ("state" )
218+ if ! util .IsStringInSlice (state , []string {"all" , "open" , "closed" }, true ) {
219+ state = "all"
220+ }
221+ c .Data ["State" ] = state
222+ var showClosed util.OptionalBool
223+ switch state {
224+ case "all" :
225+ showClosed = util .OptionalBoolNone
226+ case "closed" :
227+ showClosed = util .OptionalBoolTrue
228+ case "open" :
229+ showClosed = util .OptionalBoolFalse
230+ }
231+
232+ var issueTypeBool util.OptionalBool
233+ issueType := c .FormString ("issueType" )
234+ switch issueType {
235+ case "issues" :
236+ issueTypeBool = util .OptionalBoolFalse
237+ case "pulls" :
238+ issueTypeBool = util .OptionalBoolTrue
239+ default :
240+ issueTypeBool = util .OptionalBoolNone
241+ }
242+ c .Data ["IssueType" ] = issueType
243+
244+ var labelIDs []int64
245+ selectedLabels := c .FormString ("labels" )
246+ c .Data ["Labels" ] = selectedLabels
247+ if len (selectedLabels ) > 0 && selectedLabels != "0" {
248+ var err error
249+ labelIDs , err = base .StringsToInt64s (strings .Split (selectedLabels , "," ))
250+ if err != nil {
251+ c .ServerError ("StringsToInt64s" , err )
252+ return
253+ }
254+ }
255+
256+ count , err := issues_model .CountIssues (& issues_model.IssuesOptions {
257+ SubscriberID : c .Doer .ID ,
258+ IsClosed : showClosed ,
259+ IsPull : issueTypeBool ,
260+ LabelIDs : labelIDs ,
261+ })
262+ if err != nil {
263+ c .ServerError ("CountIssues" , err )
264+ return
265+ }
266+ issues , err := issues_model .Issues (& issues_model.IssuesOptions {
267+ ListOptions : db.ListOptions {
268+ PageSize : setting .UI .IssuePagingNum ,
269+ Page : page ,
270+ },
271+ SubscriberID : c .Doer .ID ,
272+ SortType : sortType ,
273+ IsClosed : showClosed ,
274+ IsPull : issueTypeBool ,
275+ LabelIDs : labelIDs ,
276+ })
277+ if err != nil {
278+ c .ServerError ("Issues" , err )
279+ return
280+ }
281+
282+ commitStatuses , lastStatus , err := pull_service .GetIssuesAllCommitStatus (c , issues )
283+ if err != nil {
284+ c .ServerError ("GetIssuesAllCommitStatus" , err )
285+ return
286+ }
287+ c .Data ["CommitLastStatus" ] = lastStatus
288+ c .Data ["CommitStatuses" ] = commitStatuses
289+ c .Data ["Issues" ] = issues
290+
291+ c .Data ["IssueRefEndNames" ], c .Data ["IssueRefURLs" ] = issue_service .GetRefEndNamesAndURLs (issues , "" )
292+
293+ commitStatus , err := pull_service .GetIssuesLastCommitStatus (c , issues )
294+ if err != nil {
295+ c .ServerError ("GetIssuesLastCommitStatus" , err )
296+ return
297+ }
298+ c .Data ["CommitStatus" ] = commitStatus
299+
300+ issueList := issues_model .IssueList (issues )
301+ approvalCounts , err := issueList .GetApprovalCounts (c )
302+ if err != nil {
303+ c .ServerError ("ApprovalCounts" , err )
304+ return
305+ }
306+ c .Data ["ApprovalCounts" ] = func (issueID int64 , typ string ) int64 {
307+ counts , ok := approvalCounts [issueID ]
308+ if ! ok || len (counts ) == 0 {
309+ return 0
310+ }
311+ reviewTyp := issues_model .ReviewTypeApprove
312+ if typ == "reject" {
313+ reviewTyp = issues_model .ReviewTypeReject
314+ } else if typ == "waiting" {
315+ reviewTyp = issues_model .ReviewTypeRequest
316+ }
317+ for _ , count := range counts {
318+ if count .Type == reviewTyp {
319+ return count .Count
320+ }
321+ }
322+ return 0
323+ }
324+
325+ c .Data ["Status" ] = 1
326+ c .Data ["Title" ] = c .Tr ("notification.subscriptions" )
327+
328+ // redirect to last page if request page is more than total pages
329+ pager := context .NewPagination (int (count ), setting .UI .IssuePagingNum , page , 5 )
330+ if pager .Paginater .Current () < page {
331+ c .Redirect (fmt .Sprintf ("/notifications/subscriptions?page=%d" , pager .Paginater .Current ()))
332+ return
333+ }
334+ pager .AddParam (c , "sort" , "SortType" )
335+ pager .AddParam (c , "state" , "State" )
336+ c .Data ["Page" ] = pager
337+
338+ c .HTML (http .StatusOK , tplNotificationSubscriptions )
339+ }
340+
341+ // NotificationWatching returns the list of watching repos
342+ func NotificationWatching (c * context.Context ) {
343+ page := c .FormInt ("page" )
344+ if page < 1 {
345+ page = 1
346+ }
347+
348+ var orderBy db.SearchOrderBy
349+ c .Data ["SortType" ] = c .FormString ("sort" )
350+ switch c .FormString ("sort" ) {
351+ case "newest" :
352+ orderBy = db .SearchOrderByNewest
353+ case "oldest" :
354+ orderBy = db .SearchOrderByOldest
355+ case "recentupdate" :
356+ orderBy = db .SearchOrderByRecentUpdated
357+ case "leastupdate" :
358+ orderBy = db .SearchOrderByLeastUpdated
359+ case "reversealphabetically" :
360+ orderBy = db .SearchOrderByAlphabeticallyReverse
361+ case "alphabetically" :
362+ orderBy = db .SearchOrderByAlphabetically
363+ case "moststars" :
364+ orderBy = db .SearchOrderByStarsReverse
365+ case "feweststars" :
366+ orderBy = db .SearchOrderByStars
367+ case "mostforks" :
368+ orderBy = db .SearchOrderByForksReverse
369+ case "fewestforks" :
370+ orderBy = db .SearchOrderByForks
371+ default :
372+ c .Data ["SortType" ] = "recentupdate"
373+ orderBy = db .SearchOrderByRecentUpdated
374+ }
375+
376+ repos , count , err := repo_model .SearchRepository (& repo_model.SearchRepoOptions {
377+ ListOptions : db.ListOptions {
378+ PageSize : setting .UI .User .RepoPagingNum ,
379+ Page : page ,
380+ },
381+ Actor : c .Doer ,
382+ Keyword : c .FormTrim ("q" ),
383+ OrderBy : orderBy ,
384+ Private : c .IsSigned ,
385+ WatchedByID : c .Doer .ID ,
386+ Collaborate : util .OptionalBoolFalse ,
387+ TopicOnly : c .FormBool ("topic" ),
388+ IncludeDescription : setting .UI .SearchRepoDescription ,
389+ })
390+ if err != nil {
391+ c .ServerError ("ErrSearchRepository" , err )
392+ return
393+ }
394+ total := int (count )
395+ c .Data ["Total" ] = total
396+ c .Data ["Repos" ] = repos
397+
398+ // redirect to last page if request page is more than total pages
399+ pager := context .NewPagination (total , setting .UI .User .RepoPagingNum , page , 5 )
400+ pager .SetDefaultParams (c )
401+ c .Data ["Page" ] = pager
402+
403+ c .Data ["Status" ] = 2
404+ c .Data ["Title" ] = c .Tr ("notification.watching" )
405+
406+ c .HTML (http .StatusOK , tplNotificationSubscriptions )
407+ }
408+
200409// NewAvailable returns the notification counts
201410func NewAvailable (ctx * context.Context ) {
202411 ctx .JSON (http .StatusOK , structs.NotificationCount {New : activities_model .CountUnread (ctx , ctx .Doer .ID )})
0 commit comments