Pequeño chat JMS con ActiveMQ

De ChuWiki
Saltar a: navegación, buscar

Esto no es más que un pequeño ejemplo de uso de JMS. En concreto, bajamos y arrancamos ActiveMQ como servidor de JMS y el siguiente programita hace de cliente de Chat. Podemos arrancarlo varias veces, pero en el mismo ordenador donde corre ActiveMQ, puesto que lo busca en localhost. Debemos añadir activemq-all-5.6.0.jar en el CLASSPATH, este jar viene con ActiveMQ.

package chuidiang.ejemplos.activemq;

import java.awt.BorderLayout;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;

import javax.jms.Connection;
import javax.jms.ConnectionFactory;
import javax.jms.Destination;
import javax.jms.JMSException;
import javax.jms.MapMessage;
import javax.jms.Message;
import javax.jms.MessageConsumer;
import javax.jms.MessageListener;
import javax.jms.MessageProducer;
import javax.jms.Session;
import javax.swing.JFrame;
import javax.swing.JScrollPane;
import javax.swing.JTextArea;
import javax.swing.JTextField;

import org.apache.activemq.ActiveMQConnection;
import org.apache.activemq.ActiveMQConnectionFactory;

public class Chat {
   private MessageProducer producer;
   private String url = ActiveMQConnection.DEFAULT_BROKER_URL;

   private static String subject = "CHAT";
   private JTextField textField;
   private JTextField textFieldNombre;
   private JTextArea textArea;
   private Session session;

   public static void main(String[] args) throws JMSException {
      new Chat();
   }

   public Chat() throws JMSException {
      JFrame frame = new JFrame("chat");
      textArea = new JTextArea(15, 30);
      JScrollPane scrollPane = new JScrollPane(textArea);
      frame.getContentPane().add(scrollPane, BorderLayout.CENTER);

      textField = new JTextField(30);
      frame.getContentPane().add(textField, BorderLayout.SOUTH);

      textFieldNombre = new JTextField(30);
      frame.getContentPane().add(textFieldNombre, BorderLayout.NORTH);

      frame.pack();
      frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
      frame.setVisible(true);

      textField.addActionListener(new ActionListener() {

         @Override
         public void actionPerformed(ActionEvent e) {
            MapMessage map;
            try {
               map = session.createMapMessage();
               map.setString("usuario", textFieldNombre.getText());
               map.setString("texto", textField.getText());
               textField.setText("");
               producer.send(map);

            } catch (JMSException e1) {
               e1.printStackTrace();
            }
         }
      });

      activeMQ();
   }

   private void activeMQ() throws JMSException {
      ConnectionFactory connectionFactory = new ActiveMQConnectionFactory(url);
      Connection connection = connectionFactory.createConnection();
      connection.start();

      session = connection.createSession(false, Session.AUTO_ACKNOWLEDGE);

      // Destination represents here our queue 'TESTQUEUE' on the
      // JMS server. You don't have to do anything special on the
      // server to create it, it will be created automatically.
      Destination destination = session.createTopic(subject);

      producer = session.createProducer(destination);

      MessageConsumer consumer = session.createConsumer(destination);
      consumer.setMessageListener(new MessageListener() {

         @Override
         public void onMessage(Message message) {
            if (message instanceof MapMessage) {
               MapMessage map = (MapMessage) message;
               try {
                  String usuario = map.getString("usuario");
                  String texto = map.getString("texto");
                  textArea.append(usuario + ": " + texto + "\n");
               } catch (JMSException e) {
                  e.printStackTrace();
               }
            }

         }
      });
   }
}

En el código, unicamente fijarnos en el método activeMQ() donde se establece la conexión con el servidor JMS. Ahí se crean también el productor (el que envía los mensajes al servidor) y el consumidor (que lee los mensajes del servidor).

Arrancando varias veces obtenemos algo como en la siguiente figura. El el JTextField superior ponemos el nombre de usuario que queramos y en el JTextField inferior escribimos el texto que queramos enviar y pulsamos enter. En el actionListener() del JTextField se envía el mensaje usando el productor. En el consumidor hemos añadido un MessageListener encargado de recibir el mensaje y pintarlo en el JTextArea.


Chat-jms.png