Support "." char as user name for User/Orgs in RSS/ATOM/GPG/KEYS path ... (#23874)
- close #22301 workaround for https://github.com/go-chi/chi/issues/781
This commit is contained in:
parent
ca5722a0fa
commit
88033438aa
7 changed files with 107 additions and 15 deletions
|
@ -64,3 +64,12 @@
|
||||||
repo_id: 1700 # dangling intentional
|
repo_id: 1700 # dangling intentional
|
||||||
is_private: false
|
is_private: false
|
||||||
created_unix: 1603011541
|
created_unix: 1603011541
|
||||||
|
|
||||||
|
- id: 9
|
||||||
|
user_id: 34
|
||||||
|
op_type: 12 # close issue
|
||||||
|
act_user_id: 34
|
||||||
|
repo_id: 1 # public
|
||||||
|
is_private: false
|
||||||
|
created_unix: 1680454039
|
||||||
|
content: '4|' # issueId 5
|
||||||
|
|
|
@ -1220,3 +1220,41 @@
|
||||||
repo_admin_change_team_access: false
|
repo_admin_change_team_access: false
|
||||||
theme: ""
|
theme: ""
|
||||||
keep_activity_private: false
|
keep_activity_private: false
|
||||||
|
|
||||||
|
-
|
||||||
|
id: 34
|
||||||
|
lower_name: the_34-user.with.all.allowedchars
|
||||||
|
name: the_34-user.with.all.allowedChars
|
||||||
|
full_name: the_1-user.with.all.allowedChars
|
||||||
|
description: 'some [commonmark](https://commonmark.org/)!'
|
||||||
|
email: user34@example.com
|
||||||
|
keep_email_private: false
|
||||||
|
email_notifications_preference: enabled
|
||||||
|
passwd: ZogKvWdyEx:password
|
||||||
|
passwd_hash_algo: dummy
|
||||||
|
must_change_password: false
|
||||||
|
login_source: 0
|
||||||
|
login_name: the_34-user.with.all.allowedchars
|
||||||
|
type: 0
|
||||||
|
salt: ZogKvWdyEx
|
||||||
|
max_repo_creation: -1
|
||||||
|
is_active: true
|
||||||
|
is_admin: false
|
||||||
|
is_restricted: false
|
||||||
|
allow_git_hook: false
|
||||||
|
allow_import_local: false
|
||||||
|
allow_create_organization: false
|
||||||
|
prohibit_login: false
|
||||||
|
avatar: avatar34
|
||||||
|
avatar_email: user34@example.com
|
||||||
|
use_custom_avatar: true
|
||||||
|
num_followers: 0
|
||||||
|
num_following: 0
|
||||||
|
num_stars: 0
|
||||||
|
num_repos: 0
|
||||||
|
num_teams: 0
|
||||||
|
num_members: 0
|
||||||
|
visibility: 0
|
||||||
|
repo_admin_change_team_access: false
|
||||||
|
theme: ""
|
||||||
|
keep_activity_private: false
|
||||||
|
|
|
@ -99,13 +99,13 @@ func TestSearchUsers(t *testing.T) {
|
||||||
}
|
}
|
||||||
|
|
||||||
testUserSuccess(&user_model.SearchUserOptions{OrderBy: "id ASC", ListOptions: db.ListOptions{Page: 1}},
|
testUserSuccess(&user_model.SearchUserOptions{OrderBy: "id ASC", ListOptions: db.ListOptions{Page: 1}},
|
||||||
[]int64{1, 2, 4, 5, 8, 9, 10, 11, 12, 13, 14, 15, 16, 18, 20, 21, 24, 27, 28, 29, 30, 32})
|
[]int64{1, 2, 4, 5, 8, 9, 10, 11, 12, 13, 14, 15, 16, 18, 20, 21, 24, 27, 28, 29, 30, 32, 34})
|
||||||
|
|
||||||
testUserSuccess(&user_model.SearchUserOptions{ListOptions: db.ListOptions{Page: 1}, IsActive: util.OptionalBoolFalse},
|
testUserSuccess(&user_model.SearchUserOptions{ListOptions: db.ListOptions{Page: 1}, IsActive: util.OptionalBoolFalse},
|
||||||
[]int64{9})
|
[]int64{9})
|
||||||
|
|
||||||
testUserSuccess(&user_model.SearchUserOptions{OrderBy: "id ASC", ListOptions: db.ListOptions{Page: 1}, IsActive: util.OptionalBoolTrue},
|
testUserSuccess(&user_model.SearchUserOptions{OrderBy: "id ASC", ListOptions: db.ListOptions{Page: 1}, IsActive: util.OptionalBoolTrue},
|
||||||
[]int64{1, 2, 4, 5, 8, 10, 11, 12, 13, 14, 15, 16, 18, 20, 21, 24, 27, 28, 29, 30, 32})
|
[]int64{1, 2, 4, 5, 8, 10, 11, 12, 13, 14, 15, 16, 18, 20, 21, 24, 27, 28, 29, 30, 32, 34})
|
||||||
|
|
||||||
testUserSuccess(&user_model.SearchUserOptions{Keyword: "user1", OrderBy: "id ASC", ListOptions: db.ListOptions{Page: 1}, IsActive: util.OptionalBoolTrue},
|
testUserSuccess(&user_model.SearchUserOptions{Keyword: "user1", OrderBy: "id ASC", ListOptions: db.ListOptions{Page: 1}, IsActive: util.OptionalBoolTrue},
|
||||||
[]int64{1, 10, 11, 12, 13, 14, 15, 16, 18})
|
[]int64{1, 10, 11, 12, 13, 14, 15, 16, 18})
|
||||||
|
|
|
@ -8,6 +8,7 @@ import (
|
||||||
"net/http"
|
"net/http"
|
||||||
"os"
|
"os"
|
||||||
"path"
|
"path"
|
||||||
|
"strings"
|
||||||
|
|
||||||
"code.gitea.io/gitea/models/perm"
|
"code.gitea.io/gitea/models/perm"
|
||||||
"code.gitea.io/gitea/models/unit"
|
"code.gitea.io/gitea/models/unit"
|
||||||
|
@ -673,16 +674,47 @@ func RegisterRoutes(m *web.Route) {
|
||||||
})
|
})
|
||||||
http.ServeFile(ctx.Resp, ctx.Req, path.Join(setting.StaticRootPath, "public/img/favicon.png"))
|
http.ServeFile(ctx.Resp, ctx.Req, path.Join(setting.StaticRootPath, "public/img/favicon.png"))
|
||||||
})
|
})
|
||||||
m.Group("/{username}", func() {
|
m.Get("/{username}", func(ctx *context.Context) {
|
||||||
m.Get(".png", user.AvatarByUserName)
|
// WORKAROUND to support usernames with "." in it
|
||||||
m.Get(".keys", user.ShowSSHKeys)
|
// https://github.com/go-chi/chi/issues/781
|
||||||
m.Get(".gpg", user.ShowGPGKeys)
|
username := ctx.Params("username")
|
||||||
m.Get(".rss", feedEnabled, feed.ShowUserFeedRSS)
|
reloadParam := func(suffix string) (success bool) {
|
||||||
m.Get(".atom", feedEnabled, feed.ShowUserFeedAtom)
|
ctx.SetParams("username", strings.TrimSuffix(username, suffix))
|
||||||
m.Get("", user.Profile)
|
context_service.UserAssignmentWeb()(ctx)
|
||||||
}, func(ctx *context.Context) {
|
return !ctx.Written()
|
||||||
ctx.Data["EnableFeed"] = setting.EnableFeed
|
}
|
||||||
}, context_service.UserAssignmentWeb())
|
switch {
|
||||||
|
case strings.HasSuffix(username, ".png"):
|
||||||
|
if reloadParam(".png") {
|
||||||
|
user.AvatarByUserName(ctx)
|
||||||
|
}
|
||||||
|
case strings.HasSuffix(username, ".keys"):
|
||||||
|
if reloadParam(".keys") {
|
||||||
|
user.ShowSSHKeys(ctx)
|
||||||
|
}
|
||||||
|
case strings.HasSuffix(username, ".gpg"):
|
||||||
|
if reloadParam(".gpg") {
|
||||||
|
user.ShowGPGKeys(ctx)
|
||||||
|
}
|
||||||
|
case strings.HasSuffix(username, ".rss"):
|
||||||
|
feedEnabled(ctx)
|
||||||
|
if !ctx.Written() && reloadParam(".rss") {
|
||||||
|
context_service.UserAssignmentWeb()(ctx)
|
||||||
|
feed.ShowUserFeedRSS(ctx)
|
||||||
|
}
|
||||||
|
case strings.HasSuffix(username, ".atom"):
|
||||||
|
feedEnabled(ctx)
|
||||||
|
if !ctx.Written() && reloadParam(".atom") {
|
||||||
|
feed.ShowUserFeedAtom(ctx)
|
||||||
|
}
|
||||||
|
default:
|
||||||
|
context_service.UserAssignmentWeb()(ctx)
|
||||||
|
if !ctx.Written() {
|
||||||
|
ctx.Data["EnableFeed"] = setting.EnableFeed
|
||||||
|
user.Profile(ctx)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
})
|
||||||
m.Get("/attachments/{uuid}", repo.GetAttachment)
|
m.Get("/attachments/{uuid}", repo.GetAttachment)
|
||||||
}, ignSignIn)
|
}, ignSignIn)
|
||||||
|
|
||||||
|
|
|
@ -33,7 +33,7 @@ func TestNodeinfo(t *testing.T) {
|
||||||
DecodeJSON(t, resp, &nodeinfo)
|
DecodeJSON(t, resp, &nodeinfo)
|
||||||
assert.True(t, nodeinfo.OpenRegistrations)
|
assert.True(t, nodeinfo.OpenRegistrations)
|
||||||
assert.Equal(t, "gitea", nodeinfo.Software.Name)
|
assert.Equal(t, "gitea", nodeinfo.Software.Name)
|
||||||
assert.Equal(t, 24, nodeinfo.Usage.Users.Total)
|
assert.Equal(t, 25, nodeinfo.Usage.Users.Total)
|
||||||
assert.Equal(t, 18, nodeinfo.Usage.LocalPosts)
|
assert.Equal(t, 18, nodeinfo.Usage.LocalPosts)
|
||||||
assert.Equal(t, 2, nodeinfo.Usage.LocalComments)
|
assert.Equal(t, 2, nodeinfo.Usage.LocalComments)
|
||||||
})
|
})
|
||||||
|
|
|
@ -25,7 +25,7 @@ func TestSettingShowUserEmailExplore(t *testing.T) {
|
||||||
htmlDoc := NewHTMLParser(t, resp.Body)
|
htmlDoc := NewHTMLParser(t, resp.Body)
|
||||||
assert.Contains(t,
|
assert.Contains(t,
|
||||||
htmlDoc.doc.Find(".ui.user.list").Text(),
|
htmlDoc.doc.Find(".ui.user.list").Text(),
|
||||||
"user4@example.com",
|
"user34@example.com",
|
||||||
)
|
)
|
||||||
|
|
||||||
setting.UI.ShowUserEmail = false
|
setting.UI.ShowUserEmail = false
|
||||||
|
@ -35,7 +35,7 @@ func TestSettingShowUserEmailExplore(t *testing.T) {
|
||||||
htmlDoc = NewHTMLParser(t, resp.Body)
|
htmlDoc = NewHTMLParser(t, resp.Body)
|
||||||
assert.NotContains(t,
|
assert.NotContains(t,
|
||||||
htmlDoc.doc.Find(".ui.user.list").Text(),
|
htmlDoc.doc.Find(".ui.user.list").Text(),
|
||||||
"user4@example.com",
|
"user34@example.com",
|
||||||
)
|
)
|
||||||
|
|
||||||
setting.UI.ShowUserEmail = showUserEmail
|
setting.UI.ShowUserEmail = showUserEmail
|
||||||
|
|
|
@ -241,6 +241,19 @@ func testExportUserGPGKeys(t *testing.T, user, expected string) {
|
||||||
assert.Equal(t, expected, resp.Body.String())
|
assert.Equal(t, expected, resp.Body.String())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func TestGetUserRss(t *testing.T) {
|
||||||
|
user34 := "the_34-user.with.all.allowedChars"
|
||||||
|
req := NewRequestf(t, "GET", "/%s.rss", user34)
|
||||||
|
resp := MakeRequest(t, req, http.StatusOK)
|
||||||
|
if assert.EqualValues(t, "application/rss+xml;charset=utf-8", resp.Header().Get("Content-Type")) {
|
||||||
|
rssDoc := NewHTMLParser(t, resp.Body).Find("channel")
|
||||||
|
title, _ := rssDoc.ChildrenFiltered("title").Html()
|
||||||
|
assert.EqualValues(t, "Feed of "the_1-user.with.all.allowedChars"", title)
|
||||||
|
description, _ := rssDoc.ChildrenFiltered("description").Html()
|
||||||
|
assert.EqualValues(t, "<p>some <a href="https://commonmark.org/" rel="nofollow">commonmark</a>!</p>\n", description)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
func TestListStopWatches(t *testing.T) {
|
func TestListStopWatches(t *testing.T) {
|
||||||
defer tests.PrepareTestEnv(t)()
|
defer tests.PrepareTestEnv(t)()
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue