Hi, In this article, my aim is to create an application which uses the concept of Hibernate in Servlet with Ajax support of Jquery.
Below figure can give you the idea of final look and feel of the complete application:
DataBase:
Here I am using the MySQL Database for saving the messages entered by the users:
Copy below code to create the table in database named “test”.
DROP TABLE IF EXISTS `test`.`chatmessage`; CREATE TABLE `test`.`chatmessage` ( `Id` int(10) unsigned NOT NULL AUTO_INCREMENT, `Message` varchar(4000) NOT NULL, `userName` varchar(100) NOT NULL, `MsgTime` varchar(45) NOT NULL, `colorSelected` varchar(45) NOT NULL, PRIMARY KEY (`Id`) ) ENGINE=InnoDB AUTO_INCREMENT=400 DEFAULT CHARSET=latin1;
Hibernate:
Now, start with the hibernate part of the code.
Create the POJO (Plain Old Java Object), which mapps the table “chatmessage” to the object in our application.
package com.G2.pojo; import java.text.DateFormat; import java.text.SimpleDateFormat; import java.util.Date; public class ChatMessage { private String Message; private String userName; private String MsgTime; private Long Id; private String colorSelected; public String getColorSelected() { return colorSelected; } public void setColorSelected(String colorSelected) { this.colorSelected = colorSelected; } public String getMessage() { return Message; } public void setMessage(String message) { Message = message; } public String getUserName() { return userName; } public void setUserName(String userName) { this.userName = userName; } public Long getId() { return Id; } public void setId(Long id) { Id = id; } public String getMsgTime() { DateFormat dateFormat = new SimpleDateFormat("yyyy/MM/dd HH:mm:ss"); Date date = new Date(); return dateFormat.format(date); } public void setMsgTime(String msgTime) { MsgTime = msgTime; } }
After creating the POJO class, create the hibernate configuration file, from which the application will come to know that how to map the table’s column from database to the class members, database name and so on. The hibernate configuration file name must be “hibernate.cfg.xml“ and it should reside at the root of source code.
Code of hibernate.cfg.xml:
<?xml version='1.0' encoding='utf-8'?> <!DOCTYPE hibernate-configuration PUBLIC "-//Hibernate/Hibernate Configuration DTD//EN" "http://hibernate.sourceforge.net/hibernate-configuration-3.0.dtd"> <hibernate-configuration> <session-factory name="java:hibernate/SessionFactory"> <property name="hibernate.connection.driver_class"> com.mysql.jdbc.Driver</property> <property name="hibernate.connection.url"> jdbc:mysql://localhost/test</property> <property name="hibernate.connection.username"> username</property> <property name="hibernate.connection.password"> pwd</property> <property name="hibernate.connection.pool_size"> 10</property> <property name="show_sql"> true</property> <property name="dialect"> org.hibernate.dialect.MySQLDialect</property> <property name="hibernate.hbm2ddl.auto"> update</property> <!-- Mapping files --> <mapping resource="ChatMessage.hbm.xml"/> </session-factory> </hibernate-configuration>
To keep the code simple, normally I add different configurations for different classes in hibernate.
What is the need of dialect in hibernate:
Databases implement subtle differences in the SQL they use. Things such as data types for example vary across databases Or database specific functionality – selecting the top n rows is different depending on the database. The dialect abstracts this so you don’t have to worry about it. In short the dialect property internally creates the highly optimized query for underlying database.
Here also, as you can see, I have included file ChatMessage.hbm.xml file.
Code of ChatMessage.hbm.xml:
<?xml version="1.0"?> <!DOCTYPE hibernate-mapping PUBLIC "-//Hibernate/Hibernate Mapping DTD 3.0//EN" "http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd"> <hibernate-mapping default-lazy="false"> <class name="com.G2.pojo.ChatMessage" table="chatmessage"> <id name="id" type="long" column="Id"> <generator class="identity" /> </id> <property name="Message"> <column name="Message" /> </property> <property name="userName"> <column name="userName" /> </property> <property name="MsgTime"> <column name="MsgTime" /> </property> <property name="colorSelected"> <column name="colorSelected" /> </property> </class> </hibernate-mapping>
UI Part of the application:
For the UI, I have written lots of css classes, this is not possible to write complete code here. Please check the code from download link provided at the bottom of the article.
UI of the chat window is created to give the feel of the Gmail chat application as shown in below image:
Here, find the javascript code, which is responsible to send the AJAX request to the servlet, and getting back the response code:
<script type="text/javascript"> var uEnteredName = prompt("Please Enter Your Name"); $("#chat_Header").html(uEnteredName); $("#msg").focus(); function openEmot() { var $ele = $("#emoticons"); var visibility = $ele.css('display'); if(visibility == 'none') { $ele.show(); } else{ $ele.hide(); } } function smileyCode(iconCode) { var $msgEle = $("#msg"); $msgEle.val($msgEle.val() + iconCode); var $ele = $("#emoticons"); $ele.hide(); $msgEle.focus(); } function saveChats() { var uName = $("#chat_Header").html(); if (uName == '') { alert('Please enter your name '); return false; } var msg = $("#msg").val(); //var oldMsg = $("#chat-area").html(); var colorCode = $('input[name=nameColor]:checked', '#send-message-area') .val(); $.ajax( { type : "POST", data : "uName=" + uName + "&msg=" + msg + "&colorCode=" + colorCode, url : "Chatprocess.do", error : function(xhr, ajaxOptions, thrownError) { alert(xhr.status); alert(thrownError); }, success : function(data) { $("#chat-area").html(data); $("#ChatAtBigScreen").html(data); document .getElementById('chat-area').scrollTop = document .getElementById('chat-area').scrollHeight; document .getElementById('ChatAtBigScreen').scrollTop = document .getElementById('ChatAtBigScreen').scrollHeight; } }); return false; } $('#msg').keyup(function(e) { if (e.keyCode == 13) { saveChats(); $("#msg").val(''); } }); </script>
Utility class, responsible to save the chat in the database using hibernate:
package com.G2.Model; import java.util.ArrayList; import java.util.Iterator; import java.util.List; import org.hibernate.Query; import org.hibernate.Session; import org.hibernate.SessionFactory; import org.hibernate.Transaction; import org.hibernate.cfg.Configuration; import com.G2.pojo.ChatMessage; public class DBManager { // Read Hibernate.cfg.xml static Configuration cf = new Configuration().configure(); static SessionFactory factory = cf.buildSessionFactory(); public static void saveChat(ChatMessage chat) { Session session = null; try { session = factory.openSession(); Transaction tx = session.beginTransaction(); session.save(chat); tx.commit(); } catch (Exception e) { e.printStackTrace(); } finally { if (session != null) { // I faced problem here, if below line is not written then data automatically gets deleted after insertion session.flush(); session.close(); } } } public static List<ChatMessage> getMessages() { List<ChatMessage> MessageList = new ArrayList<ChatMessage>(); Session session = null; try { session = factory.openSession(); String SQL_QUERY = "from ChatMessage c"; Query query = session.createQuery(SQL_QUERY); Iterator<ChatMessage> it = query.iterate(); while (it.hasNext()) { ChatMessage c = it.next(); MessageList.add(c); } } catch (Exception e) { e.printStackTrace(); } finally { session.flush(); session.close(); } return MessageList; } }
As shown in above code, to work with hibernate, our application will need to read the configuration file of hibernate by below line of code:
static Configuration cf = new Configuration().configure();
Now, we will need to create the session object from the SessionFactory class:
static SessionFactory factory = cf.buildSessionFactory(); Session session = factory.openSession();
Create the object of transaction :
Transaction tx = session.beginTransaction();
To save the object in the database use save() method of the transaction.
To get the list of chat messages from the database :
String SQL_QUERY = "from ChatMessage c"; Query query = session.createQuery(SQL_QUERY); Iterator<ChatMessage> it = query.iterate();
Here object of org.hibernate.Query is created and using method iterate(), it gives all the records from the database as a object. (That is what ORM – Object Relation Mapping)
Servlet Code:
package com.G2.servlets; import java.io.IOException; import java.io.PrintWriter; import java.util.HashMap; import java.util.List; import javax.servlet.ServletException; import javax.servlet.http.HttpServlet; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import com.G2.Model.DBManager; import com.G2.pojo.ChatMessage; public class ChatProcess extends HttpServlet { @Override protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { String uName = req.getParameter("uName"); String msg = req.getParameter("msg"); String colorCode = req.getParameter("colorCode"); ChatMessage chat = new ChatMessage(); chat.setMessage(msg); chat.setUserName(uName); chat.setColorSelected(colorCode); DBManager.saveChat(chat); PrintWriter out = resp.getWriter(); List<ChatMessage> msgList = DBManager.getMessages(); StringBuilder sb = new StringBuilder(); for (ChatMessage chatMsg : msgList) { sb.append("<span style='background:#" + chatMsg.getColorSelected() + "'>" + chatMsg.getUserName() + "</span>" + chatMsg.getMessage() + "<br/><br/>"); } out.print(replaceEmoticons(sb.toString())); } private String replaceEmoticons(String msg) { String imgTag = "<img src="../images/smiley/{PH}.gif">"; String placeHolder = "{PH}"; SmileyCodes smileyCode = new SmileyCodes(); HashMap<String, String> codeMap = smileyCode.getSmileyMap(); for (Object key: codeMap.keySet()) { String val = codeMap.get(key); if(msg.contains(key.toString())) { msg = msg.replace(key.toString(), imgTag.replace(placeHolder,val)); } } return msg; } }
This servlet class is called by the ajax code, and from here the message is saved using DBManager class.
Servlet mapping in web.config
<servlet> <servlet-name>Chatprocess</servlet-name> <servlet-class>com.G2.servlets.ChatProcess</servlet-class> </servlet> <servlet-mapping> <servlet-name>Chatprocess</servlet-name> <url-pattern>/Pages/Chatprocess.do</url-pattern> </servlet-mapping>
Emoticon /Smiley part – XML Module:
As you can see in the servlet code,
SmileyCodes smileyCode = new SmileyCodes();
SmileyCodes class is responsible to render the symbol as a smiley. For the performance purpose, the smiley code is saved in xml file with corresponding image file name. Below class reads the xml and creates the HashMap (Only once).
package com.G2.servlets; import java.io.IOException; import java.io.InputStream; import java.util.HashMap; import javax.xml.parsers.DocumentBuilder; import javax.xml.parsers.DocumentBuilderFactory; import javax.xml.parsers.ParserConfigurationException; import org.w3c.dom.Document; import org.w3c.dom.Element; import org.w3c.dom.Node; import org.w3c.dom.NodeList; import org.xml.sax.SAXException; public class SmileyCodes { private static HashMap<String, String> smileyCodes = null; public static void main(String args[]) { new SmileyCodes().replaceCodeBySmiley(); } public HashMap<String, String> getSmileyMap() { if (smileyCodes == null) { replaceCodeBySmiley(); } return smileyCodes; } private void replaceCodeBySmiley() { try { if (smileyCodes == null) { SmileyCodes testMain = new SmileyCodes(); InputStream st = testMain.getClass().getResourceAsStream("/SmileyCode.xml"); DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance(); DocumentBuilder builder; smileyCodes = new HashMap<String, String>(); builder = factory.newDocumentBuilder(); Document doc = builder.parse(st); // Get Root Node and its child Node root = doc.getDocumentElement(); NodeList childNodes = root.getChildNodes(); for (int i = 0; i < childNodes.getLength(); i++) { replaceCodeBySmiley(childNodes.item(i)); } } } catch (ParserConfigurationException e) { e.printStackTrace(); } catch (SAXException e) { e.printStackTrace(); } catch (IOException e) { e.printStackTrace(); } } private void replaceCodeBySmiley(Node node) { if (node.getNodeType() == Node.ELEMENT_NODE) { Element e = (Element) node; String[] keyVal = e.getTextContent().trim().split("#"); smileyCodes.put(keyVal[0].trim(), keyVal[1].trim()); } } private String nodeType(short type) { switch (type) { case Node.ELEMENT_NODE: return "Element"; case Node.DOCUMENT_TYPE_NODE: return "Document type"; case Node.ENTITY_NODE: return "Entity"; case Node.ENTITY_REFERENCE_NODE: return "Entity reference"; case Node.NOTATION_NODE: return "Notation"; case Node.TEXT_NODE: return "Text"; case Node.COMMENT_NODE: return "Comment"; case Node.CDATA_SECTION_NODE: return "CDATA Section"; case Node.ATTRIBUTE_NODE: return "Attribute"; case Node.PROCESSING_INSTRUCTION_NODE: return "Attribute"; } return "Unidentified"; } }
Download Complete code – JQuery Chat in Hibernate (Change extension from zip to rar )
Download 2 – JQueryChat
Note:
Following jar files will be needed:
antlr-2.7.6.jar
commons-collections-3.1.jar
dom4j-1.6.1.jar
hibernate-jpa-2.0-api-1.0.0.Final.jar
hibernate-testing.jar
hibernate3.jar
javassist-3.12.0.GA.jar
jta-1.1.jar
mysql-connector-java-3.1.14-bin.jar
slf4j-api-1.6.1.jar
Leave a Reply