« Flex 2 Remoting | Main | Adding notes..... »

February 06, 2006

Updating DataService Manged Data with non-Flex Clients

One issue when building Flex 2 application is how do you leverage the Data Service features of FES when your data store is updated with a process other then a Flex client. The best way to accomplish this today is to use JMS to listen for an broadcast a change notification to all Flex clients to update their data. In this configuration, each Flex client listen to a JMS queue (using a message consumer) and call fill() when you receive a message that the queue is updated. The JMS queue is notified of a change by the external application that updateds the data. Simple as that!

To illustrate this, I've written up a simple example using the FES Sample application the Contact Manager.

Below is the JSP code that will add a name to the Contact Manager data store and send a message to a JSP topic.

<%@ page import="samples.contact.Contact,
samples.contact.ContactDAO,
java.util.Properties,
javax.naming.Context,
javax.naming.InitialContext,
javax.jms.*"%>
<%
/*

Add a name to the contact data base using the DAO. In a real world application this would be done in a transaction and the
mesage to upate would be sent only when the update is successful.

*/

Contact myContact = new Contact();
myContact.setFirstName("Eric");
myContact.setLastName( "Anderson" );

ContactDAO myDAO = new ContactDAO();
myDAO.create(myContact);
%>

<%

/*

Publish a message to a JMS queue that will key the client to update its data

*/

TopicSession _pubSession = null;
TopicSession _subSession = null;
TopicPublisher _publisher = null;
TopicConnection _connection = null;

String _providerurl = "127.0.0.1:2907";
String _ctxtFactory = "jrun.naming.JRunContextFactory";

Properties p = new Properties();
p.put(Context.PROVIDER_URL, _providerurl);
p.put(Context.INITIAL_CONTEXT_FACTORY, _ctxtFactory);
p.put(Context.SECURITY_PRINCIPAL, "admin");
p.put(Context.SECURITY_CREDENTIALS , "admin");
Context context = new InitialContext(p);
TopicConnectionFactory factory = (TopicConnectionFactory) context.lookup("jms/flex/TopicConnectionFactory");
_connection = factory.createTopicConnection();
_pubSession = _connection.createTopicSession(false, Session.AUTO_ACKNOWLEDGE);
_subSession = _connection.createTopicSession(false, Session.AUTO_ACKNOWLEDGE);
Topic topic = (Topic) context.lookup("jms/topic/flex/simpletopic");
_publisher = _pubSession.createPublisher(topic);
TopicSubscriber subscriber=_subSession.createSubscriber(topic);
_connection.start();

ObjectMessage message = _pubSession.createObjectMessage();
message.setStringProperty("userId", "");
message.setStringProperty("msg", "");
_publisher.publish(message, Message.DEFAULT_DELIVERY_MODE, Message.DEFAULT_PRIORITY, 5 * 60 * 1000);
%>

Now, all you need to do in your contactmgr.mxml is to add a message consumer as so:

<mx:Consumer id="consumer" destination="chat-topic-jms" message="getLatestData()"/>

Make sure that you call consumer.subscribe() so that the client will listen for messages.

Lastly, add the function getLatestData() which will call fill on the DataService.

public function getLatestData():void {
ds.fill(contacts, new Array());
}

Now, you should be able to update the data store with a JSP page and your Flex client will update itself without any polling needed.

Posted by eanderson at February 6, 2006 02:31 PM

Comments