| /* |
| * 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; |
| } |
| } |