Write Operations in DWR

Write operations are not allowed with the default session setting for the OpenViewInSession filter which is commonly defined in web.xml as a hibernate filter. If you want to enable write operations when using DWR (Direct Web Remoting), one of the ways is to declare a filter for DWR urls. Put the following configuration in your web.xml, also please note the url pattern in filter-mapping element.


<filter>
<filter-name>dwrWriteHibernateFilter</filter-name>
<filter-class>
some.package.name.OpenWriteSessionInViewFilter
</filter-class>
<init-param>
<param-name>singleSession</param-name>
<param-value>true</param-value>
</init-param>
<init-param>
<param-name>sessionFactoryBeanName</param-name>
<param-value>sessionFactory</param-value>
</init-param>
</filter>

<filter-mapping>
<filter-name>dwrWriteHibernateFilter</filter-name>
<url-pattern>*.dwr</url-pattern>
</filter-mapping>

The filter class as follows:

// more imports
import org.springframework.dao.DataAccessResourceFailureException;
import org.springframework.orm.hibernate3.support.OpenSessionInViewFilter;

public class OpenWriteSessionInViewFilter extends OpenSessionInViewFilter {

protected Session getSession(SessionFactory sessionFactory)
throws DataAccessResourceFailureException {
Session session = super.getSession(sessionFactory);
session.setFlushMode(FlushMode.COMMIT);
return session;
}

protected void closeSession(Session session, SessionFactory factory) {
session.flush();
super.closeSession(session, factory);
}
}

How To Define a Spring Bean With Generics Parameter

At the time when this article was written, the Spring framework does not allow to define beans in application context xml file using parameterized classes. The reason for that is that generics parameters are compiler information, and not run-time. Compiler information is something that Spring does not care about. For example, the following (or something similar) will NOT work:

<bean id="someClass" class="asia.javabeans.SomeClass<asia.javabeans.Blah>"  />

Sometimes, this restriction can create a problem if you have a parameterized class that has to be loaded by Spring. As a workaround, create an empty child class that extends your parameterized class, and then use that class’s canonical name as your bean definition. Consider the following parameterized parent and the extending child classes:

public class SomeParent<Blah> {

}

public class Child extends SomeParent<Blah> {
   // Just an empty class
}

and your Spring definition can now look like this:

<bean id="childClass" class="asia.javabeans.Child" />

The down side here is that you get stuck with an empty class, but at least you can have your bean definition in your application context xml file.

How To Select a Child Element Using jQuery

Let’s assume you have an HTML string containing a parent element with a number of children and their sub children elements. If you’d like to extract HTML of one of the children (by class name or id), you can use this jQuery line:

var html = $(htmlString).find('div.target').html();

It can be useful when you get an AJAX response from the server, and only a particular section needs to extracted.

How To Tell XStream To Not Unmarshall XML Fields

My colleague found this when he was looking for a way not to unmarshall XML fields that did not exist in his POJO using XStream. The code makes use of a MapperWrapper class:

    XStream xstream = new XStream() {
    @Override
    protected MapperWrapper wrapMapper(MapperWrapper next) {
        return new MapperWrapper(next) {

        @Override
        public boolean shouldSerializeMember(Class definedIn, String fieldName) {
            if (definedIn == Object.class) { return false; }
               return super .shouldSerializeMember(definedIn, fieldName);
            }
         };
      }
  };

Convert XML into POJO using HierarchicalStreamReader

In this example I would like to show how unmarshall XML into a POJO using HierarchicalStreamReader. I will introduce how to use  XStream and a custom XML-to-POJO converter, describe a case study and develop an application to show the solution.

Purchase History Example
Consider the following XML. It represents represents a purchase history of a customer, that has purchased different items during a week:

<PURCHASE>
	<ITEM>
		<SUBITEM>
			<CODE>PDCT-001</CODE>
			<NAME>Product-1</NAME>
			<DAY5>1.75</DAY5>
			<TOTAL>1.75</TOTAL>
		</SUBITEM>
		<SUBITEM>
			<CODE>PDCT-002</CODE>
			<NAME>Product-2</NAME>
			<DAY7>1.00</DAY7>
			<DAY6>1.75</DAY6>
			<TOTAL>2.75</TOTAL>
		</SUBITEM>
		<SUBITEM>
			<CODE>PDCT-003</CODE>
			<NAME>Product-3</NAME>
			<DAY7>4.50</DAY7>
			<DAY6>2.00</DAY6>
			<DAY5>3.00</DAY5>
			<DAY4>2.25</DAY4>
			<TOTAL>11.75</TOTAL>
		</SUBITEM>
		<SUBITEM>
			<CODE>PDCT-004</CODE>
			<NAME>Product-4</NAME>
			<DAY7>3.50</DAY7>
			<DAY6>3.75</DAY6>
			<DAY5>2.75</DAY5>
			<DAY1>3.75</DAY1>
			<TOTAL>13.75</TOTAL>
		</SUBITEM>
		<REFERENCE>9571-EDGDFG-DGSNJE-1837</REFERENCE>
		<GRANDTOTAL>30</GRANDTOTAL>
	</ITEM>
</PURCHASE>

To unmarshall the XML, I created three POJOs to represent the hierarchy of XML elements. The domain objects Purchase, Item and SubItem are involved.  The Purchase  has an Item, that has a collection of SubItem objects. My customer XML converter will transform customer’s purchase history from XML into a domain model using the POJOs.

I am not going to describe the full structure of the POJOs here, as I want to concentrate on talking about the XML converter . The source code as Eclipse project is attached to the current article, so you can download it.

I use XStream, which is a simple open-source Java library for serialize objects to and from XML. The following is the unit test case code snippet that show how I register my custom converter that is used for XML unmarshalling:

XStream xstream = new XStream(new DomDriver());
xstream.alias("PURCHASE", Purchase.class);
xstream.registerConverter(new PurchaseConverter());
Purchase purchase = (Purchase) xstream.fromXML(xmlContent);

I created an alias for Purchase that matches XML root element and registered my custom converter. The converter is a specific converter that knows how to handle this particular XML example, so it is not a generic solution. The converter code as follows:

package asia.javabeans.streamreader.util;

import asia.javabeans.streamreader.domain.Purchase;
import asia.javabeans.streamreader.domain.SubItem;

import com.thoughtworks.xstream.converters.Converter;
import com.thoughtworks.xstream.converters.MarshallingContext;
import com.thoughtworks.xstream.converters.UnmarshallingContext;
import com.thoughtworks.xstream.io.HierarchicalStreamReader;
import com.thoughtworks.xstream.io.HierarchicalStreamWriter;

/**
 * Current class represents converter for a Purchase XML.
 *
 * @author alexander.zagniotov
 *
 */
final public class PurchaseConverter implements Converter {

	private static final int NUM_OF_DAYS = 7;

	public void marshal(Object value, HierarchicalStreamWriter writer,
			MarshallingContext context) {
	}

	public Object unmarshal(HierarchicalStreamReader reader,
			UnmarshallingContext context) {

		Purchase purchase = new Purchase();

                //while there are unread XML element children and the reader has not reached the closing PURCHASE element
		while (!(reader.getNodeName().equals(XmlElements.PURCHASE) && !reader
				.hasMoreChildren())) {

			if (reader.hasMoreChildren()) {
				reader.moveDown(); // Move down to ITEM element

				// Process child SUBITEM elements of the parent ITEM
				if (reader.getNodeName().equals(XmlElements.ITEM)) {
					iterateThroughItemSubitems(reader, XmlElements.ITEM,
							XmlElements.SUBITEM, purchase);
				}
			}
                        //store value of REFERENCE element in a POJO
			if (reader.getNodeName().equals(XmlElements.REFERENCE)) {
				purchase.setReference(reader.getValue());
			}

			reader.moveUp(); // Move back up to PURCHASE element
		}

		return purchase;
	}

	private Purchase iterateThroughItemSubitems(
			HierarchicalStreamReader reader, String parentNameName,
			String childNodeName, Purchase purchase) {
		boolean hasSubitemNodes = true;

		while (reader.getNodeName().equals(parentNameName) && hasSubitemNodes) {
			reader.moveDown(); // Move down to SUBITEM element

			// We have SUBITEM element that we can read
			if (reader.getNodeName().equals(childNodeName)) {
				purchase = iterateThroughSubitemChildren(reader, childNodeName,
						purchase);
			} else { // No more children SUBITEM elements to read
				break;
			}

			reader.moveUp(); // Move back up to parent ITEM element
			continue;
		}

		return purchase;
	}

	private Purchase iterateThroughSubitemChildren(
			HierarchicalStreamReader reader, String nodeName, Purchase purchase) {
		boolean hasChildrenNodes = true;

		SubItem subItem = new SubItem();

		while (reader.getNodeName().equals(nodeName) && hasChildrenNodes) {
			// Move down to the children of current SUBITEM element
			reader.moveDown();

			if (reader.getNodeName().equals(XmlElements.CODE)) {
				String subItemCode = reader.getValue();
				subItem.setCode(subItemCode);
				reader.moveUp(); // Move back up to parent SUBITEM
				continue;
			}

			if (reader.getNodeName().equals(XmlElements.NAME)) {
				String subItemName = reader.getValue();
				subItem.setName(subItemName);
				reader.moveUp(); // Move back up to parent SUBITEM
				continue;
			}

			if (reader.getNodeName().startsWith(XmlElements.DAY)) {

				for (int i = 1; i <= NUM_OF_DAYS; i++) {
					String xmlDay = XmlElements.DAY + i;

					if (reader.getNodeName().equals(xmlDay)) {

						double hours = Double.parseDouble(reader.getValue());
						subItem.addToDailyHours(xmlDay, hours);
						purchase.addToGrandTotal(hours);
						break;
					}
				}

				reader.moveUp(); // Move back up to parent SUBITEM
				continue;
			}

			if (reader.getNodeName().equals(XmlElements.TOTAL)) {
				hasChildrenNodes = false; // This is the last child of parent SUBITEM

				String itemTotalStr = reader.getValue();
				subItem.setItemTotal(Double.parseDouble(itemTotalStr));
				purchase.getItem().addSubItem(subItem);
				reader.moveUp(); // Move back up to parent SUBITEM
				continue;
			}
		}
		return purchase;
	}

	@SuppressWarnings("unchecked")
	public boolean canConvert(Class clazz) {
		return clazz.equals(Purchase.class);
	}

}

As you can see, the key to operate a stream reader is to move it down to a child element for reading and back up to a parent element. Each time I move the reader down, it moves to an element that has not being read yet.

Conclusion

I presented a simple example where I show how to unmarshall XML into Java POJOs using HierarchicalStreamReader and XStream. The source code is attached.

I hope this tutorial was helpful to some of you,
Regards

Web Applications with AJAX, Servlets and JSON (Chinese Version)

在这篇文章中,我想说明如何的JSON(JavaScript对象
符号)和Java Servlet可以同时使用在一个小的AJAX((Asynchronous JavaScript and XML)的应用。

为了作简要介绍那些谁不熟悉使用JSON密切。JSON是一种表示数据,这使得工作轻量级语法
它比更愉快,使AJAX应用程序的XML 快。此外,当使用JSON工作,没有任何一个XML需要
解析。

在下面的例子,我将创建一个回调的servlet 获取并分析了RSS提要。然后解析数据被传递到饲料
在一个客户端JSON的形式。这些数据然后格式化并提交 给用户。客户端使用AJAX调用来查询的servlet。

对于这种应用,我使用了三个第三方库:

图书馆提供的JSON和JSON的JSON.org – RPC的Java的,允许以建立并轻松地通过Java代码解析JSON数据延长。该库可以运行在一个如Tomcat,JBoss和其他J2EE应用服务器的Servlet容器。

项目罗马
罗马是一个开放源码的Java工具,用于分析,生成和发布RSS和Atom馈送。

JDOM的XML解析器
JDOM是一个基于Java的“文档对象模型的XML文件”。 JDOM的服务作为DOM的相同目的,但更容易使用

这些库中包含的源代码,附带这篇文章。此应用程序的例子还包括作为一个WAR档案,随时可以在Tomcat部署。
以下是我的servlet实现。该servlet饲料获取并分析数据。前面提到的JSON库让我轻松地创建和填充JSON对象。

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.json.JSONArray;
import org.json.JSONObject;

import com.sun.syndication.feed.synd.SyndEntry;
import com.sun.syndication.feed.synd.SyndFeed;
import com.sun.syndication.fetcher.FeedFetcher;
import com.sun.syndication.fetcher.FetcherException;
import com.sun.syndication.fetcher.impl.FeedFetcherCache;
import com.sun.syndication.fetcher.impl.HashMapFeedInfoCache;
import com.sun.syndication.fetcher.impl.HttpURLFeedFetcher;
import com.sun.syndication.io.FeedException;

/**
* @author Alexander Zagniotov (http://javabeans.asia)
*/
public class JsonServlet extends HttpServlet {

	private static final long serialVersionUID = 1L;
	private static final String BLOG_URL = "http://javabeans.asia/rss.xml";
	private static final String CONTENT_TYPE = "application/json";
	private FeedFetcherCache feedInfoCache = null;
	private FeedFetcher feedFetcher = null;

	public void init(ServletConfig config) throws ServletException {
		super.init(config);
		feedInfoCache = HashMapFeedInfoCache.getInstance();
		feedFetcher = new HttpURLFeedFetcher(feedInfoCache);
	}

	public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {

		SyndFeed feed = this.feedFethcer(BLOG_URL);
		if (feed != null) {
			String json = this.feedToJSON(feed);
			response.setContentType(CONTENT_TYPE);
			response.setHeader("Cache-Control", "no-cache");
			response.getWriter().write(json);
		}
	}

	private SyndFeed feedFethcer(String url) {
		SyndFeed feed = null;
		try {
			feed = feedFetcher.retrieveFeed(new URL(BLOG_URL));
		} catch (IllegalArgumentException e) {
			e.printStackTrace();
		} catch (FeedException e) {
			e.printStackTrace();
		} catch (FetcherException e) {
			e.printStackTrace();
		} catch (MalformedURLException e) {
			e.printStackTrace();
		} catch (IOException e) {
			e.printStackTrace();
		}
		return feed;
	}

	private String feedToJSON(SyndFeed feed) {

		JSONObject jsonObj = new JSONObject();
		JSONArray jsonEntryTitles = new JSONArray();
		jsonObj.put("blogtitle", feed.getTitle());
		jsonObj.put("blogdescription", feed.getDescription());
		jsonObj.put("bloglanguage", feed.getLanguage());
		jsonObj.put("bloglink", feed.getLink());
		jsonObj.put("author", feed.getCopyright());

		List<?> feedEntries = feed.getEntries();

		for (Object c : feedEntries) {
			SyndEntry syndicateEntry = (SyndEntry) c;
			jsonEntryTitles.put(syndicateEntry.getTitle());
		}

		jsonObj.put("blogentrytitles", jsonEntryTitles);
		return jsonObj.toString();
	}
}

正如你可以看到它是很容易的构建在服务器端JSON对象和数组并传递给客户端。对于本示例的目的,我从RSS饲料得到我的数据,但数据也可从数据库等来

以下是我的客户端实现。客户端的servlet查询使用AJAX调用。当一个AJAX调用返回从一个JSON的Servlet的响应对象的形式,对象数据的格式以及有关的RSS供稿信息呈现给客户端:

<html>
    <head>
    <title>Java Beans dot Asia</title>

    <script language="JavaScript" type="text/javascript">

        var httpRequest = null;

    function getDescriptionAsJSON() {
        var description = document.getElementById('description');
        description.innerHTML = "Loading, please wait ...";

        var url = "http://localhost:8080/json/json";
        if(window.XMLHttpRequest){
            httpRequest = new XMLHttpRequest();
        } else if(window.ActiveXObject){
            httpRequest = new ActiveXObject("Microsoft.XMLHTTP");
        }

        httpRequest.open("GET", url, true);
        httpRequest.onreadystatechange = handler;
        httpRequest.send(null);
    }

    function handler() {
        if (httpRequest.readyState == 4) {
            if (httpRequest.status == 200) {
                processJSON(httpRequest.responseText);
            }
        }
    }

    function processJSON(jsonObjectString) {

        var description = document.getElementById('description');

        //Since JSON is a subset of JavaScript, I am using
        //JavaScript's own compiler to parse JSON in one line!

        var jsonObject = eval('(' + jsonObjectString + ')')
        var text = "";

        text += "Author: " + jsonObject.author + "< br />";
        text += "Blog Name: " + jsonObject.blogtitle + "< br />";
        text += "Blog URL: " +    jsonObject.bloglink + "< br />";
        text += "Blog Description: " +    jsonObject.blogdescription + "< br />";
        text += "Blog Language: " + jsonObject.bloglanguage + "< br />";

        description.innerHTML = text;
        var entries = "Last " + jsonObject.blogentrytitles.length + " blog entries are:nn";

        for (var index = 0; index < jsonObject.blogentrytitles.length; index ++) {
            entries += (index + 1) + ": " + jsonObject.blogentrytitles[index] + "n";
        }
        alert(entries);
    }

    </script>

    </head>
    <body>
        <img src="images/javabeansmugshot_120x120.jpg" border="1" />< br />< br />
        <div id="description"></div>< br />< br />
        <a href="javascript:void(0)" onclick="return getDescriptionAsJSON();">Click to get description!</a>
    </body>
</html>

正如你可以看到,JSON数据可以很容易地解析对与Java的脚本eval()函数帮助客户端。为了提醒 – JSON是一个Java脚本的一个子集,因此的eval()将产生一个有效的对象。

请记住,有一个额外需要照顾时,使用eval。问题是,试用版本将编译并执行Java脚本代码,回来从响应。这可能导致安全风险,如果响应数据是来自不可信来源的到来。

就是这样。我希望这个例子是明确的和有用的:)

source code json and servlets

请注意,这个例子是我和测试其工作的罚款。源代码是因为前面提到的Eclipse项目中。你可以简单地创建一个从现有的Ant build.xml文件新的Java项目。

评论表示赞赏:)

干杯

Redefining Web Applications with AJAX, Servlets and JSON

In this article I would like to show how JSON (JavaScript Object Notation) and Java servlet can be used together in a little AJAX (Asynchronous JavaScript and XML) application.

To give brief description to those who are not closely familiar with JSON -

JSON is a lightweight syntax for representing data, which makes working with it much more pleasant than with XML and makes AJAX applications faster. Also, when working with JSON, there is no need for an XML parsing.

In the following example, I am going to create a callback servlet that fetches and parses an RSS feed. Then the parsed feed data is passed to the client side in a form of JSON. The data then formatted and presented to the user. The client uses AJAX call to query the servlet.

For this application, I used three third-party libraries:

  1. JSON library provided by JSON.org and extended by JSON-RPC-Java which allows to create and easily parse JSON data through Java code. This library can run in a Servlet container such as Tomcat, JBoss and other J2EE Application servers.
  2. Project ROME
    ROME is an set of open source Java tools for parsing, generating and publishing RSS and Atom feeds.
  3. JDOM XML parser
    JDOM is a Java-based “document object model” for XML files. JDOM serves the same purpose as DOM, but is easier to use

The libraries are included in the source code which accompanies this article. This application example is also included as a WAR archive, ready to be deployed on Tomcat.

The following is my servlet implementation. The servlet fetches and parses feed data. The JSON library mentioned previously allows me easily to create and populate JSON object.

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.json.JSONArray;
import org.json.JSONObject;

import com.sun.syndication.feed.synd.SyndEntry;
import com.sun.syndication.feed.synd.SyndFeed;
import com.sun.syndication.fetcher.FeedFetcher;
import com.sun.syndication.fetcher.FetcherException;
import com.sun.syndication.fetcher.impl.FeedFetcherCache;
import com.sun.syndication.fetcher.impl.HashMapFeedInfoCache;
import com.sun.syndication.fetcher.impl.HttpURLFeedFetcher;
import com.sun.syndication.io.FeedException;

/**
* @author Alexander Zagniotov (http://javabeans.asia)
*/
public class JsonServlet extends HttpServlet {

	private static final long serialVersionUID = 1L;
	private static final String BLOG_URL = &quot;http://javabeans.asia/rss.xml&quot;;
	private static final String CONTENT_TYPE = &quot;application/json&quot;;
	private FeedFetcherCache feedInfoCache = null;
	private FeedFetcher feedFetcher = null;

	public void init(ServletConfig config) throws ServletException {
		super.init(config);
		feedInfoCache = HashMapFeedInfoCache.getInstance();
		feedFetcher = new HttpURLFeedFetcher(feedInfoCache);
	}

	public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {

		SyndFeed feed = this.feedFethcer(BLOG_URL);
		if (feed != null) {
			String json = this.feedToJSON(feed);
			response.setContentType(CONTENT_TYPE);
			response.setHeader(&quot;Cache-Control&quot;, &quot;no-cache&quot;);
			response.getWriter().write(json);
		}
	}

	private SyndFeed feedFethcer(String url) {
		SyndFeed feed = null;
		try {
			feed = feedFetcher.retrieveFeed(new URL(BLOG_URL));
		} catch (IllegalArgumentException e) {
			e.printStackTrace();
		} catch (FeedException e) {
			e.printStackTrace();
		} catch (FetcherException e) {
			e.printStackTrace();
		} catch (MalformedURLException e) {
			e.printStackTrace();
		} catch (IOException e) {
			e.printStackTrace();
		}
		return feed;
	}

	private String feedToJSON(SyndFeed feed) {

		JSONObject jsonObj = new JSONObject();
		JSONArray jsonEntryTitles = new JSONArray();
		jsonObj.put(&quot;blogtitle&quot;, feed.getTitle());
		jsonObj.put(&quot;blogdescription&quot;, feed.getDescription());
		jsonObj.put(&quot;bloglanguage&quot;, feed.getLanguage());
		jsonObj.put(&quot;bloglink&quot;, feed.getLink());
		jsonObj.put(&quot;author&quot;, feed.getCopyright());

		List&lt;?&gt; feedEntries = feed.getEntries();

		for (Object c : feedEntries) {
			SyndEntry syndicateEntry = (SyndEntry) c;
			jsonEntryTitles.put(syndicateEntry.getTitle());
		}

		jsonObj.put(&quot;blogentrytitles&quot;, jsonEntryTitles);
		return jsonObj.toString();
	}
}

As you can see it is very easy to construct JSON objects and arrays on the server side and pass them to the client. For the purpose of this example I am getting my data from RSS feed, but the data can also be coming from DB etc.

The following is my client implementation. The client queries the servlet using AJAX call. When an AJAX call returns a response from the servlet in a form of JSON object, the object data is formatted and information about the RSS feed is presented to the client:

&lt;html&gt;
    &lt;head&gt;
    &lt;title&gt;Java Beans dot Asia&lt;/title&gt;

    &lt;script language=&quot;JavaScript&quot; type=&quot;text/javascript&quot;&gt;

        var httpRequest = null;

    function getDescriptionAsJSON() {
        var description = document.getElementById('description');
        description.innerHTML = &quot;Loading, please wait ...&quot;;

        var url = &quot;http://localhost:8080/json/json&quot;;
        if(window.XMLHttpRequest){
            httpRequest = new XMLHttpRequest();
        } else if(window.ActiveXObject){
            httpRequest = new ActiveXObject(&quot;Microsoft.XMLHTTP&quot;);
        }

        httpRequest.open(&quot;GET&quot;, url, true);
        httpRequest.onreadystatechange = handler;
        httpRequest.send(null);
    }

    function handler() {
        if (httpRequest.readyState == 4) {
            if (httpRequest.status == 200) {
                processJSON(httpRequest.responseText);
            }
        }
    }

    function processJSON(jsonObjectString) {

        var description = document.getElementById('description');

        //Since JSON is a subset of JavaScript, I am using
        //JavaScript's own compiler to parse JSON in one line!

        var jsonObject = eval('(' + jsonObjectString + ')')
        var text = &quot;&quot;;

        text += &quot;Author: &quot; + jsonObject.author + &quot;&lt; br /&gt;&quot;;
        text += &quot;Blog Name: &quot; + jsonObject.blogtitle + &quot;&lt; br /&gt;&quot;;
        text += &quot;Blog URL: &quot; +    jsonObject.bloglink + &quot;&lt; br /&gt;&quot;;
        text += &quot;Blog Description: &quot; +    jsonObject.blogdescription + &quot;&lt; br /&gt;&quot;;
        text += &quot;Blog Language: &quot; + jsonObject.bloglanguage + &quot;&lt; br /&gt;&quot;;

        description.innerHTML = text;
        var entries = &quot;Last &quot; + jsonObject.blogentrytitles.length + &quot; blog entries are:nn&quot;;

        for (var index = 0; index &lt; jsonObject.blogentrytitles.length; index ++) {
            entries += (index + 1) + &quot;: &quot; + jsonObject.blogentrytitles[index] + &quot;n&quot;;
        }
        alert(entries);
    }

    &lt;/script&gt;

    &lt;/head&gt;
    &lt;body&gt;
        &lt;img src=&quot;images/javabeansmugshot_120x120.jpg&quot; border=&quot;1&quot; /&gt;&lt; br /&gt;&lt; br /&gt;
        &lt;div id=&quot;description&quot;&gt;&lt;/div&gt;&lt; br /&gt;&lt; br /&gt;
        &lt;a href=&quot;javascript:void(0)&quot; onclick=&quot;return getDescriptionAsJSON();&quot;&gt;Click to get description!&lt;/a&gt;
    &lt;/body&gt;
&lt;/html&gt;

As you could see, JSON data can be easily parsed on the client side with the help of Java script eval() function. To remind – JSON is a subset of Java script, therefore eval() will produce a valid object.

Keep in mind, that there is a need for extra care when using eval. The problem is that eval will compile and execute Java script code that coming back from the response. This could cause a security risk if the response data is coming from an untrusted source.

That’s it. I hope this example was clear and helpful :)

source json servlets ajax

Please note that this example was tested by me and its working fine. The source code as mentioned previously is included as Eclipse project. You can simply create a new Java project from the existing Ant build.xml file.

Comments/flames are appreciated :)

Cheers

JBoss Security – JMX Console

I was reading about JBoss security today, and came across the following page:
JBoss Security vulnerability JMX Management Console. The guy tells how common is to come across servers on the Internet that run completely unsecured JMX-Console.

I gave it a try, typed few keywords in Google, and voilà -
around one third of the Google results on the first page were links to various servers that run completely unsecured JBoss and JMX-console. Having said that, I would like to point out that I did not attempt anything naughty or malicious.

Its still amazes me how careless some people are – leaving an open door for anyone to come in. Come on people, surely in this day and age we all know how important is to keep web applications secured. Don’t be lazy, its not going to take much of your time since securing JMX-console its such a trivial task.

Hibernate Event Interceptor

Its quite common when you create an application, there is a need to create an audit trail on the application level where all entity insert, update and delete events are logged.

In this post, I would like to describe a simple approach that can help you to avoid littering with unnecessary statements in your application code. The solution is to register a class as a listener on Hibernate events. Once class is triggered, you will be able to write audit information to a database or log file.

The following shows a Hibernate event interceptor class that is triggered when persistent entity is inserted, deleted or updated.

public class HibernateEventInterceptor	implements	PostInsertEventListener,
							PostUpdateEventListener,
							PostDeleteEventListener,
							Initializable {

	public HibernateEventInterceptor() {

	}

	public void initialize(Configuration cfg) {

	}

	public void onPostInsert(PostInsertEvent event) {
		String entityName = event.getPersister().getEntityName();
		System.out.println("Inserted entity: " + entityName);
	}

	public void onPostUpdate(PostUpdateEvent event) {
		String entityName = event.getPersister().getEntityName();
		System.out.println("Updated entity: " + entityName);
	}

	public void onPostDelete(PostDeleteEvent event) {
		String entityName = event.getPersister().getEntityName();
		System.out.println("Deleted entity: " + entityName);
	}
}

The following shows extra configuration that must be added to persistence.xml, in order for the interceptor class to be triggered:

<persistence>
	<persistence-unit name="org.example.demo">
	<jta-data-source>java:/test</jta-data-source>
		<properties>
			.
			.
			.
		<property name="hibernate.ejb.event.post-insert" value="org.example.demo.HibernateEventInterceptor"/>
		<property name="hibernate.ejb.event.post-update" value="org.example.demo.HibernateEventInterceptor"/>
		<property name="hibernate.ejb.event.post-delete" value="org.example.demo.HibernateEventInterceptor"/>
		</properties>
	</persistence-unit>
</persistence>

Using Template to Deploy a JBoss Queue

Currently I am involved in a project, where I have to use Velocity template engine to deploy queues and message-driven beans to JBoss. Velocity is a template engine that can be used for many purposes, and in my case I am using it to generate XML descriptor for a JBoss queue, hence: some-queue-name-service.xml. Its a simple scripting language and the XML descriptor template looks quite similar to the resulting XML descriptor.

Why do we use a template for deployment?
Because some of our deployments occur at runtime, where properties for the queues and MDB’s are generated on the fly and we need a templating engine to be able generate the deployments.

So i decided to describe a process of deploying a JBoss queue. I am hoping that I will be clear enough, since i am quite new to this my self.

The setup of my system:

/opt/mitto/jboss/server/mitto/

Root directory for my JBoss instance. (the [.])

My Velocity templates sit under the root, inside dynamic-templates directory:

./dynamic-templates/

JBoss deployment service will look under the root of my JBoss instance for the dynamic-templates directory.

JBoss deployment service depends on Velocity library (velocity.jar) that must be included under the root of:

./deploy/deployment-service.sar/

XML descriptor of JBoss deployment service (jboss-service.xml) sits under:

./deploy/deployment-service.sar/META-INF/

You can see below the jboss-service.xml:

	<mbean code="org.jboss.services.deployment.DeploymentService" name="jboss:service=DeploymentService">
		<attribute name="TemplateDir">dynamic-templates</attribute>
		<attribute name="DeployDir">dynamic-deploy</attribute>
		<attribute name="UndeployDir">dynamic-undeploy</attribute>
	</mbean>

The three directories mentioned above in jboss-service.xml, sit under the root of my JBoss instance.
TemplateDir – where my deployment generation templates can be found.
UndeployDir – the generated modules go there.

DeployDir – the directory to use when I ask to deploy a generated module.

Now, inside the:

./dynamic-templates/

I have following structure:

	jbossmessaging-queue/
		            /vm/
		               jbossmessaging-queue.xml.vm
		            template-config.xml

jbossmessaging-queue – directory that contains Velocity XML descriptor template for my queue. Also it represents the name of the deployment template that should be used, when createModule() method of deployment service will be called.

template-config.xml specifies the properties for Velocity template XML descriptor for our queue. Deployment service will be able to access those properties when rendering the Velocity template and to retrieve the values of JNDIName and QueueName properties.

Below you can see the descriptor for the template-config.xml:

	<template-config template="vm/jbossmessaging-queue.xml.vm" extension="-service.xml">
		<property-list>
		<property name="QueueName" type="java.lang.String" optional="false"/>
		</property-list>
	</template-config>

jbossmessaging-queue.xml.vm mentioned above, is the name of the actual Velocity template XML descriptor for the queue, which you can see below:

	<?xml version="1.0" encoding="UTF-8"?>
	<!--  ===================  QueueName - $QueueName ======= -->
	<server>
		<mbean code="org.jboss.jms.server.destination.QueueService"
						name="jboss.messaging.destination:service=Queue,
						name=$QueueName" xmbean-dd="xmdesc/Queue-xmbean.xml">

		<depends optional-attribute-name="ServerPeer">jboss.messaging:service=ServerPeer</depends>
		<attribute name="Clustered">true</attribute>
		<depends>jboss.messaging:service=PostOffice</depends>
		</mbean>
	</server>

Implementation:
I created a service bean that will acquire proxies for the JBoss MainDeployerMBean and JBoss DeploymentServiceMBean. I will use JBoss deployment service to construct a queue module in the file system, and I will use JBoss main deployer to deploy the queue, by pointing it to the module in the file system. My implementation of my service bean as follows:

public class DeploymentService
	extends ServiceMBeanSupport
		implements DeploymentServiceMBean {

	private static final String
		JBOSS_MAIN_DEPLOYER_SERVICE = "jboss.system:service=MainDeployer";
	private static final String
		JBOSS_DEPLOYMENT_SERVICE = "jboss:service=DeploymentService";

	private MainDeployerMBean mainDeployerService = null;
	private DeploymentServiceMBean jbossDeploymentService = null;

	public void startService() throws Exception {

		try {
			//get proxy for main deployer service bean
			mainDeployerService = getJBossMainDeployer();
		}
		catch (MBeanProxyCreationException e)  {
			e.printStackTrace();
		}

		try {

			//get proxy for deployemnt service bean
			jbossDeploymentService = getJBossDeploymentService();
		}
		catch (MBeanProxyCreationException e)  {
			e.printStackTrace();
		}

		deploy();
	}

	public void stopService() {

	}

	private void deploy()  {

	//hashmap contains properties for the queue template
	HashMap<String, Object> properties = new HashMap<String, Object>();

	//short file name of my queue
	String destination = "myqueue-service.xml";

	//directory name where the queue Velocity template is kept,
	//inside 'dynamic-templates' dir
	String template = "jbossmessaging-queue";

	//property that holds a queue name for the Velocity template
	properties.put("QueueName", "myqueue");

	String resultingFileName = "";

	//create a queue module in a filesystem, at this stage queue
	//is not deployed yet.
	try {
		resultingFileName = jbossDeploymentService
				.createModule(destination, template, properties);
	} catch (Exception e) {
			e.printStackTrace();
	}

	String path = constructPath(destination);

	try {
		//check whether deployment exists for the given
		//module queue in the file system
		if (!mainDeployerService.isDeployed(path)) {

			mainDeployerService.deploy(path);
		}
	} catch (MalformedURLException e) {
		e.printStackTrace();
	}

	}

	//construct an absolute path to the queue module in a filesystem
	//for a given name.
	private String constructPath(String shortName) {
	String path = ServerConfigLocator.locate().getServerHomeDir()
				.getAbsolutePath()
				+ "/"
				+ jbossDeploymentService.getUndeployDir()
				+ "/"
				+ shortName;
		return path;
		}

	//Constructs and returns a proxy for MainDeployerMBean
	private MainDeployerMBean getJBossMainDeployer()
						throws MBeanProxyCreationException
	{
		MBeanServer server = getServer();

		ObjectName serviceName = new ObjectName(JBOSS_MAIN_DEPLOYER_SERVICE);

	//'false' -> dont make the returned proxy implement NotificationEmitter interface
		MainDeployerMBean mainDeployer =
		(MainDeployerMBean) MBeanServerInvocationHandler
					.newProxyInstance(server, serviceName,
						MainDeployerMBean.class, false);

	  return mainDeployer;
	}

	//Constructs and returns a proxy for DeploymentServiceMBean
	private DeploymentServiceMBean getJBossDeploymentService()
						throws MBeanProxyCreationException
	{
		MBeanServer server = getServer();

		ObjectName serviceName = new ObjectName(JBOSS_DEPLOYMENT_SERVICE);

	//'false' -> dont make the returned proxy implement NotificationEmitter interface
		DeploymentServiceMBean deploymentService =
		(DeploymentServiceMBean) MBeanServerInvocationHandler
					.newProxyInstance(server, serviceName,
						DeploymentServiceMBean.class, false);

	  return deploymentService;
	}

}

Two main points that i want to explain here are:
createModule() method of JBoss deployment service and
deploy() of JBoss main deployer.

createModule() - accepts three arguments: resulting file name (in this case is myqueue-service.xml), the directory name where the Velocity template is kept and a HashMap object which contains properties for the template.

JBoss deployment service will use the Velocity template to generate myqueue-service.xml module under dynamic-undeploy directory.

deploy() – accepts a path to the module in the system and deploys the module. In this case the path to the module is:

/opt/mitto/jboss/server/mitto/dynamic-undeploy/myqueue-service.xml

Thats about it :) You can use Velocity templates to deploy queues, message-driven and other types of beans. Basically anything that has XML descriptors.

I really hope I was clear enough in this example, since it is quite con-sized.