Package org.mobicents.slee.service.admin

Source Code of org.mobicents.slee.service.admin.AdminSbb

/*
* ***************************************************
*                                                 *
*  Mobicents: The Open Source JSLEE Platform      *
*                                                 *
*  Distributable under LGPL license.              *
*  See terms of license at gnu.org.               *
*                                                 *
***************************************************
*/
package org.mobicents.slee.service.admin;

import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.text.ParseException;
import java.util.HashMap;
import java.util.Properties;

import javax.jms.Connection;
import javax.jms.ConnectionFactory;
import javax.jms.JMSException;
import javax.jms.MessageProducer;
import javax.jms.Queue;
import javax.jms.TextMessage;
import javax.naming.Context;
import javax.naming.InitialContext;
import javax.naming.NamingException;
import javax.persistence.EntityManager;
import javax.sip.ClientTransaction;
import javax.sip.Dialog;
import javax.sip.InvalidArgumentException;
import javax.sip.RequestEvent;
import javax.sip.SipException;
import javax.sip.TransactionUnavailableException;
import javax.sip.address.Address;
import javax.sip.header.CallIdHeader;
import javax.sip.header.Header;
import javax.sip.message.Request;
import javax.slee.ActivityContextInterface;
import javax.slee.ChildRelation;
import javax.slee.CreateException;
import javax.slee.InitialEventSelector;
import javax.slee.SbbContext;
import javax.slee.UnrecognizedActivityException;
import javax.slee.facilities.TimerEvent;
import javax.slee.facilities.TimerFacility;
import javax.slee.facilities.TimerID;
import javax.slee.facilities.TimerOptions;

import org.apache.log4j.Logger;
import org.mobicents.mscontrol.MsConnection;
import org.mobicents.mscontrol.MsLink;
import org.mobicents.mscontrol.MsLinkEvent;
import org.mobicents.mscontrol.MsNotifyEvent;
import org.mobicents.mscontrol.MsProvider;
import org.mobicents.mscontrol.MsSignalDetector;
import org.mobicents.mscontrol.MsSignalGenerator;
import org.mobicents.mscontrol.signal.Announcement;
import org.mobicents.mscontrol.signal.Basic;
import org.mobicents.seam.Order;
import org.mobicents.slee.resource.media.ratype.MediaRaActivityContextInterfaceFactory;
import org.mobicents.slee.resource.persistence.ratype.PersistenceResourceAdaptorSbbInterface;
import org.mobicents.slee.resource.tts.ratype.TTSSession;
import org.mobicents.slee.service.callcontrol.CallControlSbbLocalObject;
import org.mobicents.slee.service.common.CommonSbb;
import org.mobicents.slee.service.events.CustomEvent;
import org.mobicents.slee.util.Session;
import org.mobicents.slee.util.SessionAssociation;

/**
* @author amit bhayani
*/
public abstract class AdminSbb extends CommonSbb {

  private Logger logger = Logger.getLogger(AdminSbb.class);

  private TimerFacility timerFacility = null;

  private PersistenceResourceAdaptorSbbInterface persistenceResourceAdaptorSbbInterface = null;

  private String pathToAudioDirectory = null;

  String audioFilePath = null;

  String callerSip = null;

  String adminSip = null;

  long waitingTime = 0;

  private MsProvider msProvider;

  private MediaRaActivityContextInterfaceFactory mediaAcif;

  /** Creates a new instance of SecondBounceSbb */
  public AdminSbb() {
    super();
  }

  public void setSbbContext(SbbContext sbbContext) {
    super.setSbbContext(sbbContext);
    try {
      Context ctx = (Context) new InitialContext()
          .lookup("java:comp/env");

      audioFilePath = (String) ctx.lookup("audioFilePath");

      pathToAudioDirectory = "file:"
          + (String) ctx.lookup("pathToAudioDirectory");

      callerSip = (String) ctx.lookup("callerSip");

      adminSip = (String) ctx.lookup("adminSip");

      waitingTime = ((Long) ctx.lookup("waitingTiming")).longValue();

      // Getting Timer Facility interface
      timerFacility = (TimerFacility) ctx.lookup("slee/facilities/timer");

      persistenceResourceAdaptorSbbInterface = (PersistenceResourceAdaptorSbbInterface) ctx
          .lookup("slee/resources/pra/0.1/provider");

      msProvider = (MsProvider) ctx
          .lookup("slee/resources/media/1.0/provider");

      mediaAcif = (MediaRaActivityContextInterfaceFactory) ctx
          .lookup("slee/resources/media/1.0/acifactory");

    } catch (NamingException ne) {
      logger.error("Could not set SBB context: " + ne.toString(), ne);
    }
  }

  public void onOrderPlaced(CustomEvent event, ActivityContextInterface ac) {
    System.out
        .println("****** AdminSbb Recieved org.mobicents.slee.service.sfdemo.ORDER_PLACED ******* ");
    logger.info("AdminSbb: " + this
        + ": received an ORDER_PLACED event. OrderId = "
        + event.getOrderId() + ". ammount = " + event.getAmmount()
        + ". Customer Name = " + event.getCustomerName());

    this.setCustomEvent(event);

    TTSSession ttsSession = getTTSProvider().getNewTTSSession(
        audioFilePath, "kevin16");

    StringBuffer stringBuffer = new StringBuffer();
    stringBuffer.append(event.getCustomerName());
    stringBuffer.append(" has placed an order of $");
    stringBuffer.append(event.getAmmount());
    stringBuffer.append(". Press 1 to approve and 2 to reject.");

    ttsSession.textToAudioFile(stringBuffer.toString());
    this.setSfDemo(true);
    this.setSendBye(false);
    makeCall();

  }

  public void onOrderCancelled(CustomEvent event, ActivityContextInterface ac) {
    logger.info("****** AdminSbb Recieved ORDER_CANCELLED ******");
    if (this.getTimerID() != null)
      timerFacility.cancelTimer(this.getTimerID());
    ac.detach(getSbbContext().getSbbLocalObject());
  }

  public void onOrderRejected(CustomEvent event, ActivityContextInterface ac) {

    logger.info("****** AdminSbb Recieved ORDER_REJECTED ******* ");
    timerFacility.cancelTimer(this.getTimerID());
    ac.detach(getSbbContext().getSbbLocalObject());
  }

  public void onOrderApproved(CustomEvent event, ActivityContextInterface ac) {

    logger.info("****** AdminSbb Recieved ORDER_APPROVED ******* ");
    timerFacility.cancelTimer(this.getTimerID());
    ac.detach(getSbbContext().getSbbLocalObject());
  }

  public void onBeforeOrderProcessed(CustomEvent event,
      ActivityContextInterface ac) {
    System.out
        .println("****** AdminSbb Recieved BEFORE_ORDER_PROCESSED ******* ");
    logger.info("AdminSbb: " + this
        + ": received an ORDER_PLACED event. OrderId = "
        + event.getOrderId() + ". ammount = " + event.getAmmount()
        + ". Customer Name = " + event.getCustomerName());

    this.setCustomEvent(event);

    TTSSession ttsSession = getTTSProvider().getNewTTSSession(
        audioFilePath, "kevin16");

    StringBuffer stringBuffer = new StringBuffer();
    stringBuffer.append(event.getCustomerName());
    stringBuffer.append(" has placed an order of $");
    stringBuffer.append(event.getAmmount());
    stringBuffer.append(". Press 1 to approve and 2 to reject.");

    ttsSession.textToAudioFile(stringBuffer.toString());

    setTimer(ac);
  }

  public void onTimerEvent(TimerEvent event, ActivityContextInterface aci) {
    makeCall();
  }

  /**
   * This method sets the Timer Object for passed ACI
   *
   * @param ac
   */
  private void setTimer(ActivityContextInterface ac) {
    TimerOptions options = new TimerOptions();
    options.setPersistent(true);

    // Set the timer on ACI
    TimerID timerID = this.timerFacility.setTimer(ac, null, System
        .currentTimeMillis()
        + waitingTime, options);

    this.setTimerID(timerID);
  }

  private void makeCall() {

    try {
      // Set the caller address to the address of our call controller
      Address callerAddress = getSipUtils()
          .convertURIToAddress(callerSip);
      callerAddress.setDisplayName(callerSip);

      // Retrieve the callee addresses from the event
      Address calleeAddress = getSipUtils().convertURIToAddress(adminSip);

      // Build the INVITE request
      Request request = getSipUtils().buildInvite(callerAddress,
          calleeAddress, null, 1);

      // Create a new transaction based on the generated request
      ClientTransaction ct = getSipProvider().getNewClientTransaction(
          request);

      Header h = ct.getRequest().getHeader(CallIdHeader.NAME);
      String calleeCallId = ((CallIdHeader) h).getCallId();

      SessionAssociation sa = new SessionAssociation(
          "org.mobicents.slee.service.callcontrol.CallControlSbb$InitialState");

      Session calleeSession = new Session(calleeCallId);
      calleeSession.setSipAddress(calleeAddress);
      calleeSession.setToBeCancelledClientTransaction(ct);

      // The dialog for the client transaction in which the INVITE is sent
      Dialog dialog = ct.getDialog();
      if (dialog != null && logger.isDebugEnabled()) {
        logger
            .debug("Obtained dialog from ClientTransaction : automatic dialog support on");
      }
      if (dialog == null) {
        // Automatic dialog support turned off
        try {
          dialog = getSipProvider().getNewDialog(ct);
          if (logger.isDebugEnabled()) {
            logger
                .debug("Obtained dialog for INVITE request to callee with getNewDialog");
          }
        } catch (Exception e) {
          logger.error("Error getting dialog", e);
        }
      }

      if (logger.isDebugEnabled()) {
        logger
            .debug("Obtained dialog in onThirdPCCTriggerEvent : callId = "
                + dialog.getCallId().getCallId());
      }
      // Get activity context from factory
      ActivityContextInterface sipACI = getSipActivityContextInterfaceFactory()
          .getActivityContextInterface(dialog);

      ActivityContextInterface clientSipACI = getSipActivityContextInterfaceFactory()
          .getActivityContextInterface(ct);

      calleeSession.setDialog(dialog);
      sa.setCalleeSession(calleeSession);

      Session callerSession = new Session();

      // Create a new caller address from caller URI specified in the
      // event (the real caller address)
      // since we need this in the next INVITE.
      callerAddress = getSipUtils().convertURIToAddress(callerSip);
      callerSession.setSipAddress(callerAddress);
      // Since we don't have the client transaction for the caller yet,
      // just set the to be cancelled client transaction to null.
      callerSession.setToBeCancelledClientTransaction(null);
      sa.setCallerSession(callerSession);

      // put the callId for the callee dialog in the cache
      getCacheUtility().put(calleeCallId, sa);

      ChildRelation relation = getCallControlSbbChild();
      // Create child SBB
      CallControlSbbLocalObject child = (CallControlSbbLocalObject) relation
          .create();

      setChildSbbLocalObject(child);

      child.setParent(getSbbContext().getSbbLocalObject());

      // Attach child SBB to the activity context
      sipACI.attach(child);
      clientSipACI.attach(child);
      sipACI.attach(this.getSbbContext().getSbbLocalObject());
      // Send the INVITE request
      ct.sendRequest();

    } catch (ParseException parExc) {
      logger.error("Parse Exception while parsing the callerAddess",
          parExc);
    } catch (InvalidArgumentException invalidArgExcep) {
      logger.error(
          "InvalidArgumentException while building Invite Request",
          invalidArgExcep);
    } catch (TransactionUnavailableException tranUnavExce) {
      logger
          .error(
              "TransactionUnavailableException when trying to getNewClientTransaction",
              tranUnavExce);
    } catch (UnrecognizedActivityException e) {
      // TODO Auto-generated catch block
      logger
          .error(
              "UnrecognizedActivityException when trying to getActivityContextInterface",
              e);
    } catch (CreateException creaExce) {
      logger.error("CreateException while trying to create Child",
          creaExce);
    } catch (SipException sipExec) {
      logger.error("SipException while trying to send INVITE Request",
          sipExec);
    }
  }

  public void onLinkReleased(MsLinkEvent evt, ActivityContextInterface aci) {
    logger.info("-----onLinkReleased-----");
    aci.detach(getSbbContext().getSbbLocalObject());
    if (this.getSendBye()) {
      getChildSbbLocalObject().sendBye();
    }
  }

  public void onAnnouncementComplete(MsNotifyEvent evt,
      ActivityContextInterface aci) {
    logger.info("Announcement complete: ");
    if (this.getSendBye()) {
      MsLink link = this.getLink();
      link.release();
    }
  }

  public void onInfoEvent(RequestEvent request, ActivityContextInterface aci) {
    System.out.println("onInfoEvent received");
    try {
      getSipUtils().sendStatefulOk(request);
    } catch (Exception e) {
      e.printStackTrace();
    }

    Properties p = new Properties();
    try {
      p.load(new ByteArrayInputStream(request.getRequest()
          .getRawContent()));
    } catch (IOException e) {
      // TODO Auto-generated catch block
      e.printStackTrace();
    }

    String dtmf = p.getProperty("Signal");
    System.out.println("The Dtmf is " + dtmf);

    int cause = Integer.parseInt(dtmf);

    EntityManager mgr = null;
    Order order = null;
    boolean successful = false;
    String audioFile = null;

    String destinationName = "/queue/B";

    InitialContext ic = null;
    ConnectionFactory cf = null;
    Connection jmsConnection = null;

    switch (cause) {
    case Basic.CAUSE_DIGIT_1:
      audioFile = pathToAudioDirectory + "OrderApproved.wav";
      if (this.getSfDemo()) {
        System.out.println("Lookup the Queue and put value");
        try {
          ic = new InitialContext();

          cf = (ConnectionFactory) ic.lookup("/ConnectionFactory");
          Queue queue = (Queue) ic.lookup(destinationName);
          logger.info("Queue " + destinationName + " exists");

          jmsConnection = cf.createConnection();
          javax.jms.Session jmsSession = jmsConnection.createSession(
              false, javax.jms.Session.AUTO_ACKNOWLEDGE);
          MessageProducer sender = jmsSession.createProducer(queue);

          TextMessage message = jmsSession.createTextMessage(this
              .getCustomEvent().getOrderId()
              + ",1");
          sender.send(message);
          logger.info("The message was successfully sent to the "
              + queue.getQueueName() + " queue");

        } catch (Exception e) {
          logger.error("Exception while trying to send message", e);
        } finally {
          if (ic != null) {
            try {
              ic.close();
            } catch (Exception e) {
              logger.error("Exception while closing the IC", e);
            }
          }
          try {
            if (jmsConnection != null) {
              jmsConnection.close();
            }
          } catch (JMSException jmse) {
            logger.error("Could not close connection "
                + jmsConnection + " exception was " + jmse,
                jmse);
          }
        }

      } else {
        mgr = this.persistenceResourceAdaptorSbbInterface
            .createEntityManager(new HashMap(), "custom-pu");

        order = (Order) mgr.createQuery(
            "select o from Order o where o.orderId = :orderId")
            .setParameter("orderId",
                this.getCustomEvent().getOrderId())
            .getSingleResult();

        order.setStatus(Order.Status.PROCESSING);

        mgr.flush();
        mgr.close();
      }
      successful = true;
      break;
    case Basic.CAUSE_DIGIT_2:
      audioFile = pathToAudioDirectory + "OrderCancelled.wav";
      if (this.getSfDemo()) {
        System.out.println("Lookup the Queue and put value");
        try {
          ic = new InitialContext();

          cf = (ConnectionFactory) ic.lookup("/ConnectionFactory");
          Queue queue = (Queue) ic.lookup(destinationName);
          logger.info("Queue " + destinationName + " exists");

          jmsConnection = cf.createConnection();
          javax.jms.Session jmsSession = jmsConnection.createSession(
              false, javax.jms.Session.AUTO_ACKNOWLEDGE);
          MessageProducer sender = jmsSession.createProducer(queue);

          TextMessage message = jmsSession.createTextMessage(this
              .getCustomEvent().getOrderId()
              + ",2");
          sender.send(message);
          logger.info("The message was successfully sent to the "
              + queue.getQueueName() + " queue");

        } catch (Exception e) {
          logger.error("Exception while trying to send message", e);
        } finally {
          if (ic != null) {
            try {
              ic.close();
            } catch (Exception e) {
              logger.error("Exception while closing the IC", e);
            }
          }
          try {
            if (jmsConnection != null) {
              jmsConnection.close();
            }
          } catch (JMSException jmse) {
            logger.error("Could not close connection "
                + jmsConnection + " exception was " + jmse,
                jmse);
          }
        }

      } else {
        mgr = this.persistenceResourceAdaptorSbbInterface
            .createEntityManager(new HashMap(), "custom-pu");

        order = (Order) mgr.createQuery(
            "select o from Order o where o.orderId = :orderId")
            .setParameter("orderId",
                this.getCustomEvent().getOrderId())
            .getSingleResult();

        order.setStatus(Order.Status.CANCELLED);

        mgr.flush();
        mgr.close();
      }
      successful = true;

      break;
    default:
      audioFile = pathToAudioDirectory + "AdminReConfirm.wav";

      break;
    }
    this.setSendBye(successful);

    MsSignalGenerator generator = msProvider.getSignalGenerator(this
        .getAnnouncementEndpointName());

    try {
      ActivityContextInterface generatorActivity = mediaAcif
          .getActivityContextInterface(generator);
      generatorActivity.attach(getSbbContext().getSbbLocalObject());

      generator.apply(Announcement.PLAY, new String[] { audioFile });

      // this.initDtmfDetector(getConnection(), this.getEndpointName());
    } catch (UnrecognizedActivityException e) {
      e.printStackTrace();
    }
  }

  public void onLinkCreated(MsLinkEvent evt, ActivityContextInterface aci) {
    logger.info("--------onLinkCreated------------");
    MsLink link = evt.getSource();
    String announcementEndpoint = link.getEndpoints()[1];

    String endpointName = null;
    if (this.getEndpointName() == null) {
      this.setEndpointName(link.getEndpoints()[0]);
    }

    if (this.getAnnouncementEndpointName() == null) {
      this.setAnnouncementEndpointName(announcementEndpoint);
    }

    endpointName = this.getEndpointName();

    logger.info("endpoint name: " + endpointName);
    logger.info("Announcement endpoint: " + announcementEndpoint);

    MsSignalGenerator generator = msProvider
        .getSignalGenerator(announcementEndpoint);

    try {
      ActivityContextInterface generatorActivity = mediaAcif
          .getActivityContextInterface(generator);
      generatorActivity.attach(getSbbContext().getSbbLocalObject());

      String announcementFile = "file:" + audioFilePath;
      generator.apply(Announcement.PLAY,
          new String[] { announcementFile });

      this.initDtmfDetector(getConnection(), endpointName);

    } catch (UnrecognizedActivityException e) {
      e.printStackTrace();
    }

  }

  public MsLink getLink() {
    ActivityContextInterface[] activities = getSbbContext().getActivities();
    for (int i = 0; i < activities.length; i++) {
      if (activities[i].getActivity() instanceof MsLink) {
        return (MsLink) activities[i].getActivity();
      }
    }
    return null;
  }

  private MsConnection getConnection() {
    ActivityContextInterface[] activities = getSbbContext().getActivities();
    for (int i = 0; i < activities.length; i++) {
      if (activities[i].getActivity() instanceof MsConnection) {
        return (MsConnection) activities[i].getActivity();
      }
    }
    return null;
  }

  private void initDtmfDetector(MsConnection connection, String endpointName) {
    MsSignalDetector dtmfDetector = msProvider
        .getSignalDetector(endpointName);
    try {
      ActivityContextInterface dtmfAci = mediaAcif
          .getActivityContextInterface(dtmfDetector);
      dtmfAci.attach(getSbbContext().getSbbLocalObject());
      dtmfDetector.receive(Basic.DTMF, connection, new String[] {});
    } catch (UnrecognizedActivityException e) {
      e.printStackTrace();
    }
  }

  public InitialEventSelector orderIdSelect(InitialEventSelector ies) {
    Object event = ies.getEvent();
    long orderId = 0;
    if (event instanceof CustomEvent) {
      orderId = ((CustomEvent) event).getOrderId();
    } else {
      // If something else, use activity context.
      ies.setActivityContextSelected(true);
      return ies;
    }
    // Set the convergence name
    if (logger.isDebugEnabled()) {
      logger.debug("Setting convergence name to: " + orderId);
    }
    ies.setCustomName(String.valueOf(orderId));
    return ies;
  }

  // child relation
  public abstract ChildRelation getCallControlSbbChild();

  // 'timerID' CMP field setter
  public abstract void setTimerID(TimerID value);

  // 'timerID' CMP field getter
  public abstract TimerID getTimerID();

  public abstract void setCustomEvent(CustomEvent customEvent);

  public abstract CustomEvent getCustomEvent();

  public abstract void setSendBye(boolean isBye);

  public abstract boolean getSendBye();

  public abstract void setOrderApproved(boolean fireOrderApproved);

  public abstract boolean getOrderApproved();

  public abstract void setEndpointName(String endPoint);

  public abstract String getEndpointName();

  public abstract void setSfDemo(boolean sfDemo);

  public abstract boolean getSfDemo();

  public abstract void setAnnouncementEndpointName(String endPoint);

  public abstract String getAnnouncementEndpointName();

  public abstract void setChildSbbLocalObject(
      CallControlSbbLocalObject childSbbLocalObject);

  public abstract CallControlSbbLocalObject getChildSbbLocalObject();

}
TOP

Related Classes of org.mobicents.slee.service.admin.AdminSbb

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.