From c938b29276d31ba7b8a9d87f7e0fcfc652155d65 Mon Sep 17 00:00:00 2001 From: Olena Radiboh Date: Wed, 17 Jan 2018 18:14:08 +0200 Subject: [PATCH] Introducing to new tests for simple message flow (Smpp->Smpp and Smpp->Sip). Related jiras: MSB-336, MSB-337 --- .../java/org/mobicents/smsc/domain/Sip.java | 7 +- .../smsc/mproc/impl/MProcRuleDefaultImpl.java | 6 +- test/features/pom.xml | 14 + .../mobicents/protocols/smpp/HelperClass.java | 61 -- .../protocols/smpp/MProcManagementProxy.java | 46 ++ .../mobicents/protocols/smpp/SipClient.java | 660 ++++++++++++++++++ .../protocols/smpp/SipManagementProxy.java | 49 ++ .../simpleflow/IncomingFromSmppToAll.java | 250 +++++++ 8 files changed, 1029 insertions(+), 64 deletions(-) delete mode 100644 test/features/src/main/java/org/mobicents/protocols/smpp/HelperClass.java create mode 100644 test/features/src/test/java/org/mobicents/protocols/smpp/MProcManagementProxy.java create mode 100644 test/features/src/test/java/org/mobicents/protocols/smpp/SipClient.java create mode 100644 test/features/src/test/java/org/mobicents/protocols/smpp/SipManagementProxy.java create mode 100644 test/features/src/test/java/org/mobicents/protocols/smpp/simpleflow/IncomingFromSmppToAll.java diff --git a/core/domain/src/main/java/org/mobicents/smsc/domain/Sip.java b/core/domain/src/main/java/org/mobicents/smsc/domain/Sip.java index c13c907e4..a4d55c3e5 100644 --- a/core/domain/src/main/java/org/mobicents/smsc/domain/Sip.java +++ b/core/domain/src/main/java/org/mobicents/smsc/domain/Sip.java @@ -3,6 +3,7 @@ */ package org.mobicents.smsc.domain; +import java.io.Serializable; import java.util.regex.Matcher; import java.util.regex.Pattern; @@ -15,9 +16,11 @@ * @author Amit Bhayani * */ -public class Sip implements SipMBean { +public class Sip implements SipMBean, Serializable { - private static final String SIP_NAME = "name"; + private static final long serialVersionUID = 1L; + + private static final String SIP_NAME = "name"; private static final String SIP_CLUSTER_NAME = "clusterName"; diff --git a/core/smsc-common-library/src/main/java/org/mobicents/smsc/mproc/impl/MProcRuleDefaultImpl.java b/core/smsc-common-library/src/main/java/org/mobicents/smsc/mproc/impl/MProcRuleDefaultImpl.java index bc6558599..3383d4f45 100644 --- a/core/smsc-common-library/src/main/java/org/mobicents/smsc/mproc/impl/MProcRuleDefaultImpl.java +++ b/core/smsc-common-library/src/main/java/org/mobicents/smsc/mproc/impl/MProcRuleDefaultImpl.java @@ -22,6 +22,7 @@ package org.mobicents.smsc.mproc.impl; +import java.io.Serializable; import java.util.regex.Matcher; import java.util.regex.Pattern; @@ -56,7 +57,10 @@ * @author sergey vetyutnev * */ -public class MProcRuleDefaultImpl extends MProcRuleBaseImpl implements MProcRuleDefault { +public class MProcRuleDefaultImpl extends MProcRuleBaseImpl implements MProcRuleDefault, Serializable { + + private static final long serialVersionUID = 1L; + private static final String DEST_TON_MASK = "destTonMask"; private static final String DEST_NPI_MASK = "destNpiMask"; private static final String DEST_DIG_MASK = "destDigMask"; diff --git a/test/features/pom.xml b/test/features/pom.xml index f62d1dde2..42f6c5d47 100644 --- a/test/features/pom.xml +++ b/test/features/pom.xml @@ -114,6 +114,20 @@ domain ${project.version} + + javax.sip + jain-sip-api + + + javax.sip + jain-sip-ri + 7.0.6.326 + + + org.mobicents.javax.sip + mobicents-jain-sip-ext + 7.0.4.23 + diff --git a/test/features/src/main/java/org/mobicents/protocols/smpp/HelperClass.java b/test/features/src/main/java/org/mobicents/protocols/smpp/HelperClass.java deleted file mode 100644 index 78ae7e34d..000000000 --- a/test/features/src/main/java/org/mobicents/protocols/smpp/HelperClass.java +++ /dev/null @@ -1,61 +0,0 @@ -package org.mobicents.protocols.smpp; - -import javax.management.MBeanServerConnection; -import javax.management.ObjectName; - -import org.restcomm.smpp.Esme; - -public class HelperClass { - public static Esme createEsme(MBeanServerConnection mbsc, ObjectName esmeManagementName, String type, String esmeName, - String clusterName, String systemId, String password, String localAddress, int localPort, String srcAdressRange) - throws Exception { - return createEsme(mbsc, esmeManagementName, type, esmeName, clusterName, systemId, password, localAddress, localPort, - srcAdressRange, -1, -1, -1, 1); - } - - public static Esme createEsme(MBeanServerConnection mbsc, ObjectName esmeManagementName, String type, String esmeName, - String clusterName, String systemId, String password, String localAddress, int localPort, String srcAdressRange, - int windowSize, int overloadThreshold, int normalThreshold,int destAddressLimit) throws Exception { - String[] signature = new String[] { String.class.getName(), String.class.getName(), String.class.getName(), - String.class.getName(), int.class.getName(), boolean.class.getName(), String.class.getName(), - String.class.getName(), String.class.getName(), byte.class.getName(), byte.class.getName(), - String.class.getName(), String.class.getName(), int.class.getName(), long.class.getName(), long.class.getName(), - long.class.getName(), long.class.getName(), long.class.getName(), String.class.getName(), - boolean.class.getName(), int.class.getName(), int.class.getName(), long.class.getName(), int.class.getName(), - int.class.getName(), String.class.getName(), int.class.getName(), int.class.getName(), String.class.getName(), - int.class.getName(), boolean.class.getName(), long.class.getName(), long.class.getName(), long.class.getName(), - long.class.getName(), int.class.getName(), int.class.getName(), int.class.getName(), int.class.getName(), - int.class.getName(), int.class.getName(), int.class.getName() }; - - Object[] params = new Object[] { esmeName, systemId, password, localAddress, localPort, false, "TRANSCEIVER", "", "3.4", - (byte) 0xFF, (byte) 0xFF, srcAdressRange, type, windowSize, 10000L, -1L, 5000L, -1L, 60000L, clusterName, true, 30000, 0, - 0L, -1, -1, "^[0-9a-zA-Z]*", -1, -1, srcAdressRange, 122, false, 0L, 0L, 0L, 0L, -1, -1, destAddressLimit, -1, -1, overloadThreshold, normalThreshold }; - - return (Esme) mbsc.invoke(esmeManagementName, "createEsme", params, signature); - } - - public static void startEsme(MBeanServerConnection mbsc, ObjectName esmeManagementName, String name) throws Exception { - String[] signature = new String[] { String.class.getName() }; - Object[] params = new Object[] { name }; - mbsc.invoke(esmeManagementName, "startEsme", params, signature); - } - - public static void stopEsme(MBeanServerConnection mbsc, ObjectName esmeManagementName, String name) throws Exception { - String[] signature = new String[] { String.class.getName() }; - Object[] params = new Object[] { name }; - mbsc.invoke(esmeManagementName, "stopEsme", params, signature); - } - - public static void destroyEsme(MBeanServerConnection mbsc, ObjectName esmeManagementName, String name) throws Exception { - String[] signature = new String[] { String.class.getName() }; - Object[] params = new Object[] { name }; - mbsc.invoke(esmeManagementName, "destroyEsme", params, signature); - } - - public static Esme getEsmeByName(MBeanServerConnection mbsc, ObjectName esmeManagementName, String name) throws Exception { - String[] signature = new String[] { String.class.getName() }; - Object[] params = new Object[] { name }; - - return (Esme) mbsc.invoke(esmeManagementName, "getEsmeByName", params, signature); - } -} diff --git a/test/features/src/test/java/org/mobicents/protocols/smpp/MProcManagementProxy.java b/test/features/src/test/java/org/mobicents/protocols/smpp/MProcManagementProxy.java new file mode 100644 index 000000000..1c6cb9538 --- /dev/null +++ b/test/features/src/test/java/org/mobicents/protocols/smpp/MProcManagementProxy.java @@ -0,0 +1,46 @@ +package org.mobicents.protocols.smpp; + +import java.util.HashMap; + +import javax.management.MBeanServerConnection; +import javax.management.ObjectName; +import javax.management.remote.JMXConnector; +import javax.management.remote.JMXConnectorFactory; +import javax.management.remote.JMXServiceURL; + +public class MProcManagementProxy { + public static final String JMX_DOMAIN = "org.mobicents.smsc"; + public static final String JMX_NAME_SMSC_MANAGEMENT = "SmscManagement"; + public static final String JMX_LAYER_MPROC_MANAGEMENT = "MProcManagement"; + + private MBeanServerConnection mbsc; + private ObjectName mprocManagementName; + + public MProcManagementProxy() throws Exception { + // Provide credentials required by server for user authentication + HashMap environment = new HashMap(); + // String[] credentials = new String[] {"admin", "admin"}; + // environment.put (JMXConnector.CREDENTIALS, credentials); + + // Create JMXServiceURL of JMX Connector (must be known in advance) + JMXServiceURL url; + + url = new JMXServiceURL("service:jmx:rmi://127.0.0.1/jndi/rmi://127.0.0.1:1190/jmxconnector"); + + // Get JMX connector + JMXConnector jmxc = JMXConnectorFactory.connect(url, environment); + + mprocManagementName = new ObjectName( + JMX_DOMAIN + ":layer=" + JMX_LAYER_MPROC_MANAGEMENT + ",name=" + JMX_NAME_SMSC_MANAGEMENT); + + // Get MBean server connection + mbsc = jmxc.getMBeanServerConnection(); + } + + public void createMProcRule(int id, String parametersString) throws Exception { + String[] signature = new String[] { int.class.getName(), String.class.getName(), String.class.getName() }; + Object[] params = new Object[] { id, "mproc", parametersString }; + mbsc.invoke(mprocManagementName, "createMProcRule", params, signature); + } + +} diff --git a/test/features/src/test/java/org/mobicents/protocols/smpp/SipClient.java b/test/features/src/test/java/org/mobicents/protocols/smpp/SipClient.java new file mode 100644 index 000000000..68feb920d --- /dev/null +++ b/test/features/src/test/java/org/mobicents/protocols/smpp/SipClient.java @@ -0,0 +1,660 @@ +package org.mobicents.protocols.smpp; + +/* + * JBoss, Home of Professional Open Source + * Copyright 2011, Red Hat, Inc. and individual contributors + * by the @authors tag. See the copyright.txt in the distribution for a + * full listing of individual contributors. + * + * This is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as + * published by the Free Software Foundation; either version 2.1 of + * the License, or (at your option) any later version. + * + * This software is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this software; if not, write to the Free + * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA + * 02110-1301 USA, or see the FSF site: http://www.fsf.org. + */ + +import gov.nist.javax.sip.header.From; +import gov.nist.javax.sip.stack.NioMessageProcessorFactory; + +import java.text.ParseException; +import java.util.ArrayList; +import java.util.LinkedList; +import java.util.ListIterator; +import java.util.Properties; +import java.util.Random; +import java.util.TimerTask; + +import javax.sip.ClientTransaction; +import javax.sip.Dialog; +import javax.sip.DialogState; +import javax.sip.DialogTerminatedEvent; +import javax.sip.IOExceptionEvent; +import javax.sip.InvalidArgumentException; +import javax.sip.ListeningPoint; +import javax.sip.PeerUnavailableException; +import javax.sip.RequestEvent; +import javax.sip.ResponseEvent; +import javax.sip.ServerTransaction; +import javax.sip.SipException; +import javax.sip.SipFactory; +import javax.sip.SipListener; +import javax.sip.SipProvider; +import javax.sip.SipStack; +import javax.sip.TransactionAlreadyExistsException; +import javax.sip.TransactionTerminatedEvent; +import javax.sip.TransactionUnavailableException; +import javax.sip.address.Address; +import javax.sip.address.AddressFactory; +import javax.sip.address.SipURI; +import javax.sip.address.URI; +import javax.sip.header.CSeqHeader; +import javax.sip.header.CallIdHeader; +import javax.sip.header.ContactHeader; +import javax.sip.header.ContentTypeHeader; +import javax.sip.header.FromHeader; +import javax.sip.header.Header; +import javax.sip.header.HeaderFactory; +import javax.sip.header.MaxForwardsHeader; +import javax.sip.header.RouteHeader; +import javax.sip.header.ToHeader; +import javax.sip.header.ViaHeader; +import javax.sip.message.MessageFactory; +import javax.sip.message.Request; +import javax.sip.message.Response; + +//import org.mobicents.tools.smpp.balancer.ConfigInit; + +import junit.framework.TestCase; +import static junit.framework.TestCase.fail; + +public class SipClient implements SipListener { + public AddressFactory addressFactory; + + private MessageFactory messageFactory; + + public HeaderFactory headerFactory; + + private SipProvider sipProvider; + + private SipStack sipStack; + + private ContactHeader contactHeader; + + private ListeningPoint listeningPoint; + + private ClientTransaction inviteTid; + + private Dialog dialog; + + public boolean callerSendsBye; + + private boolean isCompactForm; + + private boolean isWildcardContactHeader; + + public void setCompactForm(boolean isCompactForm) { + this.isCompactForm = isCompactForm; + } + + public Request inviteRequest; + private boolean isSlowResponse = false; + public void setIsSlowResponse(boolean isSlowResponse) + { + this.isSlowResponse = isSlowResponse; + } + + boolean started = false; + + private String localIPAddress="127.0.0.1"; + public String peerHostPort ="127.0.0.1:5060"; + public String transport ="udp"; + + public LinkedList requests = new LinkedList(); + public LinkedList responses = new LinkedList(); + + private int localPort=5033; + private int randomizer; + + public SipClient() + { + randomizer=(new Random()).nextInt(Integer.MAX_VALUE)+1; + } + + public SipClient(String transport,int port) + { + this(); + this.transport=transport; + this.peerHostPort = "127.0.0.1:" + port; + + } + + public SipClient(String transport,int port,int localPort) + { + this(); + this.transport=transport; + this.peerHostPort = "127.0.0.1:" + port; + this.localPort=localPort; + } + + public SipClient(String transport,int port,int localPort, boolean ipv6) + { + this(); + this.transport=transport; + this.peerHostPort = "[::1]:" + port; + this.localIPAddress = "[::1]"; + this.localPort=localPort; + } + + class ByeTask extends TimerTask { + Dialog dialog; + public ByeTask(Dialog dialog) { + this.dialog = dialog; + } + public void run () { + try { + Request byeRequest = this.dialog.createRequest(Request.BYE); + ClientTransaction ct = sipProvider.getNewClientTransaction(byeRequest); + dialog.sendRequest(ct); + } catch (Exception ex) { + ex.printStackTrace(); + fail("Unexpected exception "); + } + + } + + } + public void processInvite(Request request, ServerTransaction stx) { + try { + if(isSlowResponse) + { + try { + Thread.sleep(10000); + } catch (InterruptedException e1) { + e1.printStackTrace(); + } + } + inviteRequest = request; + Response response = messageFactory.createResponse(180, request); + contactHeader = headerFactory.createContactHeader(addressFactory.createAddress("sip:here@" + localIPAddress + ":" + localPort)); + response.addHeader(contactHeader); + dialog = stx.getDialog(); + //check removing incorrect patching last via https://github.com/RestComm/load-balancer/issues/97 + FromHeader fromHeader = (FromHeader)response.getHeader(From.NAME); + URI currUri = fromHeader.getAddress().getURI(); + String fromUser = null; + if(currUri.isSipURI()) + { + fromUser = ((SipURI)currUri).getUser(); + if(fromUser.equals("senderToNexmo")) + { + ViaHeader lastViaHeader = null; + ListIterator it = response.getHeaders(ViaHeader.NAME); + while(it.hasNext()) + lastViaHeader = it.next(); + lastViaHeader.setReceived("127.0.0.2"); + lastViaHeader.setParameter("rport", "1111"); + + } + } + stx.sendResponse(response); + try { + Thread.sleep(1000); + } catch (InterruptedException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } + response = messageFactory.createResponse(200, request); + contactHeader = headerFactory.createContactHeader(addressFactory.createAddress("sip:here@" + localIPAddress + ":" + localPort)); + response.addHeader(contactHeader); + dialog = stx.getDialog(); + stx.sendResponse(response ); + } catch (SipException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } catch (InvalidArgumentException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } catch (ParseException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } + } + public void processAck(Request request, ServerTransaction stx) { + } + + public void processRequest(RequestEvent requestReceivedEvent) { + Request request = requestReceivedEvent.getRequest(); + requests.add(request); + ServerTransaction serverTransactionId = requestReceivedEvent + .getServerTransaction(); + if(serverTransactionId == null) { + try { + serverTransactionId = sipProvider.getNewServerTransaction(request); + } catch (TransactionAlreadyExistsException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } catch (TransactionUnavailableException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } + } + + System.out.println("\n\nRequest " + request.getMethod() + + " received at " + sipStack.getStackName() + + " with server transaction id " + serverTransactionId); + + if (request.getMethod().equals(Request.INVITE)) { + processInvite(request, serverTransactionId); + } else if (request.getMethod().equals(Request.BYE)) { + processBye(request, serverTransactionId); + } else if (request.getMethod().equals(Request.ACK)) { + processAck(request, serverTransactionId); + } else { + try { + serverTransactionId.sendResponse( messageFactory.createResponse(200,request) ); + } catch (Exception e) { + e.printStackTrace(); + fail("Unxepcted exception "); + } + } + + } + + public void processBye(Request request, + ServerTransaction serverTransactionId) { + try { + System.out.println("SipClient: got a bye ."); + if (serverTransactionId == null) { + System.out.println("SipClient: null TID."); + return; + } + Dialog dialog = serverTransactionId.getDialog(); + System.out.println("Dialog State = " + dialog.getState()); + Response response = messageFactory.createResponse(200, request); + serverTransactionId.sendResponse(response); + System.out.println("SipClient: Sending OK."); + System.out.println("Dialog State = " + dialog.getState()); + + } catch (Exception ex) { + fail("Unexpected exception"); + + } + } + + // Save the created ACK request, to respond to retransmitted 2xx + private Request ackRequest; + + public void processResponse(ResponseEvent responseReceivedEvent) { + System.out.println("Got a response"); + Response response = (Response) responseReceivedEvent.getResponse(); + responses.add(response); + ClientTransaction tid = responseReceivedEvent.getClientTransaction(); + CSeqHeader cseq = (CSeqHeader) response.getHeader(CSeqHeader.NAME); + + System.out.println("Response received : Status Code = " + + response.getStatusCode() + " " + cseq); + + if (tid == null) { + + // RFC3261: MUST respond to every 2xx + if (ackRequest!=null && dialog!=null) { + System.out.println("re-sending ACK"); + try { + dialog.sendAck(ackRequest); + } catch (SipException se) { + se.printStackTrace(); + fail("Unxpected exception "); + } + } + return; + } + // If the caller is supposed to send the bye + + System.out.println("transaction state is " + tid.getState()); + System.out.println("Dialog = " + tid.getDialog()); + if(tid.getDialog()!=null) + System.out.println("Dialog State is " + tid.getDialog().getState()); + + TestCase.assertSame("Checking dialog identity",tid.getDialog(), this.dialog); + + try { + if (response.getStatusCode() == Response.OK) { + if (cseq.getMethod().equals(Request.INVITE)) { + System.out.println("Dialog after 200 OK " + dialog); + System.out.println("Dialog State after 200 OK " + dialog.getState()); + Request ackRequest = dialog.createAck(cseq.getSeqNumber()); + System.out.println("Sending ACK"); + dialog.sendAck(ackRequest); + + } else if (cseq.getMethod().equals(Request.CANCEL)) { + if (dialog.getState() == DialogState.CONFIRMED) { + // oops cancel went in too late. Need to hang up the + // dialog. + System.out + .println("Sending BYE -- cancel went in too late !!"); + Request byeRequest = dialog.createRequest(Request.BYE); + ClientTransaction ct = sipProvider + .getNewClientTransaction(byeRequest); + dialog.sendRequest(ct); + + } + + } + } + } catch (Exception ex) { + ex.printStackTrace(); + + } + + } + + public void processTimeout(javax.sip.TimeoutEvent timeoutEvent) { + + System.out.println("Transaction Time out"); + } + + public void sendCancel() { + try { + System.out.println("Sending cancel"); + Request cancelRequest = inviteTid.createCancel(); + ClientTransaction cancelTid = sipProvider + .getNewClientTransaction(cancelRequest); + cancelTid.sendRequest(); + } catch (Exception ex) { + ex.printStackTrace(); + } + } + + synchronized public void start() { + started = true; + SipFactory sipFactory = null; + sipStack = null; + sipFactory = SipFactory.getInstance(); + sipFactory.resetFactory(); + Properties properties = new Properties(); + properties.setProperty("javax.sip.STACK_NAME", "SipClient " + randomizer); + properties.setProperty("gov.nist.javax.sip.MESSAGE_PROCESSOR_FACTORY", NioMessageProcessorFactory.class.getName()); + properties.setProperty("javax.sip.OUTBOUND_PROXY", peerHostPort + "/" + + transport); + if(isCompactForm) + { + System.out.println("COMPACT FORM ENABLED"); + properties.setProperty("gov.nist.javax.sip.COMPACT_FORM_HEADER", "true"); + } + // If you want to use UDP then uncomment this. + properties.setProperty("javax.sip.STACK_NAME", "SipClient"); + properties.setProperty("gov.nist.javax.sip.REENTRANT_LISTENER", "true"); + + // The following properties are specific to nist-sip + // and are not necessarily part of any other jain-sip + // implementation. + // You can set a max message size for tcp transport to + // guard against denial of service attack. + properties.setProperty("gov.nist.javax.sip.DEBUG_LOG", + "logs/sipclientdebug.txt"); + properties.setProperty("gov.nist.javax.sip.SERVER_LOG", + "logs/sipclientlog.txt"); + + // Drop the client connection after we are done with the transaction. + properties.setProperty("gov.nist.javax.sip.CACHE_CLIENT_CONNECTIONS", + "false"); + // Set to 0 (or NONE) in your production code for max speed. + // You need 16 (or TRACE) for logging traces. 32 (or DEBUG) for debug + traces. + // Your code will limp at 32 but it is best for debugging. + properties.setProperty("gov.nist.javax.sip.TRACE_LEVEL", "DEBUG"); + + + try { + // Create SipStack object + sipStack = sipFactory.createSipStack(properties); + headerFactory = sipFactory.createHeaderFactory(); + addressFactory = sipFactory.createAddressFactory(); + messageFactory = sipFactory.createMessageFactory(); + System.out.println("createSipStack " + sipStack); + } catch (PeerUnavailableException e) { + // could not find + // gov.nist.jain.protocol.ip.sip.SipStackImpl + // in the classpath + e.printStackTrace(); + System.err.println(e.getMessage()); + System.exit(0); + } + + try { + headerFactory = sipFactory.createHeaderFactory(); + addressFactory = sipFactory.createAddressFactory(); + messageFactory = sipFactory.createMessageFactory(); + listeningPoint = sipStack.createListeningPoint(localIPAddress, localPort, transport); + sipProvider = sipStack.createSipProvider(listeningPoint); + SipClient listener = this; + sipProvider.addSipListener(listener); + sipStack.start(); + } catch(Exception e) { + e.printStackTrace(); + } + + } + + public void sendInitialInvite(){ + sendInitial("BigGuy", "here.com", "INVITE",null, null, null); + } + + public void sendInitial(String method) { + sendInitial("BigGuy", "here.com", method, null, null, null); + } + + public void sendInitial(String method,RouteHeader route) { + sendInitial("BigGuy", "here.com", method, route, null, null); + } + + public void sendInitial(String fromUser, String fromHost, String method, RouteHeader route, String[] headerNames, String[] headerContents) { + try{ + if(!started) start(); + String fromName = fromUser; + String fromSipAddress = fromHost; + String fromDisplayName = "The Master Blaster"; + + String toSipAddress = "there.com"; + String toUser = "LittleGuy"; + String toDisplayName = "The Little Blister"; + + // create >From Header + SipURI fromAddress = addressFactory.createSipURI(fromName, + fromSipAddress); + + Address fromNameAddress = addressFactory.createAddress(fromAddress); + fromNameAddress.setDisplayName(fromDisplayName); + FromHeader fromHeader = headerFactory.createFromHeader( + fromNameAddress, "12345"); + + // create To Header + SipURI toAddress = addressFactory + .createSipURI(toUser, toSipAddress); + Address toNameAddress = addressFactory.createAddress(toAddress); + toNameAddress.setDisplayName(toDisplayName); + ToHeader toHeader = headerFactory.createToHeader(toNameAddress, + null); + + // create Request URI + SipURI requestURI = addressFactory.createSipURI(toUser, + peerHostPort); + + // Create ViaHeaders + + ArrayList viaHeaders = new ArrayList(); + + String ipAddress = null; + + if(fromUser.equals("KostyaNosach")) + ipAddress = "127.0.0.2"; + else + ipAddress = listeningPoint.getIPAddress(); + ViaHeader viaHeader = headerFactory.createViaHeader(ipAddress,sipProvider.getListeningPoint(transport).getPort(), transport, null); + + // add via headers + viaHeaders.add(viaHeader); + + // Create ContentTypeHeader + ContentTypeHeader contentTypeHeader = headerFactory + .createContentTypeHeader("application", "sdp"); + + // Create a new CallId header + CallIdHeader callIdHeader = sipProvider.getNewCallId(); + + // Create a new Cseq header + CSeqHeader cSeqHeader = headerFactory.createCSeqHeader(1L, + method); + + // Create a new MaxForwardsHeader + MaxForwardsHeader maxForwards = headerFactory + .createMaxForwardsHeader(70); + + // Create the request. + Request request = messageFactory.createRequest(requestURI, + method, callIdHeader, cSeqHeader, fromHeader, + toHeader, viaHeaders, maxForwards); + // Create contact headers + String host = localIPAddress; + + SipURI contactUrl = addressFactory.createSipURI(fromName, host); + contactUrl.setPort(listeningPoint.getPort()); + contactUrl.setLrParam(); + + // Create the contact name address. + SipURI contactURI = addressFactory.createSipURI(fromName, host); + contactURI.setPort(sipProvider.getListeningPoint(transport) + .getPort()); + + Address contactAddress = addressFactory.createAddress(contactURI); + + // Add the contact address. + contactAddress.setDisplayName(fromName); + + if(!isWildcardContactHeader) + { + contactHeader = headerFactory.createContactHeader(contactAddress); + } + else + { + contactHeader = headerFactory.createContactHeader(); + } + request.addHeader(contactHeader); + + + // to the outgoing SIP request. + // Add the extension header. + Header extensionHeader = headerFactory.createHeader("My-Header", + "my header value"); + request.addHeader(extensionHeader); + + if(headerNames != null) { + for(int q=0; q"); + request.addHeader(callInfoHeader); + + // Create the client transaction. + inviteTid = sipProvider.getNewClientTransaction(request); + + // send the request out. + inviteTid.sendRequest(); + + dialog = inviteTid.getDialog(); + + } catch (Exception ex) { + System.out.println(ex.getMessage()); + ex.printStackTrace(); + fail("Unxpected exception "); + } + } + + public void sendMessage() throws SipException { + Request r = dialog.createRequest("MESSAGE"); + dialog.sendRequest(sipProvider.getNewClientTransaction(r)); + } + + public void sendBye() throws SipException { + Request r = dialog.createRequest("BYE"); + dialog.sendRequest(sipProvider.getNewClientTransaction(r)); + } + + + + public void processIOException(IOExceptionEvent exceptionEvent) { + System.out.println("IOException happened for " + + exceptionEvent.getHost() + " port = " + + exceptionEvent.getPort()); + + } + + public void processTransactionTerminated( + TransactionTerminatedEvent transactionTerminatedEvent) { + + + + } + + public void processDialogTerminated( + DialogTerminatedEvent dialogTerminatedEvent) { + System.out.println("dialogTerminatedEvent"); + + } + + public void stop() { + + if(sipStack != null) + this.sipStack.stop(); + started = false; + } + + public boolean isWildcardContactHeader() { + return isWildcardContactHeader; + } + + public void setWildcardContactHeader(boolean isWildcardContactHeader) { + this.isWildcardContactHeader = isWildcardContactHeader; + } + +} \ No newline at end of file diff --git a/test/features/src/test/java/org/mobicents/protocols/smpp/SipManagementProxy.java b/test/features/src/test/java/org/mobicents/protocols/smpp/SipManagementProxy.java new file mode 100644 index 000000000..0012d202e --- /dev/null +++ b/test/features/src/test/java/org/mobicents/protocols/smpp/SipManagementProxy.java @@ -0,0 +1,49 @@ +package org.mobicents.protocols.smpp; + +import java.util.HashMap; +import java.util.List; + +import javax.management.MBeanServerConnection; +import javax.management.ObjectName; +import javax.management.remote.JMXConnector; +import javax.management.remote.JMXConnectorFactory; +import javax.management.remote.JMXServiceURL; + +import org.mobicents.smsc.domain.Sip; + +public class SipManagementProxy { + public static final String JMX_DOMAIN = "org.mobicents.smsc"; + public static final String JMX_NAME_SMSC_MANAGEMENT = "SmscManagement"; + public static final String JMX_LAYER_SIP_MANAGEMENT = "SipManagement"; + + private MBeanServerConnection mbsc; + private ObjectName sipManagementName; + + public SipManagementProxy() throws Exception { + // Provide credentials required by server for user authentication + HashMap environment = new HashMap(); + // String[] credentials = new String[] {"admin", "admin"}; + // environment.put (JMXConnector.CREDENTIALS, credentials); + + // Create JMXServiceURL of JMX Connector (must be known in advance) + JMXServiceURL url; + + url = new JMXServiceURL("service:jmx:rmi://127.0.0.1/jndi/rmi://127.0.0.1:1190/jmxconnector"); + + // Get JMX connector + JMXConnector jmxc = JMXConnectorFactory.connect(url, environment); + + sipManagementName = new ObjectName( + JMX_DOMAIN + ":layer=" + JMX_LAYER_SIP_MANAGEMENT + ",name=" + JMX_NAME_SMSC_MANAGEMENT); + + // Get MBean server connection + mbsc = jmxc.getMBeanServerConnection(); + } + + public int getSipPort() throws Exception { + String[] signature = new String[] { String.class.getName() }; + Object[] params = new Object[] { "SIP" }; + Sip sip = (Sip) mbsc.invoke(sipManagementName, "getSipByName", params, signature); + return sip.getPort(); + } +} diff --git a/test/features/src/test/java/org/mobicents/protocols/smpp/simpleflow/IncomingFromSmppToAll.java b/test/features/src/test/java/org/mobicents/protocols/smpp/simpleflow/IncomingFromSmppToAll.java new file mode 100644 index 000000000..97381e262 --- /dev/null +++ b/test/features/src/test/java/org/mobicents/protocols/smpp/simpleflow/IncomingFromSmppToAll.java @@ -0,0 +1,250 @@ +package org.mobicents.protocols.smpp.simpleflow; + +import static org.testng.Assert.assertEquals; + +import java.util.Random; +import java.util.concurrent.Executors; +import java.util.concurrent.ScheduledThreadPoolExecutor; +import java.util.concurrent.ThreadFactory; +import java.util.concurrent.atomic.AtomicInteger; + +import org.apache.log4j.Logger; +import org.mobicents.protocols.smpp.Client; +import org.mobicents.protocols.smpp.DBProxy; +import org.mobicents.protocols.smpp.MProcManagementProxy; +import org.mobicents.protocols.smpp.SipClient; +import org.mobicents.protocols.smpp.SipManagementProxy; +import org.mobicents.protocols.smpp.SmppManagementProxy; +import org.mobicents.protocols.smpp.SmscManagementProxy; +import org.mobicents.smsc.domain.StoreAndForwordMode; +import org.restcomm.smpp.Esme; +import org.testng.annotations.AfterClass; +import org.testng.annotations.AfterMethod; +import org.testng.annotations.BeforeClass; +import org.testng.annotations.BeforeMethod; +import org.testng.annotations.Test; + +import com.cloudhopper.smpp.impl.DefaultSmppSessionHandler; +import com.cloudhopper.smpp.pdu.EnquireLink; +import com.cloudhopper.smpp.pdu.PduRequest; +import com.cloudhopper.smpp.pdu.PduResponse; + +public class IncomingFromSmppToAll { + private static Logger logger = Logger.getLogger(IncomingFromSmppToAll.class); + + private SmppManagementProxy smppManagementProxy; + private SmscManagementProxy smscManagementProxy; + private SipManagementProxy sipManagementProxy; + private MProcManagementProxy mprocManagementProxy; + private DBProxy dbProxy; + + private static final StoreAndForwordMode SF_MODE = StoreAndForwordMode.fast; + + private Esme esmeSender; + + private Client sender; + + private String systemId = "test"; + private String password = "password"; + private String localAddress = "127.0.0.1"; + private int addrRange = 5123; + + private int localPort = 51233; + + private int initialDefaultWindowSize; + private String initialKeyspaceName; + private String keyspaceName = "RestCommSMSCTest"; + private StoreAndForwordMode initialStoreAndForwardMode; + + private ScheduledThreadPoolExecutor monitorExecutor; + + Random random = new Random(); + int startMprocId; + + @BeforeClass + public void setUpClass() throws Exception { + logger.info("setUpClass"); + + mprocManagementProxy = new MProcManagementProxy(); + smppManagementProxy = new SmppManagementProxy(); + smscManagementProxy = new SmscManagementProxy(); + sipManagementProxy = new SipManagementProxy(); + + dbProxy = new DBProxy(smscManagementProxy.getHosts(), smscManagementProxy.getPort(), smscManagementProxy.getUser(), + smscManagementProxy.getPass()); + + monitorExecutor = (ScheduledThreadPoolExecutor) Executors.newScheduledThreadPool(16, new ThreadFactory() { + private AtomicInteger sequence = new AtomicInteger(0); + + @Override + public Thread newThread(Runnable r) { + Thread t = new Thread(r); + t.setName("SmppClientSessionWindowMonitorPool-" + sequence.getAndIncrement()); + return t; + } + }); + + keyspaceName = keyspaceName + "_SIMPLE_" + System.currentTimeMillis(); + dbProxy.createKeyspace(keyspaceName); + + initialStoreAndForwardMode = smscManagementProxy.getStoreAndForwardMode(); + smscManagementProxy.setStoreAndForwardMode(SF_MODE); + + initialKeyspaceName = smscManagementProxy.getKeyspaceName(); + logger.info("initialKeyspaceName is " + initialKeyspaceName); + smscManagementProxy.setKeyspaceName(keyspaceName); + smscManagementProxy.restartDBOperations(); + logger.info("new keyspaceName is " + smscManagementProxy.getKeyspaceName()); + + initialDefaultWindowSize = smppManagementProxy.getDefaultWindowSize(); + logger.info("initialDefaultWindowSize is " + initialDefaultWindowSize); + smppManagementProxy.setDefaultWindowSize(1); + smppManagementProxy.stopSmppServerManagament(); + smppManagementProxy.startSmppServerManagament(); + logger.info("new defaultWindowSize is " + smppManagementProxy.getDefaultWindowSize()); + + } + + @AfterClass + public void tearDownClass() throws Exception { + logger.info("tearDownClass"); + + monitorExecutor.shutdownNow(); + + smscManagementProxy.setStoreAndForwardMode(initialStoreAndForwardMode); + + smscManagementProxy.setKeyspaceName(initialKeyspaceName); + smscManagementProxy.restartDBOperations(); + + dbProxy.dropKeyspace(keyspaceName); + + smppManagementProxy.setDefaultWindowSize(initialDefaultWindowSize); + smppManagementProxy.stopSmppServerManagament(); + smppManagementProxy.startSmppServerManagament(); + } + + @BeforeMethod + public void beforeTest() throws Exception { + + createSenderEsme(); + } + + @AfterMethod + public void afterTest() throws Exception { + + if (sender != null && sender.isStarted()) { + sender.stop(); + } + + if (esmeSender != null) { + smppManagementProxy.stopEsme(esmeSender.getName()); + smppManagementProxy.destroyEsme(esmeSender.getName()); + } + + } + + private void createSenderEsme() throws Exception { + esmeSender = smppManagementProxy.createEsme("SERVER", "sender_", "sender", systemId, password, localAddress, -1, + String.valueOf(addrRange)); + + smppManagementProxy.startEsme(esmeSender.getName()); + } + + private Client startClient(DefaultSmppSessionHandler handler, int port, String addr) throws Exception { + + Client client = new Client(handler, monitorExecutor, systemId, password, localAddress, port, addr); + client.init(); + + return client; + } + + @Test + public void testSmppToSmpp() throws Exception { + + + Esme esmeReceiver = smppManagementProxy.createEsme("SERVER", "receiver_", "receiver", systemId, password, localAddress, -1, + String.valueOf(addrRange + 1)); + + smppManagementProxy.startEsme(esmeReceiver.getName()); + + AtomicInteger reqReceived = new AtomicInteger(); + Client receiver = null; + + try { + sender = startClient(new DefaultSmppSessionHandler(), localPort, String.valueOf(addrRange)); + receiver = startClient(new SmppReceiverHandler(reqReceived), localPort+1, String.valueOf(addrRange+1)); + } catch (Exception ex) { + ex.printStackTrace(); + } + + logger.info("Test preparation completed. Clients are connected"); + logger.info("Sending message..."); + + sender.sendRequestPdu("Simple Smpp-Smpp Message", String.valueOf(addrRange), String.valueOf(addrRange + 1)); + + + Thread.sleep(5 * 1000); + + assertEquals(reqReceived.get(), 1); + + if (receiver != null && receiver.isStarted()) { + receiver.stop(); + } + + if (esmeReceiver != null) { + smppManagementProxy.stopEsme(esmeReceiver.getName()); + smppManagementProxy.destroyEsme(esmeReceiver.getName()); + } + } + + private int generateMprocId() { + return 22000 + random.nextInt(10000); + } + + @Test + public void testSmppToSip() throws Exception { + int sipAddrRange = 5555; + mprocManagementProxy.createMProcRule(generateMprocId(), "destdigmask 5555 newnetworkid 30"); + + try { + sender = startClient(new DefaultSmppSessionHandler(), localPort, String.valueOf(addrRange)); + } catch (Exception ex) { + ex.printStackTrace(); + } + + int sipPort = sipManagementProxy.getSipPort(); + SipClient sipClient = new SipClient("udp", 5060, sipPort); + sipClient.start(); + + Thread.sleep(5 * 1000); + + logger.info("Test preparation completed. Clients are connected"); + logger.info("Sending message..."); + + sender.sendRequestPdu("Simple Smpp-Sip Message", String.valueOf(addrRange), String.valueOf(sipAddrRange)); + + Thread.sleep(5 * 1000); + + assertEquals(sipClient.requests.size(), 1); + } +} + +class SmppReceiverHandler extends DefaultSmppSessionHandler { + private AtomicInteger reqReceived; + + public SmppReceiverHandler(AtomicInteger reqReceived) { + super(); + this.reqReceived = reqReceived; + } + + @Override + public PduResponse firePduRequestReceived(PduRequest pduRequest) { + if ((pduRequest instanceof EnquireLink)) { + return pduRequest.createResponse(); + } + System.out.println(System.currentTimeMillis() + " ------------------------New request recieved"); + reqReceived.incrementAndGet(); + + return pduRequest.createResponse(); + } +}