<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>Les Hazlewood &#187; Software</title>
	<atom:link href="http://leshazlewood.com/category/software/feed/" rel="self" type="application/rss+xml" />
	<link>http://leshazlewood.com</link>
	<description>Where Les is More</description>
	<lastBuildDate>Tue, 28 Jun 2011 21:39:24 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.2.1</generator>
		<item>
		<title>Apache Shiro San Francisco JUG presentation</title>
		<link>http://leshazlewood.com/2010/09/20/apache-shiro-san-francisco-jug-presentation/</link>
		<comments>http://leshazlewood.com/2010/09/20/apache-shiro-san-francisco-jug-presentation/#comments</comments>
		<pubDate>Mon, 20 Sep 2010 19:37:31 +0000</pubDate>
		<dc:creator>admin</dc:creator>
				<category><![CDATA[Apache]]></category>
		<category><![CDATA[Java]]></category>
		<category><![CDATA[Shiro]]></category>
		<category><![CDATA[Software]]></category>

		<guid isPermaLink="false">http://leshazlewood.com/?p=101</guid>
		<description><![CDATA[<p>For those that might be interested and if you are near the San Francisco/Bay area, I will be presenting <a href="http://www.sfjava.org/calendar/13539905/">Super Simple Application Security with Apache Shiro</a> to the San Francisco Java User Group on 12 October 2010 at 6:30 pm PDT. Please see the link to RSVP &#8211; seats are limited!</p>]]></description>
			<content:encoded><![CDATA[<p>For those that might be interested and if you are near the San Francisco/Bay area, I will be presenting <a href="http://www.sfjava.org/calendar/13539905/">Super Simple Application Security with Apache Shiro</a> to the San Francisco Java User Group on 12 October 2010 at 6:30 pm PDT.  Please see the link to RSVP &#8211; seats are limited!</p>
]]></content:encoded>
			<wfw:commentRss>http://leshazlewood.com/2010/09/20/apache-shiro-san-francisco-jug-presentation/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>OSGi, Maven, Pax, and web applications</title>
		<link>http://leshazlewood.com/2010/09/08/osgi-maven-pax-and-web-applications/</link>
		<comments>http://leshazlewood.com/2010/09/08/osgi-maven-pax-and-web-applications/#comments</comments>
		<pubDate>Wed, 08 Sep 2010 23:26:17 +0000</pubDate>
		<dc:creator>admin</dc:creator>
				<category><![CDATA[Java]]></category>
		<category><![CDATA[OSGi]]></category>
		<category><![CDATA[Software]]></category>

		<guid isPermaLink="false">http://leshazlewood.com/?p=71</guid>
		<description><![CDATA[<p>This post is written for developers that are trying to deploy a .war file inside of an OSGi runtime environment.  I experienced a lot of pain along the way to making my solution work, so hopefully this will alleviate any pain that you might have.</p> The Scenario <p>This post primarily reflects the environment in which [...]]]></description>
			<content:encoded><![CDATA[<p>This post is written for developers that are trying to deploy a .war file inside of an OSGi runtime environment.  I experienced a lot of pain along the way to making my solution work, so hopefully this will alleviate any pain that you might have.</p>
<h2>The Scenario</h2>
<p>This post primarily reflects the environment in which I am writing and deploying my application.  Here are the key points that led me up to my course of action:</p>
<ul>
<li>I use Maven to manage my project.</li>
<li>I already had an existing web application .war that had no &#8216;knowledge&#8217; of OSGi.</li>
<li>I knew I would need to &#8216;OSGi-ify&#8217; the .war and turn it into a bundle, since this is required by the OSGi 4.2 Enterprise specification</li>
<li>Once I had the new OSGi-compatible .war, I would need to quickly and easily start it up in an OSGi environment to test it.</li>
</ul>
<h2>The Setup</h2>
<p>Based on my above environment/needs, I decided on the following:</p>
<ul>
<li>Because I use maven and I have created plain (non-web) OSGi bundles with the <a title="Maven Bundle Plugin" href="http://felix.apache.org/site/apache-felix-maven-bundle-plugin-bnd.html" target="_blank">Maven Bundle Plugin</a> in the past, it would make sense for me to use it again to make my .war into a bundle.</li>
<li>Again, because I use maven, I want to launch my &#8216;OSGi-ified&#8217; .war in an OSGi environment directly from maven.  I didn&#8217;t want to do anything painful like manually copy and install the .war into an OSGi container installed elsewhere.  That would be a pain that would frustrate me and infringe on my productivity.The <a title="Maven Pax Plugin" href="http://www.ops4j.org/projects/pax/construct/maven-pax-plugin/" target="_blank">Maven Pax Plugin</a> looked like it could easily start an OSGi runtime (Felix, Equinox, etc)  as well as provide the additional web support that is required to launch .war files.  So, I decided to give that a go.</li>
</ul>
<h2>The Solution</h2>
<h3>Step 1: Make your .war OSGi-compatible</h3>
<p>This was actually pretty easy, but there were two major problems I encountered along the way that caused me hours of suffering.  May my pain be your salvation! <img src='http://leshazlewood.com/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' /> </p>
<p>Using the <code>maven-bundle-plugin</code>, you essentially tell it to create a <code>MANIFEST.MF</code> file with OSGi entries, and then you tell the <code>maven-war-plugin</code> to use that generated file.  All it takes is adding the following two plugins to your war project&#8217;s <code>&lt;plugins&gt;</code> section:</p>
<pre>
&lt;plugin&gt;
  &lt;artifactId&gt;maven-war-plugin&lt;/artifactId&gt;
  &lt;configuration&gt;
    &lt;archive&gt;
      &lt;manifestFile&gt;${project.build.outputDirectory}/META-INF/MANIFEST.MF&lt;/manifestFile&gt;
    &lt;/archive&gt;
  &lt;/configuration&gt;
&lt;/plugin&gt;
&lt;!--
    Enable support for non-bundle packaging types
    See: http://felix.apache.org/site/apache-felix-maven-bundle-plugin-bnd.html
--&gt;
&lt;plugin&gt;
  &lt;groupId&gt;org.apache.felix&lt;/groupId&gt;
  &lt;artifactId&gt;maven-bundle-plugin&lt;/artifactId&gt;
  &lt;extensions&gt;true&lt;/extensions&gt;
  &lt;executions&gt;
    &lt;execution&gt;
      &lt;id&gt;bundle-manifest&lt;/id&gt;
      &lt;phase&gt;process-classes&lt;/phase&gt;
      &lt;goals&gt;
        &lt;goal&gt;manifest&lt;/goal&gt;
      &lt;/goals&gt;
      &lt;configuration&gt;
        &lt;instructions&gt;
          &lt;Bundle-SymbolicName&gt;CHANGEME&lt;/Bundle-SymbolicName&gt;
          &lt;Export-Package/&gt;
          &lt;Import-Package&gt;javax.servlet,javax.servlet.http,javax.servlet.*,javax.servlet.jsp.*,javax.servlet.jsp.jstl.*&lt;/Import-Package&gt;
          &lt;DynamicImport-Package&gt;javax.*, org.xml.sax, org.xml.sax.*, org.w3c.*&lt;/DynamicImport-Package&gt;
          &lt;Bundle-ClassPath&gt;.,WEB-INF/classes&lt;/Bundle-ClassPath&gt;
          &lt;Embed-Directory&gt;WEB-INF/lib&lt;/Embed-Directory&gt;
          &lt;Embed-Dependency&gt;*;scope=compile|runtime&lt;/Embed-Dependency&gt;
          &lt;Embed-Transitive&gt;true&lt;/Embed-Transitive&gt;
          &lt;Web-ContextPath&gt;CHANGEME&lt;/Web-ContextPath&gt;
          &lt;Webapp-Context&gt;CHANGEME&lt;/Webapp-Context&gt;
        &lt;/instructions&gt;
      &lt;/configuration&gt;
    &lt;/execution&gt;
  &lt;/executions&gt;
  &lt;configuration&gt;
    &lt;supportedProjectTypes&gt;
      &lt;supportedProjectType&gt;jar&lt;/supportedProjectType&gt;
      &lt;supportedProjectType&gt;bundle&lt;/supportedProjectType&gt;
      &lt;supportedProjectType&gt;war&lt;/supportedProjectType&gt;
    &lt;/supportedProjectTypes&gt;
    &lt;instructions&gt;
      &lt;!-- ... etc ... --&gt;
    &lt;/instructions&gt;
  &lt;/configuration&gt;
&lt;/plugin&gt;
</pre>
<p>Just remember to set the values appropriate to your application, namely those for the <code>&lt;Bundle-SymbolicName&gt;</code> and <code>&lt;Web-ContextPath&gt;</code> and <code>&lt;Webapp-Context&gt;</code> entries (we&#8217;ll discuss the latter two shortly).</p>
<p>After you&#8217;ve added the plugins and changed the appropriate values, a normal maven build (e.g. <code>mvn package</code> or <code>mvn install</code>) will produce your OSGi-compatible .war!</p>
<p>But what you see is deceptively simple &#8211; there are two things that prevented me from deploying successfully for hours.  Make sure you avoid them:</p>
<h4>Manifest Entries: <code>&lt;Web-ContextPath&gt;</code> or <code>&lt;Webapp-Context&gt;</code>?</h4>
<p>Notice the two following lines in the <code>maven-bundle-plugin</code>&#8216;s <code>&lt;instructions&gt;</code> element:</p>
<pre>
&lt;Web-ContextPath&gt;CHANGEME&lt;/Web-ContextPath&gt;
&lt;Webapp-Context&gt;CHANGEME&lt;/Webapp-Context&gt;
</pre>
<p>Doesn&#8217;t that look annoyingly repetitive to you?  Why do we need two?</p>
<p>Well, let&#8217;s cover what they are.  As you might have guessed by looking at either one individually, they specify the context path under which your web app will be accessible, for example <code>http://localhost:8080/myContextPath</code>.  If you don&#8217;t specify them, most OSGi web container implementations will default your context path to your .war&#8217;s <code>Bundle-SymbolicName</code>,  For example, servicing your webapp from <code>http://localhost:8080/com.company.my.bundle.symbolicName</code>.  That&#8217;s just plain ugly, so you really want to specify them to ensure your urls look sane.  But why are there two entries?</p>
<p>When I originally added the manifest entries, the only one I specified was the <code>&lt;Web-ContextPath&gt;</code> entry.  This is after all the correct Manifest entry as mandated by the OSGi 4.2 Web Applications Specification (Chapter 128 in the OSGi Compendium document).  I read the specification and added that entry accordingly.  All should work fine then, right?</p>
<p>Well, it would have if the Pax Web support used by the <code>maven-pax-plugin</code> used to launch the .war (covered below), was 100% OSGi 4.2 compliant.  It&#8217;s not.  I sat at my desk for hours, running various tests until 3:30 in the morning, swearing at myself that I couldn&#8217;t believe I was screwing things up, when all the documentation said it should be right!</p>
<p>Much to my early-morning chagrin, I discovered that the existing Pax Web support (0.7.2 at the time of this writing), does not yet understand the OSGi standard <code>&lt;Web-ContextPath&gt;</code> entry.  There is currently an outstanding <a title="Jira issue" href="http://issues.ops4j.org/browse/PAXWEB-206" target="_blank">Jira issue</a> for them to fix this.  Until that is fixed, we&#8217;ll need to add both: the OSGi standard one to ensure it works in your standard OSGi deployment environment and the Pax Web-specific <code>&lt;Webapp-Context&gt;</code> one to make Pax happy while you&#8217;re testing with Maven.  When that Jira issue is fixed, you can remove it and keep the standard one.</p>
<p>But what if you don&#8217;t want to launch your .war using the <code>maven-pax-plugin</code>?  You can remove the non-standard entry, right?  </p>
<p>Well, not so fast &#8211; there are OSGi container distributions, such as <a title="Apache Karaf"  href="http://karaf.apache.org/" _target="_blank">Apache Karaf</a> (which is the Felix OSGi runtime + a lot of nice enterprise features), that use the same exact Pax Web mechanism as their implementation to support .war deployments.  That means if you deploy your .war to Apache Karaf as your production environment, because Karaf uses the same Pax Web mechanisms, the non-standard <code>&lt;Webapp-Context&gt;</code> entry must still be specified.</p>
<p>Its safest to keep both entries and have them both reference a maven property that you can set once to avoid repeating yourself:</p>
<pre>
&lt;properties&gt;
    &lt;web.contextPath&gt;foo&lt;/web.contextPath&gt;
    ...
&lt;/properties&gt;

...
    &lt;instructions&gt;
        ...
        &lt;Web-ContextPath&gt;${web.contextPath}&lt;/Web-ContextPath&gt;
        &lt;Webapp-Context&gt;${web.contextPath}&lt;/Webapp-Context&gt;
    &lt;/instructions&gt;
...
</pre>
<h4>web.xml: use a <code>&lt;welcome-file-list&gt;</code></h4>
<p>Now that we got the Manifest entries out of the way, there&#8217;s one final issue that caused me grief: welcome files.</p>
<p>My web app has an <code>index.jsp</code> file at the root of the war file.  It is incredibly simple &#8211; all it does is redirect the user to a nice &#8216;home&#8217; landing page:</p>
<pre>
&lt;%@ page session=&quot;false&quot; %&gt;
&lt;%@ taglib prefix=&quot;c&quot; uri=&quot;http://java.sun.com/jsp/jstl/core&quot; %&gt;
&lt;%-- Redirect to the home page --%&gt;
&lt;c:redirect url=&quot;/home/&quot;/&gt;
</pre>
<p>Trivial, right?</p>
<p>Well, my <code>web.xml</code> in my pre-OSGi .war did NOT have a <code>&lt;welcome-file-list&gt;</code> entry in it.  Tomcat and Jetty don&#8217;t care about this &#8211; they have a list of sensible defaults.  Because of that, I haven&#8217;t specified a welcome-file-list in years &#8211; I just didn&#8217;t think about it.</p>
<p>However, the  the OSGi war deployer mechanism I was using (Pax Web&#8217;s war extender) does require it.  It was not able to handle a request coming in to <code>http://localhost:8080/myapp</code>.  It didn&#8217;t know to automatically use the <code>http://localhost:8080/myapp/index.jsp</code> file.</p>
<p>This was equally as frustrating as the non-standard Manifest entry discussed above and further contributed to my hours-long &#8220;shoot me now, I hate OSGi&#8221; session &#8211; there were no error messages explaining why the request failed (terribly frustrating).  But I eventually figured it out by going through the arduous process of setting up an entirely separate &#8216;clean room&#8217; .war project and trying different things from scratch.</p>
<p>I added the following XML snippet at the bottom of my web.xml file, and all was well again:</p>
<pre>
&lt;web-app ...&gt;
    ...
    &lt;welcome-file-list&gt;
        &lt;welcome-file&gt;index.jsp&lt;/welcome-file&gt;
    &lt;/welcome-file-list&gt;

&lt;/web-app&gt;
</pre>
<h3>Step 2: Launch your OSGi .war from Maven</h3>
<p>Now that you have an OSGi-compatible .war, ideally you want to be able to launch it and test it immediately.  It would be a major pain to have to build your .war and manually copy it or install it into your OSGi deployment environment (e.g. Apache Karaf, Eclipse Virgo, Apache Geronimo, etc&#8230;).  We want instant gratification with no setup!!!</p>
<p>It&#8217;s the <code>maven-pax-plugin</code> to the rescue! (with the exception of the manifest entry and welcome-file-list complaints above)</p>
<p>Once you&#8217;ve completed both parts of step 1 above, the rest is smooth sailing.  Add the following plugin to your .war project&#8217;s <code>&lt;plugins&gt;</code> section:</p>
<pre>
&lt;plugin&gt;
    &lt;groupId&gt;org.ops4j&lt;/groupId&gt;
    &lt;artifactId&gt;maven-pax-plugin&lt;/artifactId&gt;
    &lt;configuration&gt;
        &lt;provision&gt;
            &lt;param&gt;--platform=felix&lt;/param&gt;
            &lt;param&gt;--profiles=compendium,web,war&lt;/param&gt;
        &lt;/provision&gt;
    &lt;/configuration&gt;
&lt;/plugin&gt;
</pre>
<p>Notice that the first <code>&lt;param&gt;</code>, <code>--platform=felix</code>,  reflects my personal test environment.  You could specify <code>--platform=equinox</code> to use the Eclipse Equinox OSGi framework instead.  You could also specify other platforms as well.  See the <a href="http://www.ops4j.org/projects/pax/construct/maven-pax-plugin/index.html">maven-pax-plugin</a> and <a title="Pax Runner" href="http://paxrunner.ops4j.org/display/paxrunner/Pax+Runner" target="_blank">Pax Runner</a> documentation for more options.  You&#8217;ll naturally choose settings that will best reflect your production runtime environment.</p>
<p>The second <code>&lt;param&gt;</code> is what is important for testing .wars.  It specifies Pax Runner profiles that enable .wars to be deployed.  You can add other profiles as necessary, but those three are required for deploying .wars.</p>
<p>To run your web app, just execute the following:</p>
<p><code>mvn install pax:run</code></p>
<p>Super easy!</p>
<h2>Success!</h2>
<p>Once the two issues above were taken care of, and I could launch my new OSGi .war, it was accessible via <code>http://localhost:8080/myapp</code> and everything worked as expected.</p>
<p>But I hope this helps you, weary-eyed OSGi blog-searcher.  Good luck!</p>
]]></content:encoded>
			<wfw:commentRss>http://leshazlewood.com/2010/09/08/osgi-maven-pax-and-web-applications/feed/</wfw:commentRss>
		<slash:comments>4</slash:comments>
		</item>
		<item>
		<title>Free as in Speach or Free as in Beer?</title>
		<link>http://leshazlewood.com/2009/12/21/free-as-in-beer/</link>
		<comments>http://leshazlewood.com/2009/12/21/free-as-in-beer/#comments</comments>
		<pubDate>Mon, 21 Dec 2009 19:17:00 +0000</pubDate>
		<dc:creator>admin</dc:creator>
				<category><![CDATA[General]]></category>
		<category><![CDATA[Software]]></category>

		<guid isPermaLink="false">http://www.leshazlewood.com/?p=54</guid>
		<description><![CDATA[<p>I never understood this line when discussing Open-Source Software. Richard Stallman attempted to clarify the differences in Open-Source distribution models by saying &#8220;Free as in speach, not free as in beer&#8221;.</p> <p>&#8220;Free as in beer&#8221; is meant to signify a gratis, or no-cost (no money) distribution (but it is not necessarily free to do with [...]]]></description>
			<content:encoded><![CDATA[<p>I never understood this line when discussing Open-Source Software.  Richard Stallman attempted to clarify the differences in Open-Source distribution models by saying &#8220;Free as in speach, not free as in beer&#8221;.</p>
<p>&#8220;Free as in beer&#8221; is meant to signify a gratis, or no-cost (no money) distribution (but it is not necessarily free to do with as you please), while &#8220;Free as in speach&#8221; is meant to represent freedom of use &#8211; with little or no restrictions.</p>
<p>When was the last time you received free beer?</p>
<p>And if you did receive a free beer, couldn&#8217;t you do with it as you pleased?  Like drink it or maybe even give it to another friend because you know if you drink more, you&#8217;ll have no cognitive functions left to try and understand what the stupid phrase &#8220;Free as in speach, but not free as in beer&#8221; means?</p>
<p>I think we shud shtop wif fis analogie.  It surtanly onli cnfsed me mur. Hiccup.</p>
<p>Wikipedia explains it well enough by saying <a href="http://en.wikipedia.org/wiki/Gratis_versus_Libre">Gratis vs Libre</a></p>
<p>See?  Latin <em>is</em> still useful!</p>
<p>Hiccup.</p>
]]></content:encoded>
			<wfw:commentRss>http://leshazlewood.com/2009/12/21/free-as-in-beer/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Java Class Naming Conventions</title>
		<link>http://leshazlewood.com/2009/03/03/java-class-naming-conventions/</link>
		<comments>http://leshazlewood.com/2009/03/03/java-class-naming-conventions/#comments</comments>
		<pubDate>Tue, 03 Mar 2009 17:42:04 +0000</pubDate>
		<dc:creator>admin</dc:creator>
				<category><![CDATA[Java]]></category>
		<category><![CDATA[Software]]></category>

		<guid isPermaLink="false">http://www.leshazlewood.com/?p=49</guid>
		<description><![CDATA[<p>Ok, I&#8217;m about to go on a rant, because I come across something regularly that really, really, REALLY irritates me:</p> <p>Whenever you see a class that implements an interface SomeName, and the name of that class is SomeNameImpl.</p> <p>Guess what folks, EVERY implementation of an interface is an &#8216;Impl&#8217;. If you suffix &#8216;Impl&#8217; at the [...]]]></description>
			<content:encoded><![CDATA[<p>Ok, I&#8217;m about to go on a rant, because I come across something regularly that really, really, <em>REALLY</em> irritates me:</p>
<p>Whenever you see a class that implements an interface <em>SomeName</em>, and the name of that class is <em>SomeName</em><strong>Impl</strong>.</p>
<p>Guess what folks, <strong>EVERY</strong> implementation of an interface is an &#8216;Impl&#8217;.  If you suffix &#8216;Impl&#8217; at the end of your class name, you&#8217;re being short sighted and portraying a potential lack of understanding of Interface-Driven Design:  that you can have more than one implementation.</p>
<p>What if you ever create a new implementation?  What if, when testing other components, you create a Test<em>SomeName</em> implementation or a Mock<em>SomeName</em> implementation?  Then the <em>SomeName</em>Impl doesn&#8217;t make much sense anymore, does it?  It could be a cause of confusion as to why you have more than one &#8216;Impl&#8217;, or, worse, perhaps it might make people think that you should <em>only</em> ever have one &#8216;Impl&#8217;.</p>
<p>Instead, if you need a default implementation, and can&#8217;t yet think of other cases where you might have other implementations, just call it Default<em>SomeName</em>.  Then you&#8217;re telling the world, &#8220;Hey, this is our default implementation of this interface, and if any more ever are needed, we can create them, <em>prefixed</em> with a more meaningful name.&#8221;.</p>
<p>Yes, I&#8217;m an OO naming zealot, but you&#8217;d be surprised at how this little change, in conjunction with other &#8216;trivial&#8217; changes, make code more readable, easy to understand, and most important, adaptable to change over time.</p>
]]></content:encoded>
			<wfw:commentRss>http://leshazlewood.com/2009/03/03/java-class-naming-conventions/feed/</wfw:commentRss>
		<slash:comments>8</slash:comments>
		</item>
		<item>
		<title>Root Persistent Class for ORM Hierarchies (Hibernate, et. al.)</title>
		<link>http://leshazlewood.com/2008/01/01/root-persistent-class-for-orm-hierarchies-hibernate-et-al/</link>
		<comments>http://leshazlewood.com/2008/01/01/root-persistent-class-for-orm-hierarchies-hibernate-et-al/#comments</comments>
		<pubDate>Tue, 01 Jan 2008 18:29:38 +0000</pubDate>
		<dc:creator>admin</dc:creator>
				<category><![CDATA[General]]></category>
		<category><![CDATA[Java]]></category>
		<category><![CDATA[Software]]></category>

		<guid isPermaLink="false">http://www.leshazlewood.com/?p=39</guid>
		<description><![CDATA[<p>Ok, I&#8217;m about to divulge to the world one of my little programming gems &#8211; something I&#8217;ve used on every single project for almost the last 4 years now. It is very easily translated to any other OO language as well, especially C# for the .NET/Hibernate.NET folks.</p> <p>I haven&#8217;t been keeping it secret or anything, [...]]]></description>
			<content:encoded><![CDATA[<p>Ok, I&#8217;m about to divulge to the world one of my little programming gems &#8211; something I&#8217;ve used on <em>every single project</em> for almost the last 4 years now.  It is very easily translated to any other OO language as well, especially C# for the .NET/Hibernate.NET folks.</p>
<p>I haven&#8217;t been keeping it secret or anything, I guess I just never took the time to write it out for general public.  So when someone reading my blog asked to see the source for it, I figured now is as good a time as any to write about it.</p>
<p>It is a root/base class from which all my persistent Classes extend.  To put it another way, if I have Java instances that I need to store to a database through Hibernate or some other EIS API, every one of those instance Classes extend from this base class (either directly or indirectly in an OO hierarchy).  Every entity in every persistent class hierarchy I&#8217;ve used in the last 4 years has it as its hierarchy root &#8211; it is versatile and resilient <img src='http://leshazlewood.com/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' /> </p>
<p>Now, if you&#8217;ve used Hibernate much before, you&#8217;ll realize this isn&#8217;t the world&#8217;s biggest secret &#8211; most people do something similar.  Its a great idea.  I&#8217;m just making mine available to the world in case there are those that haven&#8217;t done something similar yet, or if those who have just want to see how I do things.</p>
<p>What is this class called?  I call it <code>Entity</code>.  In Object-Relational Mapping circles, the word Entity often comes up in the context of object persistence discussions &#8211; &#8220;Persistent Object&#8221;, &#8220;Persistent Entity&#8221;, &#8220;Base Persistent Object&#8221;, etc.  I personally think &#8220;Entity&#8221; is elegantly succinct, so I stuck with it.</p>
<p>Before going on to the code, I just want to clarify my Entity class a little bit.  It is <strong>not</strong> an implementation of what many call the &#8220;Active Record design pattern&#8221;.  This means this base entity class doesn&#8217;t know how to persist or delete itself via any <code>save()</code> or <code>delete()</code> methods.</p>
<p>I&#8217;m a firm believer in keeping persistence logic code <em>out</em> of my domain model to prevent the chance of polluting the rest of my application with those APIs (it goes beyond API pollution too &#8211; google the principal of &#8220;<a href="http://www.google.com/search?q=Low+Coupling+High+Cohesion">Low Coupling, High Cohesion</a>&#8221; for more info).  Anyway, and I relegate all such logic to <a href="http://en.wikipedia.org/wiki/Data_Access_Object">DAO</a> implementations and all of my domain classes remain nice and clean.</p>
<p>Ok, so now that point is settled, here&#8217;s my oh-so-yummy-and-incredibly-useful Entity class:</p>
<pre>import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;

import java.io.Serializable;

/**
 * Root parent class for all persistent object entities.
 *
 * &lt;strong&gt;NOTE:&lt;/strong&gt; Subclasses should &lt;em&gt;always&lt;/em&gt; provide a unique
 * onEquals() and hashCode() implementation and these should not use
 * the id() property - i.e. always keep in mind the subclass&#039; &#039;business keys&#039;
 * when implementing those methods.
 *
 * @author Les Hazlewood
 */
public abstract class Entity implements Identifiable, Serializable, Cloneable {

    protected transient final Log log = LogFactory.getLog(getClass());

    /**
     * RDBMS Primary key, aka &#039;surrogate key&#039;.  Long surrogate keys are best
     * for RDBMS performance (for many reasons that can&#039;t be expanded on here)
     * But, every single table should _always_ have a &#039;business key&#039; - a unique
     * constraint across one or more columns that guarantee row duplicates will
     * never occur. Null value means the object hasn&#039;t been persisted to the RDBMS
     */
    protected Long id = null;

    /**
     * Used for optimistic locking to ensure two threads (even across different machines)
     * don&#039;t simultaneously overwrite entity state - not necessarily used by all subclasses.
     * Pretty much required if in a high-concurrency environment and/or if using distributed
     * caching in a cluster.   It (and its corresponding mutator methods) is not called
     * &#039;version&#039; to prevent eliminating that name from subclasses should the business
     * domain naming conventions require it.  Also &#039;entityVersion&#039; is self-documenting
     * and leaves little room for incorrect interpretation.
     */
    protected int entityVersion = -1;

    public Entity() {
    }

    public Long getId() {
        return this.id;
    }

    /**
     * Should &lt;em&gt;never&lt;/em&gt; be called directly.  Only via Hibernate or other EIS framework, since
     * they get the ID from the RDBMS directly.
     *
     * This method can be removed entirely if the EIS framework supports setting the ID property
     * directly (e.g. through reflection).  Hibernate does support this, it is called &#039;property access&#039;.
     */
    public void setId(Long id) {
        this.id = id;
    }

    public int getEntityVersion() {
        return this.entityVersion;
    }

    /**
     * For the same reasons as the setId() method, this should only be called by a
     * framework and never directly.  Can be removed if the framework supports property access.
     */
    public void setEntityVersion(int entityVersion) {
        this.entityVersion = entityVersion;
    }

    /**
     * This method is declared final and does a lot of performance optimization:
     *
     * It delegates the actual &quot;equals&quot; check to subclasses via the onEquals method, but
     * it will only do so if the object for equality comparison is
     *
     * &lt;ol&gt;
     * &lt;li&gt;not the same memory location as the current object (fast sanity check)&lt;/li&gt;
     * &lt;li&gt;of type Entity or one of its subclasses&lt;/li&gt;
     * &lt;li&gt;Does not have the same id() property&lt;/li&gt;
     * &lt;/ol&gt;
     *
     * #3 is important:  this is because if two different entities have the ID property
     * already populated, then they have already been inserted in the database, and
     * because of unique constraints on the database (i.e. your &#039;business key&#039;), you
     * can &lt;em&gt;guarantee&lt;/em&gt; that the objects are not the same and there is no need
     * to incur attribute-based comparisons for equals() checks.
     *
     * This little technique is a massive performance improvement given the number of times
     * equals checks happen in most applications.
     */
    public final boolean equals(Object o) {
        if (o == this) {
            return true;
        }

        if (o instanceof Entity) {
            Entity e = (Entity) o;
            Long thisId = getId();
            Long otherId = e.getId();
            if (thisId != null &amp;&amp; otherId != null) {
                return thisId.equals(otherId) &amp;&amp;
                        getClass().isAssignableFrom(e.getClass());
            } else {
                return onEquals(e);
            }
        }

        return false;
    }

    /**
     * Subclasses must do an equals comparison based on business keys here.
     */
    public abstract boolean onEquals(Entity e);

    public abstract int hashCode();

    /**
     * If children classes override they must always call super.clone() to get the object
     * with which they manipulate further to clone remaining attributes.  Never acquire
     * the cloned object directly via &#039;new&#039; operator (this is true regardless of this Entity
     * class or not).
     */
    @Override
    @SuppressWarnings({&quot;CloneDoesntDeclareCloneNotSupportedException&quot;})
    public Object clone() {

        Entity e;
        try {
            e = (Entity) super.clone();
        } catch (CloneNotSupportedException neverHappens) {
            // Should _never_ happen since this class is Cloneable and
            // a direct subclass of Object
            throw new InternalError(&quot;Unable to clone object of type [&quot; + getClass().getName() + &quot;]&quot;);
        }

        e.setId(null);
        e.setEntityVersion(-1);
        return e;
    }

    /**
     * Returns a StringBuffer representing the toString function of the class implementation. This
     * should be overridden by all children classes using &lt;tt&gt;super.toStringBuffer()&lt;/tt&gt; as the
     * base, adding properties to the returned StringBuffer.
     *
     * @return a &lt;tt&gt;StringBuffer&lt;/tt&gt; reperesenting the &lt;tt&gt;toString&lt;/tt&gt; value of this object.
     */
    public StringBuffer toStringBuffer() {
        StringBuffer sb = new StringBuffer();
        sb.append(&quot;id=&quot;).append(getId());
        return sb;
    }

    /**
     * Returns toStringBuffer().toString().  Declared as &#039;final&#039; to require subclasses to override
     * the {@link #toStringBuffer()} method, a cleaner and better performing mechanism for toString();
     *
     * @return toStringBuffer().toString()
     */
    public final String toString() {
        return toStringBuffer().toString();
    }
}
</pre>
<p>You&#8217;ll notice that the Entity class also implements <code>Identifiable</code>, which is nothing more than this:</p>
<pre>
/**
  * @author Les Hazlewood
  */
public interface Identifiable {
    Long getId();
}
</pre>
<p>This doesn&#8217;t look too useful, but I have another interface that subclasses (&#8216;sub interfaces&#8217;?) it:</p>
<pre>/**
  * @author Les Hazlewood
  */
public interface Referenceable extends Identifiable {
    String getLabel();
}
</pre>
<p><code>Referenceable</code> is particularly useful in GUI/web code where you might want to present a list of options to the user, and the list-generation code only cares about IDs and readable strings to present to the user.  For example, a drop-down/select box:</p>
<p><code>$referenceable.label</code></p>
<p>The list generation code doesn&#8217;t care if the collection it is processing has User elements, or EmailAddress elements, or anything else.  Ahh, the beauty of polymorphism <img src='http://leshazlewood.com/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' /> </p>
<p>Anyway, I hope you find this Entity class as useful as I have &#8211; it is the staple by which I develop all of my domain models in Java.</p>
<p>Cheers,</p>
<p>Les</p>
]]></content:encoded>
			<wfw:commentRss>http://leshazlewood.com/2008/01/01/root-persistent-class-for-orm-hierarchies-hibernate-et-al/feed/</wfw:commentRss>
		<slash:comments>5</slash:comments>
		</item>
		<item>
		<title>Configuration-hell remedy with Singleton injection &#8211; DON&#039;T do it</title>
		<link>http://leshazlewood.com/2007/12/10/configuration-hell-remedy-with-singleton-injection-dont-do-it/</link>
		<comments>http://leshazlewood.com/2007/12/10/configuration-hell-remedy-with-singleton-injection-dont-do-it/#comments</comments>
		<pubDate>Tue, 11 Dec 2007 03:22:12 +0000</pubDate>
		<dc:creator>admin</dc:creator>
				<category><![CDATA[General]]></category>
		<category><![CDATA[Java]]></category>
		<category><![CDATA[Software]]></category>

		<guid isPermaLink="false">http://www.leshazlewood.com/?p=38</guid>
		<description><![CDATA[<p>So, I just finished reading <a href="http://springtips.blogspot.com/2007/06/configuration-hell-remedy-with.html">this blog post</a> about Spring configuration advocating static getInstance() methods in some places in your code to reduce the amount of Spring xml config. Since I posted a reply on that blog, and the author would probably be inclined to moderate my entry and delete it because I directly [...]]]></description>
			<content:encoded><![CDATA[<p>So, I just finished reading <a href="http://springtips.blogspot.com/2007/06/configuration-hell-remedy-with.html">this blog post</a> about Spring configuration advocating static <code>getInstance()</code> methods in some places in your code to reduce the amount of Spring xml config.  Since I posted a reply on that blog, and the author would probably be inclined to moderate my entry and delete it because I directly oppose his position, I&#8217;ve reposted it here for the benefit of others to read.</p>
<p>THAT POST ADVOCATES POOR ARCHITECTURE.  IGNORE IT.</p>
<p>If you&#8217;re relatively new to the Spring framework, ignore the recommendations in that post entirely &#8211; you&#8217;ll be saving yourself a _lot_ of pain in your software architecture.</p>
<p>Basically, here&#8217;s my reply:</p>
<p>This is a really bad idea and is exactly what Spring pojo-based Dependency Injection was created to avoid &#8211; to replace the Service Locator pattern.  What you&#8217;re providing in a static getInstance() call is essentially a type-specific Service Locator.</p>
<p>Statics are evil &#8211; they&#8217;re inherently non-OO and usually encourage poor programming practices, especially the proliferation of unnecessary functional programming in an OO language.  They should only be used to overcome poor programming situations outside of your control &#8211; i.e. a tool to use in an extremely limited basis only when you can&#8217;t use something else.</p>
<p>And although what you describe might make your life easier in the immediate sense, it significantly complicates it in other ways.  How, for example, would you unit test your code properly without introducing dependencies not required for the test?  Cleaner instance-level DI allows you do do things such as creating mock objects and anonymous inner classes for testing that is not possible with static singletons or where you would have to change a lot of code.</p>
<p>If you want to make your life easy, use autowiring &#8211; that&#8217;s exactly why it was created.  The new Spring 2.0 XML namespaces also simplify things greatly, reducing XML config.  And, with IDEs like Eclipse and IntelliJ IDEA that actually can traverse, manage, and refactor the XML spring files for you, the &#8220;XML Hell&#8221; argument for using Static singletons, especially when your own code suffers greatly in flexibility, is not really an issue.</p>
<p>Bottom line &#8211; never let laziness dictate your software architecture (especially when similar alternatives like autowiring exist), and stick with the pragmatic, well-thought and proven truly Object-Oriented solution.</p>
<p>I just thought it important to raise the issue on this for anybody reading this blog entry, especially those relatively new to Spring.  What is mentioned is _not_ a good idea for 99% of cases, and the less-experienced Spring folks shouldn&#8217;t be led down a dangerous path.  It could introduce really bad habits that would hurt you later on.</p>
]]></content:encoded>
			<wfw:commentRss>http://leshazlewood.com/2007/12/10/configuration-hell-remedy-with-singleton-injection-dont-do-it/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>Consistent Cache Configuration: Spring, Hibernate, EhCache, Shiro, et. al.</title>
		<link>http://leshazlewood.com/2007/12/06/spring-cache-configuration-hibernate-ehcache-et-al/</link>
		<comments>http://leshazlewood.com/2007/12/06/spring-cache-configuration-hibernate-ehcache-et-al/#comments</comments>
		<pubDate>Fri, 07 Dec 2007 02:55:42 +0000</pubDate>
		<dc:creator>admin</dc:creator>
				<category><![CDATA[General]]></category>
		<category><![CDATA[Java]]></category>
		<category><![CDATA[Software]]></category>

		<guid isPermaLink="false">http://www.leshazlewood.com/?p=37</guid>
		<description><![CDATA[<p>Have you ever wanted to use caching in your Spring/Hibernate application beyond just supporting Hibernate&#8217;s 2nd-level cache?</p> <p>If you know what a Hibernate 2nd-level cache is, you really know how huge its performance benefits are. Wouldn&#8217;t it be useful to utilize caching for other things in your application? Even if you don&#8217;t explicitly use a [...]]]></description>
			<content:encoded><![CDATA[<p>Have you ever wanted to use caching in your Spring/Hibernate application beyond just supporting Hibernate&#8217;s 2nd-level cache?</p>
<p>If you know what a Hibernate 2nd-level cache is, you really know how huge its performance benefits are.  Wouldn&#8217;t it be useful to utilize caching for other things in your application?  Even if you don&#8217;t explicitly use a caching API in your app, you still might already be using caching without knowing it &#8211; other open source frameworks in addition to Hibernate utilize caching internally for the same performance benefits.</p>
<p>This article explains how to achieve the following:</p>
<p>1) I know I&#8217;m going to utilize caching for Hibernate&#8217;s 2nd-level cache, but I want to enable that same caching support to other libraries and frameworks that might need it.  It would also nice to have if I ever need to use it in my own application code directly.</p>
<p>2) My application is Spring-configured, so I want to configure that caching support in Spring like everything else and then have all the frameworks/libraries, including Hibernate, to use these Spring-configured cache beans.</p>
<p>Unfortunately Hibernate makes this a pain to do.</p>
<p>Hibernate uses something called a CacheProvider to support its 2nd-level cache.  A Hibernate SessionFactory uses a single CacheProvider to maintain/manage the individual Cache instances used by the 2nd-level cache.</p>
<p>Now here&#8217;s the problem:  This CacheProvider is instantiated by Hibernate based on text configuration properties specified to the SessionFactory.   When the SessionFactory starts up, it reads these properties, finds the one called <code>hibernate.cache.provider_class</code> which specifies a fully-qualified class name of the CacheProvider implementation, and creates a new instance of that class via reflection.  It then uses that instance from then on to manage the Cache instances it needs.</p>
<p>For existing spring configs, here is a simplified example (note the 2nd hibernate property):</p>
<div class="code"><code><br />
<bean id="hibernateSessionFactory"<br />
    class="org.springframework.orm.hibernate3.LocalSessionFactoryBean"></p>
<property name="dataSource" ref="dataSource"/>
<property name="mappingResources">
<list>
        <!-- hbm.xml files listed... -->
        </list>
    </property>
<property name="hibernateProperties">
        <value><br />
        hibernate.dialect = org.hibernate.dialect.MySQL5InnoDBDialect<br />
        hibernate.cache.provider_class = net.sf.ehcache.hibernate.EhCacheProvider<br />
        </value>
    </property>
    <!-- Other properties as necessary --><br />
</bean><br />
</code></div>
<p>Why is this a problem?  Because you can&#8217;t easily configure your CacheProvider instance yourself and then just tell the SessionFactory to use it.  The SessionFactory interface and its default implementation do not have setter methods that would allow you to do so.  This means you can&#8217;t use Dependency-Injection to set the CacheProvider instance on the Hibernate SessionFactory in Spring or any other DI microcontainer.</p>
<p>This is a problem for me too.  The scenario that prompted this article happens to me quite a bit &#8211; I use Hibernate plus other libraries that benefit from caching.  My own open-source project, <a href="http://cwiki.apache.org/SHIRO/">Apache Shiro</a>, can use caching to greatly speed up security checks.  When I use Hibernate and Shiro in the same application, I want both frameworks to use the same underlying cache infrastructure.  And although Shiro supports DI for its cache support, Hibernate does not, which means I have to jump through hoops to get Hibernate to play nice.</p>
<p>Where does <a href="http://ehcache.sourceforge.net">Ehcache</a> come in to this?  Well, Ehcache is one of the more well-known and stable open-source caching solution for enterprise applications.  It is stable and has a long history, it is extremely efficient with goodies like smart multi-threading under the hood, and now with Ehcache 1.3+, supports multicast distributed caching in a cluster &#8211; a huge benefit in enterprise apps.  Basically, for open-source options, it is one of the best you can get. Cheers to Greg Luck for creating and supporting this great library (Another wonderful Open Source alternative is <a href="http://www.terracotta.org/">TerraCotta</a>, take a look at that too).</p>
<p>So, in this particular example, I&#8217;m using EhCache but I also want to use it not just for Hibernate, but for <a href="http://cwiki.apache.org/SHIRO/">Shiro</a> and everything else that could use a Cache.  And until now, I&#8217;ve been using Ehcache as Hibernate&#8217;s cache provider using the aforementioned text property.  Hibernate would create an instance of EhCacheProvider and use it internally.  Basically this EhCacheProvider implementation is a wrapper around EhCache&#8217;s own API of a CacheManager.</p>
<p>The CacheManager is <em>really</em> what I want to configure in Spring.  Typically it is good practice and much easier to specify a single CacheManager for an application, which uses a single ehcache.xml file for all configuration.  Then you can use this one ehcache.xml file for your Hibernate cache configuration, as well as for any other library that would use EhCache under the hood.</p>
<p>So, since you can&#8217;t inject a CacheManager into Hibernate&#8217;s SessionFactory, how do you do this in Spring?</p>
<p>Well, Since Hibernate instantiates the CacheProvider itself, and we can&#8217;t inject anything, our only option left is via static memory.  Blech, I know &#8211; I don&#8217;t like statics any more than you do, but don&#8217;t worry &#8211; it is _only_ used as a mechanism to make Hibernate play nice and its never used anywhere else in your config or application code.</p>
<p><strong>*</strong>Note that static memory will only allow a single CacheManager to be used across the entire VM, so if you need more than one Hibernate SessionFactory, each with its own separate cache configs, you&#8217;ll need to do more trickery (maybe 2 static fields?  one per SessionFactory?  You&#8217;ll know more about your app than I do, so I&#8217;ll leave how to do that to you.  But you can use this the following technique and expand on it for your environment).</p>
<p>Let&#8217;s get to the code, its only one class.   You&#8217;ll create your own CacheProvider implementation to statically reference a CacheManager instance.  The CacheManager instance will be configured in Spring, and we&#8217;ll get to that in a bit.  Here&#8217;s the CacheProvider implementation:</p>
<div class="code"><code><br />
package com.leshazlewood.hibernate;</p>
<p>import net.sf.ehcache.CacheManager;<br />
import org.apache.commons.logging.Log;<br />
import org.apache.commons.logging.LogFactory;<br />
import org.hibernate.cache.Cache;<br />
import org.hibernate.cache.CacheException;<br />
import org.hibernate.cache.CacheProvider;<br />
import org.hibernate.cache.Timestamper;</p>
<p>import java.util.Properties;</p>
<p>/**<br />
 * @author Les Hazlewood<br />
 */<br />
public class ExternalEhCacheProvider implements CacheProvider {</p>
<p>    protected transient final Log log = LogFactory.getLog(getClass());</p>
<p>    private static CacheManager cacheManager = null;</p>
<p>    /**<br />
     * This is the method that is called by an external framework (e.g. Spring) to set the<br />
     * constructed CacheManager for all instances of this class.  Therefore, when<br />
     * Hibernate instantiates this class, the previously statically injected CacheManager<br />
     * will be used for all hibernate calls to build caches.<br />
     * @param cacheManager the CacheManager instance to use for a HibernateSession factory using<br />
     * this class as its cache.provider_class.<br />
     */<br />
    public static void setCacheManager(CacheManager cacheManager) {<br />
        ExternalEhCacheProvider.cacheManager = cacheManager;<br />
    }</p>
<p>    public Cache buildCache(String name, Properties properties) throws CacheException {<br />
        try {<br />
            net.sf.ehcache.Ehcache cache = cacheManager.getEhcache(name);<br />
            if (cache == null) {<br />
                if ( log.isWarnEnabled() ) {<br />
                    log.warn( "Unable to find EHCache configuration for cache named [" + name + "].  Using defaults.");<br />
                }<br />
                cacheManager.addCache( name );<br />
                cache = cacheManager.getEhcache(name);<br />
                if (log.isDebugEnabled()) {<br />
                    log.debug("Started EHCache region '" + name + "'");<br />
                }<br />
            }<br />
            return new net.sf.ehcache.hibernate.EhCache(cache);<br />
        } catch (net.sf.ehcache.CacheException e) {<br />
            throw new CacheException(e);<br />
        }<br />
    }</p>
<p>    public long nextTimestamp() {<br />
        return Timestamper.next();<br />
    }</p>
<p>    public void start(Properties properties) throws CacheException {<br />
        //ignored, CacheManager lifecycle handled by the IoC container<br />
    }</p>
<p>    public void stop() {<br />
        //ignored, CacheManager lifecycle handled by the IoC container<br />
    }</p>
<p>    public boolean isMinimalPutsEnabledByDefault() {<br />
        return false;<br />
    }<br />
}<br />
</code></div>
<p>Ok, now that you have this class, what do you do with it?  Well the first thing is to change your <code>hibernate.cache.provider_class</code> value to now be <code>com.leshazlewood.hibernate.ExternalEhCacheProvider</code> in your Hibernate SessionFactory bean definition.  Then you want to define your CacheManager instance as a bean in your Spring config.  Next you want to tell this CacheProvider implementation to use that instance when Hibernate needs to use caching functions.</p>
<p>We do that via a cool little Spring trick &#8211; by using the MethodInvokingFactoryBean.  Basically this bean will call a static method at application startup with specified method arguments.  Its a handy little tool that we can use to statically call the setter method that makes the CacheProvider work:</p>
<div class="code"><code><br />
<bean id="ehcacheCacheManager" class="net.sf.ehcache.CacheManager" destroy-method="shutdown"><br />
    <!-- If you want to specify a custom ehcache.xml file (recommended in general but<br />
           required if defining more than one cacheManager beans),<br />
           uncomment the following line to point to your configuration.  You can use Spring's<br />
           Resource support to define the value.  If you don't uncomment,  EhCache's<br />
           internal defaults will be used.<br />
    <constructor-arg type="java.net.URL" value="classpath:/ehcache.xml"/><br />
    --><br />
</bean><br />
<bean id="cacheProviderCacheManagerInjector"<br />
         class="org.springframework.beans.factory.config.MethodInvokingFactoryBean"></p>
<property name="staticMethod" value="com.leshazlewood.hibernate.ExternalEhCacheProvider.setCacheManager"/>
<property name="arguments">
<list>
            <ref bean="ehcacheCacheManager"/>
        </list>
    </property>
</bean><br />
</code></div>
<p>So the above spring config says:  At application startup, create the CacheManager instance named &#8216;ehcacheCacheManager&#8217; and then inject it into the ExternalEhCacheProvider via that class&#8217;s &#8216;setCacheManager&#8217; static method.</p>
<p>But are we finished?</p>
<p>Well, not quite.  We have one piece of cleanup work to do.</p>
<p>The experienced Spring folks will recognize that there can possibly be a race condition with our Hibernate SessionFactory and CacheManager/CacheProvider definitions.  Yes, our Spring-configured CacheManager instance will be created and injected into the ExternalEhCacheProvider class correctly, and our Hibernate SessionFactory bean instance will be created correctly.  But, what if the Hibernate SessionFactory tries to use a ExternalEhCacheProvider instance before it is ready to be used? (i.e. before the static CacheManager property has been injected?)</p>
<p>To prevent this race condition and guarantee that the ExternalEhCacheProvider&#8217;s internal CacheManager instance is set so it is available when the Hibernate SessionFactory needs it, we use the spring bean &#8216;depends-on&#8217; attribute in our SessionFactory definition:</p>
<div class="code"><code><br />
<bean id="hibernateSessionFactory"<br />
    class="org.springframework.orm.hibernate3.LocalSessionFactoryBean"<br />
    depends-on="cacheProviderCacheManagerInjector"></p>
<property name="dataSource" ref="dataSource"/>
<property name="mappingResources">
<list>
        <!-- hbm.xml files listed... -->
        </list>
    </property>
<property name="hibernateProperties">
        <value><br />
        hibernate.dialect = org.hibernate.dialect.MySQL5InnoDBDialect<br />
        hibernate.cache.provider_class = com.leshazlewood.hibernate.ExternalEhCacheProvider<br />
        </value>
    </property>
    <!-- Other properties as necessary --><br />
</bean><br />
</code></div>
<p>So, although our Hibernate SessionFactory bean doesn&#8217;t actually use the CacheManager as a property &#8211; otherwise this whole article would be pointless <img src='http://leshazlewood.com/wp-includes/images/smilies/icon_wink.gif' alt=';)' class='wp-smiley' />  &#8211; we force it to wait until the cacheProviderCacheManagerInjector bean has done its work before we allow it to initialize.</p>
<p>We make the &#8216;depends-on&#8217; attribute point to this injector (MethodInvokingFactoryBean) instance specifically (as opposed to the ehcacheCacheManager bean) because we care that it is not only created, but also injected too.</p>
<p>There.  Now we&#8217;re done. <img src='http://leshazlewood.com/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' /> </p>
<p>Now when the Hibernate SessionFactory bean starts up and creates its <code>hibernate.cache.provider_class</code> instance, we can rest assured that it will access our Spring-configured CacheManager.</p>
<p>And, you&#8217;ll be able to use that same Spring-configured &#8216;ehcacheCacheManager&#8217; bean and inject it into Shiro, or any other framework that supports simple Dependency Injection.  Because this bean is an application singleton and uses a single config file, now all of your caching config across the entire application is easily manged from the same location &#8211; very convenient.</p>
<p>Have fun!</p>
]]></content:encoded>
			<wfw:commentRss>http://leshazlewood.com/2007/12/06/spring-cache-configuration-hibernate-ehcache-et-al/feed/</wfw:commentRss>
		<slash:comments>22</slash:comments>
		</item>
		<item>
		<title>Spring Application Bootstrap Data</title>
		<link>http://leshazlewood.com/2007/07/30/spring-application-bootstrap-data/</link>
		<comments>http://leshazlewood.com/2007/07/30/spring-application-bootstrap-data/#comments</comments>
		<pubDate>Tue, 31 Jul 2007 02:30:03 +0000</pubDate>
		<dc:creator>admin</dc:creator>
				<category><![CDATA[General]]></category>
		<category><![CDATA[Java]]></category>
		<category><![CDATA[Software]]></category>

		<guid isPermaLink="false">http://www.leshazlewood.com/?p=31</guid>
		<description><![CDATA[<p>When you install an application for the first time, many times you want &#8216;bootstrap&#8217; data to exist before the application is used for the very first time. Here&#8217;s a simple but easy technique to get bootstrap data inserted into your application upon first startup.</p> <p>Prior to the following approach, I used to have &#8216;default.data&#8217; and [...]]]></description>
			<content:encoded><![CDATA[<p>When you install an application for the first time, many times you want &#8216;bootstrap&#8217; data to exist before the application is used for the very first time.  Here&#8217;s a simple but easy technique to get bootstrap data inserted into your application upon first startup.</p>
<p>Prior to the following approach, I used to have &#8216;default.data&#8217; and &#8216;sample.data&#8217; tasks in my ant scripts that either ran SQL manually, or started up a separate Spring ApplicationContext and inserted data explicitly.  You had to run it manually from ant, which 1) required that ant be installed and 2) that you had the project checked out on the box that you were installing data to.  Many production and QA environments didn&#8217;t meet this criteria, and even if they did, it is still cumbersome and isn&#8217;t as nice as an &#8216;automatic&#8217; solution.</p>
<p>My newer automatic solution moves this type of data insertion logic into the actual application, where it is better managed and tested.  There is another benefit too though:  Since I use Hibernate and JCR as the EIS-tier APIs, it is <em>far easier</em> to insert data via these standard APIs than to do so via raw SQL.  This is because you can write all of your initial data objects and graphs with Java or Groovy POJOs, utilizing the benefits of powerful IDE coding features, and let the Hibernate and JCR frameworks insert all the data with dependencies for you: a massive time saver.</p>
<p>So, here&#8217;s a simple way to do this:</p>
<p>You create a POJO that will execute at application startup automatically after its dependencies have been injected.  Here&#8217;s an example:</p>
<div class="code"><code><br />
import org.springframework.beans.factory.InitializingBean;<br />
import org.springframework.transaction.PlatformTransactionManager;<br />
import org.springframework.transaction.TransactionStatus;<br />
import org.springframework.transaction.support.TransactionCallback;<br />
import org.springframework.transaction.support.TransactionTemplate;</p>
<p>public class BootstrapDataPopulator implements InitializingBean {</p>
<p>    private transient final Log log = LogFactory.getLog( getClass() );</p>
<p>    //Spring's transaction manager - needed to ensure data is inserted in a transaction:<br />
    //any failures, and we can roll back everything.<br />
    private PlatformTransactionManager transactionManager = null;</p>
<p>    //all other managers/dependencies here</p>
<p>    public BootstrapDataPopulator() {<br />
    }</p>
<p>    public void setTransactionManager( PlatformTransactionManager transactionManager ) {<br />
        this.transactionManager = transactionManager;<br />
    }</p>
<p>    //other dependency setter methods</p>
<p>    public void afterPropertiesSet() throws Exception {<br />
        if ( this.transactionManager == null ) {<br />
            throw new IllegalStateException( "transactionManager property must be set." );<br />
        }<br />
        //assert other injected dependencies here</p>
<p>        TransactionTemplate txnTemplate = new TransactionTemplate( this.transactionManager );<br />
        txnTemplate.afterPropertiesSet();</p>
<p>        txnTemplate.execute( new TransactionCallback() {<br />
            public Object doInTransaction( TransactionStatus status ) {<br />
                try {<br />
                    insertBoostrapData();<br />
                } catch ( Exception e ) {<br />
                    //error - roll back.  Runtime exception triggers rollback:<br />
                    if ( e instanceof RuntimeException ) {<br />
                        throw (RuntimeException)e;<br />
                    } else {<br />
                        throw new RuntimeException( e );<br />
                    }<br />
                }<br />
                return null;<br />
            }<br />
        } );<br />
    }</p>
<p>    private boolean guestUserExists() {<br />
        return userManager.findUserByUsername( "guest" ) != null;<br />
    }</p>
<p>    protected void insertBoostrapData() throws Exception {<br />
        //if the guest user account exists, take this as a sign that the bootstrap data populator has<br />
        //already been run, so just exit quietly:<br />
        if ( guestUserExists() ) {<br />
            if ( log.isDebugEnabled() ) {<br />
                log.debug( "Bootstrap data insertion has already occurred.  Returning quietly." );<br />
            }<br />
            return;<br />
        }</p>
<p>        if ( log.isInfoEnabled() ) {<br />
            log.info( "Inserting bootstrap data..." );<br />
        }</p>
<p>        //otherwise, populate bootstrap data:<br />
        log.debug("Creating guest user...");<br />
        User guestUser = someManager.create( new User( "Guest", "guest@domain.com" ) );</p>
<p>        //insert all other objects and call any other helper methods here</p>
<p>    }<br />
}</code></div>
<p>The key to this code working as a POJO in your normal application configuration is due to two things:</p>
<ol>
<li>The insertBootstrapData() method is wrapped in the TransactionTemplate.  If anything goes wrong during the execution of that method, it will be rolled back and the database remains in a consistent state</li>
<li>The first bit of code in insertBootstrapData() checks to see if a well-known entity already exists in the database.  If it does, you can assume that the bootstrap data has already been inserted, and return quietly.</li>
</ol>
<p>You can create other &#8216;Bootstrap Beans&#8217; like this to do other things as well.  The above one initialized RDBMS data.  You can have another one that initializes your JCR repository.  Or another that checks against a license store to ensure that the application installed is allowed to be installed.  All sorts of things&#8230;</p>
]]></content:encoded>
			<wfw:commentRss>http://leshazlewood.com/2007/07/30/spring-application-bootstrap-data/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>Java Email Address class</title>
		<link>http://leshazlewood.com/2006/11/06/emailaddress-java-class/</link>
		<comments>http://leshazlewood.com/2006/11/06/emailaddress-java-class/#comments</comments>
		<pubDate>Mon, 06 Nov 2006 17:04:42 +0000</pubDate>
		<dc:creator>admin</dc:creator>
				<category><![CDATA[General]]></category>
		<category><![CDATA[Java]]></category>
		<category><![CDATA[Software]]></category>

		<guid isPermaLink="false">http://www.leshazlewood.com/?p=23</guid>
		<description><![CDATA[<p>UPDATE: This Java class was updated on February 1st, 2008 to account for domain literals and quoted strings such as &#8220;John Smith&#8221; &#60;john.smith@somewhere.com&#62;. It is now effectively the only complete and semantically correct email validator for Java.</p> <p>PETTY REQUEST: The update required considerably more effort than the original as it now accounts for all valid [...]]]></description>
			<content:encoded><![CDATA[<p><strong>UPDATE:  This Java class was updated on February 1st, 2008 to account for domain literals and quoted strings</strong> such as &#8220;John Smith&#8221; &lt;john.smith@somewhere.com&gt;.  It is now effectively <em>the only</em> complete and semantically correct email validator for Java.</p>
<p><em>PETTY REQUEST</em>:  The update required considerably more effort than the original as it now accounts for all valid RFC parsing conditions.  Because of this, and that this page is easily my most visited, I&#8217;d appreciate it if you could show your appreciation by hooking a brother up and clicking on some ads.  It helps pay for my hosting.  Thanks!</p>
<p>I&#8217;m writing a new open source CMS (Community Management System) based entirely on the Spring Framework and Hibernate.</p>
<p>This CMS will take many cues from Drupal and other PHP based CMS systems, but be far more flexible, have fantastic OO and design pattern architectures and be a benefit to the Java Enterprise software community.  I&#8217;ve decided to abandon JSR-168 support &#8211; I want a much cleaner, easier to implement, OO-based and typesafe &#8220;plugin&#8221; support framework &#8211; which I&#8217;m working on now.  Suffice it to say I&#8217;m not a fan of JSR-168, but that&#8217;s a whole &#8216;nuther post.</p>
<p>Anyway, In this CMS, I&#8217;m using time-honored OO classes I&#8217;ve used on many many projects.  One such is the EmailAddress class that I&#8217;ve referenced in <a href="http://www.leshazlewood.com/?p=5">earlier post</a>s in this blog for email address validation.  I&#8217;ve gotten some good feedback on this class, so I thought I&#8217;d just post the whole thing in case anyone wants to benefit from it (instead of just using code chunks I&#8217;ve posted before).</p>
<p>Here it is:</p>
<div class="code"><code>/*<br />
 * Copyright 2008 Les Hazlewood<br />
 *<br />
 * Licensed under the Apache License, Version 2.0 (the "License");<br />
 * you may not use this file except in compliance with the License.<br />
 * You may obtain a copy of the License at<br />
 *<br />
 *     http://www.apache.org/licenses/LICENSE-2.0<br />
 *<br />
 * Unless required by applicable law or agreed to in writing, software<br />
 * distributed under the License is distributed on an "AS IS" BASIS,<br />
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.<br />
 * See the License for the specific language governing permissions and<br />
 * limitations under the License.<br />
 */</p>
<p>import java.io.Serializable;<br />
import java.util.regex.Pattern;</p>
<p>/**<br />
 * An email address represents the textual string of an<br />
 * <a href="http://www.ietf.org/rfc/rfc2822.txt">RFC 2822</a> email address and other corresponding<br />
 * information of interest.<br />
 *<br />
 *
<p>If you use this code, please keep the author information in tact and reference<br />
 * my site at <a href="http://www.leshazlewood.com">leshazlewood.com</a>.  Thanks!<br />
 *<br />
 * @author Les Hazlewood<br />
 */<br />
public class EmailAddress implements Serializable {</p>
<p>    /**<br />
     * This constant states that domain literals are allowed in the email address, e.g.:<br />
     *<br />
     *
<p><tt>someone@[192.168.1.100]</tt> or <br/><br />
     * <tt>john.doe@[23:33:A2:22:16:1F]</tt> or <br/><br />
     * <tt>me@[my computer]</tt></p>
<p>     *<br />
     *
<p>The RFC says these are valid email addresses, but most people don't like allowing them.<br />
     * If you don't want to allow them, and only want to allow valid domain names<br />
     * (<a href="http://www.ietf.org/rfc/rfc1035.txt">RFC 1035</a>, x.y.z.com, etc),<br />
     * change this constant to <tt>false</tt>.<br />
     *<br />
     *
<p>Its default value is <tt>true</tt> to remain RFC 2822 compliant, but<br />
     * you should set it depending on what you need for your application.<br />
     */<br />
    private static final boolean ALLOW_DOMAIN_LITERALS = true;</p>
<p>    /**<br />
     * This contstant states that quoted identifiers are allowed<br />
     * (using quotes and angle brackets around the raw address) are allowed, e.g.:<br />
     *<br />
     *
<p><tt>"John Smith" &lt;john.smith@somewhere.com&gt;</tt><br />
     *<br />
     *
<p>The RFC says this is a valid mailbox.  If you don't want to<br />
     * allow this, because for example, you only want users to enter in<br />
     * a raw address (<tt>john.smith@somewhere.com</tt> - no quotes or angle<br />
     * brackets), then change this constant to <tt>false</tt>.<br />
     *<br />
     *
<p>Its default value is <tt>true</tt> to remain RFC 2822 compliant, but<br />
     * you should set it depending on what you need for your application.<br />
     */<br />
    private static final boolean ALLOW_QUOTED_IDENTIFIERS = true;</p>
<p>    // RFC 2822 2.2.2 Structured Header Field Bodies<br />
    private static final String wsp = "[ \\t]"; //space or tab<br />
    private static final String fwsp = wsp + "*";</p>
<p>    //RFC 2822 3.2.1 Primitive tokens<br />
    private static final String dquote = "\\\"";<br />
    //ASCII Control characters excluding white space:<br />
    private static final String noWsCtl = "\\x01-\\x08\\x0B\\x0C\\x0E-\\x1F\\x7F";<br />
    //all ASCII characters except CR and LF:<br />
    private static final String asciiText = "[\\x01-\\x09\\x0B\\x0C\\x0E-\\x7F]";</p>
<p>    // RFC 2822 3.2.2 Quoted characters:<br />
    //single backslash followed by a text char<br />
    private static final String quotedPair = "(\\\\" + asciiText + ")";</p>
<p>    //RFC 2822 3.2.4 Atom:<br />
    private static final String atext = "[a-zA-Z0-9\\!\\#\\$\\%\\&#038;\\'\\*\\+\\-\\/\\=\\?\\^\\_\\`\\{\\|\\}\\~]";<br />
    private static final String atom = fwsp + atext + "+" + fwsp;<br />
    private static final String dotAtomText = atext + "+" + "(" + "\\." + atext + "+)*";<br />
    private static final String dotAtom = fwsp + "(" + dotAtomText + ")" + fwsp;</p>
<p>    //RFC 2822 3.2.5 Quoted strings:<br />
    //noWsCtl and the rest of ASCII except the doublequote and backslash characters:<br />
    private static final String qtext = "[" + noWsCtl + "\\x21\\x23-\\x5B\\x5D-\\x7E]";<br />
    private static final String qcontent = "(" + qtext + "|" + quotedPair + ")";<br />
    private static final String quotedString = dquote + "(" + fwsp + qcontent + ")*" + fwsp + dquote;</p>
<p>    //RFC 2822 3.2.6 Miscellaneous tokens<br />
    private static final String word = "((" + atom + ")|(" + quotedString + "))";<br />
    private static final String phrase = word + "+"; //one or more words.</p>
<p>    //RFC 1035 tokens for domain names:<br />
    private static final String letter = "[a-zA-Z]";<br />
    private static final String letDig = "[a-zA-Z0-9]";<br />
    private static final String letDigHyp = "[a-zA-Z0-9-]";<br />
    private static final String rfcLabel = letDig + "(" + letDigHyp + "{0,61}" + letDig + ")?";<br />
    private static final String rfc1035DomainName = rfcLabel + "(\\." + rfcLabel + ")*\\." + letter + "{2,6}";</p>
<p>    //RFC 2822 3.4 Address specification<br />
    //domain text - non white space controls and the rest of ASCII chars not including [, ], or \:<br />
    private static final String dtext = "[" + noWsCtl + "\\x21-\\x5A\\x5E-\\x7E]";<br />
    private static final String dcontent = dtext + "|" + quotedPair;<br />
    private static final String domainLiteral = "\\[" + "(" + fwsp + dcontent + "+)*" + fwsp + "\\]";<br />
    private static final String rfc2822Domain = "(" + dotAtom + "|" + domainLiteral + ")";</p>
<p>    private static final String domain = ALLOW_DOMAIN_LITERALS ? rfc2822Domain : rfc1035DomainName;</p>
<p>    private static final String localPart = "((" + dotAtom + ")|(" + quotedString + "))";<br />
    private static final String addrSpec = localPart + "@" + domain;<br />
    private static final String angleAddr = "<" + addrSpec + ">";<br />
    private static final String nameAddr = "(" + phrase + ")?" + fwsp + angleAddr;<br />
    private static final String mailbox = nameAddr + "|" + addrSpec;</p>
<p>    //now compile a pattern for efficient re-use:<br />
    //if we're allowing quoted identifiers or not:<br />
    private static final String patternString = ALLOW_QUOTED_IDENTIFIERS ? mailbox : addrSpec;<br />
    public static final Pattern VALID_PATTERN = Pattern.compile(patternString);</p>
<p>    //class attributes<br />
    private String text;<br />
    private boolean bouncing = true;<br />
    private boolean verified = false;<br />
    private String label;</p>
<p>    public EmailAddress() {<br />
        super();<br />
    }</p>
<p>    public EmailAddress(String text) {<br />
        super();<br />
        setText(text);<br />
    }</p>
<p>    /**<br />
     * Returns the actual email address string, e.g. <tt>someone@somewhere.com</tt><br />
     *<br />
     * @return the actual email address string.<br />
     */<br />
    public String getText() {<br />
        return text;<br />
    }</p>
<p>    public void setText(String text) {<br />
        this.text = text;<br />
    }</p>
<p>    /**<br />
     * Returns whether or not any emails sent to this email address come back as bounced<br />
     * (undeliverable).<br />
     *<br />
     *
<p>Default is <tt>false</tt> for convenience's sake - if a bounced message is ever received for this<br />
     * address, this value should be set to <tt>true</tt> until verification can made.<br />
     *<br />
     * @return whether or not any emails sent to this email address come back as bounced<br />
     *         (undeliverable).<br />
     */<br />
    public boolean isBouncing() {<br />
        return bouncing;<br />
    }</p>
<p>    public void setBouncing(boolean bouncing) {<br />
        this.bouncing = bouncing;<br />
    }</p>
<p>    /**<br />
     * Returns whether or not the party associated with this email has verified that it is<br />
     * their email address.<br />
     *<br />
     *
<p>Verification is usually done by sending an email to this<br />
     * address and waiting for the party to respond or click a specific link in the email.<br />
     *<br />
     *
<p>Default is <tt>false</tt>.<br />
     *<br />
     * @return whether or not the party associated with this email has verified that it is<br />
     *         their email address.<br />
     */<br />
    public boolean isVerified() {<br />
        return verified;<br />
    }</p>
<p>    public void setVerified(boolean verified) {<br />
        this.verified = verified;<br />
    }</p>
<p>    /**<br />
     * Party label associated with this address, for example, 'Home', 'Work', etc.<br />
     *<br />
     * @return a label associated with this address, for example 'Home', 'Work', etc.<br />
     */<br />
    public String getLabel() {<br />
        return label;<br />
    }</p>
<p>    public void setLabel(String label) {<br />
        this.label = label;<br />
    }</p>
<p>    /**<br />
     * Returns whether or not the text represented by this object instance is valid<br />
     * according to the <tt>RFC 2822</tt> rules.<br />
     *<br />
     * @return true if the text represented by this instance is valid according<br />
     *         to RFC 2822, false otherwise.<br />
     */<br />
    public boolean isValid() {<br />
        return isValidText(getText());<br />
    }</p>
<p>    /**<br />
     * Utility method that checks to see if the specified string is a valid<br />
     * email address according to the * RFC 2822 specification.<br />
     *<br />
     * @param email the email address string to test for validity.<br />
     * @return true if the given text valid according to RFC 2822, false otherwise.<br />
     */<br />
    public static boolean isValidText(String email) {<br />
        return (email != null) &#038;&#038; VALID_PATTERN.matcher(email).matches();<br />
    }</p>
<p>    public boolean equals(Object o) {<br />
        if (o instanceof EmailAddress) {<br />
            EmailAddress ea = (EmailAddress) o;<br />
            return getText().equals(ea.getText());<br />
        }<br />
        return false;<br />
    }</p>
<p>    public int hashCode() {<br />
        return getText().hashCode();<br />
    }</p>
<p>    public String toString() {<br />
        return getText();<br />
    }</p>
<p>    public static void main(String[] args) {<br />
        String addy = "\"John Smith\" <john.smith@u.washington.edu>";<br />
        if (isValidText(addy)) {<br />
            System.out.println("Valid email address.");<br />
        } else {<br />
            System.out.println("Invalid email address!");<br />
        }<br />
    }<br />
}</code></div>
]]></content:encoded>
			<wfw:commentRss>http://leshazlewood.com/2006/11/06/emailaddress-java-class/feed/</wfw:commentRss>
		<slash:comments>42</slash:comments>
		</item>
		<item>
		<title>Connecting to Ingres 2006 on Linux via JDBC</title>
		<link>http://leshazlewood.com/2006/08/02/connecting-to-ingres-2006-on-linux-via-jdbc/</link>
		<comments>http://leshazlewood.com/2006/08/02/connecting-to-ingres-2006-on-linux-via-jdbc/#comments</comments>
		<pubDate>Wed, 02 Aug 2006 20:45:44 +0000</pubDate>
		<dc:creator>admin</dc:creator>
				<category><![CDATA[General]]></category>
		<category><![CDATA[Software]]></category>

		<guid isPermaLink="false">http://www.leshazlewood.com/?p=21</guid>
		<description><![CDATA[<p>Ok, I had a hell of a time trying to get this figured out. It seems like my Ingres 2006 install environment did not match the documentation on the ingres website, which looks to be docos for the older r3 product. This seriously sucked. C&#8217;mon guys &#8211; get the docos right.</p> <p>Anway, here&#8217;s what I [...]]]></description>
			<content:encoded><![CDATA[<p>Ok, I had a <em>hell</em> of a time trying to get this figured out.  It seems like my Ingres 2006 install environment did not match the documentation on the ingres website, which looks to be docos for the older r3 product.  This <em>seriously</em> sucked.  C&#8217;mon guys &#8211; get the docos right.</p>
<p>Anway, here&#8217;s what I had to do.</p>
<p>I didn&#8217;t install this ingres instance, but I did realize that a process named &#8216;iijdbc&#8217; was running.  Apparently this is what allows jdbc to connect to an Ingres 2006 installation.  We do not have Data Access Server running (iigdc).</p>
<p>When doing a process listing, this is what I get:</p>
<div class="code"><code>> ps aux | grep ingres<br />
ingres    3903  0.0  0.0 11140 2228 pts/0    S    15:50   0:00 /ingres/application/ingres/bin/iigcn II gcn<br />
ingres    4038  0.0  1.0 145164 55068 pts/0  Sl   15:50   0:00 /ingres/application/ingres/bin/iidbms recovery (dmfrcp) II<br />
ingres    4156  0.0  0.0 86212 3748 pts/0    S    15:50   0:00 /ingres/application/ingres/bin/dmfacp II<br />
ingres    4177  0.0  0.7 322120 37260 pts/0  Sl   15:50   0:00 /ingres/application/ingres/bin/iidbms dbms (default) II<br />
ingres    4335  0.0  0.0 59244 2768 pts/0    S    15:50   0:00 /ingres/application/ingres/bin/iijdbc II jdbc</code></div>
<p>And here is the corresponding output from the &#8216;ingstatus&#8217; command (corroborates the above, just less verbose):</p>
<div class="code"><code>> ingstatus<br />
Ingres II name server (iigcn)               - running<br />
Ingres II recovery server (dmfrcp)          - running<br />
Ingres II DBMS server (iidbms)              - 1 running<br />
Ingres II Net server (iigcc)                - not active<br />
Ingres II Data Access server (iigcd)        - not active<br />
Ingres II JDBC server (iijdbc)              - 1 running<br />
Ingres II archiver process (dmfacp)         - running</code></div>
<p>So, given this starting point, here&#8217;s what I had to do:</p>
<p>As the ingres user, we had created a &#8216;cls&#8217; database via the createdb command.  Then we used accessdb to create the &#8216;cls&#8217; user account inside ingres.  Then we loaded the sql schema via accessdb.</p>
<p>So now, I had a cls user account and a schema with tables, but I couldn&#8217;t connect for the life of me over JDBC using Ingres 2006&#8242;s provided jdbc driver (found at <code>$II_SYSTEM/ingres/lib/edbc.jar</code>).</p>
<p>It turns out this is because Ingres uses Operating System user accounts for logging in over tcp.  So, this meant I had to create a cls user as root:</p>
<div class="code"><code># adduser cls</code></div>
<p>and gave it a suitable password:</p>
<div class="code"><code># passwd cls</code></div>
<p>(this OS level password is then used for the JDBC connection later on).</p>
<p>Now that there is an OS user called &#8216;cls&#8217; &#8211; exactly the same as my previously created Ingres database &#8211; I then had to let ingres know about this os user account and password:</p>
<p>(as root):</p>
<div class="code"><code># . /home/ingres/.ingIIbash<br />
# mkvalidpw</code></div>
<p>This command compiles and installs a program called &#8216;ingvalidpw&#8217; that is not is not included in the standard Ingres2006 installation.  This allows you to validate if a password is valid against an operating system user account known to Ingres.</p>
<p>Once that&#8217;s done, you&#8217;ll have to restart Ingres (as root):</p>
<div class="code"><code># /etc/init.d/ingresII restart</code></div>
<p>To validate that Ingres password checking works, you should see that the Ingres env var <code>II_SHADOW_PWD</code> is set to the location of that compiled ingvalidpw executable:</p>
<div class="code"><code># su - ingres<br />
> ingprenv</code></div>
<p>In the list that is generated, you should see the <code>II_SHADOW_PWD</code> var set.</p>
<p>Now, you can verify that the username and password you would use for JDBC for your user will work:</p>
<div class="code"><code>echo <username>
<password> | $II_SYSTEM/ingres/bin/ingvalidpw ; echo $?</code></div>
<p>If you see any value other than 0 returned, then the username/password entered doesn&#8217;t match the OS username/password.  If you do see non-zero, then you can look in the <code>$II_SYSTEM/ingres/files/iipwd/ingvalidpw.c</code> file and see what the integer corresponds to find out what went wrong.</p>
<p>I then fired up <a href="http://www.minq.se/products/dbvis/">DB Visualizer</a>, pointed it to the edbc.jar file I specified earlier, and then used this url:</p>
<div class="code"><code>jdbc:edbc://<host>:21071/<dbname></code></div>
<p>So, in my case it looked like this:</p>
<div class="code"><code>jdbc:edbc://localhost:21071/cls</code></div>
<p>I clicked &#8216;test connection&#8217; in DbVisualizer, and lo and behold!  I was able to access all my tables!</p>
<p>I hope this is of use for someone &#8211; it took me close to 3 or 4 hours to get this working.</p>
<p>Here is the original Ingres forums thread that led me to my posting (you may need an Ingres account to access it, but its free):</p>
<p><a href="http://opensource.ingres.com/projects/ingres/forum/30/121418044682?b_start:int=0#235464875124">http://opensource.ingres.com/projects/ingres/forum/30/121418044682?b_start:int=0#235464875124</a></p>
]]></content:encoded>
			<wfw:commentRss>http://leshazlewood.com/2006/08/02/connecting-to-ingres-2006-on-linux-via-jdbc/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
	</channel>
</rss>

