Skip to content

Commit d1e67d7

Browse files
authored
Fix bug preventing transfer to private organization (#12497)
* Fix bug preventing transfer to private organization The code assessing whether a private organization was visible to a user before allowing transfer was incorrect due to testing membership the wrong way round This PR fixes this issue and renames the function performing the test to be clearer. Further looking at the API for transfer repository - no testing was performed to ensure that the acting user could actually see the new owning organization. Signed-off-by: Andrew Thornton <[email protected]> * change IsUserPartOfOrg everywhere
1 parent f50364a commit d1e67d7

File tree

6 files changed

+19
-10
lines changed

6 files changed

+19
-10
lines changed

models/migrations/v111.go

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -148,15 +148,15 @@ func addBranchProtectionCanPushAndEnableWhitelist(x *xorm.Engine) error {
148148
if user == nil {
149149
hasOrgVisible = repoOwner.Visibility == VisibleTypePublic
150150
} else if !user.IsAdmin {
151-
isUserPartOfOrg, err := sess.
151+
hasMemberWithUserID, err := sess.
152152
Where("uid=?", user.ID).
153153
And("org_id=?", repoOwner.ID).
154154
Table("org_user").
155155
Exist()
156156
if err != nil {
157157
hasOrgVisible = false
158158
}
159-
if (repoOwner.Visibility == VisibleTypePrivate || user.IsRestricted) && !isUserPartOfOrg {
159+
if (repoOwner.Visibility == VisibleTypePrivate || user.IsRestricted) && !hasMemberWithUserID {
160160
hasOrgVisible = false
161161
}
162162
}

models/org.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -435,7 +435,7 @@ func hasOrgVisible(e Engine, org *User, user *User) bool {
435435
return true
436436
}
437437

438-
if (org.Visibility == structs.VisibleTypePrivate || user.IsRestricted) && !org.isUserPartOfOrg(e, user.ID) {
438+
if (org.Visibility == structs.VisibleTypePrivate || user.IsRestricted) && !org.hasMemberWithUserID(e, user.ID) {
439439
return false
440440
}
441441
return true

models/user.go

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -610,12 +610,12 @@ func (u *User) IsUserOrgOwner(orgID int64) bool {
610610
return isOwner
611611
}
612612

613-
// IsUserPartOfOrg returns true if user with userID is part of the u organisation.
614-
func (u *User) IsUserPartOfOrg(userID int64) bool {
615-
return u.isUserPartOfOrg(x, userID)
613+
// HasMemberWithUserID returns true if user with userID is part of the u organisation.
614+
func (u *User) HasMemberWithUserID(userID int64) bool {
615+
return u.hasMemberWithUserID(x, userID)
616616
}
617617

618-
func (u *User) isUserPartOfOrg(e Engine, userID int64) bool {
618+
func (u *User) hasMemberWithUserID(e Engine, userID int64) bool {
619619
isMember, err := isOrganizationMember(e, u.ID, userID)
620620
if err != nil {
621621
log.Error("IsOrganizationMember: %v", err)

routers/api/v1/repo/transfer.go

Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@ import (
1212
"code.gitea.io/gitea/modules/context"
1313
"code.gitea.io/gitea/modules/convert"
1414
"code.gitea.io/gitea/modules/log"
15+
"code.gitea.io/gitea/modules/structs"
1516
api "code.gitea.io/gitea/modules/structs"
1617
repo_service "code.gitea.io/gitea/services/repository"
1718
)
@@ -53,13 +54,21 @@ func Transfer(ctx *context.APIContext, opts api.TransferRepoOption) {
5354
newOwner, err := models.GetUserByName(opts.NewOwner)
5455
if err != nil {
5556
if models.IsErrUserNotExist(err) {
56-
ctx.Error(http.StatusNotFound, "GetUserByName", err)
57+
ctx.Error(http.StatusNotFound, "", "The new owner does not exist or cannot be found")
5758
return
5859
}
5960
ctx.InternalServerError(err)
6061
return
6162
}
6263

64+
if newOwner.Type == models.UserTypeOrganization {
65+
if !ctx.User.IsAdmin && newOwner.Visibility == structs.VisibleTypePrivate && !newOwner.HasMemberWithUserID(ctx.User.ID) {
66+
// The user shouldn't know about this organization
67+
ctx.Error(http.StatusNotFound, "", "The new owner does not exist or cannot be found")
68+
return
69+
}
70+
}
71+
6372
var teams []*models.Team
6473
if opts.TeamIDs != nil {
6574
if !newOwner.IsOrganization() {

routers/repo/setting.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -418,7 +418,7 @@ func SettingsPost(ctx *context.Context, form auth.RepoSettingForm) {
418418
}
419419

420420
if newOwner.Type == models.UserTypeOrganization {
421-
if !ctx.User.IsAdmin && newOwner.Visibility == structs.VisibleTypePrivate && !ctx.User.IsUserPartOfOrg(newOwner.ID) {
421+
if !ctx.User.IsAdmin && newOwner.Visibility == structs.VisibleTypePrivate && !newOwner.HasMemberWithUserID(ctx.User.ID) {
422422
// The user shouldn't know about this organization
423423
ctx.RenderWithErr(ctx.Tr("form.enterred_invalid_owner_name"), tplSettingsOptions, nil)
424424
return

templates/user/profile.tmpl

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -52,7 +52,7 @@
5252
<li>
5353
<ul class="user-orgs">
5454
{{range .Orgs}}
55-
{{if (or .Visibility.IsPublic (and ($.SignedUser) (or .Visibility.IsLimited (and (.IsUserPartOfOrg $.SignedUserID) .Visibility.IsPrivate) ($.IsAdmin))))}}
55+
{{if (or .Visibility.IsPublic (and ($.SignedUser) (or .Visibility.IsLimited (and (.HasMemberWithUserID $.SignedUserID) .Visibility.IsPrivate) ($.IsAdmin))))}}
5656
<li>
5757
<a href="{{.HomeLink}}"><img class="ui image poping up" src="{{.RelAvatarLink}}" data-content="{{.Name}}" data-position="top center" data-variation="tiny inverted"></a>
5858
</li>

0 commit comments

Comments
 (0)