blob: 66f25308811dbd84ad9a9670022506019b5433ea [file] [log] [blame]
/*
* Copyright 2015 Open Networking Laboratory
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.onosproject.protocol.rest.ctl;
import com.sun.jersey.api.client.Client;
import com.sun.jersey.api.client.ClientResponse;
import com.sun.jersey.api.client.WebResource;
import org.apache.commons.io.IOUtils;
import org.apache.felix.scr.annotations.Activate;
import org.apache.felix.scr.annotations.Component;
import org.apache.felix.scr.annotations.Deactivate;
import org.apache.felix.scr.annotations.Service;
import org.onlab.packet.IpAddress;
import org.onosproject.net.DeviceId;
import org.onosproject.protocol.rest.RestSBController;
import org.onosproject.protocol.rest.RestSBDevice;
import org.osgi.service.component.ComponentContext;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import javax.ws.rs.core.MediaType;
import javax.ws.rs.core.Response;
import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.nio.charset.StandardCharsets;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
/**
* The implementation of RestSBController.
*/
@Component(immediate = true)
@Service
public class RestSBControllerImpl implements RestSBController {
private static final Logger log =
LoggerFactory.getLogger(RestSBControllerImpl.class);
private static final String APPLICATION = "application/";
private static final String XML = "xml";
private static final String JSON = "json";
private static final String DOUBLESLASH = "//";
private static final String COLON = ":";
private static final int STATUS_OK = Response.Status.OK.getStatusCode();
private static final int STATUS_CREATED = Response.Status.CREATED.getStatusCode();
private static final int STATUS_ACCEPTED = Response.Status.ACCEPTED.getStatusCode();
private static final String SLASH = "/";
private final Map<DeviceId, RestSBDevice> deviceMap = new ConcurrentHashMap<>();
Client client;
@Activate
public void activate(ComponentContext context) {
client = Client.create();
log.info("Started");
}
@Deactivate
public void deactivate() {
deviceMap.clear();
log.info("Stopped");
}
@Override
public Map<DeviceId, RestSBDevice> getDevices() {
return deviceMap;
}
@Override
public RestSBDevice getDevice(DeviceId deviceInfo) {
return deviceMap.get(deviceInfo);
}
@Override
public RestSBDevice getDevice(IpAddress ip, int port) {
for (DeviceId info : deviceMap.keySet()) {
if (IpAddress.valueOf(info.uri().getHost()).equals(ip) &&
info.uri().getPort() == port) {
return deviceMap.get(info);
}
}
return null;
}
@Override
public void addDevice(RestSBDevice device) {
deviceMap.put(device.deviceId(), device);
}
@Override
public void removeDevice(RestSBDevice device) {
deviceMap.remove(device.deviceId());
}
@Override
public boolean post(DeviceId device, String request, InputStream payload, String mediaType) {
WebResource webResource = getWebResource(device, request);
ClientResponse response = null;
if (payload != null) {
try {
response = webResource.accept(mediaType)
.post(ClientResponse.class, IOUtils.toString(payload, StandardCharsets.UTF_8));
} catch (IOException e) {
log.error("Cannot do POST {} request on device {} because can't read payload",
request, device);
}
} else {
response = webResource.accept(mediaType)
.post(ClientResponse.class);
}
return checkReply(response);
}
@Override
public boolean put(DeviceId device, String request, InputStream payload, String mediaType) {
WebResource webResource = getWebResource(device, request);
ClientResponse response = null;
if (payload != null) {
try {
response = webResource.accept(mediaType)
.put(ClientResponse.class, IOUtils.toString(payload, StandardCharsets.UTF_8));
} catch (IOException e) {
log.error("Cannot do PUT {} request on device {} because can't read payload",
request, device);
}
} else {
response = webResource.accept(mediaType)
.put(ClientResponse.class);
}
return checkReply(response);
}
@Override
public InputStream get(DeviceId device, String request, String mediaType) {
WebResource webResource = getWebResource(device, request);
String type;
switch (mediaType) {
case XML:
type = MediaType.APPLICATION_XML;
break;
case JSON:
type = MediaType.APPLICATION_JSON;
break;
default:
throw new IllegalArgumentException("Unsupported media type " + mediaType);
}
return new ByteArrayInputStream(webResource.accept(type).get(ClientResponse.class)
.getEntity(String.class)
.getBytes(StandardCharsets.UTF_8));
}
@Override
public boolean delete(DeviceId device, String request, InputStream payload, String mediaType) {
WebResource webResource = getWebResource(device, request);
ClientResponse response = null;
if (payload != null) {
try {
response = webResource.accept(mediaType)
.delete(ClientResponse.class, IOUtils.toString(payload, StandardCharsets.UTF_8));
} catch (IOException e) {
log.error("Cannot do PUT {} request on device {} because can't read payload",
request, device);
}
} else {
response = webResource.accept(mediaType)
.delete(ClientResponse.class);
}
return checkReply(response);
}
private WebResource getWebResource(DeviceId device, String request) {
return Client.create().resource(deviceMap.get(device).protocol() + COLON +
DOUBLESLASH +
deviceMap.get(device).ip().toString() +
COLON + deviceMap.get(device).port() +
SLASH + request);
}
private boolean checkReply(ClientResponse response) {
if (response != null) {
if (response.getStatus() == STATUS_OK ||
response.getStatus() == STATUS_CREATED ||
response.getStatus() == STATUS_ACCEPTED) {
return true;
} else {
log.error("Failed request: HTTP error code : "
+ response.getStatus());
return false;
}
}
log.error("Null reply from device");
return false;
}
}