2021-06-09 02:33:54 +03:00
// Copyright 2021 The Gitea Authors. All rights reserved.
2022-11-27 21:20:29 +03:00
// SPDX-License-Identifier: MIT
2021-06-09 02:33:54 +03:00
package explore
import (
2023-03-29 16:41:45 +03:00
"fmt"
2021-06-09 02:33:54 +03:00
"net/http"
2024-06-13 12:13:11 +03:00
"strings"
2021-06-09 02:33:54 +03:00
2021-09-24 14:32:56 +03:00
"code.gitea.io/gitea/models/db"
2021-12-10 04:27:50 +03:00
repo_model "code.gitea.io/gitea/models/repo"
2021-06-09 02:33:54 +03:00
"code.gitea.io/gitea/modules/base"
2022-06-25 20:06:01 +03:00
"code.gitea.io/gitea/modules/log"
2021-06-09 02:33:54 +03:00
"code.gitea.io/gitea/modules/setting"
2022-06-25 20:06:01 +03:00
"code.gitea.io/gitea/modules/sitemap"
2024-02-27 10:12:22 +03:00
"code.gitea.io/gitea/services/context"
2021-06-09 02:33:54 +03:00
)
const (
// tplExploreRepos explore repositories page template
2023-02-04 16:26:38 +03:00
tplExploreRepos base . TplName = "explore/repos"
2023-03-29 16:41:45 +03:00
relevantReposOnlyParam string = "only_show_relevant"
2021-06-09 02:33:54 +03:00
)
// RepoSearchOptions when calling search repositories
type RepoSearchOptions struct {
2023-02-24 22:11:31 +03:00
OwnerID int64
Private bool
Restricted bool
PageSize int
OnlyShowRelevant bool
TplName base . TplName
2021-06-09 02:33:54 +03:00
}
// RenderRepoSearch render repositories search page
2023-02-24 22:11:31 +03:00
// This function is also used to render the Admin Repository Management page.
2021-06-09 02:33:54 +03:00
func RenderRepoSearch ( ctx * context . Context , opts * RepoSearchOptions ) {
2022-06-25 20:06:01 +03:00
// Sitemap index for sitemap paths
2024-06-19 01:32:45 +03:00
page := int ( ctx . PathParamInt64 ( "idx" ) )
isSitemap := ctx . PathParam ( "idx" ) != ""
2022-06-25 20:06:01 +03:00
if page <= 1 {
page = ctx . FormInt ( "page" )
}
2021-06-09 02:33:54 +03:00
if page <= 0 {
page = 1
}
2022-06-25 20:06:01 +03:00
if isSitemap {
opts . PageSize = setting . UI . SitemapPagingNum
}
2021-06-09 02:33:54 +03:00
var (
2023-02-24 22:11:31 +03:00
repos [ ] * repo_model . Repository
count int64
err error
orderBy db . SearchOrderBy
2021-06-09 02:33:54 +03:00
)
2024-06-13 12:13:11 +03:00
sortOrder := strings . ToLower ( ctx . FormString ( "sort" ) )
2023-11-09 13:11:45 +03:00
if sortOrder == "" {
sortOrder = setting . UI . ExploreDefaultSort
}
2024-06-15 09:45:02 +03:00
if order , ok := repo_model . OrderByFlatMap [ sortOrder ] ; ok {
2024-06-13 12:13:11 +03:00
orderBy = order
} else {
sortOrder = "recentupdate"
2021-11-24 12:49:20 +03:00
orderBy = db . SearchOrderByRecentUpdated
2021-06-09 02:33:54 +03:00
}
2024-06-13 12:13:11 +03:00
ctx . Data [ "SortType" ] = sortOrder
2021-06-09 02:33:54 +03:00
2021-08-11 18:08:52 +03:00
keyword := ctx . FormTrim ( "q" )
2022-08-25 21:38:41 +03:00
2023-02-24 22:11:31 +03:00
ctx . Data [ "OnlyShowRelevant" ] = opts . OnlyShowRelevant
2022-08-25 21:38:41 +03:00
2021-07-29 04:42:15 +03:00
topicOnly := ctx . FormBool ( "topic" )
2021-06-09 02:33:54 +03:00
ctx . Data [ "TopicOnly" ] = topicOnly
2022-01-28 14:29:04 +03:00
language := ctx . FormTrim ( "language" )
ctx . Data [ "Language" ] = language
2024-03-03 13:18:34 +03:00
archived := ctx . FormOptionalBool ( "archived" )
ctx . Data [ "IsArchived" ] = archived
fork := ctx . FormOptionalBool ( "fork" )
ctx . Data [ "IsFork" ] = fork
mirror := ctx . FormOptionalBool ( "mirror" )
ctx . Data [ "IsMirror" ] = mirror
template := ctx . FormOptionalBool ( "template" )
ctx . Data [ "IsTemplate" ] = template
private := ctx . FormOptionalBool ( "private" )
ctx . Data [ "IsPrivate" ] = private
2022-11-19 11:12:33 +03:00
repos , count , err = repo_model . SearchRepository ( ctx , & repo_model . SearchRepoOptions {
2021-09-24 14:32:56 +03:00
ListOptions : db . ListOptions {
2021-06-09 02:33:54 +03:00
Page : page ,
PageSize : opts . PageSize ,
} ,
2022-03-22 10:03:22 +03:00
Actor : ctx . Doer ,
2021-06-09 02:33:54 +03:00
OrderBy : orderBy ,
Private : opts . Private ,
Keyword : keyword ,
OwnerID : opts . OwnerID ,
AllPublic : true ,
AllLimited : true ,
TopicOnly : topicOnly ,
2022-01-28 14:29:04 +03:00
Language : language ,
2021-06-09 02:33:54 +03:00
IncludeDescription : setting . UI . SearchRepoDescription ,
2023-02-24 22:11:31 +03:00
OnlyShowRelevant : opts . OnlyShowRelevant ,
2024-03-03 13:18:34 +03:00
Archived : archived ,
Fork : fork ,
Mirror : mirror ,
Template : template ,
IsPrivate : private ,
2021-06-09 02:33:54 +03:00
} )
if err != nil {
ctx . ServerError ( "SearchRepository" , err )
return
}
2022-06-25 20:06:01 +03:00
if isSitemap {
m := sitemap . NewSitemap ( )
for _ , item := range repos {
m . Add ( sitemap . URL { URL : item . HTMLURL ( ) , LastMod : item . UpdatedUnix . AsTimePtr ( ) } )
}
ctx . Resp . Header ( ) . Set ( "Content-Type" , "text/xml" )
if _ , err := m . WriteTo ( ctx . Resp ) ; err != nil {
log . Error ( "Failed writing sitemap: %v" , err )
}
return
}
2021-06-09 02:33:54 +03:00
ctx . Data [ "Keyword" ] = keyword
ctx . Data [ "Total" ] = count
ctx . Data [ "Repos" ] = repos
ctx . Data [ "IsRepoIndexerEnabled" ] = setting . Indexer . RepoIndexerEnabled
pager := context . NewPagination ( int ( count ) , opts . PageSize , page , 5 )
pager . SetDefaultParams ( ctx )
2024-03-16 15:07:56 +03:00
pager . AddParamString ( "topic" , fmt . Sprint ( topicOnly ) )
pager . AddParamString ( "language" , language )
2023-03-29 16:41:45 +03:00
pager . AddParamString ( relevantReposOnlyParam , fmt . Sprint ( opts . OnlyShowRelevant ) )
2021-06-09 02:33:54 +03:00
ctx . Data [ "Page" ] = pager
ctx . HTML ( http . StatusOK , opts . TplName )
}
// Repos render explore repositories page
func Repos ( ctx * context . Context ) {
ctx . Data [ "UsersIsDisabled" ] = setting . Service . Explore . DisableUsersPage
ctx . Data [ "Title" ] = ctx . Tr ( "explore" )
ctx . Data [ "PageIsExplore" ] = true
ctx . Data [ "PageIsExploreRepositories" ] = true
ctx . Data [ "IsRepoIndexerEnabled" ] = setting . Indexer . RepoIndexerEnabled
var ownerID int64
2022-03-22 10:03:22 +03:00
if ctx . Doer != nil && ! ctx . Doer . IsAdmin {
ownerID = ctx . Doer . ID
2021-06-09 02:33:54 +03:00
}
2023-03-29 16:41:45 +03:00
onlyShowRelevant := setting . UI . OnlyShowRelevantRepos
_ = ctx . Req . ParseForm ( ) // parse the form first, to prepare the ctx.Req.Form field
if len ( ctx . Req . Form [ relevantReposOnlyParam ] ) != 0 {
onlyShowRelevant = ctx . FormBool ( relevantReposOnlyParam )
}
2021-06-09 02:33:54 +03:00
RenderRepoSearch ( ctx , & RepoSearchOptions {
2023-02-24 22:11:31 +03:00
PageSize : setting . UI . ExplorePagingNum ,
OwnerID : ownerID ,
Private : ctx . Doer != nil ,
TplName : tplExploreRepos ,
2023-03-29 16:41:45 +03:00
OnlyShowRelevant : onlyShowRelevant ,
2021-06-09 02:33:54 +03:00
} )
}