summaryrefslogtreecommitdiffstats
path: root/routers/web/explore/user.go
diff options
context:
space:
mode:
authorDaniel Baumann <daniel@debian.org>2024-10-18 20:33:49 +0200
committerDaniel Baumann <daniel@debian.org>2024-10-18 20:33:49 +0200
commitdd136858f1ea40ad3c94191d647487fa4f31926c (patch)
tree58fec94a7b2a12510c9664b21793f1ed560c6518 /routers/web/explore/user.go
parentInitial commit. (diff)
downloadforgejo-dd136858f1ea40ad3c94191d647487fa4f31926c.tar.xz
forgejo-dd136858f1ea40ad3c94191d647487fa4f31926c.zip
Adding upstream version 9.0.0.upstream/9.0.0upstreamdebian
Signed-off-by: Daniel Baumann <daniel@debian.org>
Diffstat (limited to 'routers/web/explore/user.go')
-rw-r--r--routers/web/explore/user.go163
1 files changed, 163 insertions, 0 deletions
diff --git a/routers/web/explore/user.go b/routers/web/explore/user.go
new file mode 100644
index 0000000..b79a79f
--- /dev/null
+++ b/routers/web/explore/user.go
@@ -0,0 +1,163 @@
+// Copyright 2021 The Gitea Authors. All rights reserved.
+// SPDX-License-Identifier: MIT
+
+package explore
+
+import (
+ "bytes"
+ "net/http"
+
+ "code.gitea.io/gitea/models/db"
+ user_model "code.gitea.io/gitea/models/user"
+ "code.gitea.io/gitea/modules/base"
+ "code.gitea.io/gitea/modules/container"
+ "code.gitea.io/gitea/modules/log"
+ "code.gitea.io/gitea/modules/optional"
+ "code.gitea.io/gitea/modules/setting"
+ "code.gitea.io/gitea/modules/sitemap"
+ "code.gitea.io/gitea/modules/structs"
+ "code.gitea.io/gitea/services/context"
+)
+
+const (
+ // tplExploreUsers explore users page template
+ tplExploreUsers base.TplName = "explore/users"
+)
+
+var nullByte = []byte{0x00}
+
+func isKeywordValid(keyword string) bool {
+ return !bytes.Contains([]byte(keyword), nullByte)
+}
+
+// RenderUserSearch render user search page
+func RenderUserSearch(ctx *context.Context, opts *user_model.SearchUserOptions, tplName base.TplName) {
+ // Sitemap index for sitemap paths
+ opts.Page = int(ctx.ParamsInt64("idx"))
+ isSitemap := ctx.Params("idx") != ""
+ if opts.Page <= 1 {
+ opts.Page = ctx.FormInt("page")
+ }
+ if opts.Page <= 1 {
+ opts.Page = 1
+ }
+
+ if isSitemap {
+ opts.PageSize = setting.UI.SitemapPagingNum
+ }
+
+ var (
+ users []*user_model.User
+ count int64
+ err error
+ orderBy db.SearchOrderBy
+ )
+
+ // we can not set orderBy to `models.SearchOrderByXxx`, because there may be a JOIN in the statement, different tables may have the same name columns
+
+ sortOrder := ctx.FormString("sort")
+ if sortOrder == "" {
+ sortOrder = setting.UI.ExploreDefaultSort
+ }
+ ctx.Data["SortType"] = sortOrder
+
+ switch sortOrder {
+ case "newest":
+ orderBy = "`user`.id DESC"
+ case "oldest":
+ orderBy = "`user`.id ASC"
+ case "leastupdate":
+ orderBy = "`user`.updated_unix ASC"
+ case "reversealphabetically":
+ orderBy = "`user`.name DESC"
+ case "lastlogin":
+ orderBy = "`user`.last_login_unix ASC"
+ case "reverselastlogin":
+ orderBy = "`user`.last_login_unix DESC"
+ case "alphabetically":
+ orderBy = "`user`.name ASC"
+ case "recentupdate":
+ fallthrough
+ default:
+ // in case the sortType is not valid, we set it to recentupdate
+ sortOrder = "recentupdate"
+ ctx.Data["SortType"] = "recentupdate"
+ orderBy = "`user`.updated_unix DESC"
+ }
+
+ if opts.SupportedSortOrders != nil && !opts.SupportedSortOrders.Contains(sortOrder) {
+ ctx.NotFound("unsupported sort order", nil)
+ return
+ }
+
+ opts.Keyword = ctx.FormTrim("q")
+ opts.OrderBy = orderBy
+ if len(opts.Keyword) == 0 || isKeywordValid(opts.Keyword) {
+ users, count, err = user_model.SearchUsers(ctx, opts)
+ if err != nil {
+ ctx.ServerError("SearchUsers", err)
+ return
+ }
+ }
+ if isSitemap {
+ m := sitemap.NewSitemap()
+ for _, item := range users {
+ 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
+ }
+
+ ctx.Data["Keyword"] = opts.Keyword
+ ctx.Data["Total"] = count
+ ctx.Data["Users"] = users
+ ctx.Data["UsersTwoFaStatus"] = user_model.UserList(users).GetTwoFaStatus(ctx)
+ ctx.Data["ShowUserEmail"] = setting.UI.ShowUserEmail
+ ctx.Data["IsRepoIndexerEnabled"] = setting.Indexer.RepoIndexerEnabled
+
+ pager := context.NewPagination(int(count), opts.PageSize, opts.Page, 5)
+ pager.SetDefaultParams(ctx)
+ for paramKey, paramVal := range opts.ExtraParamStrings {
+ pager.AddParamString(paramKey, paramVal)
+ }
+ ctx.Data["Page"] = pager
+
+ ctx.HTML(http.StatusOK, tplName)
+}
+
+// Users render explore users page
+func Users(ctx *context.Context) {
+ if setting.Service.Explore.DisableUsersPage {
+ ctx.Redirect(setting.AppSubURL + "/explore/repos")
+ return
+ }
+ ctx.Data["Title"] = ctx.Tr("explore")
+ ctx.Data["PageIsExplore"] = true
+ ctx.Data["PageIsExploreUsers"] = true
+ ctx.Data["IsRepoIndexerEnabled"] = setting.Indexer.RepoIndexerEnabled
+
+ supportedSortOrders := container.SetOf(
+ "newest",
+ "oldest",
+ "alphabetically",
+ "reversealphabetically",
+ )
+ sortOrder := ctx.FormString("sort")
+ if sortOrder == "" {
+ sortOrder = "newest"
+ ctx.SetFormString("sort", sortOrder)
+ }
+
+ RenderUserSearch(ctx, &user_model.SearchUserOptions{
+ Actor: ctx.Doer,
+ Type: user_model.UserTypeIndividual,
+ ListOptions: db.ListOptions{PageSize: setting.UI.ExplorePagingNum},
+ IsActive: optional.Some(true),
+ Visible: []structs.VisibleType{structs.VisibleTypePublic, structs.VisibleTypeLimited, structs.VisibleTypePrivate},
+
+ SupportedSortOrders: supportedSortOrders,
+ }, tplExploreUsers)
+}