Skip to content

Commit 4be5879

Browse files
committed
Change team mention rules to gh's style
* use org's avator as team avator in ui Signed-off-by: a1012112796 <[email protected]>
1 parent ffe92b7 commit 4be5879

File tree

7 files changed

+59
-35
lines changed

7 files changed

+59
-35
lines changed

models/issue.go

Lines changed: 44 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -1838,30 +1838,43 @@ func (issue *Issue) ResolveMentionsByVisibility(ctx DBContext, doer *User, menti
18381838
if err = issue.loadRepo(ctx.e); err != nil {
18391839
return
18401840
}
1841-
resolved := make(map[string]bool, 20)
1842-
names := make([]string, 0, 20)
1841+
1842+
resolved := make(map[string]bool, 10)
1843+
var mentionTeams []string
1844+
1845+
if err := issue.Repo.getOwner(ctx.e); err != nil {
1846+
return nil, err
1847+
}
1848+
1849+
repoOwnerIsOrg := issue.Repo.Owner.IsOrganization()
1850+
if repoOwnerIsOrg {
1851+
mentionTeams = make([]string, 5)
1852+
}
1853+
18431854
resolved[doer.LowerName] = true
18441855
for _, name := range mentions {
18451856
name := strings.ToLower(name)
18461857
if _, ok := resolved[name]; ok {
18471858
continue
18481859
}
1849-
resolved[name] = false
1850-
names = append(names, name)
1851-
}
1852-
1853-
if err := issue.Repo.getOwner(ctx.e); err != nil {
1854-
return nil, err
1860+
if repoOwnerIsOrg && strings.Contains(name, "/") {
1861+
names := strings.Split(name, "/")
1862+
if len(names) < 2 || names[0] != issue.Repo.Owner.LowerName {
1863+
continue
1864+
}
1865+
mentionTeams = append(mentionTeams, names[1])
1866+
resolved[name] = true
1867+
} else {
1868+
resolved[name] = false
1869+
}
18551870
}
18561871

1857-
if issue.Repo.Owner.IsOrganization() {
1858-
// Since there can be users with names that match the name of a team,
1859-
// if the team exists and can read the issue, the team takes precedence.
1860-
teams := make([]*Team, 0, len(names))
1872+
if issue.Repo.Owner.IsOrganization() && len(mentionTeams) > 0 {
1873+
teams := make([]*Team, 0, len(mentionTeams))
18611874
if err := ctx.e.
18621875
Join("INNER", "team_repo", "team_repo.team_id = team.id").
18631876
Where("team_repo.repo_id=?", issue.Repo.ID).
1864-
In("team.lower_name", names).
1877+
In("team.lower_name", mentionTeams).
18651878
Find(&teams); err != nil {
18661879
return nil, fmt.Errorf("find mentioned teams: %v", err)
18671880
}
@@ -1874,7 +1887,7 @@ func (issue *Issue) ResolveMentionsByVisibility(ctx DBContext, doer *User, menti
18741887
for _, team := range teams {
18751888
if team.Authorize >= AccessModeOwner {
18761889
checked = append(checked, team.ID)
1877-
resolved[team.LowerName] = true
1890+
resolved[issue.Repo.Owner.LowerName+"/"+team.LowerName] = true
18781891
continue
18791892
}
18801893
has, err := ctx.e.Get(&TeamUnit{OrgID: issue.Repo.Owner.ID, TeamID: team.ID, Type: unittype})
@@ -1883,10 +1896,10 @@ func (issue *Issue) ResolveMentionsByVisibility(ctx DBContext, doer *User, menti
18831896
}
18841897
if has {
18851898
checked = append(checked, team.ID)
1886-
resolved[team.LowerName] = true
1899+
resolved[issue.Repo.Owner.LowerName+"/"+team.LowerName] = true
18871900
}
18881901
}
1889-
if len(checked) != 0 {
1902+
if len(checked) > 0 {
18901903
teamusers := make([]*User, 0, 20)
18911904
if err := ctx.e.
18921905
Join("INNER", "team_user", "team_user.uid = `user`.id").
@@ -1907,24 +1920,28 @@ func (issue *Issue) ResolveMentionsByVisibility(ctx DBContext, doer *User, menti
19071920
}
19081921
}
19091922
}
1923+
}
19101924

1911-
// Remove names already in the list to avoid querying the database if pending names remain
1912-
names = make([]string, 0, len(resolved))
1913-
for name, already := range resolved {
1914-
if !already {
1915-
names = append(names, name)
1916-
}
1917-
}
1918-
if len(names) == 0 {
1919-
return
1925+
// Remove names already in the list to avoid querying the database if pending names remain
1926+
mentionUsers := make([]string, 0, len(resolved))
1927+
for name, already := range resolved {
1928+
if !already {
1929+
mentionUsers = append(mentionUsers, name)
19201930
}
19211931
}
1932+
if len(mentionUsers) == 0 {
1933+
return
1934+
}
1935+
1936+
if users == nil {
1937+
users = make([]*User, 0, len(mentionUsers))
1938+
}
19221939

1923-
unchecked := make([]*User, 0, len(names))
1940+
unchecked := make([]*User, 0, len(mentionUsers))
19241941
if err := ctx.e.
19251942
Where("`user`.is_active = ?", true).
19261943
And("`user`.prohibit_login = ?", false).
1927-
In("`user`.lower_name", names).
1944+
In("`user`.lower_name", mentionUsers).
19281945
Find(&unchecked); err != nil {
19291946
return nil, fmt.Errorf("find mentioned users: %v", err)
19301947
}

models/issue_test.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -400,5 +400,5 @@ func TestIssue_ResolveMentions(t *testing.T) {
400400
// Private repo, not a team member
401401
testSuccess("user17", "big_test_private_4", "user20", []string{"user5"}, []int64{})
402402
// Private repo, whole team
403-
testSuccess("user17", "big_test_private_4", "user15", []string{"owners"}, []int64{18})
403+
testSuccess("user17", "big_test_private_4", "user15", []string{"user17/owners"}, []int64{18})
404404
}

modules/markup/html.go

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -568,7 +568,7 @@ func replaceContentList(node *html.Node, i, j int, newNodes []*html.Node) {
568568
}
569569
}
570570

571-
func mentionProcessor(ctx *postProcessCtx, node *html.Node) {
571+
func mentionProcessor(ctx *postProcessCtx, node *html.Node) { // TODO
572572
// We replace only the first mention; other mentions will be addressed later
573573
found, loc := references.FindFirstMentionBytes([]byte(node.Data))
574574
if !found {
@@ -577,8 +577,12 @@ func mentionProcessor(ctx *postProcessCtx, node *html.Node) {
577577
mention := node.Data[loc.Start:loc.End]
578578
var teams string
579579
teams, ok := ctx.metas["teams"]
580-
if ok && strings.Contains(teams, ","+strings.ToLower(mention[1:])+",") {
581-
replaceContent(node, loc.Start, loc.End, createLink(util.URLJoin(setting.AppURL, "org", ctx.metas["org"], "teams", mention[1:]), mention, "mention"))
580+
// team mention should follow @orgName/teamName style
581+
if ok && strings.Contains(mention, "/") {
582+
mentionOrgAndTeam := strings.Split(mention, "/")
583+
if mentionOrgAndTeam[0][1:] == ctx.metas["org"] && strings.Contains(teams, ","+strings.ToLower(mentionOrgAndTeam[1])+",") {
584+
replaceContent(node, loc.Start, loc.End, createLink(util.URLJoin(setting.AppURL, "org", ctx.metas["org"], "teams", mentionOrgAndTeam[1]), mention, "mention"))
585+
}
582586
} else {
583587
replaceContent(node, loc.Start, loc.End, createLink(util.URLJoin(setting.AppURL, mention[1:]), mention, "mention"))
584588
}

modules/references/references.go

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -26,8 +26,8 @@ var (
2626
// While fast, this is also incorrect and lead to false positives.
2727
// TODO: fix invalid linking issue
2828

29-
// mentionPattern matches all mentions in the form of "@user"
30-
mentionPattern = regexp.MustCompile(`(?:\s|^|\(|\[)(@[0-9a-zA-Z-_]+|@[0-9a-zA-Z-_][0-9a-zA-Z-_.]+[0-9a-zA-Z-_])(?:\s|[:,;.?!]\s|[:,;.?!]?$|\)|\])`)
29+
// mentionPattern matches all mentions in the form of "@user" or "@org/team"
30+
mentionPattern = regexp.MustCompile(`(?:\s|^|\(|\[)(@[0-9a-zA-Z-_]+|@[0-9a-zA-Z-_]+\/?[0-9a-zA-Z-_]+|@[0-9a-zA-Z-_][0-9a-zA-Z-_.]+\/?[0-9a-zA-Z-_.]+[0-9a-zA-Z-_])(?:\s|[:,;.?!]\s|[:,;.?!]?$|\)|\])`)
3131
// issueNumericPattern matches string that references to a numeric issue, e.g. #1287
3232
issueNumericPattern = regexp.MustCompile(`(?:\s|^|\(|\[)([#!][0-9]+)(?:\s|$|\)|\]|[:;,.?!]\s|[:;,.?!]$)`)
3333
// issueAlphanumericPattern matches string that references to an alphanumeric issue, e.g. ABC-1234

routers/repo/issue.go

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2577,4 +2577,6 @@ func handleTeamMentions(ctx *context.Context) {
25772577
}
25782578

25792579
ctx.Data["MentionableTeams"] = ctx.Repo.Owner.Teams
2580+
ctx.Data["MentionableTeamsOrg"] = ctx.Repo.Owner.Name
2581+
ctx.Data["MentionableTeamsOrgAvator"] = ctx.Repo.Owner.RelAvatarLink()
25802582
}

templates/base/head.tmpl

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -56,7 +56,8 @@
5656
name: '{{.Name}}', fullname: '{{.FullName}}', avatar: '{{.RelAvatarLink}}'}],
5757
{{ end }}
5858
{{ range .MentionableTeams }}
59-
['{{.Name}}', {key: '{{.Name}}', value: '{{.Name}}', name: '{{.Name}}'}],
59+
['{{$.MentionableTeamsOrg}}/{{.Name}}', {key: '{{$.MentionableTeamsOrg}}/{{.Name}}', value: '{{$.MentionableTeamsOrg}}/{{.Name}}',
60+
name: '{{$.MentionableTeamsOrg}}/{{.Name}}', avatar: '{{$.MentionableTeamsOrgAvator}}'}],
6061
{{ end }}
6162
]).values()),
6263
{{end}}

web_src/js/features/tribute.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -36,7 +36,7 @@ function makeCollections({mentions, emoji}) {
3636
menuItemTemplate: (item) => {
3737
return `
3838
<div class="tribute-item">
39-
${item.original.avatar !== '' ? `<img src="${item.original.avatar}"/>` : ''}
39+
<img src="${item.original.avatar}"/>
4040
<span class="name">${item.original.name}</span>
4141
${item.original.fullname && item.original.fullname !== '' ? `<span class="fullname">${item.original.fullname}</span>` : ''}
4242
</div>

0 commit comments

Comments
 (0)