mirror of
https://github.com/apache/cloudstack.git
synced 2025-12-17 11:04:00 +01:00
Added 2 new api commands for 1-1 nat feauture: enable/disableOneToOneNat. Here is the 1-1 nat api summary:
* to enable 1-1 nat for ip/vm use enalbeOneToOneNat api * to open port range (or multiple port ranges) use createIpForwardingRule api. * to delete one port range use deleteIpForwardingRule api. * to disable 1-1 nat use disableOneToOneNat api.
This commit is contained in:
parent
c70113835d
commit
731e78937f
@ -28,7 +28,9 @@ import com.cloud.api.Parameter;
|
|||||||
import com.cloud.api.ServerApiException;
|
import com.cloud.api.ServerApiException;
|
||||||
import com.cloud.api.response.FirewallRuleResponse;
|
import com.cloud.api.response.FirewallRuleResponse;
|
||||||
import com.cloud.event.EventTypes;
|
import com.cloud.event.EventTypes;
|
||||||
|
import com.cloud.exception.InvalidParameterValueException;
|
||||||
import com.cloud.exception.NetworkRuleConflictException;
|
import com.cloud.exception.NetworkRuleConflictException;
|
||||||
|
import com.cloud.network.IpAddress;
|
||||||
import com.cloud.network.rules.PortForwardingRule;
|
import com.cloud.network.rules.PortForwardingRule;
|
||||||
import com.cloud.user.Account;
|
import com.cloud.user.Account;
|
||||||
import com.cloud.user.UserContext;
|
import com.cloud.user.UserContext;
|
||||||
@ -46,9 +48,6 @@ public class CreateIpForwardingRuleCmd extends BaseAsyncCreateCmd implements Por
|
|||||||
|
|
||||||
@Parameter(name=ApiConstants.IP_ADDRESS, type=CommandType.STRING, required=true, description="the public IP address of the forwarding rule, already associated via associateIp")
|
@Parameter(name=ApiConstants.IP_ADDRESS, type=CommandType.STRING, required=true, description="the public IP address of the forwarding rule, already associated via associateIp")
|
||||||
private String ipAddress;
|
private String ipAddress;
|
||||||
|
|
||||||
@Parameter(name=ApiConstants.VIRTUAL_MACHINE_ID, type=CommandType.LONG, required=true, description="the ID of the virtual machine for the forwarding rule")
|
|
||||||
private Long virtualMachineId;
|
|
||||||
|
|
||||||
@Parameter(name=ApiConstants.START_PORT, type=CommandType.INTEGER, required=true, description="the start port for the rule")
|
@Parameter(name=ApiConstants.START_PORT, type=CommandType.INTEGER, required=true, description="the start port for the rule")
|
||||||
private Integer startPort;
|
private Integer startPort;
|
||||||
@ -58,6 +57,7 @@ public class CreateIpForwardingRuleCmd extends BaseAsyncCreateCmd implements Por
|
|||||||
|
|
||||||
@Parameter(name=ApiConstants.PROTOCOL, type=CommandType.STRING, required=true, description="the protocol for the rule. Valid values are TCP or UDP.")
|
@Parameter(name=ApiConstants.PROTOCOL, type=CommandType.STRING, required=true, description="the protocol for the rule. Valid values are TCP or UDP.")
|
||||||
private String protocol;
|
private String protocol;
|
||||||
|
|
||||||
|
|
||||||
/////////////////////////////////////////////////////
|
/////////////////////////////////////////////////////
|
||||||
/////////////////// Accessors ///////////////////////
|
/////////////////// Accessors ///////////////////////
|
||||||
@ -66,10 +66,6 @@ public class CreateIpForwardingRuleCmd extends BaseAsyncCreateCmd implements Por
|
|||||||
public String getIpAddress() {
|
public String getIpAddress() {
|
||||||
return ipAddress;
|
return ipAddress;
|
||||||
}
|
}
|
||||||
|
|
||||||
public long getVirtualMachineId() {
|
|
||||||
return virtualMachineId;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int getStartPort() {
|
public int getStartPort() {
|
||||||
return startPort;
|
return startPort;
|
||||||
@ -113,7 +109,7 @@ public class CreateIpForwardingRuleCmd extends BaseAsyncCreateCmd implements Por
|
|||||||
public void create() {
|
public void create() {
|
||||||
PortForwardingRule rule;
|
PortForwardingRule rule;
|
||||||
try {
|
try {
|
||||||
rule = _rulesService.createPortForwardingRule(this, virtualMachineId, true);
|
rule = _rulesService.createPortForwardingRule(this, getVirtualMachineId(), true);
|
||||||
} catch (NetworkRuleConflictException e) {
|
} catch (NetworkRuleConflictException e) {
|
||||||
s_logger.info("Unable to create Port Forwarding Rule due to " + e.getMessage());
|
s_logger.info("Unable to create Port Forwarding Rule due to " + e.getMessage());
|
||||||
throw new ServerApiException(BaseCmd.NETWORK_RULE_CONFLICT_ERROR, e.getMessage());
|
throw new ServerApiException(BaseCmd.NETWORK_RULE_CONFLICT_ERROR, e.getMessage());
|
||||||
@ -140,7 +136,7 @@ public class CreateIpForwardingRuleCmd extends BaseAsyncCreateCmd implements Por
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String getEventDescription() {
|
public String getEventDescription() {
|
||||||
return ("Creating an ipforwarding 1:1 NAT rule for "+ipAddress+" with virtual machine:"+virtualMachineId);
|
return ("Creating an ipforwarding 1:1 NAT rule for "+ipAddress+" with virtual machine:"+ getVirtualMachineId());
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -225,5 +221,16 @@ public class CreateIpForwardingRuleCmd extends BaseAsyncCreateCmd implements Por
|
|||||||
public boolean isOneToOneNat() {
|
public boolean isOneToOneNat() {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public long getVirtualMachineId() {
|
||||||
|
IpAddress ip = _networkService.getIp(new Ip(ipAddress));
|
||||||
|
if (ip == null) {
|
||||||
|
throw new InvalidParameterValueException("Ip address " + ipAddress + " doesn't exist in the system");
|
||||||
|
} else {
|
||||||
|
return _networkService.getIp(new Ip(ipAddress)).getVmId();
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@ -28,6 +28,7 @@ import com.cloud.api.Parameter;
|
|||||||
import com.cloud.api.ServerApiException;
|
import com.cloud.api.ServerApiException;
|
||||||
import com.cloud.api.response.SuccessResponse;
|
import com.cloud.api.response.SuccessResponse;
|
||||||
import com.cloud.event.EventTypes;
|
import com.cloud.event.EventTypes;
|
||||||
|
import com.cloud.exception.InvalidParameterValueException;
|
||||||
import com.cloud.network.rules.PortForwardingRule;
|
import com.cloud.network.rules.PortForwardingRule;
|
||||||
|
|
||||||
@Implementation(description="Deletes an ip forwarding rule", responseObject=SuccessResponse.class)
|
@Implementation(description="Deletes an ip forwarding rule", responseObject=SuccessResponse.class)
|
||||||
@ -79,7 +80,12 @@ public class DeleteIpForwardingRuleCmd extends BaseAsyncCmd {
|
|||||||
@Override
|
@Override
|
||||||
public long getEntityOwnerId() {
|
public long getEntityOwnerId() {
|
||||||
if (ownerId == null) {
|
if (ownerId == null) {
|
||||||
ownerId = _entityMgr.findById(PortForwardingRule.class, id).getAccountId();
|
PortForwardingRule rule = _entityMgr.findById(PortForwardingRule.class, id);
|
||||||
|
if (rule == null) {
|
||||||
|
throw new InvalidParameterValueException("Unable to find firewall rule by id: " + id);
|
||||||
|
} else {
|
||||||
|
ownerId = rule.getAccountId();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
return ownerId;
|
return ownerId;
|
||||||
}
|
}
|
||||||
|
|||||||
88
api/src/com/cloud/api/commands/DisableOneToOneNat.java
Normal file
88
api/src/com/cloud/api/commands/DisableOneToOneNat.java
Normal file
@ -0,0 +1,88 @@
|
|||||||
|
/**
|
||||||
|
* Copyright (C) 2010 Cloud.com, Inc. All rights reserved.
|
||||||
|
*
|
||||||
|
* This software is licensed under the GNU General Public License v3 or later.
|
||||||
|
*
|
||||||
|
* It is free software: you can redistribute it and/or modify
|
||||||
|
* it under the terms of the GNU General Public License as published by
|
||||||
|
* the Free Software Foundation, either version 3 of the License, or any later version.
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
package com.cloud.api.commands;
|
||||||
|
|
||||||
|
import org.apache.log4j.Logger;
|
||||||
|
|
||||||
|
import com.cloud.api.ApiConstants;
|
||||||
|
import com.cloud.api.BaseAsyncCmd;
|
||||||
|
import com.cloud.api.BaseCmd;
|
||||||
|
import com.cloud.api.Implementation;
|
||||||
|
import com.cloud.api.Parameter;
|
||||||
|
import com.cloud.api.ServerApiException;
|
||||||
|
import com.cloud.api.response.SuccessResponse;
|
||||||
|
import com.cloud.event.EventTypes;
|
||||||
|
import com.cloud.exception.ResourceUnavailableException;
|
||||||
|
import com.cloud.network.IpAddress;
|
||||||
|
import com.cloud.utils.net.Ip;
|
||||||
|
|
||||||
|
@Implementation(description="Disables one to one nat rule", responseObject=SuccessResponse.class)
|
||||||
|
public class DisableOneToOneNat extends BaseAsyncCmd {
|
||||||
|
public static final Logger s_logger = Logger.getLogger(DeletePortForwardingRuleCmd.class.getName());
|
||||||
|
private static final String s_name = "disableonetoonenatresponse";
|
||||||
|
|
||||||
|
/////////////////////////////////////////////////////
|
||||||
|
//////////////// API parameters /////////////////////
|
||||||
|
/////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
@Parameter(name=ApiConstants.IP_ADDRESS, type=CommandType.STRING, required=true, description="the public IP address for which one-to-one nat feature is being disableed")
|
||||||
|
private String ipAddress;
|
||||||
|
|
||||||
|
/////////////////////////////////////////////////////
|
||||||
|
/////////////////// Accessors ///////////////////////
|
||||||
|
/////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
public String getIpAddress() {
|
||||||
|
return ipAddress;
|
||||||
|
}
|
||||||
|
|
||||||
|
/////////////////////////////////////////////////////
|
||||||
|
/////////////// API Implementation///////////////////
|
||||||
|
/////////////////////////////////////////////////////
|
||||||
|
@Override
|
||||||
|
public String getCommandName() {
|
||||||
|
return s_name;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getEventType() {
|
||||||
|
return EventTypes.EVENT_DISABLE_ONE_TO_ONE_NAT;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getEventDescription() {
|
||||||
|
return ("Disabling one to one nat for ip=" + ipAddress);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public long getEntityOwnerId() {
|
||||||
|
return _entityMgr.findById(IpAddress.class, ipAddress).getAccountId();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void execute() throws ResourceUnavailableException {
|
||||||
|
boolean result = _rulesService.disableOneToOneNat(new Ip(ipAddress));
|
||||||
|
|
||||||
|
if (result) {
|
||||||
|
SuccessResponse response = new SuccessResponse(getCommandName());
|
||||||
|
this.setResponseObject(response);
|
||||||
|
} else {
|
||||||
|
throw new ServerApiException(BaseCmd.INTERNAL_ERROR, "Failed to disable oneToOne nat rule");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
86
api/src/com/cloud/api/commands/EnableOneToOneNat.java
Normal file
86
api/src/com/cloud/api/commands/EnableOneToOneNat.java
Normal file
@ -0,0 +1,86 @@
|
|||||||
|
/**
|
||||||
|
* Copyright (C) 2010 Cloud.com, Inc. All rights reserved.
|
||||||
|
*
|
||||||
|
* This software is licensed under the GNU General Public License v3 or later.
|
||||||
|
*
|
||||||
|
* It is free software: you can redistribute it and/or modify
|
||||||
|
* it under the terms of the GNU General Public License as published by
|
||||||
|
* the Free Software Foundation, either version 3 of the License, or any later version.
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
|
||||||
|
package com.cloud.api.commands;
|
||||||
|
|
||||||
|
import org.apache.log4j.Logger;
|
||||||
|
|
||||||
|
import com.cloud.api.ApiConstants;
|
||||||
|
import com.cloud.api.BaseCmd;
|
||||||
|
import com.cloud.api.Implementation;
|
||||||
|
import com.cloud.api.Parameter;
|
||||||
|
import com.cloud.api.ServerApiException;
|
||||||
|
import com.cloud.api.response.SuccessResponse;
|
||||||
|
import com.cloud.exception.NetworkRuleConflictException;
|
||||||
|
import com.cloud.utils.net.Ip;
|
||||||
|
|
||||||
|
@Implementation(description="Enables one to one nat for the ip address", responseObject=SuccessResponse.class)
|
||||||
|
public class EnableOneToOneNat extends BaseCmd{
|
||||||
|
public static final Logger s_logger = Logger.getLogger(CreateIpForwardingRuleCmd.class.getName());
|
||||||
|
|
||||||
|
private static final String s_name = "enableonetoonenatresponse";
|
||||||
|
|
||||||
|
/////////////////////////////////////////////////////
|
||||||
|
//////////////// API parameters /////////////////////
|
||||||
|
/////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
@Parameter(name=ApiConstants.IP_ADDRESS, type=CommandType.STRING, required=true, description="the public IP address for which one-to-one nat feature is being enabled")
|
||||||
|
private String ipAddress;
|
||||||
|
|
||||||
|
@Parameter(name=ApiConstants.VIRTUAL_MACHINE_ID, type=CommandType.LONG, required=true, description="the ID of the virtual machine for enabling one-to-one nat feature")
|
||||||
|
private Long virtualMachineId;
|
||||||
|
|
||||||
|
/////////////////////////////////////////////////////
|
||||||
|
/////////////////// Accessors ///////////////////////
|
||||||
|
/////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
public String getIpAddress() {
|
||||||
|
return ipAddress;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Long getVirtualMachineId() {
|
||||||
|
return virtualMachineId;
|
||||||
|
}
|
||||||
|
|
||||||
|
/////////////////////////////////////////////////////
|
||||||
|
/////////////// API Implementation///////////////////
|
||||||
|
/////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getCommandName() {
|
||||||
|
return s_name;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void execute(){
|
||||||
|
try {
|
||||||
|
boolean result = _rulesService.enableOneToOneNat(new Ip(ipAddress), virtualMachineId);
|
||||||
|
if (result) {
|
||||||
|
SuccessResponse response = new SuccessResponse(getCommandName());
|
||||||
|
this.setResponseObject(response);
|
||||||
|
} else {
|
||||||
|
throw new ServerApiException(BaseCmd.INTERNAL_ERROR, "Failed to enable one-to-one nat");
|
||||||
|
}
|
||||||
|
} catch (NetworkRuleConflictException ex) {
|
||||||
|
s_logger.info("Network rule conflict: " + ex.getMessage());
|
||||||
|
s_logger.trace("Network Rule Conflict: ", ex);
|
||||||
|
throw new ServerApiException(BaseCmd.NETWORK_RULE_CONFLICT_ERROR, ex.getMessage());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
@ -183,4 +183,9 @@ public class EventTypes {
|
|||||||
|
|
||||||
//Custom certificates
|
//Custom certificates
|
||||||
public static final String EVENT_UPLOAD_CUSTOM_CERTIFICATE = "UPLOAD.CUSTOM.CERTIFICATE";
|
public static final String EVENT_UPLOAD_CUSTOM_CERTIFICATE = "UPLOAD.CUSTOM.CERTIFICATE";
|
||||||
|
|
||||||
|
//OneToOnenat
|
||||||
|
public static final String EVENT_ENABLE_ONE_TO_ONE_NAT = "ONETOONENAT.ENABLE";
|
||||||
|
public static final String EVENT_DISABLE_ONE_TO_ONE_NAT = "ONETOONENAT.DISABLE";
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@ -66,4 +66,6 @@ public interface IpAddress extends ControlledEntity {
|
|||||||
boolean readyToUse();
|
boolean readyToUse();
|
||||||
|
|
||||||
Long getAssociatedWithNetworkId();
|
Long getAssociatedWithNetworkId();
|
||||||
|
|
||||||
|
Long getVmId();
|
||||||
}
|
}
|
||||||
|
|||||||
@ -32,6 +32,7 @@ import com.cloud.exception.PermissionDeniedException;
|
|||||||
import com.cloud.exception.ResourceAllocationException;
|
import com.cloud.exception.ResourceAllocationException;
|
||||||
import com.cloud.exception.ResourceUnavailableException;
|
import com.cloud.exception.ResourceUnavailableException;
|
||||||
import com.cloud.offering.NetworkOffering;
|
import com.cloud.offering.NetworkOffering;
|
||||||
|
import com.cloud.utils.net.Ip;
|
||||||
|
|
||||||
|
|
||||||
public interface NetworkService {
|
public interface NetworkService {
|
||||||
@ -58,4 +59,6 @@ public interface NetworkService {
|
|||||||
|
|
||||||
Network getNetwork(long networkId);
|
Network getNetwork(long networkId);
|
||||||
|
|
||||||
|
IpAddress getIp(Ip ip);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@ -54,4 +54,9 @@ public interface RulesService {
|
|||||||
public List<? extends PortForwardingRule> listPortForwardingRules(ListPortForwardingRulesCmd cmd);
|
public List<? extends PortForwardingRule> listPortForwardingRules(ListPortForwardingRulesCmd cmd);
|
||||||
|
|
||||||
boolean applyPortForwardingRules(Ip ip, Account caller) throws ResourceUnavailableException;
|
boolean applyPortForwardingRules(Ip ip, Account caller) throws ResourceUnavailableException;
|
||||||
|
|
||||||
|
boolean enableOneToOneNat(Ip ipAddress, long vmId) throws NetworkRuleConflictException;
|
||||||
|
|
||||||
|
boolean disableOneToOneNat(Ip ipAddress);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@ -111,9 +111,11 @@ deletePortForwardingRule=com.cloud.api.commands.DeletePortForwardingRuleCmd;15
|
|||||||
#### updatePortForwardingRule=com.cloud.api.commands.UpdatePortForwardingRuleCmd;15
|
#### updatePortForwardingRule=com.cloud.api.commands.UpdatePortForwardingRuleCmd;15
|
||||||
|
|
||||||
#### NAT commands
|
#### NAT commands
|
||||||
|
enableOneToOneNat=com.cloud.api.commands.EnableOneToOneNat;15
|
||||||
createIpForwardingRule=com.cloud.api.commands.CreateIpForwardingRuleCmd;15
|
createIpForwardingRule=com.cloud.api.commands.CreateIpForwardingRuleCmd;15
|
||||||
deleteIpForwardingRule=com.cloud.api.commands.DeleteIpForwardingRuleCmd;15
|
deleteIpForwardingRule=com.cloud.api.commands.DeleteIpForwardingRuleCmd;15
|
||||||
listIpForwardingRules=com.cloud.api.commands.ListIpForwardingRulesCmd;15
|
listIpForwardingRules=com.cloud.api.commands.ListIpForwardingRulesCmd;15
|
||||||
|
disableOneToOneNat=com.cloud.api.commands.DisableOneToOneNat;15
|
||||||
|
|
||||||
#### load balancer commands
|
#### load balancer commands
|
||||||
createLoadBalancerRule=com.cloud.api.commands.CreateLoadBalancerRuleCmd;15
|
createLoadBalancerRule=com.cloud.api.commands.CreateLoadBalancerRuleCmd;15
|
||||||
|
|||||||
@ -65,6 +65,9 @@ public class IPAddressVO implements IpAddress {
|
|||||||
@Column(name="one_to_one_nat")
|
@Column(name="one_to_one_nat")
|
||||||
private boolean oneToOneNat;
|
private boolean oneToOneNat;
|
||||||
|
|
||||||
|
@Column(name="vm_id")
|
||||||
|
private Long associatedWithVmId;
|
||||||
|
|
||||||
@Column(name="state")
|
@Column(name="state")
|
||||||
private State state;
|
private State state;
|
||||||
|
|
||||||
@ -121,6 +124,15 @@ public class IPAddressVO implements IpAddress {
|
|||||||
public void setAssociatedWithNetworkId(Long networkId) {
|
public void setAssociatedWithNetworkId(Long networkId) {
|
||||||
this.associatedWithNetworkId = networkId;
|
this.associatedWithNetworkId = networkId;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Long getVmId() {
|
||||||
|
return associatedWithVmId;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setAssociatedWithVmId(Long vmId) {
|
||||||
|
this.associatedWithVmId = vmId;
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Long getAllocatedInDomainId() {
|
public Long getAllocatedInDomainId() {
|
||||||
@ -193,5 +205,6 @@ public class IPAddressVO implements IpAddress {
|
|||||||
@Override
|
@Override
|
||||||
public String toString() {
|
public String toString() {
|
||||||
return new StringBuilder("Ip[").append(address).append("-").append(dataCenterId).append("]").toString();
|
return new StringBuilder("Ip[").append(address).append("-").append(dataCenterId).append("]").toString();
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@ -1979,4 +1979,9 @@ public class NetworkManagerImpl implements NetworkManager, NetworkService, Manag
|
|||||||
assert vos.size() <= 1 : "If we have multiple networks of the same type, then this method should no longer be used.";
|
assert vos.size() <= 1 : "If we have multiple networks of the same type, then this method should no longer be used.";
|
||||||
return vos.size() == 1 ? vos.get(0) : null;
|
return vos.size() == 1 ? vos.get(0) : null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public IpAddress getIp(Ip ip) {
|
||||||
|
return _ipAddressDao.findById(ip);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -79,6 +79,11 @@ public class PublicIp implements PublicIpAddress {
|
|||||||
return _addr.isOneToOneNat();
|
return _addr.isOneToOneNat();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Long getVmId() {
|
||||||
|
return _addr.getVmId();
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Date getAllocatedTime() {
|
public Date getAllocatedTime() {
|
||||||
return _addr.getAllocatedTime();
|
return _addr.getAllocatedTime();
|
||||||
|
|||||||
@ -29,7 +29,7 @@ import com.cloud.utils.net.Ip;
|
|||||||
* Data Access Object for user_ip_address and ip_forwarding tables
|
* Data Access Object for user_ip_address and ip_forwarding tables
|
||||||
*/
|
*/
|
||||||
public interface FirewallRulesDao extends GenericDao<FirewallRuleVO, Long> {
|
public interface FirewallRulesDao extends GenericDao<FirewallRuleVO, Long> {
|
||||||
List<FirewallRuleVO> listByIpAndNotRevoked(Ip ip);
|
List<FirewallRuleVO> listByIpAndNotRevoked(Ip ip, Boolean isOneToOneNat);
|
||||||
|
|
||||||
boolean setStateToAdd(FirewallRuleVO rule);
|
boolean setStateToAdd(FirewallRuleVO rule);
|
||||||
|
|
||||||
|
|||||||
@ -59,6 +59,7 @@ public class FirewallRulesDaoImpl extends GenericDaoBase<FirewallRuleVO, Long> i
|
|||||||
IpNotRevokedSearch = createSearchBuilder();
|
IpNotRevokedSearch = createSearchBuilder();
|
||||||
IpNotRevokedSearch.and("ip", IpNotRevokedSearch.entity().getSourceIpAddress(), Op.EQ);
|
IpNotRevokedSearch.and("ip", IpNotRevokedSearch.entity().getSourceIpAddress(), Op.EQ);
|
||||||
IpNotRevokedSearch.and("state", IpNotRevokedSearch.entity().getState(), Op.NEQ);
|
IpNotRevokedSearch.and("state", IpNotRevokedSearch.entity().getState(), Op.NEQ);
|
||||||
|
IpNotRevokedSearch.and("oneToOneNat", IpNotRevokedSearch.entity().isOneToOneNat(), Op.EQ);
|
||||||
IpNotRevokedSearch.done();
|
IpNotRevokedSearch.done();
|
||||||
|
|
||||||
ReleaseSearch = createSearchBuilder();
|
ReleaseSearch = createSearchBuilder();
|
||||||
@ -91,10 +92,13 @@ public class FirewallRulesDaoImpl extends GenericDaoBase<FirewallRuleVO, Long> i
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public List<FirewallRuleVO> listByIpAndNotRevoked(Ip ip) {
|
public List<FirewallRuleVO> listByIpAndNotRevoked(Ip ip, Boolean isOneToOneNat) {
|
||||||
SearchCriteria<FirewallRuleVO> sc = IpNotRevokedSearch.create();
|
SearchCriteria<FirewallRuleVO> sc = IpNotRevokedSearch.create();
|
||||||
sc.setParameters("ip", ip);
|
sc.setParameters("ip", ip);
|
||||||
sc.setParameters("state", State.Revoke);
|
sc.setParameters("state", State.Revoke);
|
||||||
|
if (isOneToOneNat != null) {
|
||||||
|
sc.setParameters("oneToOneNat", isOneToOneNat);
|
||||||
|
}
|
||||||
|
|
||||||
return listBy(sc);
|
return listBy(sc);
|
||||||
}
|
}
|
||||||
|
|||||||
@ -152,6 +152,7 @@ public class IPAddressDaoImpl extends GenericDaoBase<IPAddressVO, Ip> implements
|
|||||||
address.setAllocatedTime(null);
|
address.setAllocatedTime(null);
|
||||||
address.setSourceNat(false);
|
address.setSourceNat(false);
|
||||||
address.setOneToOneNat(false);
|
address.setOneToOneNat(false);
|
||||||
|
address.setAssociatedWithVmId(null);
|
||||||
address.setState(State.Free);
|
address.setState(State.Free);
|
||||||
address.setAssociatedWithNetworkId(null);
|
address.setAssociatedWithNetworkId(null);
|
||||||
update(ipAddress, address);
|
update(ipAddress, address);
|
||||||
|
|||||||
@ -36,7 +36,6 @@ import com.cloud.api.commands.UpdateLoadBalancerRuleCmd;
|
|||||||
import com.cloud.dc.dao.VlanDao;
|
import com.cloud.dc.dao.VlanDao;
|
||||||
import com.cloud.domain.dao.DomainDao;
|
import com.cloud.domain.dao.DomainDao;
|
||||||
import com.cloud.event.EventTypes;
|
import com.cloud.event.EventTypes;
|
||||||
import com.cloud.event.EventVO;
|
|
||||||
import com.cloud.event.UsageEventVO;
|
import com.cloud.event.UsageEventVO;
|
||||||
import com.cloud.event.dao.EventDao;
|
import com.cloud.event.dao.EventDao;
|
||||||
import com.cloud.event.dao.UsageEventDao;
|
import com.cloud.event.dao.UsageEventDao;
|
||||||
@ -399,7 +398,7 @@ public class LoadBalancingRulesManagerImpl implements LoadBalancingRulesManager,
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean removeAllLoadBalanacers(Ip ip) {
|
public boolean removeAllLoadBalanacers(Ip ip) {
|
||||||
List<FirewallRuleVO> rules = _rulesDao.listByIpAndNotRevoked(ip);
|
List<FirewallRuleVO> rules = _rulesDao.listByIpAndNotRevoked(ip, null);
|
||||||
if (rules != null)
|
if (rules != null)
|
||||||
s_logger.debug("Found " + rules.size() + " lb rules to cleanup");
|
s_logger.debug("Found " + rules.size() + " lb rules to cleanup");
|
||||||
for (FirewallRule rule : rules) {
|
for (FirewallRule rule : rules) {
|
||||||
|
|||||||
@ -83,7 +83,7 @@ public class RulesManagerImpl implements RulesManager, RulesService, Manager {
|
|||||||
public void detectRulesConflict(FirewallRule newRule, IpAddress ipAddress) throws NetworkRuleConflictException {
|
public void detectRulesConflict(FirewallRule newRule, IpAddress ipAddress) throws NetworkRuleConflictException {
|
||||||
assert newRule.getSourceIpAddress().equals(ipAddress.getAddress()) : "You passed in an ip address that doesn't match the address in the new rule";
|
assert newRule.getSourceIpAddress().equals(ipAddress.getAddress()) : "You passed in an ip address that doesn't match the address in the new rule";
|
||||||
|
|
||||||
List<FirewallRuleVO> rules = _firewallDao.listByIpAndNotRevoked(newRule.getSourceIpAddress());
|
List<FirewallRuleVO> rules = _firewallDao.listByIpAndNotRevoked(newRule.getSourceIpAddress(), null);
|
||||||
assert (rules.size() >= 1) : "For network rules, we now always first persist the rule and then check for network conflicts so we should at least have one rule at this point.";
|
assert (rules.size() >= 1) : "For network rules, we now always first persist the rule and then check for network conflicts so we should at least have one rule at this point.";
|
||||||
|
|
||||||
for (FirewallRuleVO rule : rules) {
|
for (FirewallRuleVO rule : rules) {
|
||||||
@ -92,9 +92,9 @@ public class RulesManagerImpl implements RulesManager, RulesService, Manager {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (rule.isOneToOneNat() && !newRule.isOneToOneNat()) {
|
if (rule.isOneToOneNat() && !newRule.isOneToOneNat()) {
|
||||||
throw new NetworkRuleConflictException("There is already port forwarding rule specified for the " + newRule.getSourceIpAddress());
|
throw new NetworkRuleConflictException("There is 1 to 1 Nat rule specified for the " + newRule.getSourceIpAddress());
|
||||||
} else if (!rule.isOneToOneNat() && newRule.isOneToOneNat()) {
|
} else if (!rule.isOneToOneNat() && newRule.isOneToOneNat()) {
|
||||||
throw new NetworkRuleConflictException("There is already 1 to 1 Nat rule specified for the " + newRule.getSourceIpAddress());
|
throw new NetworkRuleConflictException("There is already firewall rule specified for the " + newRule.getSourceIpAddress());
|
||||||
}
|
}
|
||||||
|
|
||||||
if (rule.getNetworkId() != newRule.getNetworkId() && rule.getState() != State.Revoke) {
|
if (rule.getNetworkId() != newRule.getNetworkId() && rule.getState() != State.Revoke) {
|
||||||
@ -133,6 +133,7 @@ public class RulesManagerImpl implements RulesManager, RulesService, Manager {
|
|||||||
throw new InvalidParameterValueException("Invalid user vm: " + userVm.getId());
|
throw new InvalidParameterValueException("Invalid user vm: " + userVm.getId());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
_accountMgr.checkAccess(caller, ipAddress);
|
||||||
_accountMgr.checkAccess(caller, userVm);
|
_accountMgr.checkAccess(caller, userVm);
|
||||||
|
|
||||||
// validate that IP address and userVM belong to the same account
|
// validate that IP address and userVM belong to the same account
|
||||||
@ -193,13 +194,10 @@ public class RulesManagerImpl implements RulesManager, RulesService, Manager {
|
|||||||
long accountId = network.getAccountId();
|
long accountId = network.getAccountId();
|
||||||
long domainId = network.getDomainId();
|
long domainId = network.getDomainId();
|
||||||
|
|
||||||
checkIpAndUserVm(ipAddress, vm, caller);
|
if (isNat && (ipAddress.isSourceNat() || !ipAddress.isOneToOneNat() || ipAddress.getVmId() == null)) {
|
||||||
if (isNat && (ipAddress.isSourceNat())) {
|
|
||||||
throw new NetworkRuleConflictException("Can't do one to one NAT on ip address: " + ipAddress.getAddress());
|
throw new NetworkRuleConflictException("Can't do one to one NAT on ip address: " + ipAddress.getAddress());
|
||||||
}
|
}
|
||||||
|
|
||||||
Transaction txn = Transaction.currentTxn();
|
|
||||||
txn.start();
|
|
||||||
PortForwardingRuleVO newRule =
|
PortForwardingRuleVO newRule =
|
||||||
new PortForwardingRuleVO(rule.getXid(),
|
new PortForwardingRuleVO(rule.getXid(),
|
||||||
rule.getSourceIpAddress(),
|
rule.getSourceIpAddress(),
|
||||||
@ -213,12 +211,6 @@ public class RulesManagerImpl implements RulesManager, RulesService, Manager {
|
|||||||
accountId,
|
accountId,
|
||||||
domainId, vmId, isNat);
|
domainId, vmId, isNat);
|
||||||
newRule = _forwardingDao.persist(newRule);
|
newRule = _forwardingDao.persist(newRule);
|
||||||
|
|
||||||
if (isNat && !ipAddress.isOneToOneNat()) {
|
|
||||||
ipAddress.setOneToOneNat(true);
|
|
||||||
_ipAddressDao.update(ipAddress.getAddress(), ipAddress);
|
|
||||||
}
|
|
||||||
txn.commit();
|
|
||||||
|
|
||||||
try {
|
try {
|
||||||
detectRulesConflict(newRule, ipAddress);
|
detectRulesConflict(newRule, ipAddress);
|
||||||
@ -230,21 +222,48 @@ public class RulesManagerImpl implements RulesManager, RulesService, Manager {
|
|||||||
_usageEventDao.persist(usageEvent);
|
_usageEventDao.persist(usageEvent);
|
||||||
return newRule;
|
return newRule;
|
||||||
} catch (Exception e) {
|
} catch (Exception e) {
|
||||||
txn.start();
|
|
||||||
_forwardingDao.remove(newRule.getId());
|
_forwardingDao.remove(newRule.getId());
|
||||||
if (isNat) {
|
|
||||||
ipAddress.setOneToOneNat(false);
|
|
||||||
_ipAddressDao.update(ipAddress.getAddress(), ipAddress);
|
|
||||||
}
|
|
||||||
txn.commit();
|
|
||||||
if (e instanceof NetworkRuleConflictException) {
|
if (e instanceof NetworkRuleConflictException) {
|
||||||
throw (NetworkRuleConflictException)e;
|
throw (NetworkRuleConflictException)e;
|
||||||
}
|
}
|
||||||
|
|
||||||
throw new CloudRuntimeException("Unable to add rule for " + newRule.getSourceIpAddress(), e);
|
throw new CloudRuntimeException("Unable to add rule for " + newRule.getSourceIpAddress(), e);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean enableOneToOneNat(Ip ip, long vmId) throws NetworkRuleConflictException{
|
||||||
|
IPAddressVO ipAddress = _ipAddressDao.findById(ip);
|
||||||
|
Account caller = UserContext.current().getCaller();
|
||||||
|
|
||||||
|
UserVmVO vm = null;
|
||||||
|
vm = _vmDao.findById(vmId);
|
||||||
|
if (vm == null) {
|
||||||
|
throw new InvalidParameterValueException("Can't enable one-to-one nat for the address " + ipAddress + ", invalid virtual machine id specified (" + vmId + ").");
|
||||||
|
}
|
||||||
|
|
||||||
|
checkIpAndUserVm(ipAddress, vm, caller);
|
||||||
|
|
||||||
|
if (ipAddress.isSourceNat()) {
|
||||||
|
throw new InvalidParameterValueException("Can't enable one to one nat, ip address: " + ip.addr() + " is a sourceNat ip address");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!ipAddress.isOneToOneNat()) {
|
||||||
|
List<FirewallRuleVO> rules = _firewallDao.listByIpAndNotRevoked(ip, false);
|
||||||
|
if (rules != null && !rules.isEmpty()) {
|
||||||
|
throw new NetworkRuleConflictException("Failed to enable one to one nat for the ip address " + ipAddress.getAddress() + " as it already has firewall rules assigned");
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
if (ipAddress.getVmId() != null && ipAddress.getVmId().longValue() != vmId) {
|
||||||
|
throw new NetworkRuleConflictException("Failed to enable one to one nat for the ip address " + ipAddress.getAddress() + " and vm id=" + vmId + " as it's already assigned to antoher vm");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
ipAddress.setOneToOneNat(true);
|
||||||
|
ipAddress.setAssociatedWithVmId(vmId);
|
||||||
|
return _ipAddressDao.update(ipAddress.getAddress(), ipAddress);
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
protected Pair<Network, Ip> getUserVmGuestIpAddress(UserVm vm) {
|
protected Pair<Network, Ip> getUserVmGuestIpAddress(UserVm vm) {
|
||||||
Ip dstIp = null;
|
Ip dstIp = null;
|
||||||
List<? extends Nic> nics = _networkMgr.getNics(vm);
|
List<? extends Nic> nics = _networkMgr.getNics(vm);
|
||||||
@ -276,14 +295,6 @@ public class RulesManagerImpl implements RulesManager, RulesService, Manager {
|
|||||||
rule.setState(State.Revoke);
|
rule.setState(State.Revoke);
|
||||||
_firewallDao.update(rule.getId(), rule);
|
_firewallDao.update(rule.getId(), rule);
|
||||||
}
|
}
|
||||||
if (rule.isOneToOneNat()) {
|
|
||||||
if (s_logger.isDebugEnabled()) {
|
|
||||||
s_logger.debug("Removing one to one nat so setting the ip back to one to one nat is false: " + rule.getSourceIpAddress());
|
|
||||||
}
|
|
||||||
IPAddressVO ipAddress = _ipAddressDao.findById(rule.getSourceIpAddress());
|
|
||||||
ipAddress.setOneToOneNat(false);
|
|
||||||
_ipAddressDao.update(ipAddress.getAddress(), ipAddress);
|
|
||||||
}
|
|
||||||
|
|
||||||
// Save and create the event
|
// Save and create the event
|
||||||
String ruleName = rule.getPurpose() == Purpose.Firewall ? "Firewall" : (rule.isOneToOneNat() ? "ip forwarding" : "port forwarding");
|
String ruleName = rule.getPurpose() == Purpose.Firewall ? "Firewall" : (rule.isOneToOneNat() ? "ip forwarding" : "port forwarding");
|
||||||
@ -339,7 +350,7 @@ public class RulesManagerImpl implements RulesManager, RulesService, Manager {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public List<? extends FirewallRule> listFirewallRules(Ip ip) {
|
public List<? extends FirewallRule> listFirewallRules(Ip ip) {
|
||||||
return _firewallDao.listByIpAndNotRevoked(ip);
|
return _firewallDao.listByIpAndNotRevoked(ip, null);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -557,5 +568,53 @@ public class RulesManagerImpl implements RulesManager, RulesService, Manager {
|
|||||||
public List<? extends PortForwardingRule> listByNetworkId(long networkId) {
|
public List<? extends PortForwardingRule> listByNetworkId(long networkId) {
|
||||||
return _forwardingDao.listByNetworkId(networkId);
|
return _forwardingDao.listByNetworkId(networkId);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public boolean isLastOneToOneNatRule(FirewallRule ruleToCheck) {
|
||||||
|
List<FirewallRuleVO> rules = _firewallDao.listByIpAndNotRevoked(ruleToCheck.getSourceIpAddress(), false);
|
||||||
|
if (rules != null && !rules.isEmpty()) {
|
||||||
|
for (FirewallRuleVO rule : rules) {
|
||||||
|
if (ruleToCheck.getId() == rule.getId()) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
if (rule.isOneToOneNat()) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean disableOneToOneNat(Ip ip){
|
||||||
|
Account caller = UserContext.current().getCaller();
|
||||||
|
|
||||||
|
IPAddressVO ipAddress = _ipAddressDao.findById(ip);
|
||||||
|
checkIpAndUserVm(ipAddress, null, caller);
|
||||||
|
|
||||||
|
if (!ipAddress.isOneToOneNat()) {
|
||||||
|
throw new InvalidParameterValueException("One to one nat is not enabled for the ip: " + ip.addr());
|
||||||
|
}
|
||||||
|
|
||||||
|
List<FirewallRuleVO> rules = _firewallDao.listByIpAndNotRevoked(ip, true);
|
||||||
|
if (rules != null) {
|
||||||
|
for (FirewallRuleVO rule : rules) {
|
||||||
|
rule.setState(State.Revoke);
|
||||||
|
_firewallDao.update(rule.getId(), rule);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (applyPortForwardingRules(ip, true)) {
|
||||||
|
ipAddress.setOneToOneNat(false);
|
||||||
|
ipAddress.setAssociatedWithVmId(null);
|
||||||
|
_ipAddressDao.update(ipAddress.getAddress(), ipAddress);
|
||||||
|
return true;
|
||||||
|
} else {
|
||||||
|
s_logger.warn("Failed to disable one to one nat for the ip address " + ip.addr());
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@ -682,6 +682,7 @@ CREATE TABLE `cloud`.`user_ip_address` (
|
|||||||
`allocated` datetime NULL COMMENT 'Date this ip was allocated to someone',
|
`allocated` datetime NULL COMMENT 'Date this ip was allocated to someone',
|
||||||
`vlan_db_id` bigint unsigned NOT NULL,
|
`vlan_db_id` bigint unsigned NOT NULL,
|
||||||
`one_to_one_nat` int(1) unsigned NOT NULL default '0',
|
`one_to_one_nat` int(1) unsigned NOT NULL default '0',
|
||||||
|
`vm_id` bigint unsigned COMMENT 'vm id the one_to_one nat ip is assigned to',
|
||||||
`state` char(32) NOT NULL default 'Free' COMMENT 'state of the ip address',
|
`state` char(32) NOT NULL default 'Free' COMMENT 'state of the ip address',
|
||||||
`mac_address` bigint unsigned NOT NULL COMMENT 'mac address of this ip',
|
`mac_address` bigint unsigned NOT NULL COMMENT 'mac address of this ip',
|
||||||
`network_id` bigint unsigned COMMENT 'network this public ip address is associated with',
|
`network_id` bigint unsigned COMMENT 'network this public ip address is associated with',
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user