/* Copyright [2011] [University of Rostock] * * 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.ws4d.coap.connection; import java.net.InetAddress; import org.ws4d.coap.interfaces.CoapChannel; import org.ws4d.coap.interfaces.CoapMessage; import org.ws4d.coap.interfaces.CoapRequest; import org.ws4d.coap.interfaces.CoapResponse; import org.ws4d.coap.interfaces.CoapServer; import org.ws4d.coap.interfaces.CoapServerChannel; import org.ws4d.coap.interfaces.CoapSocketHandler; import org.ws4d.coap.messages.BasicCoapRequest; import org.ws4d.coap.messages.BasicCoapResponse; import org.ws4d.coap.messages.CoapEmptyMessage; import org.ws4d.coap.messages.CoapMediaType; import org.ws4d.coap.messages.CoapPacketType; import org.ws4d.coap.messages.CoapResponseCode; /** * @author Christian Lerche <christian.lerche@uni-rostock.de> */ public class BasicCoapServerChannel extends BasicCoapChannel implements CoapServerChannel{ CoapServer server = null; public BasicCoapServerChannel(CoapSocketHandler socketHandler, CoapServer server, InetAddress remoteAddress, int remotePort) { super(socketHandler, remoteAddress, remotePort); this.server = server; } public void close() { socketHandler.removeServerChannel(this); } public void handleMessage(CoapMessage message) { /* message MUST be a request */ if (message.isEmpty()){ return; } if (!message.isRequest()){ return; //throw new IllegalStateException("Incomming server message is not a request"); } BasicCoapRequest request = (BasicCoapRequest) message; CoapChannel channel = request.getChannel(); /* TODO make this cast safe */ server.onRequest((CoapServerChannel) channel, request); } /*TODO: implement */ public void lostConnection(boolean notReachable, boolean resetByServer){ server.onSeparateResponseFailed(this); } public BasicCoapResponse createResponse(CoapMessage request, CoapResponseCode responseCode) { return createResponse(request, responseCode, null); } public BasicCoapResponse createResponse(CoapMessage request, CoapResponseCode responseCode, CoapMediaType contentType){ BasicCoapResponse response; if (request.getPacketType() == CoapPacketType.CON) { response = new BasicCoapResponse(CoapPacketType.ACK, responseCode, request.getMessageID(), request.getToken()); } else if (request.getPacketType() == CoapPacketType.NON) { response = new BasicCoapResponse(CoapPacketType.NON, responseCode, request.getMessageID(), request.getToken()); } else { throw new IllegalStateException("Create Response failed, Request is neither a CON nor a NON packet"); } if (contentType != null && contentType != CoapMediaType.UNKNOWN){ response.setContentType(contentType); } response.setChannel(this); return response; } public CoapResponse createSeparateResponse(CoapRequest request, CoapResponseCode responseCode) { BasicCoapResponse response = null; if (request.getPacketType() == CoapPacketType.CON) { /* The separate Response is CON (normally a Response is ACK or NON) */ response = new BasicCoapResponse(CoapPacketType.CON, responseCode, channelManager.getNewMessageID(), request.getToken()); /*send ack immediately */ sendMessage(new CoapEmptyMessage(CoapPacketType.ACK, request.getMessageID())); } else if (request.getPacketType() == CoapPacketType.NON){ /* Just a normal response*/ response = new BasicCoapResponse(CoapPacketType.NON, responseCode, request.getMessageID(), request.getToken()); } else { throw new IllegalStateException("Create Response failed, Request is neither a CON nor a NON packet"); } response.setChannel(this); return response; } public void sendSeparateResponse(CoapResponse response) { sendMessage(response); } public CoapResponse createNotification(CoapRequest request, CoapResponseCode responseCode, int sequenceNumber){ /*use the packet type of the request: if con than con otherwise non*/ if (request.getPacketType() == CoapPacketType.CON){ return createNotification(request, responseCode, sequenceNumber, true); } else { return createNotification(request, responseCode, sequenceNumber, false); } } public CoapResponse createNotification(CoapRequest request, CoapResponseCode responseCode, int sequenceNumber, boolean reliable){ BasicCoapResponse response = null; CoapPacketType packetType; if (reliable){ packetType = CoapPacketType.CON; } else { packetType = CoapPacketType.NON; } response = new BasicCoapResponse(packetType, responseCode, channelManager.getNewMessageID(), request.getToken()); response.setChannel(this); response.setObserveOption(sequenceNumber); return response; } public void sendNotification(CoapResponse response) { sendMessage(response); } }