Skip to content

Commit

Permalink
add org team permission check
Browse files Browse the repository at this point in the history
  • Loading branch information
yp05327 committed Feb 21, 2023
1 parent fb5031b commit 667f68e
Show file tree
Hide file tree
Showing 10 changed files with 82 additions and 30 deletions.
26 changes: 26 additions & 0 deletions models/organization/org.go
Original file line number Diff line number Diff line change
Expand Up @@ -239,6 +239,32 @@ func (org *Organization) CustomAvatarRelativePath() string {
return org.Avatar
}

// UnitPermission returns unit permission
func (org *Organization) UnitPermission(ctx context.Context, doer *user_model.User, unitType unit.Type) perm.AccessMode {
if doer != nil {
teams, err := GetUserOrgTeams(ctx, org.ID, doer.ID)
if err != nil {
log.Error("GetUserOrgTeams: %v", err)
return perm.AccessModeNone
}

if err := teams.LoadUnits(ctx); err != nil {
log.Error("LoadUnits: %v", err)
return perm.AccessModeNone
}

if len(teams) > 0 {
return teams.UnitMaxAccess(unitType)
}
}

if org.Visibility.IsPublic() {
return perm.AccessModeRead
}

return perm.AccessModeNone
}

// CreateOrganization creates record of a new organization.
func CreateOrganization(org *Organization, owner *user_model.User) (err error) {
if !owner.CanCreateOrganization() {
Expand Down
5 changes: 5 additions & 0 deletions models/user/user.go
Original file line number Diff line number Diff line change
Expand Up @@ -393,6 +393,11 @@ func (u *User) IsOrganization() bool {
return u.Type == UserTypeOrganization
}

// IsIndividual returns true if user is actually a individual user.
func (u *User) IsIndividual() bool {
return u.Type == UserTypeIndividual
}

// DisplayName returns full name if it's not empty,
// returns username otherwise.
func (u *User) DisplayName() string {
Expand Down
30 changes: 8 additions & 22 deletions modules/context/org.go
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,6 @@ import (
"code.gitea.io/gitea/models/perm"
"code.gitea.io/gitea/models/unit"
user_model "code.gitea.io/gitea/models/user"
"code.gitea.io/gitea/modules/log"
"code.gitea.io/gitea/modules/setting"
"code.gitea.io/gitea/modules/structs"
)
Expand All @@ -31,29 +30,11 @@ type Organization struct {
}

func (org *Organization) CanWriteUnit(ctx *Context, unitType unit.Type) bool {
if ctx.Doer == nil {
return false
}
return org.UnitPermission(ctx, ctx.Doer.ID, unitType) >= perm.AccessModeWrite
return org.Organization.UnitPermission(ctx, ctx.Doer, unitType) >= perm.AccessModeWrite
}

func (org *Organization) UnitPermission(ctx *Context, doerID int64, unitType unit.Type) perm.AccessMode {
if doerID > 0 {
teams, err := organization.GetUserOrgTeams(ctx, org.Organization.ID, doerID)
if err != nil {
log.Error("GetUserOrgTeams: %v", err)
return perm.AccessModeNone
}
if len(teams) > 0 {
return teams.UnitMaxAccess(unitType)
}
}

if org.Organization.Visibility == structs.VisibleTypePublic {
return perm.AccessModeRead
}

return perm.AccessModeNone
func (org *Organization) CanReadUnit(ctx *Context, unitType unit.Type) bool {
return org.Organization.UnitPermission(ctx, ctx.Doer, unitType) >= perm.AccessModeRead
}

func GetOrganizationByParams(ctx *Context) {
Expand Down Expand Up @@ -170,6 +151,7 @@ func HandleOrgAssignment(ctx *Context, args ...bool) {
}
ctx.Data["IsOrganizationOwner"] = ctx.Org.IsOwner
ctx.Data["IsOrganizationMember"] = ctx.Org.IsMember
ctx.Data["IsProjectEnabled"] = true
ctx.Data["IsPackageEnabled"] = setting.Packages.Enabled
ctx.Data["IsRepoIndexerEnabled"] = setting.Indexer.RepoIndexerEnabled
ctx.Data["IsPublicMember"] = func(uid int64) bool {
Expand Down Expand Up @@ -245,6 +227,10 @@ func HandleOrgAssignment(ctx *Context, args ...bool) {
return
}
}

ctx.Data["CanReadProjects"] = ctx.Org.CanReadUnit(ctx, unit.TypeProjects)
ctx.Data["CanReadPackages"] = ctx.Org.CanReadUnit(ctx, unit.TypePackages)
ctx.Data["CanReadCode"] = ctx.Org.CanReadUnit(ctx, unit.TypeCode)
}

// OrgAssignment returns a middleware to handle organization assignment
Expand Down
3 changes: 2 additions & 1 deletion routers/web/org/home.go
Original file line number Diff line number Diff line change
Expand Up @@ -156,6 +156,7 @@ func Home(ctx *context.Context) {
pager.SetDefaultParams(ctx)
pager.AddParam(ctx, "language", "Language")
ctx.Data["Page"] = pager

ctx.Data["ContextUser"] = ctx.ContextUser

ctx.HTML(http.StatusOK, tplOrgHome)
}
2 changes: 2 additions & 0 deletions routers/web/shared/user/header.go
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,8 @@ import (
)

func RenderUserHeader(ctx *context.Context) {
ctx.Data["IsProjectEnabled"] = true
ctx.Data["IsPackageEnabled"] = setting.Packages.Enabled
ctx.Data["IsRepoIndexerEnabled"] = setting.Indexer.RepoIndexerEnabled
ctx.Data["ContextUser"] = ctx.ContextUser
}
1 change: 1 addition & 0 deletions routers/web/user/code.go
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@ func CodeSearch(ctx *context.Context) {
return
}

ctx.Data["IsProjectEnabled"] = true
ctx.Data["IsPackageEnabled"] = setting.Packages.Enabled
ctx.Data["IsRepoIndexerEnabled"] = setting.Indexer.RepoIndexerEnabled
ctx.Data["Title"] = ctx.Tr("explore.code")
Expand Down
1 change: 1 addition & 0 deletions routers/web/user/profile.go
Original file line number Diff line number Diff line change
Expand Up @@ -288,6 +288,7 @@ func Profile(ctx *context.Context) {
pager.AddParam(ctx, "language", "Language")
}
ctx.Data["Page"] = pager
ctx.Data["IsProjectEnabled"] = true
ctx.Data["IsPackageEnabled"] = setting.Packages.Enabled
ctx.Data["IsRepoIndexerEnabled"] = setting.Indexer.RepoIndexerEnabled

Expand Down
32 changes: 29 additions & 3 deletions routers/web/web.go
Original file line number Diff line number Diff line change
Expand Up @@ -869,8 +869,21 @@ func RegisterRoutes(m *web.Route) {
}

m.Group("/projects", func() {
m.Get("", org.Projects)
m.Get("/{id}", org.ViewProject)
m.Group("", func() {
m.Get("", org.Projects)
m.Get("/{id}", org.ViewProject)
}, func(ctx *context.Context) {
if ctx.ContextUser == nil {
ctx.NotFound("Project", nil)
return
}
if ctx.ContextUser.IsOrganization() {
if !ctx.Org.CanReadUnit(ctx, unit.TypeProjects) {
ctx.NotFound("Project", nil)
return
}
}
})
m.Group("", func() { //nolint:dupl
m.Get("/new", org.NewProject)
m.Post("/new", web.Bind(forms.CreateProjectForm{}), org.NewProjectPost)
Expand Down Expand Up @@ -907,7 +920,20 @@ func RegisterRoutes(m *web.Route) {
})
}, repo.MustEnableProjects)

m.Get("/code", user.CodeSearch)
m.Group("", func() {
m.Get("/code", user.CodeSearch)
}, func(ctx *context.Context) {
if ctx.ContextUser == nil {
ctx.NotFound("Code", nil)
return
}
if ctx.ContextUser.IsOrganization() {
if !ctx.Org.CanReadUnit(ctx, unit.TypeCode) {
ctx.NotFound("Code", nil)
return
}
}
})
}, context_service.UserAssignmentWeb())

// ***** Release Attachment Download without Signin
Expand Down
6 changes: 4 additions & 2 deletions templates/org/menu.tmpl
Original file line number Diff line number Diff line change
Expand Up @@ -3,15 +3,17 @@
<a class="{{if .PageIsViewRepositories}}active {{end}}item" href="{{$.Org.HomeLink}}">
{{svg "octicon-repo"}} {{.locale.Tr "user.repositories"}}
</a>
{{if and .IsProjectEnabled (and .ContextUser.IsOrganization .CanReadProjects)}}
<a class="{{if .PageIsViewProjects}}active {{end}}item" href="{{$.Org.HomeLink}}/-/projects">
{{svg "octicon-project"}} {{.locale.Tr "user.projects"}}
</a>
{{if .IsPackageEnabled}}
{{end}}
{{if and .IsPackageEnabled (and .ContextUser.IsOrganization .CanReadPackages)}}
<a class="item" href="{{$.Org.HomeLink}}/-/packages">
{{svg "octicon-package"}} {{.locale.Tr "packages.title"}}
</a>
{{end}}
{{if .IsRepoIndexerEnabled}}
{{if and .IsRepoIndexerEnabled (and .ContextUser.IsOrganization .CanReadCode)}}
<a class="item" href="{{$.Org.HomeLink}}/-/code">
{{svg "octicon-code"}}&nbsp;{{$.locale.Tr "org.code"}}
</a>
Expand Down
6 changes: 4 additions & 2 deletions templates/user/overview/header.tmpl
Original file line number Diff line number Diff line change
Expand Up @@ -22,15 +22,17 @@
<a class="item" href="{{.ContextUser.HomeLink}}">
{{svg "octicon-repo"}} {{.locale.Tr "user.repositories"}}
</a>
{{if and .IsProjectEnabled (or .ContextUser.IsIndividual (and .ContextUser.IsOrganization .CanReadProjects))}}
<a href="{{.ContextUser.HomeLink}}/-/projects" class="{{if .PageIsViewProjects}}active {{end}}item">
{{svg "octicon-project"}} {{.locale.Tr "user.projects"}}
</a>
{{if .IsPackageEnabled}}
{{end}}
{{if and .IsPackageEnabled (or .ContextUser.IsIndividual (and .ContextUser.IsOrganization .CanReadPackages))}}
<a href="{{.ContextUser.HomeLink}}/-/packages" class="{{if .IsPackagesPage}}active {{end}}item">
{{svg "octicon-package"}} {{.locale.Tr "packages.title"}}
</a>
{{end}}
{{if .IsRepoIndexerEnabled}}
{{if and .IsRepoIndexerEnabled (or .ContextUser.IsIndividual (and .ContextUser.IsOrganization .CanReadCode))}}
<a href="{{.ContextUser.HomeLink}}/-/code" class="{{if .IsCodePage}}active {{end}}item">
{{svg "octicon-code"}} {{.locale.Tr "user.code"}}
</a>
Expand Down

0 comments on commit 667f68e

Please sign in to comment.