/* * Copyright 2015 Okinawa Open Laboratory, General Incorporated Association * * 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.okinawaopenlabs.ofpm.client; import static org.okinawaopenlabs.constants.ErrorMessage.*; import static org.okinawaopenlabs.constants.OfpmDefinition.*; import java.util.List; import java.util.Map; import javax.ws.rs.core.MediaType; import javax.ws.rs.core.MultivaluedMap; import org.apache.commons.lang.StringUtils; import org.apache.log4j.Logger; import org.okinawaopenlabs.constants.OfcClientDefinition; import org.okinawaopenlabs.ofpm.exception.OFCClientException; import org.okinawaopenlabs.ofpm.json.common.BaseResponse; import org.okinawaopenlabs.ofpm.json.ofc.SetFlowToOFC; import org.okinawaopenlabs.ofpm.json.ofc.SetFlowToOFC.Action; import org.okinawaopenlabs.ofpm.json.ofc.SetFlowToOFC.Match; import com.sun.jersey.api.client.Client; import com.sun.jersey.api.client.ClientHandlerException; import com.sun.jersey.api.client.ClientResponse; import com.sun.jersey.api.client.UniformInterfaceException; import com.sun.jersey.api.client.WebResource; import com.sun.jersey.api.client.WebResource.Builder; import com.sun.jersey.core.util.MultivaluedMapImpl; public class OFCClientImpl implements OFCClient { private static final Logger logger = Logger.getLogger(OFCClientImpl.class); /* (non-Javadoc) * @see org.okinawaopenlabs.ofpm.client.OFCClient#setFlows(Map<String, Object>) */ @Override public BaseResponse addFlows(String ofIp, SetFlowToOFC requestData) throws OFCClientException { final String fname = "setFlows"; if (logger.isDebugEnabled()) { logger.debug(String.format("%s(ofIp=%s, requestData=%s) - start", fname, ofIp, requestData)); } BaseResponse ret = new BaseResponse(); ret.setStatus(STATUS_INTERNAL_ERROR); try { String url = "http://" + ofIp + OFC_ADD_FLOWENTRY_PATH; ret = postRequest(url, requestData); } catch (UniformInterfaceException uie) { logger.error(uie.getMessage()); throw new OFCClientException(String.format(CONNECTION_FAIL, "OFC-" + ofIp)); } catch (ClientHandlerException che) { logger.error(che); throw new OFCClientException(String.format(CONNECTION_FAIL, "OFC-" + ofIp)); } catch (Exception e) { logger.error(e.getMessage()); throw new OFCClientException(UNEXPECTED_ERROR); } if (logger.isDebugEnabled()) { logger.debug(String.format("%s(ret=%s) - end", fname, ret.toJson())); } return ret; } /* (non-Javadoc) * @see org.okinawaopenlabs.ofpm.client.OFCClient#deleteFlows(Map<String, Object> flow) */ @Override public BaseResponse deleteFlows(String ofIp, SetFlowToOFC requestData) throws OFCClientException { final String fname = "deleteFlows"; if (logger.isDebugEnabled()) { logger.debug(String.format("%s(ofIp=%s, requestData=%s) - start", fname, ofIp, requestData)); } BaseResponse ret = new BaseResponse(); ret.setStatus(STATUS_INTERNAL_ERROR); try { String url = "http://" + ofIp + OFC_DELETE_FLOWENTRY_PATH; ret = postRequest(url, requestData); } catch (UniformInterfaceException uie) { logger.error(uie.getMessage()); throw new OFCClientException(String.format(CONNECTION_FAIL, "OFC-" + ofIp)); } catch (ClientHandlerException che) { logger.error(che); throw new OFCClientException(String.format(CONNECTION_FAIL, "OFC-" + ofIp)); } catch (Exception e) { logger.error(e.getMessage()); throw new OFCClientException(UNEXPECTED_ERROR); } if (logger.isDebugEnabled()) { logger.debug(String.format("%s(ret=%s) - end", fname, ret.toJson())); } return ret; } public BaseResponse postRequest(String url, SetFlowToOFC requestData) throws OFCClientException { final String fname = "setFlows"; if (logger.isDebugEnabled()) { logger.debug(String.format("%s(url=%s, requestData=%s) - start", fname, url, requestData)); } BaseResponse ret = new BaseResponse(); try { WebResource resource = Client.create().resource(url); Builder resBuilder = resource.entity(requestData.toJson()); resBuilder = resBuilder.accept(MediaType.APPLICATION_JSON); resBuilder = resBuilder.type(MediaType.APPLICATION_JSON); ClientResponse res = resBuilder.post(ClientResponse.class); if (res.getStatus() != STATUS_SUCCESS) { logger.error(res.getStatus()); throw new OFCClientException(String.format(WRONG_RESPONSE, "OFC-" + url)); } ret.setStatus(res.getStatus()); } catch (UniformInterfaceException uie) { logger.error(uie.getMessage()); throw new OFCClientException(String.format(CONNECTION_FAIL, "OFC-" + url)); } catch (ClientHandlerException che) { logger.error(che); throw new OFCClientException(String.format(CONNECTION_FAIL, "OFC-" + url)); } catch (Exception e) { logger.error(e.getMessage()); throw new OFCClientException(UNEXPECTED_ERROR); } if (logger.isDebugEnabled()) { logger.debug(String.format("%s(ret=%s) - end", fname, ret.toJson())); } return ret; } public SetFlowToOFC createRequestData(Long dpid, Long priority, Match match, List<Action> actions) { final String fname = "createRequestData"; if (logger.isDebugEnabled()) { logger.debug(String.format("%s(dpid=%s, priority=%s, match=%s, actions=%s) - start", fname, dpid, priority, match, actions)); } SetFlowToOFC requestData = new SetFlowToOFC(); requestData.setDpid(dpid); requestData.setPriority(priority); if (match != null) { requestData.setMatch(match); } else { requestData.setMatch(requestData.new Match()); } if (actions != null) { requestData.setActions(actions); } if (logger.isDebugEnabled()) { logger.debug(String.format("%s(requestData=%s) - end", fname, requestData.toJson())); } return requestData; } public SetFlowToOFC createMatchForInPort(SetFlowToOFC requestData, Long inPort) { final String fname = "createMatchForInPort"; if (logger.isDebugEnabled()) { logger.debug(String.format("%s(requestData=%s, inPort=%s) - start", fname, requestData, inPort)); } Match match = requestData.getMatch(); match.setIn_port(inPort); if (logger.isDebugEnabled()) { logger.debug(String.format("%s(ret=%s) - end", fname, requestData.toJson())); } return requestData; } public SetFlowToOFC createMatchForInPortDlVlan(SetFlowToOFC requestData, Long inPort, Long vlanId) { final String fname = "createMatchForInPortDlVlan"; if (logger.isDebugEnabled()) { logger.debug(String.format("%s(requestData=%s, inPort=%s, vlanId=%s) - start", fname, requestData, inPort, vlanId)); } Match match = requestData.getMatch(); match.setIn_port(inPort); match.setDl_vlan(vlanId); if (logger.isDebugEnabled()) { logger.debug(String.format("%s(ret=%s) - end", fname, requestData.toJson())); } return requestData; } public SetFlowToOFC createMatchForDlVlan(SetFlowToOFC requestData, Long vlanId) { final String fname = "createMatchForDlVlan"; if (logger.isDebugEnabled()) { logger.debug(String.format("%s(requestData=%s, vlanId=%s) - start", fname, requestData, vlanId)); } Match match = requestData.getMatch(); match.setDl_vlan(vlanId); if (logger.isDebugEnabled()) { logger.debug(String.format("%s(ret=%s) - end", fname, requestData.toJson())); } return requestData; } public SetFlowToOFC createActionsForPushVlan(SetFlowToOFC requestData, Long outPort, Long vlanId) { final String fname = "createActionsForPushVlan"; if (logger.isDebugEnabled()) { logger.debug(String.format("%s(requestData=%s, outPort=%s, vlanId=%s) - start", fname, requestData, outPort, vlanId)); } List<SetFlowToOFC.Action> retActions = requestData.getActions(); Action pushVlanAction = requestData.new Action(); pushVlanAction.setType(OfcClientDefinition.ACTION_TYPE_PUSH_VLAN); pushVlanAction.setEthertype(OfcClientDefinition.ACTION_TYPE_PUSH_VLAN_ETH_TYPE); retActions.add(pushVlanAction); Action pushSetFieldAction = requestData.new Action(); pushSetFieldAction.setType(OfcClientDefinition.ACTION_TYPE_SET_FIELD); pushSetFieldAction.setField(OfcClientDefinition.ACTION_TYPE_SET_FIELD_VLAN_VID); pushSetFieldAction.setValue(vlanId); retActions.add(pushSetFieldAction); Action pushOutputAction = requestData.new Action(); pushOutputAction.setType(OfcClientDefinition.ACTION_TYPE_OUTPUT); pushOutputAction.setPort(outPort); retActions.add(pushOutputAction); if (logger.isDebugEnabled()) { logger.debug(String.format("%s(ret=%s) - end", fname, requestData.toJson())); } return requestData; } public SetFlowToOFC createActionsForPushOuter_tag(SetFlowToOFC requestData, Long outPort, Long vlanId, Long dfvlanId) { final String fname = "createActionsForPushVlan"; if (logger.isDebugEnabled()) { logger.debug(String.format("%s(requestData=%s, outPort=%s, vlanId=%s) - start", fname, requestData, outPort, vlanId)); } List<SetFlowToOFC.Action> retActions = requestData.getActions(); Action popVlanAction = requestData.new Action(); popVlanAction.setType(OfcClientDefinition.ACTION_TYPE_POP_VLAN); retActions.add(popVlanAction); Action pushVlanAction = requestData.new Action(); pushVlanAction.setType(OfcClientDefinition.ACTION_TYPE_PUSH_VLAN); pushVlanAction.setEthertype(OfcClientDefinition.ACTION_TYPE_PUSH_Outer_ETH_TYPE); retActions.add(pushVlanAction); Action pushSetFieldAction = requestData.new Action(); pushSetFieldAction.setType(OfcClientDefinition.ACTION_TYPE_SET_FIELD); pushSetFieldAction.setField(OfcClientDefinition.ACTION_TYPE_SET_FIELD_VLAN_VID); pushSetFieldAction.setValue(dfvlanId); retActions.add(pushSetFieldAction); Action pushVlanAction_outer = requestData.new Action(); pushVlanAction_outer.setType(OfcClientDefinition.ACTION_TYPE_PUSH_VLAN); pushVlanAction_outer.setEthertype(OfcClientDefinition.ACTION_TYPE_PUSH_VLAN_ETH_TYPE); retActions.add(pushVlanAction_outer); Action pushSetFieldAction_outer = requestData.new Action(); pushSetFieldAction_outer.setType(OfcClientDefinition.ACTION_TYPE_SET_FIELD); pushSetFieldAction_outer.setField(OfcClientDefinition.ACTION_TYPE_SET_FIELD_VLAN_VID); pushSetFieldAction_outer.setValue(vlanId); retActions.add(pushSetFieldAction_outer); Action pushOutputAction = requestData.new Action(); pushOutputAction.setType(OfcClientDefinition.ACTION_TYPE_OUTPUT); pushOutputAction.setPort(outPort); retActions.add(pushOutputAction); if (logger.isDebugEnabled()) { logger.debug(String.format("%s(ret=%s) - end", fname, requestData.toJson())); } return requestData; } public SetFlowToOFC createActionsForPopVlan(SetFlowToOFC requestData, Long outPort) { final String fname = "createActionsForPopVlan"; if (logger.isDebugEnabled()) { logger.debug(String.format("%s(requestData=%s, outPort=%s) - start", fname, requestData, outPort)); } List<SetFlowToOFC.Action> retActions = requestData.getActions(); Action popVlanAction = requestData.new Action(); popVlanAction.setType(OfcClientDefinition.ACTION_TYPE_POP_VLAN); retActions.add(popVlanAction); Action pushOutputAction = requestData.new Action(); pushOutputAction.setType(OfcClientDefinition.ACTION_TYPE_OUTPUT); pushOutputAction.setPort(outPort); retActions.add(pushOutputAction); if (logger.isDebugEnabled()) { logger.debug(String.format("%s(ret=%s) - end", fname, requestData.toJson())); } return requestData; } public SetFlowToOFC createActionsForPopOuter_tag(SetFlowToOFC requestData, Long outPort) { final String fname = "createActionsForPopVlan"; if (logger.isDebugEnabled()) { logger.debug(String.format("%s(requestData=%s, outPort=%s) - start", fname, requestData, outPort)); } List<SetFlowToOFC.Action> retActions = requestData.getActions(); Action popVlanAction = requestData.new Action(); popVlanAction.setType(OfcClientDefinition.ACTION_TYPE_POP_VLAN); retActions.add(popVlanAction); Action rename_ethtype = requestData.new Action(); rename_ethtype.setType(OfcClientDefinition.ACTION_TYPE_SET_FIELD); rename_ethtype.setField(OfcClientDefinition.ACTION_TYPE_SET_FIELD_ETH_TYPE); rename_ethtype.setValue(OfcClientDefinition.ACTION_TYPE_PUSH_VLAN_ETH_TYPE); retActions.add(rename_ethtype); Action pushOutputAction = requestData.new Action(); pushOutputAction.setType(OfcClientDefinition.ACTION_TYPE_OUTPUT); pushOutputAction.setPort(outPort); retActions.add(pushOutputAction); if (logger.isDebugEnabled()) { logger.debug(String.format("%s(ret=%s) - end", fname, requestData.toJson())); } return requestData; } public SetFlowToOFC createActionsForOutputPort(SetFlowToOFC requestData, Long outPort) { final String fname = "createActionsForPopVlan"; if (logger.isDebugEnabled()) { logger.debug(String.format("%s(requestData=%s, outPort=%s) - start", fname, requestData, outPort)); } List<SetFlowToOFC.Action> retActions = requestData.getActions(); Action pushOutputAction = requestData.new Action(); pushOutputAction.setType(OfcClientDefinition.ACTION_TYPE_OUTPUT); pushOutputAction.setPort(outPort); retActions.add(pushOutputAction); if (logger.isDebugEnabled()) { logger.debug(String.format("%s(ret=%s) - end", fname, requestData.toJson())); } return requestData; } private boolean isNullAndEmpty(String param) { if (!StringUtils.isBlank(param)) { return false; } return true; } private boolean isNull(Boolean param) { if (param != null) { return false; } return true; } private boolean isNull(Integer param) { if (param != null) { return false; } return true; } }