[Asterisk-java-users] re: Problem with ConnectEvent
Brought to you by:
srt
From: Brett S. <bs...@no...> - 2005-12-18 11:38:11
|
Here's a technique I use to get arround the problem of trying to send an Action when you are in an event handler. If you don't know; its simply not possible. The call to 'new RecieveFax(event)' creates its own connection to the API Manager. I do wonder whether it would be better if the MangerEventHandler method was called in a seperate thread from that which the ManagerReader runs in however that may have other undesirable side affects. Alternatively the call to SendAction should probably throw an IllegalStateException rather than just timing out. As it stand its hard to diagnose why the call to SendAction fails. Basically It's necessary to send the subsequent action in a different thread from the the eventHandler otherwise the ManagerReader locks up and nothing works. The subsequent actionn should also be sent using a separate instance of the ManagerConnection. You could potentionally send the subsequent action in the event handler thread (using a separate ManagerConnection) but you will block the ManagerReader from notifying your application of other events and I'm not certain, but I suspect that there is little to be gained from holding the ManagerReader up whilst you do other work as I doubt that Asterisk is waiting on the ManagerReader and as such you really arn't doing the operation synchronously (with respect to Asterisk). So here is a sample class demonstating one possible solution. I hope this of some use. Regards, Brett. import java.io.IOException; import java.util.TreeSet; import java.util.Vector; import java.util.concurrent.LinkedBlockingQueue; import net.sf.asterisk.manager.AuthenticationFailedException; import net.sf.asterisk.manager.ManagerConnection; import net.sf.asterisk.manager.ManagerConnectionFactory; import net.sf.asterisk.manager.ManagerEventHandler; import net.sf.asterisk.manager.TimeoutException; import net.sf.asterisk.manager.action.StatusAction; import net.sf.asterisk.manager.event.ManagerEvent; import net.sf.asterisk.manager.event.NewChannelEvent; import net.sf.asterisk.manager.event.NewStateEvent; import org.apache.commons.configuration.ConfigurationException; import org.apache.log4j.Logger; <http://sourceforge.net/mailarchive/message.php?msg_id=13870642>public class FaxManagerInbound extends Thread implements ManagerEventHandler { static Logger logger = Logger.getLogger(FaxManagerInbound.class.getName()); private static FaxManagerInbound self; private boolean running; private ManagerConnection managerConnection; private Vector<Channel> channels; private static final LinkedBlockingQueue<NewChannelEvent> queue = new LinkedBlockingQueue<NewChannelEvent>(); static public FaxManagerInbound getInstance() throws ConfigurationException, IOException, AuthenticationFailedException, TimeoutException { if (self == null) { self = new FaxManagerInbound(Configuration.getInstance() .getChannels()); self.start(); } return self; } private FaxManagerInbound(TreeSet<Channel> channels) throws IOException, AuthenticationFailedException, TimeoutException { super("FaxManager Inbound"); managerConnection = connect(); // Get the list of channels we are interested in for (Channel channel : channels) { if (channel.type == ChannelManager.ChannelType.Inbound || channel.type == ChannelManager.ChannelType.Both) { this.channels.add(channel); } } } public void run() { running = true; logger.info("Inbound FaxManager started"); while (running) { try { if (!managerConnection.isConnected()) { logger .info("Inbound Manager API Connection lost; reconnecting."); managerConnection = connect(); logger.info("Inbound Manager API: reconnected"); } NewChannelEvent event = queue.take(); new RecieveFax(event); } catch (Throwable e) { // We don't like the manager shuting down just becuase of a // problem with a single fax. logger.error(e.getMessage(), e); } } logger.info("Inbound FaxManager Stopping"); } public void shutdown() { running = false; queue.notify(); notify(); } ManagerConnection connect() throws IOException, AuthenticationFailedException, TimeoutException { ManagerConnection connection = null; ManagerConnectionFactory factory = new ManagerConnectionFactory(); connection = factory.getManagerConnection(Configuration .getAsteriskHost(), Configuration.getAsteriskUsername(), Configuration.getAsteriskPassword()); // register for events connection.addEventHandler(this); // connect to Asterisk and log in managerConnection.login(); // request channel state managerConnection.sendAction(new StatusAction()); return connection; } public void handleEvent(ManagerEvent managerEvent) { if (managerEvent instanceof NewChannelEvent) { NewChannelEvent event = (NewChannelEvent) managerEvent; System.out.println(event.getState()); if (event.getState().compareToIgnoreCase("Ringing") == 0 || (event.getState().compareToIgnoreCase("Ring") == 0)) { queue.add(event); } } else if (managerEvent instanceof NewStateEvent) { NewStateEvent event = (NewStateEvent) managerEvent; System.out.println("State:" + event.getState()); System.out.println(event); } else // just print received events System.out.println("Event: " + managerEvent); } } |