}
List<LoadBalancerTO> loadBalancersToApply = new ArrayList<LoadBalancerTO>();
List<MappingState> mappingStates = new ArrayList<MappingState>();
for (int i = 0; i < loadBalancingRules.size(); i++) {
LoadBalancingRule rule = loadBalancingRules.get(i);
boolean revoked = (rule.getState().equals(FirewallRule.State.Revoke));
String protocol = rule.getProtocol();
String algorithm = rule.getAlgorithm();
String uuid = rule.getUuid();
String srcIp = _networkModel.getIp(rule.getSourceIpAddressId()).getAddress().addr();
int srcPort = rule.getSourcePortStart();
List<LbDestination> destinations = rule.getDestinations();
if (externalLoadBalancerIsInline) {
MappingNic nic = getLoadBalancingIpNic(zone, network, rule.getSourceIpAddressId(), revoked, null);
mappingStates.add(nic.getState());
NicVO loadBalancingIpNic = nic.getNic();
if (loadBalancingIpNic == null) {
continue;
}
// Change the source IP address for the load balancing rule to be the load balancing IP address
srcIp = loadBalancingIpNic.getIp4Address();
}
if ((destinations != null && !destinations.isEmpty()) || rule.isAutoScaleConfig()) {
boolean inline = _networkMgr.isNetworkInlineMode(network);
LoadBalancerTO loadBalancer = new LoadBalancerTO(uuid, srcIp, srcPort, protocol, algorithm, revoked, false, inline, destinations, rule.getStickinessPolicies());
if (rule.isAutoScaleConfig()) {
loadBalancer.setAutoScaleVmGroup(rule.getAutoScaleVmGroup());
}
loadBalancersToApply.add(loadBalancer);
}
}
try {
if (loadBalancersToApply.size() > 0) {
int numLoadBalancersForCommand = loadBalancersToApply.size();
LoadBalancerTO[] loadBalancersForCommand = loadBalancersToApply.toArray(new LoadBalancerTO[numLoadBalancersForCommand]);
LoadBalancerConfigCommand cmd = new LoadBalancerConfigCommand(loadBalancersForCommand, null);
long guestVlanTag = Integer.parseInt(network.getBroadcastUri().getHost());
cmd.setAccessDetail(NetworkElementCommand.GUEST_VLAN_TAG, String.valueOf(guestVlanTag));
Answer answer = _agentMgr.easySend(externalLoadBalancer.getId(), cmd);
if (answer == null || !answer.getResult()) {
String details = (answer != null) ? answer.getDetails() : "details unavailable";
String msg = "Unable to apply load balancer rules to the external load balancer appliance in zone " + zone.getName() + " due to: " + details + ".";
s_logger.error(msg);
throw new ResourceUnavailableException(msg, DataCenter.class, network.getDataCenterId());
}
}
} catch (Exception ex) {
if (externalLoadBalancerIsInline) {
s_logger.error("Rollbacking static nat operation of inline mode load balancing due to error on applying LB rules!");
String existedGuestIp = loadBalancersToApply.get(0).getSrcIp();
// Rollback static NAT operation in current session
for (int i = 0; i < loadBalancingRules.size(); i++) {
LoadBalancingRule rule = loadBalancingRules.get(i);
MappingState state = mappingStates.get(i);
boolean revoke;
if (state == MappingState.Create) {
revoke = true;
} else if (state == MappingState.Remove) {
revoke = false;
} else {
continue;
}
getLoadBalancingIpNic(zone, network, rule.getSourceIpAddressId(), revoke, existedGuestIp);
}
}
throw new ResourceUnavailableException(ex.getMessage(), DataCenter.class, network.getDataCenterId());
}