@Override public void onReceive(final Object message) throws Exception { final Class<?> klass = message.getClass(); final State state = fsm.state(); final ActorRef sender = sender(); final ActorRef source = self(); if (logger.isInfoEnabled()) { logger.info(" ********** UssdInterpreter's Current State: " + state.toString()); logger.info(" ********** UssdInterpreter's Processing Message: " + klass.getName()); } if (StartInterpreter.class.equals(klass)) { ussdCall = ((StartInterpreter) message).resource(); fsm.transition(message, acquiringCallInfo); } else if (message instanceof SipServletRequest) { SipServletRequest request = (SipServletRequest) message; String method = request.getMethod(); if ("INFO".equalsIgnoreCase(method)) { fsm.transition(message, processingInfoRequest); } else if ("ACK".equalsIgnoreCase(method)) { fsm.transition(message, downloadingRcml); } else if ("BYE".equalsIgnoreCase(method)) { fsm.transition(message, disconnecting); } else if ("CANCEL".equalsIgnoreCase(method)) { fsm.transition(message, cancelling); } } else if (CallStateChanged.class.equals(klass)) { final CallStateChanged event = (CallStateChanged) message; callState = event.state(); if (CallStateChanged.State.RINGING == event.state()) { if (logger.isInfoEnabled()) { logger.info("CallStateChanged.State.RINGING"); } } else if (CallStateChanged.State.IN_PROGRESS == event.state()) { if (logger.isInfoEnabled()) { logger.info("CallStateChanged.State.IN_PROGRESS"); } } else if (CallStateChanged.State.NO_ANSWER == event.state() || CallStateChanged.State.COMPLETED == event.state() || CallStateChanged.State.FAILED == event.state() || CallStateChanged.State.CANCELED == event.state()) { if (logger.isInfoEnabled()) { logger.info( "CallStateChanged.State.NO_ANSWER OR CallStateChanged.State.COMPLETED OR CallStateChanged.State.FAILED or CallStateChanged.State.CANCELED"); } fsm.transition(message, finished); } else if (CallStateChanged.State.BUSY == event.state()) { if (logger.isInfoEnabled()) { logger.info("CallStateChanged.State.BUSY"); } } // else if (CallStateChanged.State.COMPLETED == event.state()) { // logger.info("CallStateChanged.State.Completed"); // fsm.transition(message, finished); // } } else if (CallResponse.class.equals(klass)) { if (acquiringCallInfo.equals(state)) { @SuppressWarnings("unchecked") final CallResponse<CallInfo> response = (CallResponse<CallInfo>) message; // Check from whom is the message (initial call or outbound call) and update info // accordingly if (sender == ussdCall) { callInfo = response.get(); } else { outboundCallInfo = response.get(); } final String direction = callInfo.direction(); if ("inbound".equals(direction)) { ussdCall.tell(new Answer(callInfo.sid()), source); // fsm.transition(message, downloadingRcml); } else { fsm.transition(message, downloadingRcml); // fsm.transition(message, initializingCall); } } } else if (DownloaderResponse.class.equals(klass)) { final DownloaderResponse response = (DownloaderResponse) message; if (response.succeeded() && HttpStatus.SC_OK == response.get().getStatusCode()) { if (logger.isDebugEnabled()) { logger.debug( "Rcml URI : " + response.get().getURI() + "response succeeded " + response.succeeded() + ", statusCode " + response.get().getStatusCode()); } fsm.transition(message, ready); } else if (response.succeeded() && HttpStatus.SC_NOT_FOUND == response.get().getStatusCode()) { fsm.transition(message, notFound); } else { if (downloadingRcml.equals(state)) { if (fallbackUrl != null) { fsm.transition(message, downloadingFallbackRcml); } else { fsm.transition(message, finished); } } else { fsm.transition(message, finished); } } } else if (ParserFailed.class.equals(klass)) { if (logger.isInfoEnabled()) { logger.info("ParserFailed received. Will stop the call"); } fsm.transition(message, cancelling); } else if (Tag.class.equals(klass)) { final Tag verb = (Tag) message; if (ussdLanguage.equals(verb.name())) { if (ussdLanguageTag == null) { ussdLanguageTag = verb; final GetNextVerb next = GetNextVerb.instance(); parser.tell(next, source); } else { // We support only one Language element invalidVerb(verb); } return; } else if (ussdMessage.equals(verb.name())) { ussdMessageTags.add(verb); final GetNextVerb next = GetNextVerb.instance(); parser.tell(next, source); return; } else if (ussdCollect.equals(verb.name())) { if (ussdCollectTag == null) { ussdCollectTag = verb; final GetNextVerb next = GetNextVerb.instance(); parser.tell(next, source); } else { // We support only one Collect element invalidVerb(verb); } return; } else { invalidVerb(verb); } } else if (End.class.equals(klass)) { fsm.transition(message, preparingMessage); } }
// FSM logic. @Override public void onReceive(final Object message) throws Exception { final Class<?> klass = message.getClass(); final State state = fsm.state(); final ActorRef sender = sender(); if (logger.isInfoEnabled()) { logger.info( "********** Media Group " + self().path() + " Current State: \"" + state.toString()); logger.info( "********** Media Group " + self().path() + " Processing Message: \"" + klass.getName() + " sender : " + sender.getClass()); } if (Observe.class.equals(klass)) { observe(message); } else if (StopObserving.class.equals(klass)) { stopObserving(message); } else if (MediaGroupStatus.class.equals(klass)) { if (active.equals(state)) { sender().tell(new MediaGroupStateChanged(MediaGroupStateChanged.State.ACTIVE), self()); } else { sender().tell(new MediaGroupStateChanged(MediaGroupStateChanged.State.INACTIVE), self()); } } else if (StartMediaGroup.class.equals(klass)) { if (logger.isInfoEnabled()) { logger.info( "MediaGroup: " + self().path() + " got StartMediaGroup from: " + sender().path() + " endpoint: " + endpoint.path() + " isTerminated: " + endpoint.isTerminated()); } fsm.transition(message, acquiringIvr); } else if (Join.class.equals(klass)) { fsm.transition(message, acquiringInternalLink); } else if (MediaGatewayResponse.class.equals(klass)) { if (acquiringIvr.equals(state)) { fsm.transition(message, acquiringLink); } else if (acquiringLink.equals(state)) { fsm.transition(message, initializingLink); } else if (acquiringInternalLink.equals(state)) { fsm.transition(message, initializingInternalLink); } } else if (LinkStateChanged.class.equals(klass)) { final LinkStateChanged response = (LinkStateChanged) message; if (LinkStateChanged.State.CLOSED == response.state()) { if (initializingLink.equals(state)) { fsm.transition(message, openingLink); } else if (openingLink.equals(state) || deactivating.equals(state) || updatingLink.equals(state)) { fsm.transition(message, inactive); } if (initializingInternalLink.equals(state)) { fsm.transition(message, openingInternalLink); } } else if (LinkStateChanged.State.OPEN == response.state()) { if (openingLink.equals(state)) { fsm.transition(message, updatingLink); } else if (updatingLink.equals(state)) { fsm.transition(message, active); } if (openingInternalLink.equals(state)) { fsm.transition(message, updatingInternalLink); } if (updatingInternalLink.equals(state)) { fsm.transition(message, active); } } } else if (StopMediaGroup.class.equals(klass)) { if (acquiringLink.equals(state) || initializingLink.equals(state)) { fsm.transition(message, inactive); } else if (active.equals(state) || openingLink.equals(state) || updatingLink.equals(state)) { fsm.transition(message, deactivating); } } else if (EndpointStateChanged.class.equals(klass)) { onEndpointStateChanged((EndpointStateChanged) message, self(), sender); } else if (active.equals(state)) { if (Play.class.equals(klass)) { play(message); } else if (Collect.class.equals(klass)) { collect(message); } else if (Record.class.equals(klass)) { record(message); } else if (Stop.class.equals(klass)) { stop(lastEvent); // Send message to originator telling media group has been stopped // Needed for call bridging scenario, where inbound call must stop // ringing before attempting to perform join operation. sender().tell(new MediaGroupResponse<String>("stopped"), self()); } else if (IvrEndpointResponse.class.equals(klass)) { notification(message); } } else if (ivrInUse) { if (Stop.class.equals(klass)) { stop(lastEvent); } } }