Skip to content

Commit 90cd8aa

Browse files
authored
server: add support for sorting zones in UI/API (#3242)
Problem: Not able to configure a sort order for the zones that are listed in various views in the UI. Root Cause: There is no mechanism to accept sort key for existing zones or UI widget, that would allow to listing zones in the UI in a certain order. Solution: The order of zones in listed in various views in the UI can now be configured through the newly added “sort_key” field added for the zone. It can be set using updateZone API by providing “sort_key” parameter for a zone, or by reordering the items in the zones list in the UI. UI has been updated to show ordering controls in zones list view. Database changes include updating table “data_center” by adding “sort_key” column (containing integer values and defaults to zero). Signed-off-by: Rohit Yadav <rohit.yadav@shapeblue.com>
1 parent 0d6cae6 commit 90cd8aa

File tree

13 files changed

+139
-42
lines changed

13 files changed

+139
-42
lines changed

api/src/main/java/com/cloud/dc/DataCenter.java

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -16,11 +16,12 @@
1616
// under the License.
1717
package com.cloud.dc;
1818

19-
import com.cloud.org.Grouping;
19+
import java.util.Map;
20+
2021
import org.apache.cloudstack.acl.InfrastructureEntity;
2122
import org.apache.cloudstack.kernel.Partition;
2223

23-
import java.util.Map;
24+
import com.cloud.org.Grouping;
2425

2526
/**
2627
*
@@ -80,4 +81,6 @@ public enum NetworkType {
8081
String getZoneToken();
8182

8283
boolean isLocalStorageEnabled();
84+
85+
int getSortKey();
8386
}

api/src/main/java/org/apache/cloudstack/api/command/admin/zone/UpdateZoneCmd.java

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -95,6 +95,9 @@ public class UpdateZoneCmd extends BaseCmd {
9595
@Parameter(name = ApiConstants.LOCAL_STORAGE_ENABLED, type = CommandType.BOOLEAN, description = "true if local storage offering enabled, false otherwise")
9696
private Boolean localStorageEnabled;
9797

98+
@Parameter(name = ApiConstants.SORT_KEY, type = CommandType.INTEGER, description = "sort key of the zone, integer")
99+
private Integer sortKey;
100+
98101
/////////////////////////////////////////////////////
99102
/////////////////// Accessors ///////////////////////
100103
/////////////////////////////////////////////////////
@@ -163,6 +166,10 @@ public Boolean getLocalStorageEnabled() {
163166
return localStorageEnabled;
164167
}
165168

169+
public Integer getSortKey() {
170+
return sortKey;
171+
}
172+
166173
/////////////////////////////////////////////////////
167174
/////////////// API Implementation///////////////////
168175
/////////////////////////////////////////////////////

api/src/main/java/org/apache/cloudstack/query/QueryService.java

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -85,7 +85,7 @@
8585
public interface QueryService {
8686

8787
// Config keys
88-
static final ConfigKey<Boolean> AllowUserViewDestroyedVM = new ConfigKey<Boolean>("Advanced", Boolean.class, "allow.user.view.destroyed.vm", "false",
88+
ConfigKey<Boolean> AllowUserViewDestroyedVM = new ConfigKey<>("Advanced", Boolean.class, "allow.user.view.destroyed.vm", "false",
8989
"Determines whether users can view their destroyed or expunging vm ", true, ConfigKey.Scope.Account);
9090

9191
static final ConfigKey<String> UserVMBlacklistedDetails = new ConfigKey<String>("Advanced", String.class,
@@ -96,6 +96,11 @@ public interface QueryService {
9696
"user.vm.readonly.ui.details", "dataDiskController, rootDiskController",
9797
"List of UI read-only VM settings/details as comma separated string", true);
9898

99+
ConfigKey<Boolean> SortKeyAscending = new ConfigKey<>("Advanced", Boolean.class, "sortkey.algorithm", "true",
100+
"Sort algorithm - ascending or descending - to use. For entities that use sort key(template, disk offering, service offering, " +
101+
"network offering, zones), we use the flag to determine if the entities should be sorted ascending (when flag is true) " +
102+
"or descending (when flag is false). Within the scope of the config all users see the same result.", true, ConfigKey.Scope.Global);
103+
99104
ListResponse<UserResponse> searchForUsers(ListUsersCmd cmd) throws PermissionDeniedException;
100105

101106
ListResponse<EventResponse> searchForEvents(ListEventsCmd cmd);

engine/orchestration/src/main/java/org/apache/cloudstack/engine/datacenter/entity/api/db/EngineDataCenterVO.java

Lines changed: 20 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -16,14 +16,9 @@
1616
// under the License.
1717
package org.apache.cloudstack.engine.datacenter.entity.api.db;
1818

19-
import com.cloud.network.Network.Provider;
20-
import com.cloud.org.Grouping;
21-
import com.cloud.utils.NumbersUtil;
22-
import com.cloud.utils.db.GenericDao;
23-
import com.cloud.utils.db.StateMachine;
24-
import org.apache.cloudstack.api.Identity;
25-
import org.apache.cloudstack.engine.datacenter.entity.api.DataCenterResourceEntity.State;
26-
import org.apache.cloudstack.engine.datacenter.entity.api.DataCenterResourceEntity.State.Event;
19+
import java.util.Date;
20+
import java.util.Map;
21+
import java.util.UUID;
2722

2823
import javax.persistence.Column;
2924
import javax.persistence.Entity;
@@ -37,9 +32,16 @@
3732
import javax.persistence.Temporal;
3833
import javax.persistence.TemporalType;
3934
import javax.persistence.Transient;
40-
import java.util.Date;
41-
import java.util.Map;
42-
import java.util.UUID;
35+
36+
import org.apache.cloudstack.api.Identity;
37+
import org.apache.cloudstack.engine.datacenter.entity.api.DataCenterResourceEntity.State;
38+
import org.apache.cloudstack.engine.datacenter.entity.api.DataCenterResourceEntity.State.Event;
39+
40+
import com.cloud.network.Network.Provider;
41+
import com.cloud.org.Grouping;
42+
import com.cloud.utils.NumbersUtil;
43+
import com.cloud.utils.db.GenericDao;
44+
import com.cloud.utils.db.StateMachine;
4345

4446
@Entity
4547
@Table(name = "data_center")
@@ -140,6 +142,9 @@ public class EngineDataCenterVO implements EngineDataCenter, Identity {
140142
@Column(name = "is_local_storage_enabled")
141143
boolean localStorageEnabled;
142144

145+
@Column(name = "sort_key")
146+
int sortKey;
147+
143148
//orchestration
144149
@Column(name = "owner")
145150
private String owner = null;
@@ -389,6 +394,10 @@ public void setLocalStorageEnabled(boolean enabled) {
389394
this.localStorageEnabled = enabled;
390395
}
391396

397+
public int getSortKey() {
398+
return sortKey;
399+
}
400+
392401
@Override
393402
public Map<String, String> getDetails() {
394403
return details;

engine/schema/src/main/java/com/cloud/dc/DataCenterVO.java

Lines changed: 20 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -16,10 +16,9 @@
1616
// under the License.
1717
package com.cloud.dc;
1818

19-
import com.cloud.network.Network.Provider;
20-
import com.cloud.org.Grouping;
21-
import com.cloud.utils.NumbersUtil;
22-
import com.cloud.utils.db.GenericDao;
19+
import java.util.Date;
20+
import java.util.Map;
21+
import java.util.UUID;
2322

2423
import javax.persistence.Column;
2524
import javax.persistence.Entity;
@@ -31,9 +30,11 @@
3130
import javax.persistence.Table;
3231
import javax.persistence.TableGenerator;
3332
import javax.persistence.Transient;
34-
import java.util.Date;
35-
import java.util.Map;
36-
import java.util.UUID;
33+
34+
import com.cloud.network.Network.Provider;
35+
import com.cloud.org.Grouping;
36+
import com.cloud.utils.NumbersUtil;
37+
import com.cloud.utils.db.GenericDao;
3738

3839
@Entity
3940
@Table(name = "data_center")
@@ -134,6 +135,9 @@ public class DataCenterVO implements DataCenter {
134135
@Column(name = "is_local_storage_enabled")
135136
boolean localStorageEnabled;
136137

138+
@Column(name = "sort_key")
139+
int sortKey;
140+
137141
@Override
138142
public String getDnsProvider() {
139143
return dnsProvider;
@@ -363,6 +367,15 @@ public void setLocalStorageEnabled(boolean enabled) {
363367
this.localStorageEnabled = enabled;
364368
}
365369

370+
@Override
371+
public int getSortKey() {
372+
return sortKey;
373+
}
374+
375+
public void setSortKey(int newSortKey) {
376+
sortKey = newSortKey;
377+
}
378+
366379
@Override
367380
public Map<String, String> getDetails() {
368381
return details;

engine/schema/src/main/resources/META-INF/db/schema-41200to41300.sql

Lines changed: 43 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -21,3 +21,46 @@
2121

2222
-- DPDK client and server mode support
2323
ALTER TABLE `cloud`.`service_offering_details` CHANGE COLUMN `value` `value` TEXT NOT NULL;
24+
25+
-- Add `sort_key` column to data_center
26+
ALTER TABLE `cloud`.`data_center` ADD COLUMN `sort_key` INT(32) NOT NULL DEFAULT 0;
27+
28+
-- Recreate data_center_view
29+
DROP VIEW IF EXISTS `cloud`.`data_center_view`;
30+
CREATE VIEW `cloud`.`data_center_view` AS
31+
select
32+
data_center.id,
33+
data_center.uuid,
34+
data_center.name,
35+
data_center.is_security_group_enabled,
36+
data_center.is_local_storage_enabled,
37+
data_center.description,
38+
data_center.dns1,
39+
data_center.dns2,
40+
data_center.ip6_dns1,
41+
data_center.ip6_dns2,
42+
data_center.internal_dns1,
43+
data_center.internal_dns2,
44+
data_center.guest_network_cidr,
45+
data_center.domain,
46+
data_center.networktype,
47+
data_center.allocation_state,
48+
data_center.zone_token,
49+
data_center.dhcp_provider,
50+
data_center.removed,
51+
data_center.sort_key,
52+
domain.id domain_id,
53+
domain.uuid domain_uuid,
54+
domain.name domain_name,
55+
domain.path domain_path,
56+
dedicated_resources.affinity_group_id,
57+
dedicated_resources.account_id,
58+
affinity_group.uuid affinity_group_uuid
59+
from
60+
`cloud`.`data_center`
61+
left join
62+
`cloud`.`domain` ON data_center.domain_id = domain.id
63+
left join
64+
`cloud`.`dedicated_resources` ON data_center.id = dedicated_resources.data_center_id
65+
left join
66+
`cloud`.`affinity_group` ON dedicated_resources.affinity_group_id = affinity_group.id;

server/src/main/java/com/cloud/api/query/QueryManagerImpl.java

Lines changed: 6 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -2496,9 +2496,7 @@ private Pair<List<DiskOfferingJoinVO>, Integer> searchForDiskOfferingsInternal(L
24962496
// till
24972497
// root
24982498

2499-
Boolean isAscending = Boolean.parseBoolean(_configDao.getValue("sortkey.algorithm"));
2500-
isAscending = (isAscending == null ? true : isAscending);
2501-
Filter searchFilter = new Filter(DiskOfferingJoinVO.class, "sortKey", isAscending, cmd.getStartIndex(), cmd.getPageSizeVal());
2499+
Filter searchFilter = new Filter(DiskOfferingJoinVO.class, "sortKey", SortKeyAscending.value(), cmd.getStartIndex(), cmd.getPageSizeVal());
25022500
SearchCriteria<DiskOfferingJoinVO> sc = _diskOfferingJoinDao.createSearchCriteria();
25032501
sc.addAnd("type", Op.EQ, DiskOfferingVO.Type.Disk);
25042502

@@ -2638,9 +2636,7 @@ private Pair<List<ServiceOfferingJoinVO>, Integer> searchForServiceOfferingsInte
26382636
// their domains+parent domains ... all the way
26392637
// till
26402638
// root
2641-
Boolean isAscending = Boolean.parseBoolean(_configDao.getValue("sortkey.algorithm"));
2642-
isAscending = (isAscending == null ? true : isAscending);
2643-
Filter searchFilter = new Filter(ServiceOfferingJoinVO.class, "sortKey", isAscending, cmd.getStartIndex(), cmd.getPageSizeVal());
2639+
Filter searchFilter = new Filter(ServiceOfferingJoinVO.class, "sortKey", SortKeyAscending.value(), cmd.getStartIndex(), cmd.getPageSizeVal());
26442640

26452641
Account caller = CallContext.current().getCallingAccount();
26462642
Object name = cmd.getServiceOfferingName();
@@ -2814,7 +2810,7 @@ private Pair<List<DataCenterJoinVO>, Integer> listDataCentersInternal(ListZonesC
28142810
sb.join("tagSearch", tagSearch, sb.entity().getId(), tagSearch.entity().getResourceId(), JoinBuilder.JoinType.INNER);
28152811
}
28162812

2817-
Filter searchFilter = new Filter(DataCenterJoinVO.class, null, false, cmd.getStartIndex(), cmd.getPageSizeVal());
2813+
Filter searchFilter = new Filter(DataCenterJoinVO.class, "sortKey", SortKeyAscending.value(), cmd.getStartIndex(), cmd.getPageSizeVal());
28182814
SearchCriteria<DataCenterJoinVO> sc = sb.create();
28192815

28202816
if (networkType != null) {
@@ -3074,10 +3070,8 @@ private Pair<List<TemplateJoinVO>, Integer> searchForTemplatesInternal(Long temp
30743070

30753071
VMTemplateVO template = null;
30763072

3077-
Boolean isAscending = Boolean.parseBoolean(_configDao.getValue("sortkey.algorithm"));
3078-
isAscending = (isAscending == null ? Boolean.TRUE : isAscending);
3079-
Filter searchFilter = new Filter(TemplateJoinVO.class, "sortKey", isAscending, startIndex, pageSize);
3080-
searchFilter.addOrderBy(TemplateJoinVO.class, "tempZonePair", isAscending);
3073+
Filter searchFilter = new Filter(TemplateJoinVO.class, "sortKey", SortKeyAscending.value(), startIndex, pageSize);
3074+
searchFilter.addOrderBy(TemplateJoinVO.class, "tempZonePair", SortKeyAscending.value());
30813075

30823076
SearchBuilder<TemplateJoinVO> sb = _templateJoinDao.createSearchBuilder();
30833077
sb.select(null, Func.DISTINCT, sb.entity().getTempZonePair()); // select distinct (templateId, zoneId) pair
@@ -3702,6 +3696,6 @@ public String getConfigComponentName() {
37023696

37033697
@Override
37043698
public ConfigKey<?>[] getConfigKeys() {
3705-
return new ConfigKey<?>[] {AllowUserViewDestroyedVM, UserVMBlacklistedDetails, UserVMReadOnlyUIDetails};
3699+
return new ConfigKey<?>[] {AllowUserViewDestroyedVM, UserVMBlacklistedDetails, UserVMReadOnlyUIDetails, SortKeyAscending};
37063700
}
37073701
}

server/src/main/java/com/cloud/api/query/vo/DataCenterJoinVO.java

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -117,6 +117,9 @@ public class DataCenterJoinVO extends BaseViewVO implements InternalIdentity, Id
117117
@Column(name = "account_id")
118118
private long accountId;
119119

120+
@Column(name = "sort_key")
121+
private int sortKey;
122+
120123
public DataCenterJoinVO() {
121124
}
122125

@@ -221,4 +224,8 @@ public String getAffinityGroupUuid() {
221224
public long getAccountId() {
222225
return accountId;
223226
}
227+
228+
public int getSortKey() {
229+
return sortKey;
230+
}
224231
}

server/src/main/java/com/cloud/configuration/Config.java

Lines changed: 0 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -987,14 +987,6 @@ public enum Config {
987987
"30",
988988
"Garbage collection interval to destroy unused ELB vms in minutes. Minimum of 5",
989989
null),
990-
SortKeyAlgorithm(
991-
"Advanced",
992-
ManagementServer.class,
993-
Boolean.class,
994-
"sortkey.algorithm",
995-
"false",
996-
"Sort algorithm for those who use sort key(template, disk offering, service offering, network offering), true means ascending sort while false means descending sort",
997-
null),
998990
EnableEC2API("Advanced", ManagementServer.class, Boolean.class, "enable.ec2.api", "false", "enable EC2 API on CloudStack", null),
999991
EnableS3API("Advanced", ManagementServer.class, Boolean.class, "enable.s3.api", "false", "enable Amazon S3 API on CloudStack", null),
1000992
RecreateSystemVmEnabled(

server/src/main/java/com/cloud/configuration/ConfigurationManagerImpl.java

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1922,6 +1922,8 @@ public DataCenter editZone(final UpdateZoneCmd cmd) {
19221922
guestCidr = zone.getGuestNetworkCidr();
19231923
}
19241924

1925+
int sortKey = cmd.getSortKey() != null ? cmd.getSortKey() : zone.getSortKey();
1926+
19251927
// validate network domain
19261928
if (networkDomain != null && !networkDomain.isEmpty()) {
19271929
if (!NetUtils.verifyDomainName(networkDomain)) {
@@ -1944,6 +1946,7 @@ public DataCenter editZone(final UpdateZoneCmd cmd) {
19441946
zone.setInternalDns1(internalDns1);
19451947
zone.setInternalDns2(internalDns2);
19461948
zone.setGuestNetworkCidr(guestCidr);
1949+
zone.setSortKey(sortKey);
19471950
if (localStorageEnabled != null) {
19481951
zone.setLocalStorageEnabled(localStorageEnabled.booleanValue());
19491952
}

0 commit comments

Comments
 (0)