Skip to content

Commit

Permalink
fix: change owner should check required domain list
Browse files Browse the repository at this point in the history
  • Loading branch information
Qiu Jian committed Jul 29, 2020
1 parent 8fa3e77 commit 04b4ab3
Show file tree
Hide file tree
Showing 11 changed files with 93 additions and 1 deletion.
28 changes: 28 additions & 0 deletions cmd/climc/shell/compute/globalvpcs.go
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,8 @@
package compute

import (
"fmt"

"yunion.io/x/jsonutils"

"yunion.io/x/onecloud/pkg/mcclient"
Expand Down Expand Up @@ -78,4 +80,30 @@ func init() {
printObject(result)
return nil
})

R(&GlobalVpcShowOptions{}, "global-vpc-change-owner-candidate-domains", "Show candiate domains of a global vpc for changing owner", func(s *mcclient.ClientSession, args *GlobalVpcShowOptions) error {
result, err := modules.GlobalVpcs.GetSpecific(s, args.ID, "change-owner-candidate-domains", nil)
if err != nil {
return err
}
printObject(result)
return nil
})

type GlobalVpcChangeOwnerOptions struct {
ID string `help:"ID or name of vpc" json:"-"`
ProjectDomain string `json:"project_domain" help:"target domain"`
}
R(&GlobalVpcChangeOwnerOptions{}, "global-vpc-change-owner", "Change owner domain of a global vpc", func(s *mcclient.ClientSession, args *GlobalVpcChangeOwnerOptions) error {
if len(args.ProjectDomain) == 0 {
return fmt.Errorf("empty project_domain")
}
params := jsonutils.Marshal(args)
ret, err := modules.GlobalVpcs.PerformAction(s, args.ID, "change-owner", params)
if err != nil {
return err
}
printObject(ret)
return nil
})
}
4 changes: 4 additions & 0 deletions pkg/cloudcommon/db/domain.go
Original file line number Diff line number Diff line change
Expand Up @@ -77,6 +77,10 @@ func (model *SDomainizedResourceBase) GetChangeOwnerCandidateDomainIds() []strin
return nil
}

func (model *SDomainizedResourceBase) GetChangeOwnerRequiredDomainIds() []string {
return nil
}

func ValidateCreateDomainId(domainId string) error {
if !consts.GetNonDefaultDomainProjects() && domainId != identity.DEFAULT_DOMAIN_ID {
return httperrors.NewForbiddenError("project in non-default domain is prohibited")
Expand Down
9 changes: 9 additions & 0 deletions pkg/cloudcommon/db/domainresource.go
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@ import (
"yunion.io/x/sqlchemy"

"yunion.io/x/onecloud/pkg/apis"
"yunion.io/x/onecloud/pkg/cloudcommon/consts"
"yunion.io/x/onecloud/pkg/httperrors"
"yunion.io/x/onecloud/pkg/mcclient"
"yunion.io/x/onecloud/pkg/util/logclient"
Expand Down Expand Up @@ -133,6 +134,9 @@ func (model *SDomainLevelResourceBase) AllowPerformChangeOwner(ctx context.Conte
}

func (model *SDomainLevelResourceBase) PerformChangeOwner(ctx context.Context, userCred mcclient.TokenCredential, query jsonutils.JSONObject, input apis.PerformChangeDomainOwnerInput) (jsonutils.JSONObject, error) {
if !consts.GetNonDefaultDomainProjects() {
return nil, errors.Wrap(httperrors.ErrForbidden, "not allow to change owner of domain resource if non_default_domain_projects is turned off")
}
if model.GetIStandaloneModel().IsShared() {
return nil, errors.Wrap(httperrors.ErrForbidden, "cannot change owner of shared resource")
}
Expand Down Expand Up @@ -162,6 +166,11 @@ func (model *SDomainLevelResourceBase) PerformChangeOwner(ctx context.Context, u
if len(candidates) > 0 && !utils.IsInStringArray(ownerId.GetProjectDomainId(), candidates) {
return nil, errors.Wrap(httperrors.ErrForbidden, "target domain not in change owner candidate list")
}
requires := model.GetIDomainLevelModel().GetChangeOwnerRequiredDomainIds()
log.Debugf("%s required domains: %s", model.Keyword(), requires)
if len(requires) > 0 && !utils.IsInStringArray(ownerId.GetProjectDomainId(), requires) {
return nil, errors.Wrap(httperrors.ErrForbidden, "target domain not in change owner required list")
}

if !IsAdminAllowPerform(userCred, model, "change-owner") {
return nil, errors.Wrap(httperrors.ErrNotSufficientPrivilege, "require system privileges")
Expand Down
3 changes: 3 additions & 0 deletions pkg/cloudcommon/db/infraresource.go
Original file line number Diff line number Diff line change
Expand Up @@ -201,6 +201,9 @@ func (model *SInfrasResourceBase) PerformChangeOwner(
query jsonutils.JSONObject,
input apis.PerformChangeDomainOwnerInput,
) (jsonutils.JSONObject, error) {
if !consts.GetNonDefaultDomainProjects() {
return nil, errors.Wrap(httperrors.ErrForbidden, "not allow to change owner of domain resource if non_default_domain_projects is turned off")
}
if model.IsShared() {
return nil, errors.Wrap(httperrors.ErrInvalidStatus, "cannot change owner when shared!")
}
Expand Down
1 change: 1 addition & 0 deletions pkg/cloudcommon/db/managed.go
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ import (

type IOwnerResourceBaseModel interface {
GetChangeOwnerCandidateDomainIds() []string
GetChangeOwnerRequiredDomainIds() []string
}

type IManagedResourceBase interface {
Expand Down
9 changes: 9 additions & 0 deletions pkg/compute/models/globalvpcs.go
Original file line number Diff line number Diff line change
Expand Up @@ -240,3 +240,12 @@ func (globalVpc *SGlobalVpc) GetRequiredSharedDomainIds() []string {
}
return db.ISharableMergeShareRequireDomainIds(requires...)
}

func (globalVpc *SGlobalVpc) GetChangeOwnerRequiredDomainIds() []string {
requires := stringutils2.SSortedStrings{}
vpcs, _ := globalVpc.GetVpcs()
for i := range vpcs {
requires = stringutils2.Append(requires, vpcs[i].DomainId)
}
return requires
}
9 changes: 9 additions & 0 deletions pkg/compute/models/hosts.go
Original file line number Diff line number Diff line change
Expand Up @@ -5275,6 +5275,15 @@ func (host *SHost) PerformChangeOwner(ctx context.Context, userCred mcclient.Tok
return ret, nil
}

func (host *SHost) GetChangeOwnerRequiredDomainIds() []string {
requires := stringutils2.SSortedStrings{}
guests := host.GetGuests()
for i := range guests {
requires = stringutils2.Append(requires, guests[i].DomainId)
}
return requires
}

func GetHostQuotaKeysFromCreateInput(input api.HostCreateInput) quotas.SDomainRegionalCloudResourceKeys {
ownerId := &db.SOwnerId{DomainId: input.ProjectDomain}
var zone *SZone
Expand Down
9 changes: 9 additions & 0 deletions pkg/compute/models/storages.go
Original file line number Diff line number Diff line change
Expand Up @@ -1481,6 +1481,15 @@ func (storage *SStorage) performChangeOwnerInternal(ctx context.Context, userCre
return storage.SEnabledStatusInfrasResourceBase.PerformChangeOwner(ctx, userCred, query, input)
}

func (storage *SStorage) GetChangeOwnerRequiredDomainIds() []string {
requires := stringutils2.SSortedStrings{}
disks := storage.GetDisks()
for i := range disks {
requires = stringutils2.Append(requires, disks[i].DomainId)
}
return requires
}

func (storage *SStorage) PerformPublic(ctx context.Context, userCred mcclient.TokenCredential, query jsonutils.JSONObject, input apis.PerformPublicDomainInput) (jsonutils.JSONObject, error) {
// not allow to perform public for locally connected storage
if storage.IsLocal() {
Expand Down
9 changes: 9 additions & 0 deletions pkg/compute/models/vpcs.go
Original file line number Diff line number Diff line change
Expand Up @@ -1135,6 +1135,15 @@ func (vpc *SVpc) GetChangeOwnerCandidateDomainIds() []string {
return db.ISharableMergeChangeOwnerCandidateDomainIds(vpc, candidates...)
}

func (vpc *SVpc) GetChangeOwnerRequiredDomainIds() []string {
requires := stringutils2.SSortedStrings{}
wires := vpc.GetWires()
for i := range wires {
requires = stringutils2.Append(requires, wires[i].DomainId)
}
return requires
}

func (vpc *SVpc) GetRequiredSharedDomainIds() []string {
wires := vpc.GetWires()
if len(wires) == 0 {
Expand Down
9 changes: 9 additions & 0 deletions pkg/compute/models/wires.go
Original file line number Diff line number Diff line change
Expand Up @@ -1036,6 +1036,15 @@ func (wire *SWire) GetChangeOwnerCandidateDomainIds() []string {
return db.ISharableMergeChangeOwnerCandidateDomainIds(wire, candidates...)
}

func (wire *SWire) GetChangeOwnerRequiredDomainIds() []string {
requires := stringutils2.SSortedStrings{}
networks, _ := wire.getNetworks(nil, rbacutils.ScopeNone)
for i := range networks {
requires = stringutils2.Append(requires, networks[i].DomainId)
}
return requires
}

func (wire *SWire) GetRequiredSharedDomainIds() []string {
networks, _ := wire.getNetworks(nil, rbacutils.ScopeNone)
if len(networks) == 0 {
Expand Down
4 changes: 3 additions & 1 deletion pkg/mcclient/modules/mod_wires.go
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,9 @@ var (
func init() {
Wires = NewComputeManager("wire", "wires",
[]string{"ID", "Name", "Bandwidth", "Zone_ID",
"Zone", "Networks", "VPC", "VPC_ID", "public_scope"},
"Zone", "Networks", "VPC", "VPC_ID", "public_scope",
"domain_id",
},
[]string{})

registerCompute(&Wires)
Expand Down

0 comments on commit 04b4ab3

Please sign in to comment.