Skip to content

Commit a2eb7ba

Browse files
author
Prachi Damle
committed
CLOUDSTACK-2056: DeploymentPlanner choice via ServiceOffering
- Changes merged from planner_reserve branch - Exposing deploymentplanner as an optional parameter while creating a service offering - changes to DeploymentPlanningManagerImpl to make sure host reserve-release happens between conflicting planner usages.
1 parent 15be977 commit a2eb7ba

50 files changed

Lines changed: 2874 additions & 1087 deletions

File tree

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.
Lines changed: 45 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,45 @@
1+
// Licensed to the Apache Software Foundation (ASF) under one
2+
// or more contributor license agreements. See the NOTICE file
3+
// distributed with this work for additional information
4+
// regarding copyright ownership. The ASF licenses this file
5+
// to you under the Apache License, Version 2.0 (the
6+
// "License"); you may not use this file except in compliance
7+
// with the License. You may obtain a copy of the License at
8+
//
9+
// http://www.apache.org/licenses/LICENSE-2.0
10+
//
11+
// Unless required by applicable law or agreed to in writing,
12+
// software distributed under the License is distributed on an
13+
// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
14+
// KIND, either express or implied. See the License for the
15+
// specific language governing permissions and limitations
16+
// under the License.
17+
package com.cloud.deploy;
18+
19+
import java.util.List;
20+
21+
import com.cloud.exception.InsufficientServerCapacityException;
22+
import com.cloud.vm.VirtualMachine;
23+
import com.cloud.vm.VirtualMachineProfile;
24+
25+
/**
26+
*/
27+
public interface DeploymentClusterPlanner extends DeploymentPlanner {
28+
/**
29+
* This is called to determine list of possible clusters where a virtual
30+
* machine can be deployed.
31+
*
32+
* @param vm
33+
* virtual machine.
34+
* @param plan
35+
* deployment plan that tells you where it's being deployed to.
36+
* @param avoid
37+
* avoid these data centers, pods, clusters, or hosts.
38+
* @return DeployDestination for that virtual machine.
39+
*/
40+
List<Long> orderClusters(VirtualMachineProfile<? extends VirtualMachine> vm, DeploymentPlan plan, ExcludeList avoid)
41+
throws InsufficientServerCapacityException;
42+
43+
PlannerResourceUsage getResourceUsage();
44+
45+
}

api/src/com/cloud/deploy/DeploymentPlanner.java

Lines changed: 22 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,7 @@
3535
/**
3636
*/
3737
public interface DeploymentPlanner extends Adapter {
38+
3839
/**
3940
* plan is called to determine where a virtual machine should be running.
4041
*
@@ -46,6 +47,7 @@ public interface DeploymentPlanner extends Adapter {
4647
* avoid these data centers, pods, clusters, or hosts.
4748
* @return DeployDestination for that virtual machine.
4849
*/
50+
@Deprecated
4951
DeployDestination plan(VirtualMachineProfile<? extends VirtualMachine> vm, DeploymentPlan plan, ExcludeList avoid) throws InsufficientServerCapacityException;
5052

5153
/**
@@ -88,6 +90,10 @@ public enum AllocationAlgorithm {
8890
userconcentratedpod_firstfit;
8991
}
9092

93+
public enum PlannerResourceUsage {
94+
Shared, Dedicated;
95+
}
96+
9197
public static class ExcludeList {
9298
private Set<Long> _dcIds;
9399
private Set<Long> _podIds;
@@ -99,10 +105,22 @@ public ExcludeList() {
99105
}
100106

101107
public ExcludeList(Set<Long> _dcIds, Set<Long> _podIds, Set<Long> _clusterIds, Set<Long> _hostIds, Set<Long> _poolIds) {
102-
this._dcIds = _dcIds;
103-
this._podIds = _podIds;
104-
this._clusterIds = _clusterIds;
105-
this._poolIds = _poolIds;
108+
if (_dcIds != null) {
109+
this._dcIds = new HashSet<Long>(_dcIds);
110+
}
111+
if (_podIds != null) {
112+
this._podIds = new HashSet<Long>(_podIds);
113+
}
114+
if (_clusterIds != null) {
115+
this._clusterIds = new HashSet<Long>(_clusterIds);
116+
}
117+
118+
if (_hostIds != null) {
119+
this._hostIds = new HashSet<Long>(_hostIds);
120+
}
121+
if (_poolIds != null) {
122+
this._poolIds = new HashSet<Long>(_poolIds);
123+
}
106124
}
107125

108126
public boolean add(InsufficientCapacityException e) {

api/src/com/cloud/event/EventTypes.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -423,6 +423,7 @@ public class EventTypes {
423423
public static final String EVENT_INTERNAL_LB_VM_START = "INTERNALLBVM.START";
424424
public static final String EVENT_INTERNAL_LB_VM_STOP = "INTERNALLBVM.STOP";
425425

426+
public static final String EVENT_HOST_RESERVATION_RELEASE = "HOST.RESERVATION.RELEASE";
426427
// Dedicated guest vlan range
427428
public static final String EVENT_GUEST_VLAN_RANGE_DEDICATE = "GUESTVLANRANGE.DEDICATE";
428429
public static final String EVENT_DEDICATED_GUEST_VLAN_RANGE_RELEASE = "GUESTVLANRANGE.RELEASE";
@@ -728,7 +729,6 @@ public class EventTypes {
728729
entityEventDetails.put(EVENT_AUTOSCALEVMGROUP_UPDATE, AutoScaleVmGroup.class.getName());
729730
entityEventDetails.put(EVENT_AUTOSCALEVMGROUP_ENABLE, AutoScaleVmGroup.class.getName());
730731
entityEventDetails.put(EVENT_AUTOSCALEVMGROUP_DISABLE, AutoScaleVmGroup.class.getName());
731-
732732
entityEventDetails.put(EVENT_GUEST_VLAN_RANGE_DEDICATE, GuestVlan.class.getName());
733733
entityEventDetails.put(EVENT_DEDICATED_GUEST_VLAN_RANGE_RELEASE, GuestVlan.class.getName());
734734
}

api/src/com/cloud/offering/ServiceOffering.java

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -108,4 +108,6 @@ public enum StorageType {
108108
boolean getDefaultUse();
109109

110110
String getSystemVmType();
111+
112+
String getDeploymentPlanner();
111113
}

api/src/com/cloud/resource/ResourceService.java

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -100,11 +100,13 @@ public interface ResourceService {
100100
Swift discoverSwift(AddSwiftCmd addSwiftCmd) throws DiscoveryException;
101101

102102
S3 discoverS3(AddS3Cmd cmd) throws DiscoveryException;
103-
103+
104104
List<HypervisorType> getSupportedHypervisorTypes(long zoneId, boolean forVirtualRouter, Long podId);
105105

106106
Pair<List<? extends Swift>, Integer> listSwifts(ListSwiftsCmd cmd);
107107

108108
List<? extends S3> listS3s(ListS3sCmd cmd);
109109

110+
boolean releaseHostReservation(Long hostId);
111+
110112
}

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

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -419,5 +419,7 @@ Ternary<Pair<List<? extends Host>, Integer>, List<? extends Host>, Map<Host, Boo
419419
* @return List of capacities
420420
*/
421421
List<? extends Capacity> listTopConsumedResources(ListCapacityCmd cmd);
422+
423+
List<String> listDeploymentPlanners();
422424

423425
}

api/src/org/apache/cloudstack/api/ApiConstants.java

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -496,6 +496,7 @@ public class ApiConstants {
496496
public static final String AFFINITY_GROUP_NAMES = "affinitygroupnames";
497497
public static final String ASA_INSIDE_PORT_PROFILE = "insideportprofile";
498498
public static final String AFFINITY_GROUP_ID = "affinitygroupid";
499+
public static final String DEPLOYMENT_PLANNER = "deploymentplanner";
499500
public static final String ACL_ID = "aclid";
500501
public static final String NUMBER = "number";
501502

Lines changed: 71 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,71 @@
1+
// Licensed to the Apache Software Foundation (ASF) under one
2+
// or more contributor license agreements. See the NOTICE file
3+
// distributed with this work for additional information
4+
// regarding copyright ownership. The ASF licenses this file
5+
// to you under the Apache License, Version 2.0 (the
6+
// "License"); you may not use this file except in compliance
7+
// with the License. You may obtain a copy of the License at
8+
//
9+
// http://www.apache.org/licenses/LICENSE-2.0
10+
//
11+
// Unless required by applicable law or agreed to in writing,
12+
// software distributed under the License is distributed on an
13+
// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
14+
// KIND, either express or implied. See the License for the
15+
// specific language governing permissions and limitations
16+
// under the License.
17+
package org.apache.cloudstack.api.command.admin.config;
18+
19+
import java.util.ArrayList;
20+
import java.util.List;
21+
22+
import org.apache.cloudstack.api.APICommand;
23+
import org.apache.cloudstack.api.BaseListCmd;
24+
import org.apache.cloudstack.api.response.DeploymentPlannersResponse;
25+
import org.apache.cloudstack.api.response.ListResponse;
26+
import org.apache.log4j.Logger;
27+
28+
@APICommand(name = "listDeploymentPlanners", description = "Lists all DeploymentPlanners available.", responseObject = DeploymentPlannersResponse.class)
29+
public class ListDeploymentPlannersCmd extends BaseListCmd {
30+
public static final Logger s_logger = Logger.getLogger(ListDeploymentPlannersCmd.class.getName());
31+
32+
private static final String s_name = "listdeploymentplannersresponse";
33+
34+
/////////////////////////////////////////////////////
35+
//////////////// API parameters /////////////////////
36+
/////////////////////////////////////////////////////
37+
38+
39+
/////////////////////////////////////////////////////
40+
/////////////////// Accessors ///////////////////////
41+
/////////////////////////////////////////////////////
42+
43+
44+
/////////////////////////////////////////////////////
45+
/////////////// API Implementation///////////////////
46+
/////////////////////////////////////////////////////
47+
48+
@Override
49+
public String getCommandName() {
50+
return s_name;
51+
}
52+
53+
@Override
54+
public void execute(){
55+
List<String> planners = _mgr.listDeploymentPlanners();
56+
ListResponse<DeploymentPlannersResponse> response = new ListResponse<DeploymentPlannersResponse>();
57+
List<DeploymentPlannersResponse> plannerResponses = new ArrayList<DeploymentPlannersResponse>();
58+
59+
for (String planner : planners) {
60+
DeploymentPlannersResponse plannerResponse = new DeploymentPlannersResponse();
61+
plannerResponse.setName(planner);
62+
plannerResponse.setObjectName("deploymentPlanner");
63+
plannerResponses.add(plannerResponse);
64+
}
65+
66+
response.setResponses(plannerResponses);
67+
response.setResponseName(getCommandName());
68+
this.setResponseObject(response);
69+
70+
}
71+
}
Lines changed: 105 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,105 @@
1+
// Licensed to the Apache Software Foundation (ASF) under one
2+
// or more contributor license agreements. See the NOTICE file
3+
// distributed with this work for additional information
4+
// regarding copyright ownership. The ASF licenses this file
5+
// to you under the Apache License, Version 2.0 (the
6+
// "License"); you may not use this file except in compliance
7+
// with the License. You may obtain a copy of the License at
8+
//
9+
// http://www.apache.org/licenses/LICENSE-2.0
10+
//
11+
// Unless required by applicable law or agreed to in writing,
12+
// software distributed under the License is distributed on an
13+
// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
14+
// KIND, either express or implied. See the License for the
15+
// specific language governing permissions and limitations
16+
// under the License.
17+
package org.apache.cloudstack.api.command.admin.host;
18+
19+
import org.apache.cloudstack.api.APICommand;
20+
import org.apache.cloudstack.api.ApiConstants;
21+
import org.apache.cloudstack.api.ApiErrorCode;
22+
import org.apache.cloudstack.api.BaseAsyncCmd;
23+
import org.apache.cloudstack.api.Parameter;
24+
import org.apache.cloudstack.api.ServerApiException;
25+
import org.apache.cloudstack.api.response.HostResponse;
26+
import org.apache.cloudstack.api.response.SuccessResponse;
27+
import org.apache.log4j.Logger;
28+
29+
import com.cloud.async.AsyncJob;
30+
import com.cloud.event.EventTypes;
31+
import com.cloud.user.Account;
32+
import com.cloud.user.UserContext;
33+
34+
@APICommand(name = "releaseHostReservation", description = "Releases host reservation.", responseObject = SuccessResponse.class)
35+
public class ReleaseHostReservationCmd extends BaseAsyncCmd {
36+
public static final Logger s_logger = Logger.getLogger(ReleaseHostReservationCmd.class.getName());
37+
38+
private static final String s_name = "releasehostreservationresponse";
39+
40+
/////////////////////////////////////////////////////
41+
//////////////// API parameters /////////////////////
42+
/////////////////////////////////////////////////////
43+
44+
@Parameter(name=ApiConstants.ID, type=CommandType.UUID, entityType=HostResponse.class,
45+
required=true, description="the host ID")
46+
private Long id;
47+
48+
/////////////////////////////////////////////////////
49+
/////////////////// Accessors ///////////////////////
50+
/////////////////////////////////////////////////////
51+
52+
public Long getId() {
53+
return id;
54+
}
55+
56+
/////////////////////////////////////////////////////
57+
/////////////// API Implementation///////////////////
58+
/////////////////////////////////////////////////////
59+
60+
@Override
61+
public String getCommandName() {
62+
return s_name;
63+
}
64+
65+
@Override
66+
public long getEntityOwnerId() {
67+
Account account = UserContext.current().getCaller();
68+
if (account != null) {
69+
return account.getId();
70+
}
71+
72+
return Account.ACCOUNT_ID_SYSTEM;
73+
}
74+
75+
@Override
76+
public String getEventType() {
77+
return EventTypes.EVENT_HOST_RESERVATION_RELEASE;
78+
}
79+
80+
@Override
81+
public String getEventDescription() {
82+
return "releasing reservation for host: " + getId();
83+
}
84+
85+
@Override
86+
public AsyncJob.Type getInstanceType() {
87+
return AsyncJob.Type.Host;
88+
}
89+
90+
@Override
91+
public Long getInstanceId() {
92+
return getId();
93+
}
94+
95+
@Override
96+
public void execute(){
97+
boolean result = _resourceService.releaseHostReservation(getId());
98+
if (result) {
99+
SuccessResponse response = new SuccessResponse(getCommandName());
100+
this.setResponseObject(response);
101+
} else {
102+
throw new ServerApiException(ApiErrorCode.INTERNAL_ERROR, "Failed to release host reservation");
103+
}
104+
}
105+
}

api/src/org/apache/cloudstack/api/command/admin/offering/CreateServiceOfferingCmd.java

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -84,6 +84,9 @@ public class CreateServiceOfferingCmd extends BaseCmd {
8484
@Parameter(name=ApiConstants.NETWORKRATE, type=CommandType.INTEGER, description="data transfer rate in megabits per second allowed. Supported only for non-System offering and system offerings having \"domainrouter\" systemvmtype")
8585
private Integer networkRate;
8686

87+
@Parameter(name = ApiConstants.DEPLOYMENT_PLANNER, type = CommandType.STRING, description = "The deployment planner heuristics used to deploy a VM of this offering. If null, value of global config vm.deployment.planner is used")
88+
private String deploymentPlanner;
89+
8790
/////////////////////////////////////////////////////
8891
/////////////////// Accessors ///////////////////////
8992
/////////////////////////////////////////////////////
@@ -148,6 +151,9 @@ public Integer getNetworkRate() {
148151
return networkRate;
149152
}
150153

154+
public String getDeploymentPlanner() {
155+
return deploymentPlanner;
156+
}
151157

152158
/////////////////////////////////////////////////////
153159
/////////////// API Implementation///////////////////

0 commit comments

Comments
 (0)