Skip to content

Commit deaf910

Browse files
author
Harikrishna Patnala
committed
CLOUDSTACK-741: Granular Global Parameters and adding fixes for CLOUDSTACK-2176, CLOUDSTACK-2198, CLOUDSTACK-2200
Adding the zone, cluster, account level parameters The parameters at scope (zone/cluster/pool/account) can be updated by updateConfiguration API with additional parameter zoneid/clusterid/accountid/storagepoolid Whenever these scoped parameters are used in CS they get value from the corresponding details table if not defined get value from global parameter. Same with the listConfiguration API with additional parameter zoneid/clusterid/accountid/storagepoolid
1 parent b2fdd5e commit deaf910

29 files changed

Lines changed: 389 additions & 201 deletions

api/src/com/cloud/configuration/ConfigurationService.java

Lines changed: 8 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,11 @@
2020

2121
import javax.naming.NamingException;
2222

23+
import com.cloud.exception.InvalidParameterValueException;
24+
import com.cloud.exception.InsufficientCapacityException;
25+
import com.cloud.exception.ConcurrentOperationException;
26+
import com.cloud.exception.ResourceUnavailableException;
27+
import com.cloud.exception.ResourceAllocationException;
2328
import org.apache.cloudstack.api.command.admin.config.UpdateCfgCmd;
2429
import org.apache.cloudstack.api.command.admin.ldap.LDAPConfigCmd;
2530
import org.apache.cloudstack.api.command.admin.ldap.LDAPRemoveCmd;
@@ -46,10 +51,6 @@
4651
import com.cloud.dc.DataCenter;
4752
import com.cloud.dc.Pod;
4853
import com.cloud.dc.Vlan;
49-
import com.cloud.exception.ConcurrentOperationException;
50-
import com.cloud.exception.InsufficientCapacityException;
51-
import com.cloud.exception.ResourceAllocationException;
52-
import com.cloud.exception.ResourceUnavailableException;
5354
import com.cloud.network.Networks.TrafficType;
5455
import com.cloud.offering.DiskOffering;
5556
import com.cloud.offering.NetworkOffering;
@@ -65,7 +66,7 @@ public interface ConfigurationService {
6566
* - the command wrapping name and value parameters
6667
* @return updated configuration object if successful
6768
*/
68-
Configuration updateConfiguration(UpdateCfgCmd cmd);
69+
Configuration updateConfiguration(UpdateCfgCmd cmd) throws InvalidParameterValueException;
6970

7071
/**
7172
* Create a service offering through the API
@@ -250,7 +251,7 @@ public interface ConfigurationService {
250251

251252
NetworkOffering getNetworkOffering(long id);
252253

253-
Integer getNetworkOfferingNetworkRate(long networkOfferingId);
254+
Integer getNetworkOfferingNetworkRate(long networkOfferingId, Long dataCenterId);
254255

255256
Account getVlanAccount(long vlanId);
256257

@@ -262,7 +263,7 @@ public interface ConfigurationService {
262263

263264
Long getDefaultPageSize();
264265

265-
Integer getServiceOfferingNetworkRate(long serviceOfferingId);
266+
Integer getServiceOfferingNetworkRate(long serviceOfferingId, Long dataCenterId);
266267

267268
DiskOffering getDiskOffering(long diskOfferingId);
268269

api/src/com/cloud/network/NetworkModel.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -181,7 +181,7 @@ Map<PublicIpAddress, Set<Service>> getIpToServices(List<? extends PublicIpAddres
181181
/**
182182
* @return
183183
*/
184-
String getDefaultNetworkDomain();
184+
String getDefaultNetworkDomain(long zoneId);
185185

186186
/**
187187
* @param ntwkOffId

api/src/org/apache/cloudstack/api/command/admin/config/ListCfgsByCmd.java

Lines changed: 32 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -45,11 +45,17 @@ public class ListCfgsByCmd extends BaseListCmd {
4545
@Parameter(name = ApiConstants.NAME, type = CommandType.STRING, description = "lists configuration by name")
4646
private String configName;
4747

48-
@Parameter(name=ApiConstants.SCOPE, type = CommandType.STRING, description = "scope(zone/cluster/pool/account) of the parameter that needs to be updated")
49-
private String scope;
48+
@Parameter(name=ApiConstants.ZONE_ID, type=CommandType.UUID, entityType=ZoneResponse.class, description="the ID of the Zone to update the parameter value for corresponding zone")
49+
private Long zone_id;
5050

51-
@Parameter(name=ApiConstants.ID, type = CommandType.UUID, entityType = {ZoneResponse.class, ClusterResponse.class, StoragePoolResponse.class, AccountResponse.class}, description = "corresponding ID of the scope")
52-
private Long id;
51+
@Parameter(name=ApiConstants.CLUSTER_ID, type=CommandType.UUID, entityType=ClusterResponse.class, description="the ID of the Cluster to update the parameter value for corresponding cluster")
52+
private Long cluster_id;
53+
54+
@Parameter(name=ApiConstants.STORAGE_ID, type=CommandType.UUID, entityType=StoragePoolResponse.class, description="the ID of the Storage pool to update the parameter value for corresponding storage pool")
55+
private Long storagepool_id;
56+
57+
@Parameter(name=ApiConstants.ACCOUNT_ID, type=CommandType.UUID, entityType=AccountResponse.class, description="the ID of the Account to update the parameter value for corresponding account")
58+
private Long account_id;
5359

5460

5561
// ///////////////////////////////////////////////////
@@ -64,14 +70,21 @@ public String getConfigName() {
6470
return configName;
6571
}
6672

67-
public String getScope() {
68-
return scope;
73+
public Long getZoneId() {
74+
return zone_id;
75+
}
76+
77+
public Long getClusterId() {
78+
return cluster_id;
6979
}
7080

71-
public Long getId() {
72-
return id;
81+
public Long getStoragepoolId() {
82+
return storagepool_id;
7383
}
7484

85+
public Long getAccountId() {
86+
return account_id;
87+
}
7588

7689
@Override
7790
public Long getPageSizeVal() {
@@ -100,10 +113,17 @@ public void execute() {
100113
for (Configuration cfg : result.first()) {
101114
ConfigurationResponse cfgResponse = _responseGenerator.createConfigurationResponse(cfg);
102115
cfgResponse.setObjectName("configuration");
103-
if (scope != null) {
104-
cfgResponse.setScope(scope);
105-
} else {
106-
cfgResponse.setScope("global");
116+
if(getZoneId() != null) {
117+
cfgResponse.setScope("zone");
118+
}
119+
if(getClusterId() != null) {
120+
cfgResponse.setScope("cluster");
121+
}
122+
if(getStoragepoolId() != null) {
123+
cfgResponse.setScope("storagepool");
124+
}
125+
if(getAccountId() != null) {
126+
cfgResponse.setScope("account");
107127
}
108128
configResponses.add(cfgResponse);
109129
}

api/src/org/apache/cloudstack/api/command/admin/config/UpdateCfgCmd.java

Lines changed: 34 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -43,11 +43,17 @@ public class UpdateCfgCmd extends BaseCmd {
4343
@Parameter(name=ApiConstants.VALUE, type=CommandType.STRING, description="the value of the configuration", length=4095)
4444
private String value;
4545

46-
@Parameter(name=ApiConstants.SCOPE, type = CommandType.STRING, description = "scope(zone/cluster/pool/account) of the parameter that needs to be updated")
47-
private String scope;
46+
@Parameter(name=ApiConstants.ZONE_ID, type=CommandType.UUID, entityType=ZoneResponse.class, description="the ID of the Zone to update the parameter value for corresponding zone")
47+
private Long zone_id;
4848

49-
@Parameter(name=ApiConstants.ID, type = CommandType.UUID, entityType = {ZoneResponse.class, ClusterResponse.class, StoragePoolResponse.class, AccountResponse.class}, description = "corresponding ID of the scope")
50-
private Long id;
49+
@Parameter(name=ApiConstants.CLUSTER_ID, type=CommandType.UUID, entityType=ClusterResponse.class, description="the ID of the Cluster to update the parameter value for corresponding cluster")
50+
private Long cluster_id;
51+
52+
@Parameter(name=ApiConstants.STORAGE_ID, type=CommandType.UUID, entityType=StoragePoolResponse.class, description="the ID of the Storage pool to update the parameter value for corresponding storage pool")
53+
private Long storagepool_id;
54+
55+
@Parameter(name=ApiConstants.ACCOUNT_ID, type=CommandType.UUID, entityType=AccountResponse.class, description="the ID of the Account to update the parameter value for corresponding account")
56+
private Long account_id;
5157

5258
/////////////////////////////////////////////////////
5359
/////////////////// Accessors ///////////////////////
@@ -61,12 +67,20 @@ public String getValue() {
6167
return value;
6268
}
6369

64-
public String getScope() {
65-
return scope;
70+
public Long getZoneId() {
71+
return zone_id;
6672
}
6773

68-
public Long getId() {
69-
return id;
74+
public Long getClusterId() {
75+
return cluster_id;
76+
}
77+
78+
public Long getStoragepoolId() {
79+
return storagepool_id;
80+
}
81+
82+
public Long getAccountId() {
83+
return account_id;
7084
}
7185

7286
/////////////////////////////////////////////////////
@@ -89,12 +103,19 @@ public void execute(){
89103
if (cfg != null) {
90104
ConfigurationResponse response = _responseGenerator.createConfigurationResponse(cfg);
91105
response.setResponseName(getCommandName());
92-
if (scope != null) {
93-
response.setScope(scope);
94-
response.setValue(value);
95-
} else {
96-
response.setScope("global");
106+
if(getZoneId() != null) {
107+
response.setScope("zone");
108+
}
109+
if(getClusterId() != null) {
110+
response.setScope("cluster");
111+
}
112+
if(getStoragepoolId() != null) {
113+
response.setScope("storagepool");
114+
}
115+
if(getAccountId() != null) {
116+
response.setScope("account");
97117
}
118+
response.setValue(value);
98119
this.setResponseObject(response);
99120
} else {
100121
throw new ServerApiException(ApiErrorCode.INTERNAL_ERROR, "Failed to update config");

api/src/org/apache/cloudstack/api/response/ConfigurationResponse.java

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,9 @@ public class ConfigurationResponse extends BaseResponse {
3535
@SerializedName(ApiConstants.SCOPE) @Param(description="scope(zone/cluster/pool/account) of the parameter that needs to be updated")
3636
private String scope;
3737

38+
@SerializedName(ApiConstants.ID) @Param(description="the value of the configuration")
39+
private Long id;
40+
3841
@SerializedName(ApiConstants.DESCRIPTION) @Param(description="the description of the configuration")
3942
private String description;
4043

server/src/com/cloud/alert/AlertManagerImpl.java

Lines changed: 20 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -70,6 +70,7 @@
7070
import com.cloud.network.dao.IPAddressDao;
7171
import com.cloud.org.Grouping.AllocationState;
7272
import com.cloud.resource.ResourceManager;
73+
import com.cloud.server.ConfigurationServer;
7374
import com.cloud.storage.StorageManager;
7475
import com.cloud.storage.dao.VolumeDao;
7576
import com.cloud.utils.NumbersUtil;
@@ -106,7 +107,8 @@ public class AlertManagerImpl extends ManagerBase implements AlertManager {
106107
@Inject private PrimaryDataStoreDao _storagePoolDao;
107108
@Inject private ConfigurationDao _configDao;
108109
@Inject private ResourceManager _resourceMgr;
109-
@Inject private ConfigurationManager _configMgr;
110+
@Inject private ConfigurationManager _configMgr;
111+
@Inject ConfigurationServer _configServer;
110112
private Timer _timer = null;
111113
private float _cpuOverProvisioningFactor = 1;
112114
private long _capacityCheckPeriod = 60L * 60L * 1000L; // one hour by default
@@ -562,19 +564,30 @@ public void checkForAlerts(){
562564
float overProvFactor = 1f;
563565
capacity = _capacityDao.findCapacityBy(capacityType.intValue(), cluster.getDataCenterId(), null, cluster.getId());
564566

565-
if (capacityType == Capacity.CAPACITY_TYPE_STORAGE){
566-
capacity.add(getUsedStats(capacityType, cluster.getDataCenterId(), cluster.getPodId(), cluster.getId()));
567+
// cpu and memory allocated capacity notification threshold can be defined at cluster level, so getting the value if they are defined at cluster level
568+
double capacityValue = 0;
569+
switch (capacityType) {
570+
case Capacity.CAPACITY_TYPE_STORAGE:
571+
capacity.add(getUsedStats(capacityType, cluster.getDataCenterId(), cluster.getPodId(), cluster.getId()));
572+
capacityValue = _capacityTypeThresholdMap.get(capacityType);
573+
break;
574+
case Capacity.CAPACITY_TYPE_CPU:
575+
overProvFactor = ApiDBUtils.getCpuOverprovisioningFactor();
576+
capacityValue = Double.parseDouble(_configServer.getConfigValue(Config.CPUCapacityThreshold.key(), Config.ConfigurationParameterScope.cluster.toString(), cluster.getId()));
577+
break;
578+
case Capacity.CAPACITY_TYPE_MEMORY:
579+
capacityValue = Double.parseDouble(_configServer.getConfigValue(Config.MemoryCapacityThreshold.key(), Config.ConfigurationParameterScope.cluster.toString(), cluster.getId()));
580+
break;
581+
default:
582+
capacityValue = _capacityTypeThresholdMap.get(capacityType);
567583
}
568584
if (capacity == null || capacity.size() == 0){
569585
continue;
570-
}
571-
if (capacityType == Capacity.CAPACITY_TYPE_CPU){
572-
overProvFactor = ApiDBUtils.getCpuOverprovisioningFactor();
573586
}
574587

575588
double totalCapacity = capacity.get(0).getTotalCapacity() * overProvFactor;
576589
double usedCapacity = capacity.get(0).getUsedCapacity() + capacity.get(0).getReservedCapacity();
577-
if (totalCapacity != 0 && usedCapacity/totalCapacity > _capacityTypeThresholdMap.get(capacityType)){
590+
if (totalCapacity != 0 && usedCapacity/totalCapacity > capacityValue){
578591
generateEmailAlert(ApiDBUtils.findZoneById(cluster.getDataCenterId()), ApiDBUtils.findPodById(cluster.getPodId()), cluster,
579592
totalCapacity, usedCapacity, capacityType);
580593
}

server/src/com/cloud/api/ApiDBUtils.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1034,7 +1034,7 @@ public static Long getVlanNetworkId(long vlanId) {
10341034
}
10351035

10361036
public static Integer getNetworkRate(long networkOfferingId) {
1037-
return _configMgr.getNetworkOfferingNetworkRate(networkOfferingId);
1037+
return _configMgr.getNetworkOfferingNetworkRate(networkOfferingId, null);
10381038
}
10391039

10401040
public static Account getVlanAccount(long vlanId) {

server/src/com/cloud/capacity/dao/CapacityDao.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -41,5 +41,5 @@ List<SummedCapacity> findCapacityBy(Integer capacityType, Long zoneId,
4141
List<SummedCapacity> listCapacitiesGroupedByLevelAndType(Integer capacityType, Long zoneId, Long podId, Long clusterId, int level, Long limit);
4242
void updateCapacityState(Long dcId, Long podId, Long clusterId,
4343
Long hostId, String capacityState);
44-
List<Long> listClustersCrossingThreshold(short capacityType, Long zoneId, Float disableThreshold, long computeRequested);
44+
List<Long> listClustersCrossingThreshold(short capacityType, Long zoneId, String ConfigName, long computeRequested);
4545
}

server/src/com/cloud/capacity/dao/CapacityDaoImpl.java

Lines changed: 23 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@
2727
import javax.ejb.Local;
2828
import javax.inject.Inject;
2929

30+
import com.cloud.configuration.Config;
3031
import org.apache.cloudstack.storage.datastore.db.PrimaryDataStoreDao;
3132
import org.apache.cloudstack.storage.datastore.db.StoragePoolVO;
3233
import org.apache.log4j.Logger;
@@ -115,12 +116,20 @@ public class CapacityDaoImpl extends GenericDaoBase<CapacityVO, Long> implements
115116

116117
private static final String LIST_CAPACITY_GROUP_BY_CLUSTER_TYPE_PART2 = " GROUP BY cluster_id, capacity_type order by percent desc limit ";
117118
private static final String UPDATE_CAPACITY_STATE = "UPDATE `cloud`.`op_host_capacity` SET capacity_state = ? WHERE ";
118-
private static final String LIST_CLUSTERS_CROSSING_THRESHOLD = "SELECT cluster_id " +
119-
"FROM (SELECT cluster_id, ( (sum(capacity.used_capacity) + sum(capacity.reserved_capacity) + ?)/sum(total_capacity) ) ratio "+
120-
"FROM `cloud`.`op_host_capacity` capacity "+
121-
"WHERE capacity.data_center_id = ? AND capacity.capacity_type = ? AND capacity.total_capacity > 0 "+
122-
"GROUP BY cluster_id) tmp " +
123-
"WHERE tmp.ratio > ? ";
119+
120+
private static final String LIST_CLUSTERS_CROSSING_THRESHOLD = "SELECT clusterList.cluster_id " +
121+
"FROM ( SELECT cluster.cluster_id cluster_id, ( (sum(cluster.used) + sum(cluster.reserved) + ?)/sum(cluster.total) ) ratio, cluster.configValue value " +
122+
"FROM ( SELECT capacity.cluster_id cluster_id, capacity.used_capacity used, capacity.reserved_capacity reserved, capacity.total_capacity total, " +
123+
"CASE (SELECT count(*) FROM `cloud`.`cluster_details` details WHERE details.cluster_id = capacity.cluster_id AND details.name = ? ) " +
124+
"WHEN 1 THEN ( SELECT details.value FROM `cloud`.`cluster_details` details WHERE details.cluster_id = capacity.cluster_id AND details.name = ? ) " +
125+
"ELSE ( SELECT config.value FROM `cloud`.`configuration` config WHERE config.name = ?) " +
126+
"END configValue " +
127+
"FROM `cloud`.`op_host_capacity` capacity " +
128+
"WHERE capacity.data_center_id = ? AND capacity.capacity_type = ? AND capacity.total_capacity > 0) cluster " +
129+
130+
"GROUP BY cluster.cluster_id) clusterList " +
131+
"WHERE clusterList.ratio > clusterList.value; ";
132+
124133

125134

126135
public CapacityDaoImpl() {
@@ -146,20 +155,22 @@ public CapacityDaoImpl() {
146155
}
147156

148157
@Override
149-
public List<Long> listClustersCrossingThreshold(short capacityType, Long zoneId, Float disableThreshold, long compute_requested){
158+
public List<Long> listClustersCrossingThreshold(short capacityType, Long zoneId, String configName, long compute_requested){
150159

151160
Transaction txn = Transaction.currentTxn();
152161
PreparedStatement pstmt = null;
153162
List<Long> result = new ArrayList<Long>();
154163
StringBuilder sql = new StringBuilder(LIST_CLUSTERS_CROSSING_THRESHOLD);
155-
156-
164+
// during listing the clusters that cross the threshold
165+
// we need to check with disabled thresholds of each cluster if not defined at cluster consider the global value
157166
try {
158167
pstmt = txn.prepareAutoCloseStatement(sql.toString());
159168
pstmt.setLong(1,compute_requested);
160-
pstmt.setShort(2,capacityType);
161-
pstmt.setFloat(3,disableThreshold);
162-
pstmt.setLong(4,zoneId);
169+
pstmt.setString(2, configName);
170+
pstmt.setString(3, configName);
171+
pstmt.setString(4, configName);
172+
pstmt.setLong(5,zoneId);
173+
pstmt.setShort(6,capacityType);
163174

164175
ResultSet rs = pstmt.executeQuery();
165176
while (rs.next()) {

0 commit comments

Comments
 (0)