Merge pull request #842 in YUNIONIO/onecloud from ~QIUJIAN/onecloud:hotfix/qj-cloud-region-zone-add-usable-vpc-filter to release/2.4.0

* commit '3354b4eee55983c6d68e7823aaecc582eb19011c':
  cloud-region和zone增加usable-vpc=true的过滤器,过滤出有Avaiable VPC的cloudregion和zone
This commit is contained in:
邱剑
2018-12-25 21:00:22 +08:00
4 changed files with 58 additions and 39 deletions
+4 -3
View File
@@ -11,9 +11,10 @@ import (
func init() {
type CloudregionListOptions struct {
options.BaseListOptions
Private *bool `help:"show private cloud regions only" json:"is_private"`
Public *bool `help:"show public cloud regions only" json:"is_public"`
Usable *bool `help:"List regions that are usable"`
Private *bool `help:"show private cloud regions only" json:"is_private"`
Public *bool `help:"show public cloud regions only" json:"is_public"`
Usable *bool `help:"List regions where networks are usable"`
UsableVpc *bool `help:"List regions where VPC are usable"`
}
R(&CloudregionListOptions{}, "cloud-region-list", "List cloud regions", func(s *mcclient.ClientSession, opts *CloudregionListOptions) error {
params, err := options.ListStructToParams(opts)
+8 -22
View File
@@ -10,31 +10,17 @@ import (
func init() {
type ZoneListOptions struct {
options.BaseListOptions
Region string `help:"cloud region ID or Name"`
Usable bool `help:"List all zones that is usable"`
Private bool `help:"show all zones in private cloud regions only"`
Public bool `help:"show all zones in public cloud regions only"`
Region string `help:"cloud region ID or Name" json:"-"`
Usable *bool `help:"List all zones where networks are usable"`
UsableVpc *bool `help:"List all zones where vpc are usable"`
Private *bool `help:"show all zones in private cloud regions only"`
Public *bool `help:"show all zones in public cloud regions only"`
}
R(&ZoneListOptions{}, "zone-list", "List zones", func(s *mcclient.ClientSession, args *ZoneListOptions) error {
var params *jsonutils.JSONDict
{
var err error
params, err = args.BaseListOptions.Params()
if err != nil {
return err
}
params, err := options.ListStructToParams(args)
if err != nil {
return err
}
if args.Usable {
params.Add(jsonutils.JSONTrue, "usable")
}
if args.Private {
params.Add(jsonutils.JSONTrue, "is_private")
}
if args.Public {
params.Add(jsonutils.JSONTrue, "is_public")
}
var err error
var result *modules.ListResult
if len(args.Region) > 0 {
result, err = modules.Zones.ListInContext(s, params, &modules.Cloudregions, args.Region)
+22 -7
View File
@@ -351,25 +351,40 @@ func (manager *SCloudregionManager) ListItemFilter(ctx context.Context, q *sqlch
q = q.Equals("provider", manager.Provider)
}
if jsonutils.QueryBoolean(query, "usable", false) {
if jsonutils.QueryBoolean(query, "usable", false) || jsonutils.QueryBoolean(query, "usable_vpc", false) {
providers := CloudproviderManager.Query().SubQuery()
networks := NetworkManager.Query().SubQuery()
wires := WireManager.Query().SubQuery()
vpcs := VpcManager.Query().SubQuery()
usableNet := jsonutils.QueryBoolean(query, "usable", false)
usableVpc := jsonutils.QueryBoolean(query, "usable_vpc", false)
sq := vpcs.Query(sqlchemy.DISTINCT("cloudregion_id", vpcs.Field("cloudregion_id")))
sq = sq.Join(wires, sqlchemy.Equals(vpcs.Field("id"), wires.Field("vpc_id")))
sq = sq.Join(networks, sqlchemy.Equals(wires.Field("id"), networks.Field("wire_id")))
if usableNet {
sq = sq.Join(wires, sqlchemy.Equals(vpcs.Field("id"), wires.Field("vpc_id")))
sq = sq.Join(networks, sqlchemy.Equals(wires.Field("id"), networks.Field("wire_id")))
}
sq = sq.Join(providers, sqlchemy.Equals(vpcs.Field("manager_id"), providers.Field("id")))
sq = sq.Filter(sqlchemy.Equals(networks.Field("status"), NETWORK_STATUS_AVAILABLE))
if usableNet {
sq = sq.Filter(sqlchemy.Equals(networks.Field("status"), NETWORK_STATUS_AVAILABLE))
}
sq = sq.Filter(sqlchemy.IsTrue(providers.Field("enabled")))
sq = sq.Filter(sqlchemy.In(providers.Field("status"), CLOUD_PROVIDER_VALID_STATUS))
if usableVpc {
sq = sq.Filter(sqlchemy.Equals(vpcs.Field("status"), VPC_STATUS_AVAILABLE))
}
sq2 := vpcs.Query(sqlchemy.DISTINCT("cloudregion_id", vpcs.Field("cloudregion_id")))
sq2 = sq2.Join(wires, sqlchemy.Equals(vpcs.Field("id"), wires.Field("vpc_id")))
sq2 = sq2.Join(networks, sqlchemy.Equals(wires.Field("id"), networks.Field("wire_id")))
sq2 = sq2.Filter(sqlchemy.Equals(networks.Field("status"), NETWORK_STATUS_AVAILABLE))
if usableNet {
sq2 = sq2.Join(wires, sqlchemy.Equals(vpcs.Field("id"), wires.Field("vpc_id")))
sq2 = sq2.Join(networks, sqlchemy.Equals(wires.Field("id"), networks.Field("wire_id")))
sq2 = sq2.Filter(sqlchemy.Equals(networks.Field("status"), NETWORK_STATUS_AVAILABLE))
}
sq2 = sq2.Filter(sqlchemy.IsNullOrEmpty(vpcs.Field("manager_id")))
if usableVpc {
sq2 = sq2.Filter(sqlchemy.Equals(vpcs.Field("status"), VPC_STATUS_AVAILABLE))
}
q = q.Filter(sqlchemy.OR(
sqlchemy.In(q.Field("id"), sq.SubQuery()),
+24 -7
View File
@@ -476,34 +476,51 @@ func (manager *SZoneManager) ListItemFilter(ctx context.Context, q *sqlchemy.SQu
return nil, err
}
if jsonutils.QueryBoolean(query, "is_private", false) {
if jsonutils.QueryBoolean(query, "is_private", false) || jsonutils.QueryBoolean(query, "private", false) {
q = q.Filter(sqlchemy.OR(sqlchemy.IsNull(q.Field("external_id")),
sqlchemy.IsEmpty(q.Field("external_id"))))
}
if jsonutils.QueryBoolean(query, "is_public", false) {
if jsonutils.QueryBoolean(query, "is_public", false) || jsonutils.QueryBoolean(query, "public", false) {
q = q.Filter(sqlchemy.AND(sqlchemy.IsNotNull(q.Field("external_id")),
sqlchemy.IsNotEmpty(q.Field("external_id"))))
}
if jsonutils.QueryBoolean(query, "usable", false) {
if jsonutils.QueryBoolean(query, "usable", false) || jsonutils.QueryBoolean(query, "usable_vpc", false) {
networks := NetworkManager.Query().SubQuery()
wires := WireManager.Query().SubQuery()
vpcs := VpcManager.Query().SubQuery()
providers := CloudproviderManager.Query().SubQuery()
usableNet := jsonutils.QueryBoolean(query, "usable", false)
usableVpc := jsonutils.QueryBoolean(query, "usable_vpc", false)
sq := wires.Query(sqlchemy.DISTINCT("zone_id", wires.Field("zone_id")))
sq = sq.Join(networks, sqlchemy.Equals(wires.Field("id"), networks.Field("wire_id")))
if usableNet {
sq = sq.Join(networks, sqlchemy.Equals(wires.Field("id"), networks.Field("wire_id")))
}
sq = sq.Join(vpcs, sqlchemy.Equals(wires.Field("vpc_id"), vpcs.Field("id")))
sq = sq.Join(providers, sqlchemy.Equals(vpcs.Field("manager_id"), providers.Field("id")))
sq = sq.Filter(sqlchemy.Equals(networks.Field("status"), NETWORK_STATUS_AVAILABLE))
if usableNet {
sq = sq.Filter(sqlchemy.Equals(networks.Field("status"), NETWORK_STATUS_AVAILABLE))
}
sq = sq.Filter(sqlchemy.IsTrue(providers.Field("enabled")))
sq = sq.Filter(sqlchemy.In(providers.Field("status"), CLOUD_PROVIDER_VALID_STATUS))
if usableVpc {
sq = sq.Filter(sqlchemy.Equals(vpcs.Field("status"), VPC_STATUS_AVAILABLE))
}
sq2 := wires.Query(sqlchemy.DISTINCT("zone_id", wires.Field("zone_id")))
sq2 = sq2.Join(networks, sqlchemy.Equals(wires.Field("id"), networks.Field("wire_id")))
if usableNet {
sq2 = sq2.Join(networks, sqlchemy.Equals(wires.Field("id"), networks.Field("wire_id")))
}
sq2 = sq2.Join(vpcs, sqlchemy.Equals(wires.Field("vpc_id"), vpcs.Field("id")))
sq2 = sq2.Filter(sqlchemy.Equals(networks.Field("status"), NETWORK_STATUS_AVAILABLE))
if usableNet {
sq2 = sq2.Filter(sqlchemy.Equals(networks.Field("status"), NETWORK_STATUS_AVAILABLE))
}
sq2 = sq2.Filter(sqlchemy.IsNullOrEmpty(vpcs.Field("manager_id")))
if usableVpc {
sq2 = sq2.Filter(sqlchemy.Equals(vpcs.Field("status"), VPC_STATUS_AVAILABLE))
}
q = q.Filter(sqlchemy.OR(
sqlchemy.In(q.Field("id"), sq.SubQuery()),