What's the simplest way to deploy a Grails-generated WAR file? - java

I've been having persistent problems (for several weeks) getting Tomcat to deploy a WAR file. I'm looking for a simple server. It does not need to have a lot of functionality-it just needs to be simple to set up. In particular I'm looking for a program that I can just drop a WAR file into and have the enclosed web application launch.

You might want to give jetty runner a try. It basically just uses an embedded jetty instance to run your war file.
http://blogs.webtide.com/janb/entry/jetty_runner
It is available on Maven and it is in fact how heroku apps built with grails are ran. http://devcenter.heroku.com/articles/deploy-a-java-web-application-that-launches-with-jetty-runner

If your application does not start on tomcat, it almost certainly means it won't start on any servlet container - containers implement a spec, and are very similar in many aspects.
What you should do is go and hunt each problem one by one, until the application starts. The problem is the app, not the container.

I recently had a similar problem where my app ran fine with "grails run-app" but not as a war file. It was caused by a missing "package" line in one of the files. I was getting 404 errors. When a war file is unpacked on the server it doesn't put files in the same directory locations as when the are in the grails environment. Not sure this will help you but maybe others with similar problems.

if you get a fresh tomcat instance, generate a hellow world app and generate your war file via grails dev war it should work without a hitch. typically problems arise form adding dependencies that clash with server libs.
if you want to give other servers a try I would suggest resin as one of the easiest to setup, run and maintain.

Related

How to create a Spring web app on a server

Firstly, please excuse my horrendously general question, as my understanding of Spring is very limited, but I will expalin what I want to achieve, and hopefully someone can point me in the right direction.
I have an application that retrieves some information from some source and updates a database. I'd like to put this program on a Tomcat server, so that the application is run every day.
I'm very new to Spring, and have spent the last few days completing some basic tutorials to display Hello World! in a broswer.
However, all of the tutorials I have found relate to Controllers for URLs, which, as far as I understand, is not what I want, as my application will not have a URL and there will be nothing to display, I just want the application to "hidden" somewhere on the server, and to execute daily.
I know this is a very general question, and as I said my knowledge of Spring is next to non-existent, so I'd appreciate it if someone could point me in the right direction, I'll happily do research if I just knew what to look for.
Thanks in advance!
I would suggest using Spring Boot quite easy to start with and does all the magic for you.
There are few tutorials how to start and what you will need.
You can have a jar that will run on embedded Tomcat server provided by spring boot, or you can convert it then to a war/ear file and deploy it on External Tomcat if you wish (doesn't need to be tomcat either). You just need a deployable artefact. In this case a war or ear.
Difrence between jar, war, ear
if you then wish to convert it:
Convert a jar into a war
Deploying Spring boot apps on External servers
All the documentation you can find on Spring guides
I'd like to put this program on a Tomcat server, so that the application is run every day.
Seems to me that you don't really need Tomcat or Spring.
Why not just install your Java app on a UNIX server and have it run every day with cron ?
Spring is a very frustrating framework to learn because of all the various versions and tools out there.
Spring Boot is usually the starting point for people since it creates an executable self-contained JAR with embeded Tomcat server.
If you want to run with your own Tomcat instance, you need to look into creating a WAR/EAR file, which is an archive with a directory named WEB-INF that contains all of your Tomcat XML configurations.
Turn your Jar into a War
One of the simplest ways to start is to use Maven, add the WAR plugin to your pom.xml file, then webapp/WEB-INF directory to your project and place the web.xml config file in it.
Create and deploy web apps on Tomcat

Gradle jettyRun set webappsourcedirectory with DropWizard

So I'm developing a DropWizard application and all of the tutorials point towards compiling and running java -jar to start the web server. However while I'm doing local development this is a pretty slow work flow. Having used Jetty before I know it will autoreload and run in a daemon mode.
We're using Gradle and I found this which works to start Jetty. The first problem I encountered is this:
Directory '/src/main/webapp' specified for property 'webAppSourceDirectory' does not exist.
I found I way around this by adding
jettyRun.webAppSourceDirectory = file("src/main/java")
to the build.gradle file but of course this just lists files in that directory. Is there a directory I can point jetty to for this to work?
Or is there another way I can get DropWizard to auto reload resources and recompile?
Also Is there a way to get DropWizard to run in the background?
Dropwizard doesn't run on Jetty. It manages Jetty, as well as other tools. So manipulating jetty is not a solution for what you want to accomplish.
Or is there another way I can get DropWizard to auto reload resources
and recompile?
No AFAIK.
Also Is there a way to get DropWizard to run in the background?
Also no AFAIK. You should be able to fix that with some bash tricks.
Or maybe this might be of some help, but I don't think it will recompile and reload resources.
Dropwizard is a fairly lightweight application. In my development environment it takes about 3-5 seconds to build and start a dropwizard service; that is by using Intellij, not gradle (or maven).

How to dynamically update (hot swap) jars in a web-app?

I have a webapp in a war archive which is deployed on cloudfoundry.
One of the libraries ("somelib.jar") used by the app is made by another developer.
I would like a way for him to upload several different versions of somelib.jar and test the behaviour of the app.
I have managed to get the jar uploaded to WEB-INF/lib directory of the deployment. I have also managed to unpack the jar into WEB-INF/classes. However, I have not managed to get the new version of the jar to be used. I tried various hacks such as those described in this question and this question without any luck.
Everytime, the classes/jars that get loaded the first time get used after that, even if we replace the actual .class or .jar file in the above directories.
Is there any easy way to achieve what I want?
Note: Since I dont have control of Tomcat (where it runs), I cannot configure Tomcat or make any changes to the server. I just have control on my war file, so everything needs to be done programmatically.
EDIT: the reason I want this is to reduce our testing time. Currently someone gives me a new version of somelib.jar, I repackage it into my application, upload to CF, send him a notification, then he tests the behavior of the new jar. What I would have preferred is that he upload his jar directly to CF and do the testing whenever he has a new version without the unnecessary intermediate delay.
In tomcat 7, you can version your WAR file and the new versions will gradually kick in.
http://www.tomcatexpert.com/blog/2011/05/31/parallel-deployment-tomcat-7
In order for you to control the application server yourself, you would need to deploy a standalone app into Cloud Foundry.
This blog should help you out with that:
http://blog.cloudfoundry.com/2012/05/11/running-standalone-web-applications-on-cloud-foundry/
This way you can custom configure your tomcat.
Everytime, the classes/jars that get loaded the first time get used after that, even if we replace the actual .class or .jar file in the above directories
That's the way that normal Tomcat (Java EE) classloading works. Your classes are loaded when first deployed, and any changes will be ignored (JSPs are managed slightly differently, but only in a development environment).
You should be able to solve this problem by using the Equinox OSGi bridge servlet. I haven't done this myself, but here's a writeup by a person that I respect.

Approach to be followed for deploying the application

We have developed a web based application in java(STRUTS 2.0). Now we want to deploy the application. The client is having one pre UAT environment ,UAT environment and a production environment.
Now when we are deploying for pre-UAT we have created the copy of our project and renamed it to pre-UAT. Similarly we are planning for UAT environment and one we already have for development. So in all we will be having 3 copies of our code.
I want to ask is this approach correct or what is the standard approach followed. This is not our final release as we are first releasing a version and then we will be working on other modules.
So please can anyone guide me for approach to follow for creating this 3 different environments.Thanks in advance
I am not sure what you refer to by "we will be having 3 copies of our code". If you are implying that you actually copied the code-base around multiple times, please stop reading and refer to this:
Why is "copy and paste" of code dangerous?
And once you finish reading, do some research about source control and how to use branching/tagging for concurrent development.
If you were referring to multi-environment deployment:
Assuming your application is designed correctly (and I'm treading very carefully here), one WAR file (you were mentioning you're using Tomcat, so I am concluding that your application is packaged as a WAR) should be sufficient. The application code should be environment-independent and should read its environment-specific configuration from external resources, such as a database, configuration files or JNDI.
If your application code is environment-independent, then all you need to do is simply deploy the WAR file to each of the environments (the same WAR file), plus the environment-specific set of external artifacts (such as configuration files).

Java EE Jar file sharing

At our shop, we are maintaining roughly 20 Java EE web applications. Most of these applications are fairly CRUD-like in their architecture, with a few of them being pretty processor intensive calculation applications.
For the deployment of these applications we have been using Hudson set up to monitor our CVS repository. When we have a check-in, the projects are set to be compiled and deployed to our Tomcat 6.0 server (Solaris 10, sparc Dual-core 1.6 GHz processor, 2 GB RAM...not the beefiest machine by any stretch of the imagination...) and, if any unit-tests exist for the project, those are executed and the project is only deployed if the unit-tests pass. This works great.
Now, over time, I've noticed myself that a lot of the projects I create utilize the same .jar files over and over again (Hibernate, POI (Excel output), SQL Server JDBC driver, JSF, ICEFaces, business logic .jar files, etc.). Our practice has been to just keep a folder on our network drive stocked with all the default .jar files we have been using, and when a new project is started we copy this set of .jar files into the new project and go from there...and I feel so dirty every time this happens it has started to keep me up at night. I have been told by my co-workers that it is "extremely difficult" to set up a .jar repository on the tomcat server, which I don't buy for a second...I attribute it to pure laziness and, probably, no desire to learn the best practice. I could be wrong, however, I am just stating my feelings on the matter. This seems to bloat the size of our .war files that get deployed to the server as well.
From my understanding, Tomcat itself has a set of .jar files that are accessible to all applications deployed to it, so I would think we would be able to consolidate all of these duplicate .jar files in all our projects and move them onto the tomcat server. This would involve only updating one .jar file on the server if, for example, we need to update the ICEFaces .jar files to a new version.
Another part of me says that by including only one copy of the .jar files on the server, I might need to keep a copy of the server's lib directory in my development environment as well (i.e. include those .jar files in eclipse dependency).
My gut instinct tells me that I want to move those duplicated .jar files onto the server...will this work?
I think Maven and Ivy were born to help manage JAR dependencies. Maybe you'll find that those are helpful.
As far as the debate about duplicating the JARs in every project versus putting them in the server/lib, I think it hinges on one point: How likely is it that you'll want to upgrade every single application deployed on Tomcat at the same time? Can you ever envision a time where you might have N apps running on that server, and the (N+1)th app could want or require a newer version of a particular JAR?
If you don't mind keeping all the apps in synch, by all means have them use a common library base.
Personally, I think that disk space is cheap. My preference is to duplicate JARs for each app and put them in the WAR file. I like the partitioning. I'd like to see more of it when OSGi becomes more mainstream.
It works most of the time, but you can get into annoying situations where the jar that you have moved into tomcat is trying to make an instance of a class in one of your web application jars, leading to ClassNotFoundException s being thrown. I used to do this, but stopped because of these problems.
I really don't think putting libraries in common/lib is a good idea. The idea behind the use of war files as applications into a servlet container, is to have a real idea of isolation between your webapps. You could face errors like deploy some third party WAR (with it own libraries inside WEB-INF/lib) and it behave unexpectedly because it loaded other version of one of it libraries from the common one (remember that the regular behavior for load classes is first look at the common classloader and if you don't find the class look into the one for your webapp). Don't even mention how painful could be to move some application to other servlet container or an Application Server.
As mentioned before, you could use maven to deal with jar dependencies, and if you like the homogeneous use of libraries, define a POM parent (maven jargon) across all your applications.
In my experience you should be very careful with sharing libraries between web applications by moving them into the web container itself.
Let them live in WEB-INF/lib so your wars are self contained (you WILL be glad you did one day).
What you might consider is employing maven or Ant Ivy to pull in library jars from a common repository instead. This is very useful and should not be a problem in your scenario.
Edit: A notable exception is the Metro library - web service layer from Glassfish - which needs to be in the web container and not in the web application.

Categories