();
for(HostNodeConnector hnc : hostNodeConnectors) {
hosts.add(HostConfig.convert(hnc));
}
return new Hosts(hosts);
}
/**
* Returns a list of all Hosts : both configured via PUT API and dynamically
* learnt on the network.
*
* @param containerName
* Name of the Container. The Container name for the base
* controller is "default".
* @return List of Active Hosts.
*
*
* Example:
*
* RequestURL:
*
* http://localhost:8080/controller/nb/v2/host/default
*
* Response in XML
*
* <list>
* <hostConfig>
* <dataLayerAddress>00:00:00:00:01:01</dataLayerAddress>
* <networkAddress>1.1.1.1</networkAddress>
* <nodeType>OF</nodeType>
* <nodeId>00:00:00:00:00:00:00:01</nodeId>
* <nodeConnectorType>OF</nodeConnectorType>
* <nodeConnectorId>9</nodeConnectorId>
* <vlan>0</vlan>
* <staticHost>false</staticHost>
* </hostConfig>
* <hostConfig>
* <dataLayerAddress>00:00:00:00:02:02</dataLayerAddress>
* <networkAddress>2.2.2.2</networkAddress>
* <nodeType>OF</nodeType>
* <nodeId>00:00:00:00:00:00:00:02</nodeId>
* <nodeConnectorType>OF</nodeConnectorType>
* <nodeConnectorId>5</nodeConnectorId>
* <vlan>0</vlan>
* <staticHost>false</staticHost>
* </hostConfig>
* </list>
*
* Response in JSON:
*
* {
* "hostConfig":[
* {
* "dataLayerAddress":"00:00:00:00:01:01",
* "nodeType":"OF",
* "nodeId":"00:00:00:00:00:00:00:01",
* "nodeConnectorType":"OF",
* "nodeConnectorId":"9",
* "vlan":"0",
* "staticHost":"false",
* "networkAddress":"1.1.1.1"
* },
* {
* "dataLayerAddress":"00:00:00:00:02:02",
* "nodeType":"OF",
* "nodeId":"00:00:00:00:00:00:00:02",
* "nodeConnectorType":"OF",
* "nodeConnectorId":"5",
* "vlan":"0",
* "staticHost":"false",
* "networkAddress":"2.2.2.2"
* }
* ]
* }
*
*/
@Path("/{containerName}")
@GET
@Produces({ MediaType.APPLICATION_JSON, MediaType.APPLICATION_XML })
@TypeHint(Hosts.class)
@StatusCodes({
@ResponseCode(code = 200, condition = "Operation successful"),
@ResponseCode(code = 404, condition = "The containerName is not found"),
@ResponseCode(code = 503, condition = "One or more of Controller Services are unavailable") })
public Hosts getActiveHosts(@PathParam("containerName") String containerName) {
if (!NorthboundUtils.isAuthorized(
getUserName(), containerName, Privilege.READ, this)) {
throw new UnauthorizedException(
"User is not authorized to perform this operation on container "
+ containerName);
}
IfIptoHost hostTracker = getIfIpToHostService(containerName);
if (hostTracker == null) {
throw new ServiceUnavailableException("Host Tracker "
+ RestMessages.SERVICEUNAVAILABLE.toString());
}
return convertHosts(hostTracker.getAllHosts());
}
/**
* Returns a list of Hosts that are statically configured and are connected
* to a NodeConnector that is down.
*
* @param containerName
* Name of the Container. The Container name for the base
* controller is "default".
* @return List of inactive Hosts.
*
*
* Example:
*
* RequestURL:
*
* http://localhost:8080/controller/nb/v2/host/default/inactive
*
* Response in XML
*
* <list>
* <hostConfig>
* <dataLayerAddress>00:00:00:00:01:01</dataLayerAddress>
* <networkAddress>1.1.1.1</networkAddress>
* <nodeType>OF</nodeType>
* <nodeId>00:00:00:00:00:00:00:01</nodeId>
* <nodeConnectorType>OF</nodeConnectorType>
* <nodeConnectorId>9</nodeConnectorId>
* <vlan>0</vlan>
* <staticHost>false</staticHost>
* </hostConfig>
* <hostConfig>
* <dataLayerAddress>00:00:00:00:02:02</dataLayerAddress>
* <networkAddress>2.2.2.2</networkAddress>
* <nodeType>OF</nodeType>
* <nodeId>00:00:00:00:00:00:00:02</nodeId>
* <nodeConnectorType>OF</nodeConnectorType>
* <nodeConnectorId>5</nodeConnectorId>
* <vlan>0</vlan>
* <staticHost>false</staticHost>
* </hostConfig>
* </list>
*
* Response in JSON:
*
* {
* "hostConfig":[
* {
* "dataLayerAddress":"00:00:00:00:01:01",
* "nodeType":"OF",
* "nodeId":"00:00:00:00:00:00:00:01",
* "nodeConnectorType":"OF",
* "nodeConnectorId":"9",
* "vlan":"0",
* "staticHost":"false",
* "networkAddress":"1.1.1.1"
* },
* {
* "dataLayerAddress":"00:00:00:00:02:02",
* "nodeType":"OF",
* "nodeId":"00:00:00:00:00:00:00:02",
* "nodeConnectorType":"OF",
* "nodeConnectorId":"5",
* "vlan":"0",
* "staticHost":"false",
* "networkAddress":"2.2.2.2"
* }
* ]
* }
*
*/
@Path("/{containerName}/inactive")
@GET
@Produces({ MediaType.APPLICATION_JSON, MediaType.APPLICATION_XML })
@TypeHint(Hosts.class)
@StatusCodes({
@ResponseCode(code = 200, condition = "Operation successful"),
@ResponseCode(code = 404, condition = "The containerName is not found"),
@ResponseCode(code = 503, condition = "One or more of Controller Services are unavailable") })
public Hosts getInactiveHosts(
@PathParam("containerName") String containerName) {
if (!NorthboundUtils.isAuthorized(
getUserName(), containerName, Privilege.READ, this)) {
throw new UnauthorizedException(
"User is not authorized to perform this operation on container "
+ containerName);
}
IfIptoHost hostTracker = getIfIpToHostService(containerName);
if (hostTracker == null) {
throw new ServiceUnavailableException("Host Tracker "
+ RestMessages.SERVICEUNAVAILABLE.toString());
}
return convertHosts(hostTracker.getInactiveStaticHosts());
}
/**
* Returns a host that matches the IP Address value passed as parameter.
*
* @param containerName
* Name of the Container. The Container name for the base
* controller is "default".
* @param networkAddress
* IP Address being looked up
* @return host that matches the IP Address
*
*
* Example:
*
* RequestURL:
*
* http://localhost:8080/controller/nb/v2/host/default/1.1.1.1
*
* Response in XML
*
* <hostConfig>
* <dataLayerAddress>00:00:00:00:01:01</dataLayerAddress>
* <networkAddress>1.1.1.1</networkAddress>
* <nodeType>OF</nodeType>
* <nodeId>00:00:00:00:00:00:00:01</nodeId>
* <nodeConnectorType>OF</nodeConnectorType>
* <nodeConnectorId>9</nodeConnectorId>
* <vlan>0</vlan>
* <staticHost>false</staticHost>
* </hostConfig>
*
* Response in JSON:
*
* {
* "dataLayerAddress":"00:00:00:00:01:01",
* "nodeType":"OF",
* "nodeId":"00:00:00:00:00:00:00:01",
* "nodeConnectorType":"OF",
* "nodeConnectorId":"9",
* "vlan":"0",
* "staticHost":"false",
* "networkAddress":"1.1.1.1"
* }
*
*/
@Path("/{containerName}/{networkAddress}")
@GET
@Produces({ MediaType.APPLICATION_JSON, MediaType.APPLICATION_XML })
@TypeHint(HostConfig.class)
@StatusCodes({
@ResponseCode(code = 200, condition = "Operation successful"),
@ResponseCode(code = 404, condition = "The containerName is not found"),
@ResponseCode(code = 415, condition = "Invalid IP Address passed in networkAddress parameter"),
@ResponseCode(code = 503, condition = "One or more of Controller Services are unavailable") })
public HostConfig getHostDetails(
@PathParam("containerName") String containerName,
@PathParam("networkAddress") String networkAddress) {
if (!NorthboundUtils.isAuthorized(
getUserName(), containerName, Privilege.READ, this)) {
throw new UnauthorizedException(
"User is not authorized to perform this operation on container "
+ containerName);
}
IfIptoHost hostTracker = getIfIpToHostService(containerName);
if (hostTracker == null) {
throw new ServiceUnavailableException("Host Tracker "
+ RestMessages.SERVICEUNAVAILABLE.toString());
}
InetAddress ip;
try {
ip = InetAddress.getByName(networkAddress);
} catch (UnknownHostException e) {
throw new UnsupportedMediaTypeException(networkAddress + " "
+ RestMessages.INVALIDADDRESS.toString());
}
for (HostNodeConnector host : hostTracker.getAllHosts()) {
if (host.getNetworkAddress().equals(ip)) {
return HostConfig.convert(host);
}
}
throw new ResourceNotFoundException(RestMessages.NOHOST.toString());
}
/**
* Add a Static Host configuration
*
* @param containerName
* Name of the Container. The Container name for the base
* controller is "default".
* @param networkAddress
* Host IP Address
* @param hostConfig
* Host Config Details
* @return Response as dictated by the HTTP Response Status code
*
*
*
* Example:
*
* RequestURL:
*
* http://localhost:8080/controller/nb/v2/host/default/1.1.1.1
*
* Request in XML
*
* <hostConfig>
* <dataLayerAddress>00:00:00:00:01:01</dataLayerAddress>
* <networkAddress>1.1.1.1</networkAddress>
* <nodeType>OF</nodeType>
* <nodeId>00:00:00:00:00:00:00:01</nodeId>
* <nodeConnectorType>OF</nodeConnectorType>
* <nodeConnectorId>9</nodeConnectorId>
* <vlan>0</vlan>
* <staticHost>false</staticHost>
* </hostConfig>
*
* Request in JSON:
*
* {
* "dataLayerAddress":"00:00:00:00:01:01",
* "nodeType":"OF",
* "nodeId":"00:00:00:00:00:00:00:01",
* "nodeConnectorType":"OF",
* "nodeConnectorId":"9",
* "vlan":"0",
* "staticHost":"false",
* "networkAddress":"1.1.1.1"
* }
*
*/
@Path("/{containerName}/{networkAddress}")
@PUT
@Consumes({ MediaType.APPLICATION_JSON, MediaType.APPLICATION_XML })
@StatusCodes({
@ResponseCode(code = 201, condition = "Static host created successfully"),
@ResponseCode(code = 404, condition = "The Container Name or nodeId or configuration name is not found"),
@ResponseCode(code = 406, condition = "Cannot operate on Default Container when other Containers are active"),
@ResponseCode(code = 415, condition = "Invalid IP Address passed in networkAddress parameter"),
@ResponseCode(code = 500, condition = "Failed to create Static Host entry. Failure Reason included in HTTP Error response"),
@ResponseCode(code = 503, condition = "One or more of Controller services are unavailable") })
public Response addHost(@PathParam("containerName") String containerName,
@PathParam("networkAddress") String networkAddress,
@TypeHint(HostConfig.class) JAXBElement hostConfig) {
if (!NorthboundUtils.isAuthorized(
getUserName(), containerName, Privilege.WRITE, this)) {
throw new UnauthorizedException(
"User is not authorized to perform this operation on container "
+ containerName);
}
handleDefaultDisabled(containerName);
IfIptoHost hostTracker = getIfIpToHostService(containerName);
if (hostTracker == null) {
throw new ServiceUnavailableException("Host Tracker "
+ RestMessages.SERVICEUNAVAILABLE.toString());
}
HostConfig hc = hostConfig.getValue();
Node node = handleNodeAvailability(containerName, hc.getNodeType(), hc.getNodeId());
if (node == null) {
throw new InternalServerErrorException(
RestMessages.NONODE.toString());
}
try {
InetAddress.getByName(networkAddress);
} catch (UnknownHostException e) {
throw new UnsupportedMediaTypeException(networkAddress + " "
+ RestMessages.INVALIDADDRESS.toString());
}
if(!networkAddress.equals(hc.getNetworkAddress())) {
throw new UnsupportedMediaTypeException(networkAddress + " is not the same as "
+ hc.getNetworkAddress());
}
if(!hc.isStaticHost()) {
throw new UnsupportedMediaTypeException("StaticHost flag must be true");
}
NodeConnector nc = NodeConnector.fromStringNoNode(hc.getNodeConnectorType(), hc.getNodeConnectorId(), node);
if (nc == null) {
throw new ResourceNotFoundException(hc.getNodeConnectorType() + "|"
+ hc.getNodeConnectorId() + " : " + RestMessages.NONODE.toString());
}
Status status = hostTracker.addStaticHost(networkAddress,
hc.getDataLayerAddress(), nc, hc.getVlan());
if (status.isSuccess()) {
NorthboundUtils.auditlog("Static Host", username, "added", networkAddress, containerName);
return Response.status(Response.Status.CREATED).build();
} else if (status.getCode().equals(StatusCode.BADREQUEST)) {
throw new UnsupportedMediaTypeException(status.getDescription());
}
throw new InternalServerErrorException(status.getDescription());
}
/**
* Delete a Static Host configuration
*
* @param containerName
* Name of the Container. The Container name for the base
* controller is "default".
* @param networkAddress
* IP Address
* @return Response as dictated by the HTTP Response code.
*/
@Path("/{containerName}/{networkAddress}")
@DELETE
@Consumes({ MediaType.APPLICATION_JSON, MediaType.APPLICATION_XML })
@StatusCodes({
@ResponseCode(code = 200, condition = "Flow Config deleted successfully"),
@ResponseCode(code = 404, condition = "The Container Name or Node-id or Flow Name passed is not found"),
@ResponseCode(code = 406, condition = "Cannot operate on Default Container when other Containers are active"),
@ResponseCode(code = 415, condition = "Invalid IP Address passed in networkAddress parameter"),
@ResponseCode(code = 500, condition = "Failed to delete Flow config. Failure Reason included in HTTP Error response"),
@ResponseCode(code = 503, condition = "One or more of Controller service is unavailable") })
public Response deleteFlow(
@PathParam(value = "containerName") String containerName,
@PathParam(value = "networkAddress") String networkAddress) {
if (!NorthboundUtils.isAuthorized(
getUserName(), containerName, Privilege.WRITE, this)) {
throw new UnauthorizedException(
"User is not authorized to perform this operation on container "
+ containerName);
}
handleDefaultDisabled(containerName);
IfIptoHost hostTracker = getIfIpToHostService(containerName);
if (hostTracker == null) {
throw new ServiceUnavailableException("Host Tracker "
+ RestMessages.SERVICEUNAVAILABLE.toString());
}
try {
InetAddress.getByName(networkAddress);
} catch (UnknownHostException e) {
throw new UnsupportedMediaTypeException(networkAddress + " "
+ RestMessages.INVALIDADDRESS.toString());
}
Status status = hostTracker.removeStaticHost(networkAddress);
if (status.isSuccess()) {
NorthboundUtils.auditlog("Static Host", username, "removed", networkAddress, containerName);
return Response.ok().build();
}
throw new InternalServerErrorException(status.getDescription());
}
private void handleDefaultDisabled(String containerName) {
IContainerManager containerManager = (IContainerManager) ServiceHelper
.getGlobalInstance(IContainerManager.class, this);
if (containerManager == null) {
throw new InternalServerErrorException(
RestMessages.INTERNALERROR.toString());
}
if (containerName.equals(GlobalConstants.DEFAULT.toString())
&& containerManager.hasNonDefaultContainer()) {
throw new ResourceConflictException(
RestMessages.DEFAULTDISABLED.toString());
}
}
private Node handleNodeAvailability(String containerName, String nodeType,
String nodeId) {
Node node = Node.fromString(nodeType, nodeId);
if (node == null) {
throw new ResourceNotFoundException(nodeId + " : "
+ RestMessages.NONODE.toString());
}
ISwitchManager sm = (ISwitchManager) ServiceHelper.getInstance(
ISwitchManager.class, containerName, this);
if (sm == null) {
throw new ServiceUnavailableException("Switch Manager "
+ RestMessages.SERVICEUNAVAILABLE.toString());
}
if (!sm.getNodes().contains(node)) {
throw new ResourceNotFoundException(node.toString() + " : "
+ RestMessages.NONODE.toString());
}
return node;
}
}