Archive for the ‘Java’ Category
Switching to JBoss 7 changed a lot of things in how we build our applications, how we deploy them and how we manage them, mostly improving everything.
For me one of the biggest improvements in terms of increasing productivity and manageability is the new configuration system… simplified bliss.
One example is setting up the web container for balancing via mod_proxy_balancer.
In the past, this meant modifying the embedded tomcat connector… a primitive, ugly, dirty way of doing things :)
In AS 7, you just have to modify the $JBOSS_HOME/standalone/configuration/standalone.xml configuration file and include a system-properties config, directly under the server tag, just like this:
<property name="jvmRoute" value="httpNode1"/>
On the other side of the equation, the mod_proxy_balancer config lists the jvmRoute in the classic way:
ProxyPass /app balancer://mycluster/ stickysession=JSESSIONID|jsessionid scolonpathdelim=On nofailover=off
Be careful with the nofailover option if you are using session-state replication.
Now, if you’re using a domain scenario don’t bet all your money on this technique… I haven’t gotten to domains yet, still using the old deployment scenarios.
The jboss CLI management console is kick-ass too, making our development deployments fast as lightning, maybe I’ll write about it sometimes.
Sometimes, you’re just having a wonderful day and suddenly the worst just happens:
[ServiceController] Problem starting service jboss:service=Naming java.rmi.server.ExportException: Port already in use: 1198; nested exception is: java.net.BindException: Address already in use: JVM_Bind at sun.rmi.transport.tcp.TCPTransport.listen(TCPTransport.java:243) ............
The regular solution is to check if the port is actually used. So fire up a command prompt and netstat –aon.
If you find the port, see what process is using it and kill it ;).
If you don’t see the port you can reserve it by following the information in KB812873 – http://support.microsoft.com/kb/812873.
My ReservedPorts entry contains:
That should fix it. The bad thing is that it requires a restart.
Most of the unit tests that you write don’t need support for transactions and scopes, but if you ever want to test your web frontend code properly you’ll hit into this one.
Writing transactional unit test with JUnit, Spring and Hibernate is easy, what you want to do is:
- Add a transaction management bean in your test context:
<property name="sessionFactory" ref="sessionFactory"/>
If your transaction demarcation is correct( surrounding your dao or service ) you should be done. This is the cleanest way that I found.
Everything until now is fine and dandy. The problem arises when one of the injected beans is bound to a scope. It can be any scope but for this example I’ll take the simplest scope – the ‘session’ scope.
In a non-transactional situation this should be pretty straight forward, just implement Scope and using a ConfigurableBeanFactory register it. The fact that we are extending <a href="http://static.springsource.org/spring/docs/2.5.x/api/org/springframework/test/context/junit4/AbstractTransactionalJUnit4SpringContextTests.html"AbstractTransactionalJUnit4SpringContextTests and that our context is automatically created really kills the simple path.
You’ll get a org.springframework.beans.factory.BeanCreationException with a nested “java.lang.IllegalStateException: No Scope registered for scope ‘session’”.
But do not despair, there is simple solution available and it’s called CustomScopeConfigurer.
The fastest and cleanest way to use it is:
- Create a simple class that will be used as our scope manager. Let’s call it MockSessionScope.
- In your test context, create a CustomScopeConfigurer that will automatically register your scope on context creation:
Run your tests and you’re done!
Strolling through Google Reader, diagonally reading blog posts from the almost 1 hundred blogs that I tend to follow(1000+ unread ;) ) a phrase jump started my brain.
Not ever line of code can be reused. A lot of web development is about crafting a very specific solution. Localization, error handling, and coding conventions introduce challenges.
This is part of a post from one of the Mozilla blogs that I’m following, namely the blog of Austin King.
Now, this is as straight forward and clear as it is correct, not ever line of code can be reused. Putting it out of its initial context (web development that is) and bringing it into to context of enterprise applications it becomes pure evil, used as an excuse to re-invent a perfectly good wheel.
- Reuse as much as you can, extracting recurring pieces of code as methods
- If common code spawns between projects, always extract it in a common library
- Run a copy-paste detector such as CPD. Extract the code to methods.
- Try to keep your methods under a fixed number of lines, let’s say 20. Doing this will force you to extract consistent pieces of code in separate methods, making them more re-usable
- Try to maintain low cyclomatic complexity. Use a metrics package such as PMD or Panopticode. Refactor complex methods to smaller, less complex chunks of reusable code.
- If you have the feeling that it’s the second time you’ve written a piece of code, search for the first one, because it’s usually true.
Now go and read a good book about this kind of stuff. I recommend The Productive Programmer by Neal Ford. It’s an excellent book for beginners but don’t fear – it’s superb even if you’re an experienced developer, I caught some nice Groovy tips that made the reading worth while, maybe you’ll find something interesting too.
As OC4J has some drawbacks, here are some tips on porting Spring Framework 2+ web applications.
1. Forget about XML Schema, use DTD’s
As I was about to touch the first base, after throwing my exploded WAR in j2ee applications, OC4J started complaining about XML issues. This is what I mean:
javax.xml.parsers.ParserConfigurationException: Unable to validate using XSD: Your JAXP provider [oracle.xml.jaxp.JXDocumentBuilderFactory@1571dff] does not support XML Schema. Are you running on Java 1.4 or below with Apache Crimson? Upgrade to Apache Xerces (or Java 1.5) for full XSD support.
Yea, …nasty. As you don’t want to place Xerces and Xalan in your JRE/JDK lib, all you must do is strip the XML Schema related information and use Spring DTD’s.
2. Use ContextLoaderServlet, bootstrap listeners are for smart containers!
Don’t use ContextLoaderListener. It won’t work, as OC4J is Servlet 2.3 compliant and does not enforce loading of Listeners before load-on-startup Servlets. So, to escape the bean not found hell, use ContextLoaderServlet.
Read more about it in the Spring Framework ContextLoaderServlet javadoc.
3. Specify UTF-8 encoding
No encoding filters needed, as oposed to the Tomcat crowd. All you need to do is edit global-web-application.xml and make sure that you specify default-charset. Read more about it in the web module configuration files documentation at Oracle.
It’s a known fact: I like maven.
It improves some aspects of the development process but it also has a lot of drawbacks.
One of these drawbacks comes directly from maven’s online distributed repository architecture and can make your build process unbearable and worst of all non-reproducible.
The usage of maven assumes the presence of all required repositories and most of all the presence of a reliable Internet connection.
What happens when you need artifacts that are temporarily unreachable or you are bound behind an unreliable connection? In the worst case you get build failures but more frequently you get build times that are measured by the tens of minutes.
This would be ok if it happened once a week but it’s not ok when it happens daily to you and a dozen other team members working on the same project.
The solution we used in the past to fix this problem was a maven repository proxy called Proximity.
Proximity introduces other small problems and latencies and has proven a little unstable, requiring weekly restarts. Plus it included some settings.xml modifications in our previously hands-off newbie development setup. If you want to read a little more about Proximity you can take a look at the project website.
Proximity 1 has been deprecated and until the new Nexus will be out I decided to look for something different.
Artifactory is not (exactly) a caching proxy, like Proximity, it works by simulating and acting as a maven repository.
Every artifact cached is available as part of the local Artifactory repository and when offline, the build process is exactly the same.
It is installed in a copy/unzip and run process and works right out of the box. Some customization is needed only if you use exotic repositories that are not included in the defaults.
Artifactory also returned the development setup to its hands-off svn checkout, mvn eclipse:eclipse or idea:idea nature. It contains a good graphical interface with artifact cache invalidation, which really helps sometimes.
Take a look at the live demo, it’s worth the 5 minutes.
When running in a console window, pressing CTRL+Break signals the JVM to print out all stack traces of currently running threads.
If your application runs as a service (or linux/unix dæmon) you can’t press CTRL+Break, so you have to signal the JVM yourself to produce the stack trace. You can do that on linux by signaling a QUIT to the process, or by using jstack and the PID.
Good news, Java SE 6 on Windows comes with jstack. Yupee! ;).
So next time you need a thread dump from a java application running as a service just get the pid, fire up a cmd and run jstack <pid>.