You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@turbine.apache.org by Filippos Slavik <fs...@forthnet.gr> on 2003/12/09 22:37:14 UTC

[PATCH] workaround for EAR/WAR deployments

I'm sending my patch for Turbine based web-apps that are being deployed as a 
WAR/EAR modules.

This is a workaround and not a complete solution of the issue, since there is 
a need for a major refactoring in turbine's services which assumes that there 
is always an "applicationRoot" available.

The hack here is based on the fact that fortunately all services (or most of 
them) and the turbine's main servlet initialization access resources through 
the turbine's static getRealPath(String) method which returns an absolute 
path of the resource.

The proposed new behaviour is:

There are two new methods.

[1] java.io.InputStream getResourceAsStream(String) which returns an 
InputStream, obtained from the servlet's context, to the specified resource.

[2] java.io.File getTempFileFromResource(String) which retrieves an 
InputStream, using the above method, and writes all resource's content to a 
temporary created file somewhere in the platforms temp directory 
(File.createTempFile(Stirng, String) is used).

Turbine's static method getRealPath(String) is altered as:

1) first an attempt is made to retrieve the requested resource from the 
servlet's context and if successfull the absolute path of the temporary file 
is returned to the caller

2) if step (1) is not succesfull then the old behaviour is used instead (which 
should only happen if we're running junit tests AFAIK) 

patch against TURBINE_2_3 version.

I have succesfully compiled turbine with the patch applied and deployed an WAR 
turbine based app contained within an EAR module. Certainly this is just a 
workaround and not all services will run correctly. In my case, the following 
services were enabled during tests:
services.FactoryService.classname=org.apache.turbine.services.factory.TurbineFactoryService
services.PoolService.classname=org.apache.turbine.services.pool.TurbinePoolService
services.RunDataService.classname=org.apache.turbine.services.rundata.TurbineRunDataService
services.ServletService.classname=org.apache.turbine.services.servlet.TurbineServletService
services.AssemblerBrokerService.classname=org.apache.turbine.services.assemblerbroker.TurbineAssemblerBrokerService
services.PullService.classname=org.apache.turbine.services.pull.TurbinePullService
services.MimeTypeService.classname=org.apache.turbine.services.mimetype.TurbineMimeTypeService
services.GlobalCacheService.classname=org.apache.turbine.services.cache.TurbineGlobalCacheService
services.UniqueIdService.classname=org.apache.turbine.services.uniqueid.TurbineUniqueIdService
services.SecurityService.classname=gr.forthnet.backgroundftp.web.turbine.services.security.BackgroundFTPSecurityService
services.TemplateService.classname=org.apache.turbine.services.template.TurbineTemplateService
services.VelocityService.classname=org.apache.turbine.services.velocity.TurbineVelocityService

And I had no problems at all. 

If the patch will be accepted I would like to continue and refactor some 
services which currently requires an "applicationRoot" available. 

Best Regards 
Filippos Slavik



Index: Turbine.java
===================================================================
RCS file: /home/cvspublic/jakarta-turbine-2/src/java/org/apache/turbine/
Turbine.java,v
retrieving revision 1.45
diff -u -r1.45 Turbine.java
--- Turbine.java	2 Jul 2003 16:52:24 -0000	1.45
+++ Turbine.java	9 Dec 2003 21:14:20 -0000
@@ -54,10 +54,15 @@
  * <http://www.apache.org/>.
  */
 
+import java.io.BufferedInputStream;
+import java.io.BufferedOutputStream;
 import java.io.File;
 import java.io.FileInputStream;
 import java.io.FileNotFoundException;
+import java.io.FileOutputStream;
 import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
 import java.util.Properties;
 
 import javax.servlet.ServletConfig;
@@ -135,6 +140,7 @@
  * @author <a href="mailto:hps@intermeta.de">Henning P. Schmiedehausen</a>
  * @author <a href="mailto:quintonm@bellsouth.net">Quinton McCombs</a>
  * @author <a href="mailto:epugh@upstate.com">Eric Pugh</a>
+ * @author <a href="mailto:fsla@forthnet.gr">Filippos Slavik</a>
  * @version $Id: Turbine.java,v 1.45 2003/07/02 16:52:24 henning Exp $
  */
 public class Turbine
@@ -263,6 +269,9 @@
     private void configure(ServletConfig config, ServletContext context)
             throws Exception
     {
+		// Set the Servlet's context right away.
+		setTurbineServletContext(context);
+		
         //
         // Set up Commons Logging to use the Log4J Logging
         //
@@ -284,6 +293,14 @@
         if (applicationRoot == null || applicationRoot.equals(WEB_CONTEXT))
         {
             applicationRoot = webappRoot;
+            if(applicationRoot==null) {
+            	// if we're running within a servlet container enviroment
+            	// the applicationRoot attribute will have a null value, since
+            	// the applicationRoot can be a WAR or EAR file. Just set here
+            	// a dummy value to avoid NullPointerExceptions with jakarta's
+            	// common configuration framework
+            	applicationRoot="foo";
+            }
             // log.info("got empty or 'webContext' Application root. 
Application root now: " + applicationRoot);
         }
 
@@ -390,7 +407,7 @@
 
         
         setTurbineServletConfig(config);
-        setTurbineServletContext(context);
+        
 
         getServiceManager().setApplicationRoot(applicationRoot);
 
@@ -459,6 +476,60 @@
     }
 
     /**
+     * Returns the resource located at the named path as an 
<code>InputStream</code> object.
+     * 
+	 * @param resource_path a <code>String</code> specifying the path to the 
resource
+	 * @return the <code>InputStream</code> returned, or <code>null</code> if no 
resource exists at the specified path.
+	 */
+	public static InputStream getResourceAsStream(String resource_path) {
+    	return getTurbineServletContext().getResourceAsStream(resource_path);
+    }
+    
+    /**
+     * Returns a File instance of a given resource. This method is supplied 
here
+     * as a workaround for all turbine specific code which tries to access 
web-app
+     * resources directly with absolute paths (getRealPath()).
+     * 
+     * The tweak here is that the resource is retrieved from an 
<code>InputStream</code>
+     * acquired from the servlet's context and it is written to a temporary 
file. 
+     * 
+	 * @param resource_path a <code>String</code> specifying the path to the 
resource
+	 * @return An <code>File</code> instance pointing to the temp file or 
<code>null</code>
+	 * if the resource couldn't be found.
+	 */
+	public static File getTempFileFromResource(String resource_path) {
+    	InputStream in = null;
+    	OutputStream out = null;
+    	try {
+			File f_out = File.createTempFile("turbine_temp_resource", ".tmp");
+			f_out.deleteOnExit();
+			in = new BufferedInputStream(getResourceAsStream(resource_path));
+			out = new BufferedOutputStream(new FileOutputStream(f_out));
+			int b;
+			while((b=in.read())!=-1)
+				out.write(b);
+			return f_out;
+		} catch (Exception ex) {
+			return null;
+		} finally {
+			if(in!=null) {
+				try {
+					in.close();
+					in = null;
+				} catch(Exception ex) {
+				}
+			}
+			if(out!=null) {
+				try {
+					out.flush();
+					out.close();
+					out = null;
+				} catch(Exception ex) {
+				}
+			}
+		}
+    }
+    /**
      * Finds the specified servlet configuration/initialization
      * parameter, looking first for a servlet-specific parameter, then
      * for a global parameter, and using the provided default if not
@@ -1120,13 +1191,19 @@
      */
     public static String getRealPath(String path)
     {
-        if (path.startsWith("/"))
-        {
-            path = path.substring(1);
+        // try to retrieve the requested resource
+        // using the getTempFileFromResource(String).
+        File resource_file = getTempFileFromResource(path);
+        if(resource_file==null || !resource_file.exists()) {
+        	// oops! Resource is not available which means that
+        	// either we are not currently running within a servlet
+        	// container enviroment or we were unable to retrieve
+        	// the resource via getResourceAsStream() for some reason. 
+        	// Fallback to Turbine's default behaviour;
+			resource_file = new File(getApplicationRoot(), path.startsWith("/") ? 
path.substring(1) : path);
         }
-
-        return new File(getApplicationRoot(), path).getAbsolutePath();
-    }
+        return resource_file.getAbsolutePath();
+	}
 
     /**
      * Return an instance of the currently configured Service Manager
-- 
####################################################################
Filippos Slavik
FORTHnet R&D, Heraklion, Greece
e-mail : fsla@forthnet.gr
phone : (+30) 2811 391230
Key ID: 0xF4B5B375 Filippos Slavik(search pgp.mit.edu)
Key FingerPrint: 81D4 25D0 01EB 9DCA 62E4  B694 20E7 31FB F4B5 B375
####################################################################

"The software said 'runs on Win95 or better,' so I installed it
on Linux..."




---------------------------------------------------------------------
To unsubscribe, e-mail: turbine-dev-unsubscribe@jakarta.apache.org
For additional commands, e-mail: turbine-dev-help@jakarta.apache.org


Re: [PATCH] workaround for EAR/WAR deployments

Posted by Filippos Slavik <fs...@forthnet.gr>.
On Wednesday 10 December 2003 21:35, Eric Pugh wrote:
> You could integrate with cactus..  Look at /src/test-cactus, there are some
> examples...  Maven has a plugin as well..

Dear Eric,

I'v checked-out those cactus unit tests. I think there are is no need to write 
a specific ServletTestCase to demonstrate the functionality. You have it 
already in the CVS. For example the TurbineUserTest or the 
BaseValueParserTest or in general any ServletTestCase which in it's setUp() 
method initializes Turbine by passing the "properties" config parameter uses 
the "new" functionality.

There is need offcourse unit tests for the rest of the services. I'll provide 
some, but I think you should check first the patch I've sent few days ago and 
If you're satisfied then please commit.

Regards
Filippos Slavik

>
> > -----Original Message-----
> > From: Filippos Slavik [mailto:fsla@forthnet.gr]
> > Sent: Wednesday, December 10, 2003 7:07 PM
> > To: Turbine Developers List; Eric Pugh
> > Subject: Re: [PATCH] workaround for EAR/WAR deployments
> >
> > On Wednesday 10 December 2003 10:26, Eric Pugh wrote:
> > > Filippos,
> > >
> > > I think the patch got eaten..  Could you repost to the list
> >
> > and send it to
> >
> > > me directly?
> >
> > Ok, I'm sending the patch again as an attachement this time.
> >
> > > Also, do you have unit tests demonstrating the functionality?
> >
> > Nope, I don't have... but I don't know how I can simulate a
> > web-container
> > enviroment with a Junit testcase .. Is there any kind of
> > integration with
> > junit testcases and tomcat for instance ?
> >
> > > That would make it easier for us to write unit tests that
> >
> > validate all the
> >
> > > services.
> >
> > Slavikos
> >
> > > Eric
> > >
> > > > -----Original Message-----
> > > > From: Filippos Slavik [mailto:fsla@forthnet.gr]
> > > > Sent: Tuesday, December 09, 2003 9:37 PM
> > > > To: turbine-dev@jakarta.apache.org
> > > > Subject: [PATCH] workaround for EAR/WAR deployments
> > > >
> > > >
> > > > I'm sending my patch for Turbine based web-apps that are
> > > > being deployed as a
> > > > WAR/EAR modules.
> > > >
> > > > This is a workaround and not a complete solution of the
> > > > issue, since there is
> > > > a need for a major refactoring in turbine's services which
> > > > assumes that there
> > > > is always an "applicationRoot" available.
> > > >
> > > > The hack here is based on the fact that fortunately all
> > > > services (or most of
> > > > them) and the turbine's main servlet initialization access
> > > > resources through
> > > > the turbine's static getRealPath(String) method which returns
> > > > an absolute
> > > > path of the resource.
> > > >
> > > > The proposed new behaviour is:
> > > >
> > > > There are two new methods.
> > > >
> > > > [1] java.io.InputStream getResourceAsStream(String) which
> >
> > returns an
> >
> > > > InputStream, obtained from the servlet's context, to the
> > > > specified resource.
> > > >
> > > > [2] java.io.File getTempFileFromResource(String) which
> >
> > retrieves an
> >
> > > > InputStream, using the above method, and writes all
> > > > resource's content to a
> > > > temporary created file somewhere in the platforms temp directory
> > > > (File.createTempFile(Stirng, String) is used).
> > > >
> > > > Turbine's static method getRealPath(String) is altered as:
> > > >
> > > > 1) first an attempt is made to retrieve the requested
> > > > resource from the
> > > > servlet's context and if successfull the absolute path of the
> > > > temporary file
> > > > is returned to the caller
> > > >
> > > > 2) if step (1) is not succesfull then the old behaviour is
> > > > used instead (which
> > > > should only happen if we're running junit tests AFAIK)
> > > >
> > > > patch against TURBINE_2_3 version.
> > > >
> > > > I have succesfully compiled turbine with the patch applied
> > > > and deployed an WAR
> > > > turbine based app contained within an EAR module. Certainly
> > > > this is just a
> > > > workaround and not all services will run correctly. In my
> > > > case, the following
> > > > services were enabled during tests:
> > > > services.FactoryService.classname=org.apache.turbine.services.
> > > > factory.TurbineFactoryService
> > > > services.PoolService.classname=org.apache.turbine.services.poo
> > > > l.TurbinePoolService
> > > > services.RunDataService.classname=org.apache.turbine.services.
> > > > rundata.TurbineRunDataService
> > > > services.ServletService.classname=org.apache.turbine.services.
> > > > servlet.TurbineServletService
> > > > services.AssemblerBrokerService.classname=org.apache.turbine.s
> > > > ervices.assemblerbroker.TurbineAssemblerBrokerService
> > > > services.PullService.classname=org.apache.turbine.services.pul
> > > > l.TurbinePullService
> > > > services.MimeTypeService.classname=org.apache.turbine.services
> > > > .mimetype.TurbineMimeTypeService
> > > > services.GlobalCacheService.classname=org.apache.turbine.servi
> > > > ces.cache.TurbineGlobalCacheService
> > > > services.UniqueIdService.classname=org.apache.turbine.services
> > > > .uniqueid.TurbineUniqueIdService
> > > > services.SecurityService.classname=gr.forthnet.backgroundftp.w
> > > > eb.turbine.services.security.BackgroundFTPSecurityService
> > > > services.TemplateService.classname=org.apache.turbine.services
> > > > .template.TurbineTemplateService
> > > > services.VelocityService.classname=org.apache.turbine.services
> > > > .velocity.TurbineVelocityService
> > > >
> > > > And I had no problems at all.
> > > >
> > > > If the patch will be accepted I would like to continue and
> > > > refactor some
> > > > services which currently requires an "applicationRoot" available.
> > > >
> > > > Best Regards
> > > > Filippos Slavik
> > > >
> > > >
> > > >
> > > > Index: Turbine.java
> >
> > ===================================================================
> >
> > > > RCS file:
> > > > /home/cvspublic/jakarta-turbine-2/src/java/org/apache/turbine/
> > > > Turbine.java,v
> > > > retrieving revision 1.45
> > > > diff -u -r1.45 Turbine.java
> > > > --- Turbine.java	2 Jul 2003 16:52:24 -0000	1.45
> > > > +++ Turbine.java	9 Dec 2003 21:14:20 -0000
> > > > @@ -54,10 +54,15 @@
> > > >   * <http://www.apache.org/>.
> > > >   */
> > > >
> > > > +import java.io.BufferedInputStream;
> > > > +import java.io.BufferedOutputStream;
> > > >  import java.io.File;
> > > >  import java.io.FileInputStream;
> > > >  import java.io.FileNotFoundException;
> > > > +import java.io.FileOutputStream;
> > > >  import java.io.IOException;
> > > > +import java.io.InputStream;
> > > > +import java.io.OutputStream;
> > > >  import java.util.Properties;
> > > >
> > > >  import javax.servlet.ServletConfig;
> > > > @@ -135,6 +140,7 @@
> > > >   * @author <a href="mailto:hps@intermeta.de">Henning P.
> > > > Schmiedehausen</a>
> > > >   * @author <a href="mailto:quintonm@bellsouth.net">Quinton
> > > > McCombs</a>
> > > >   * @author <a href="mailto:epugh@upstate.com">Eric Pugh</a>
> > > > + * @author <a href="mailto:fsla@forthnet.gr">Filippos Slavik</a>
> > > >   * @version $Id: Turbine.java,v 1.45 2003/07/02 16:52:24
> > > > henning Exp $
> > > >   */
> > > >  public class Turbine
> > > > @@ -263,6 +269,9 @@
> > > >      private void configure(ServletConfig config,
> > > > ServletContext context)
> > > >              throws Exception
> > > >      {
> > > > +		// Set the Servlet's context right away.
> > > > +		setTurbineServletContext(context);
> > > > +
> > > >          //
> > > >          // Set up Commons Logging to use the Log4J Logging
> > > >          //
> > > > @@ -284,6 +293,14 @@
> > > >          if (applicationRoot == null ||
> > > > applicationRoot.equals(WEB_CONTEXT))
> > > >          {
> > > >              applicationRoot = webappRoot;
> > > > +            if(applicationRoot==null) {
> > > > +            	// if we're running within a servlet container
> > > > enviroment
> > > > +            	// the applicationRoot attribute will have a
> > > > null value, since
> > > > +            	// the applicationRoot can be a WAR or EAR
> > > > file. Just set here
> > > > +            	// a dummy value to avoid NullPointerExceptions
> > > > with jakarta's
> > > > +            	// common configuration framework
> > > > +            	applicationRoot="foo";
> > > > +            }
> > > >              // log.info("got empty or 'webContext'
> >
> > Application root.
> >
> > > > Application root now: " + applicationRoot);
> > > >          }
> > > >
> > > > @@ -390,7 +407,7 @@
> > > >
> > > >
> > > >          setTurbineServletConfig(config);
> > > > -        setTurbineServletContext(context);
> > > > +
> > > >
> > > >          getServiceManager().setApplicationRoot(applicationRoot);
> > > >
> > > > @@ -459,6 +476,60 @@
> > > >      }
> > > >
> > > >      /**
> > > > +     * Returns the resource located at the named path as an
> > > > <code>InputStream</code> object.
> > > > +     *
> > > > +	 * @param resource_path a <code>String</code>
> > > > specifying the path to the
> > > > resource
> > > > +	 * @return the <code>InputStream</code> returned, or
> > > > <code>null</code> if no
> > > > resource exists at the specified path.
> > > > +	 */
> > > > +	public static InputStream getResourceAsStream(String
> > > > resource_path) {
> > > > +    	return
> > > > getTurbineServletContext().getResourceAsStream(resource_path);
> > > > +    }
> > > > +
> > > > +    /**
> > > > +     * Returns a File instance of a given resource. This
> > > > method is supplied
> > > > here
> > > > +     * as a workaround for all turbine specific code which
> > > > tries to access
> > > > web-app
> > > > +     * resources directly with absolute paths (getRealPath()).
> > > > +     *
> > > > +     * The tweak here is that the resource is retrieved from an
> > > > <code>InputStream</code>
> > > > +     * acquired from the servlet's context and it is written
> > > > to a temporary
> > > > file.
> > > > +     *
> > > > +	 * @param resource_path a <code>String</code>
> > > > specifying the path to the
> > > > resource
> > > > +	 * @return An <code>File</code> instance pointing to
> > > > the temp file or
> > > > <code>null</code>
> > > > +	 * if the resource couldn't be found.
> > > > +	 */
> > > > +	public static File getTempFileFromResource(String
> > > > resource_path) {
> > > > +    	InputStream in = null;
> > > > +    	OutputStream out = null;
> > > > +    	try {
> > > > +			File f_out =
> > > > File.createTempFile("turbine_temp_resource", ".tmp");
> > > > +			f_out.deleteOnExit();
> > > > +			in = new
> > > > BufferedInputStream(getResourceAsStream(resource_path));
> > > > +			out = new BufferedOutputStream(new
> > > > FileOutputStream(f_out));
> > > > +			int b;
> > > > +			while((b=in.read())!=-1)
> > > > +				out.write(b);
> > > > +			return f_out;
> > > > +		} catch (Exception ex) {
> > > > +			return null;
> > > > +		} finally {
> > > > +			if(in!=null) {
> > > > +				try {
> > > > +					in.close();
> > > > +					in = null;
> > > > +				} catch(Exception ex) {
> > > > +				}
> > > > +			}
> > > > +			if(out!=null) {
> > > > +				try {
> > > > +					out.flush();
> > > > +					out.close();
> > > > +					out = null;
> > > > +				} catch(Exception ex) {
> > > > +				}
> > > > +			}
> > > > +		}
> > > > +    }
> > > > +    /**
> > > >       * Finds the specified servlet configuration/initialization
> > > >       * parameter, looking first for a servlet-specific
> > > > parameter, then
> > > >       * for a global parameter, and using the provided
> >
> > default if not
> >
> > > > @@ -1120,13 +1191,19 @@
> > > >       */
> > > >      public static String getRealPath(String path)
> > > >      {
> > > > -        if (path.startsWith("/"))
> > > > -        {
> > > > -            path = path.substring(1);
> > > > +        // try to retrieve the requested resource
> > > > +        // using the getTempFileFromResource(String).
> > > > +        File resource_file = getTempFileFromResource(path);
> > > > +        if(resource_file==null || !resource_file.exists()) {
> > > > +        	// oops! Resource is not available which means that
> > > > +        	// either we are not currently running within a servlet
> > > > +        	// container enviroment or we were unable to retrieve
> > > > +        	// the resource via getResourceAsStream() for
> > > > some reason.
> > > > +        	// Fallback to Turbine's default behaviour;
> > > > +			resource_file = new
> > > > File(getApplicationRoot(), path.startsWith("/") ?
> > > > path.substring(1) : path);
> > > >          }
> > > > -
> > > > -        return new File(getApplicationRoot(),
> > > > path).getAbsolutePath();
> > > > -    }
> > > > +        return resource_file.getAbsolutePath();
> > > > +	}
> > > >
> > > >      /**
> > > >       * Return an instance of the currently configured
> >
> > Service Manager
> >
> > > > --
> >
> > ####################################################################
> >
> > > > Filippos Slavik
> > > > FORTHnet R&D, Heraklion, Greece
> > > > e-mail : fsla@forthnet.gr
> > > > phone : (+30) 2811 391230
> > > > Key ID: 0xF4B5B375 Filippos Slavik(search pgp.mit.edu)
> > > > Key FingerPrint: 81D4 25D0 01EB 9DCA 62E4  B694 20E7 31FB
> >
> > F4B5 B375
> >
> > ####################################################################
> >
> > > > "The software said 'runs on Win95 or better,' so I installed it
> > > > on Linux..."
> >
> > ---------------------------------------------------------------------
> >
> > > > To unsubscribe, e-mail: turbine-dev-unsubscribe@jakarta.apache.org
> > > > For additional commands, e-mail:
> >
> > turbine-dev-help@jakarta.apache.org
> >
> >
> > ---------------------------------------------------------------------
> >
> > > To unsubscribe, e-mail: turbine-dev-unsubscribe@jakarta.apache.org
> > > For additional commands, e-mail: turbine-dev-help@jakarta.apache.org
> >
> > --
> > ####################################################################
> > Filippos Slavik
> > FORTHnet R&D, Heraklion, Greece
> > e-mail : fsla@forthnet.gr
> > phone : (+30) 2811 391230
> > Key ID: 0xF4B5B375 Filippos Slavik(search pgp.mit.edu)
> > Key FingerPrint: 81D4 25D0 01EB 9DCA 62E4  B694 20E7 31FB F4B5 B375
> > ####################################################################
> >
> > "The software said 'runs on Win95 or better,' so I installed it
> > on Linux..."

-- 
####################################################################
Filippos Slavik
FORTHnet R&D, Heraklion, Greece
e-mail : fsla@forthnet.gr
phone : (+30) 2811 391230
Key ID: 0xF4B5B375 Filippos Slavik(search pgp.mit.edu)
Key FingerPrint: 81D4 25D0 01EB 9DCA 62E4  B694 20E7 31FB F4B5 B375
####################################################################

"The software said 'runs on Win95 or better,' so I installed it
on Linux..."




---------------------------------------------------------------------
To unsubscribe, e-mail: turbine-dev-unsubscribe@jakarta.apache.org
For additional commands, e-mail: turbine-dev-help@jakarta.apache.org


RE: [PATCH] workaround for EAR/WAR deployments

Posted by Eric Pugh <ep...@upstate.com>.
You could integrate with cactus..  Look at /src/test-cactus, there are some
examples...  Maven has a plugin as well..

> -----Original Message-----
> From: Filippos Slavik [mailto:fsla@forthnet.gr]
> Sent: Wednesday, December 10, 2003 7:07 PM
> To: Turbine Developers List; Eric Pugh
> Subject: Re: [PATCH] workaround for EAR/WAR deployments
>
>
> On Wednesday 10 December 2003 10:26, Eric Pugh wrote:
> > Filippos,
> >
> > I think the patch got eaten..  Could you repost to the list
> and send it to
> > me directly?
>
> Ok, I'm sending the patch again as an attachement this time.
> > Also, do you have unit tests demonstrating the functionality?
>
> Nope, I don't have... but I don't know how I can simulate a
> web-container
> enviroment with a Junit testcase .. Is there any kind of
> integration with
> junit testcases and tomcat for instance ?
>
> > That would make it easier for us to write unit tests that
> validate all the
> > services.
>
> Slavikos
>
> >
> > Eric
> >
> > > -----Original Message-----
> > > From: Filippos Slavik [mailto:fsla@forthnet.gr]
> > > Sent: Tuesday, December 09, 2003 9:37 PM
> > > To: turbine-dev@jakarta.apache.org
> > > Subject: [PATCH] workaround for EAR/WAR deployments
> > >
> > >
> > > I'm sending my patch for Turbine based web-apps that are
> > > being deployed as a
> > > WAR/EAR modules.
> > >
> > > This is a workaround and not a complete solution of the
> > > issue, since there is
> > > a need for a major refactoring in turbine's services which
> > > assumes that there
> > > is always an "applicationRoot" available.
> > >
> > > The hack here is based on the fact that fortunately all
> > > services (or most of
> > > them) and the turbine's main servlet initialization access
> > > resources through
> > > the turbine's static getRealPath(String) method which returns
> > > an absolute
> > > path of the resource.
> > >
> > > The proposed new behaviour is:
> > >
> > > There are two new methods.
> > >
> > > [1] java.io.InputStream getResourceAsStream(String) which
> returns an
> > > InputStream, obtained from the servlet's context, to the
> > > specified resource.
> > >
> > > [2] java.io.File getTempFileFromResource(String) which
> retrieves an
> > > InputStream, using the above method, and writes all
> > > resource's content to a
> > > temporary created file somewhere in the platforms temp directory
> > > (File.createTempFile(Stirng, String) is used).
> > >
> > > Turbine's static method getRealPath(String) is altered as:
> > >
> > > 1) first an attempt is made to retrieve the requested
> > > resource from the
> > > servlet's context and if successfull the absolute path of the
> > > temporary file
> > > is returned to the caller
> > >
> > > 2) if step (1) is not succesfull then the old behaviour is
> > > used instead (which
> > > should only happen if we're running junit tests AFAIK)
> > >
> > > patch against TURBINE_2_3 version.
> > >
> > > I have succesfully compiled turbine with the patch applied
> > > and deployed an WAR
> > > turbine based app contained within an EAR module. Certainly
> > > this is just a
> > > workaround and not all services will run correctly. In my
> > > case, the following
> > > services were enabled during tests:
> > > services.FactoryService.classname=org.apache.turbine.services.
> > > factory.TurbineFactoryService
> > > services.PoolService.classname=org.apache.turbine.services.poo
> > > l.TurbinePoolService
> > > services.RunDataService.classname=org.apache.turbine.services.
> > > rundata.TurbineRunDataService
> > > services.ServletService.classname=org.apache.turbine.services.
> > > servlet.TurbineServletService
> > > services.AssemblerBrokerService.classname=org.apache.turbine.s
> > > ervices.assemblerbroker.TurbineAssemblerBrokerService
> > > services.PullService.classname=org.apache.turbine.services.pul
> > > l.TurbinePullService
> > > services.MimeTypeService.classname=org.apache.turbine.services
> > > .mimetype.TurbineMimeTypeService
> > > services.GlobalCacheService.classname=org.apache.turbine.servi
> > > ces.cache.TurbineGlobalCacheService
> > > services.UniqueIdService.classname=org.apache.turbine.services
> > > .uniqueid.TurbineUniqueIdService
> > > services.SecurityService.classname=gr.forthnet.backgroundftp.w
> > > eb.turbine.services.security.BackgroundFTPSecurityService
> > > services.TemplateService.classname=org.apache.turbine.services
> > > .template.TurbineTemplateService
> > > services.VelocityService.classname=org.apache.turbine.services
> > > .velocity.TurbineVelocityService
> > >
> > > And I had no problems at all.
> > >
> > > If the patch will be accepted I would like to continue and
> > > refactor some
> > > services which currently requires an "applicationRoot" available.
> > >
> > > Best Regards
> > > Filippos Slavik
> > >
> > >
> > >
> > > Index: Turbine.java
> > >
> ===================================================================
> > > RCS file:
> > > /home/cvspublic/jakarta-turbine-2/src/java/org/apache/turbine/
> > > Turbine.java,v
> > > retrieving revision 1.45
> > > diff -u -r1.45 Turbine.java
> > > --- Turbine.java	2 Jul 2003 16:52:24 -0000	1.45
> > > +++ Turbine.java	9 Dec 2003 21:14:20 -0000
> > > @@ -54,10 +54,15 @@
> > >   * <http://www.apache.org/>.
> > >   */
> > >
> > > +import java.io.BufferedInputStream;
> > > +import java.io.BufferedOutputStream;
> > >  import java.io.File;
> > >  import java.io.FileInputStream;
> > >  import java.io.FileNotFoundException;
> > > +import java.io.FileOutputStream;
> > >  import java.io.IOException;
> > > +import java.io.InputStream;
> > > +import java.io.OutputStream;
> > >  import java.util.Properties;
> > >
> > >  import javax.servlet.ServletConfig;
> > > @@ -135,6 +140,7 @@
> > >   * @author <a href="mailto:hps@intermeta.de">Henning P.
> > > Schmiedehausen</a>
> > >   * @author <a href="mailto:quintonm@bellsouth.net">Quinton
> > > McCombs</a>
> > >   * @author <a href="mailto:epugh@upstate.com">Eric Pugh</a>
> > > + * @author <a href="mailto:fsla@forthnet.gr">Filippos Slavik</a>
> > >   * @version $Id: Turbine.java,v 1.45 2003/07/02 16:52:24
> > > henning Exp $
> > >   */
> > >  public class Turbine
> > > @@ -263,6 +269,9 @@
> > >      private void configure(ServletConfig config,
> > > ServletContext context)
> > >              throws Exception
> > >      {
> > > +		// Set the Servlet's context right away.
> > > +		setTurbineServletContext(context);
> > > +
> > >          //
> > >          // Set up Commons Logging to use the Log4J Logging
> > >          //
> > > @@ -284,6 +293,14 @@
> > >          if (applicationRoot == null ||
> > > applicationRoot.equals(WEB_CONTEXT))
> > >          {
> > >              applicationRoot = webappRoot;
> > > +            if(applicationRoot==null) {
> > > +            	// if we're running within a servlet container
> > > enviroment
> > > +            	// the applicationRoot attribute will have a
> > > null value, since
> > > +            	// the applicationRoot can be a WAR or EAR
> > > file. Just set here
> > > +            	// a dummy value to avoid NullPointerExceptions
> > > with jakarta's
> > > +            	// common configuration framework
> > > +            	applicationRoot="foo";
> > > +            }
> > >              // log.info("got empty or 'webContext'
> Application root.
> > > Application root now: " + applicationRoot);
> > >          }
> > >
> > > @@ -390,7 +407,7 @@
> > >
> > >
> > >          setTurbineServletConfig(config);
> > > -        setTurbineServletContext(context);
> > > +
> > >
> > >          getServiceManager().setApplicationRoot(applicationRoot);
> > >
> > > @@ -459,6 +476,60 @@
> > >      }
> > >
> > >      /**
> > > +     * Returns the resource located at the named path as an
> > > <code>InputStream</code> object.
> > > +     *
> > > +	 * @param resource_path a <code>String</code>
> > > specifying the path to the
> > > resource
> > > +	 * @return the <code>InputStream</code> returned, or
> > > <code>null</code> if no
> > > resource exists at the specified path.
> > > +	 */
> > > +	public static InputStream getResourceAsStream(String
> > > resource_path) {
> > > +    	return
> > > getTurbineServletContext().getResourceAsStream(resource_path);
> > > +    }
> > > +
> > > +    /**
> > > +     * Returns a File instance of a given resource. This
> > > method is supplied
> > > here
> > > +     * as a workaround for all turbine specific code which
> > > tries to access
> > > web-app
> > > +     * resources directly with absolute paths (getRealPath()).
> > > +     *
> > > +     * The tweak here is that the resource is retrieved from an
> > > <code>InputStream</code>
> > > +     * acquired from the servlet's context and it is written
> > > to a temporary
> > > file.
> > > +     *
> > > +	 * @param resource_path a <code>String</code>
> > > specifying the path to the
> > > resource
> > > +	 * @return An <code>File</code> instance pointing to
> > > the temp file or
> > > <code>null</code>
> > > +	 * if the resource couldn't be found.
> > > +	 */
> > > +	public static File getTempFileFromResource(String
> > > resource_path) {
> > > +    	InputStream in = null;
> > > +    	OutputStream out = null;
> > > +    	try {
> > > +			File f_out =
> > > File.createTempFile("turbine_temp_resource", ".tmp");
> > > +			f_out.deleteOnExit();
> > > +			in = new
> > > BufferedInputStream(getResourceAsStream(resource_path));
> > > +			out = new BufferedOutputStream(new
> > > FileOutputStream(f_out));
> > > +			int b;
> > > +			while((b=in.read())!=-1)
> > > +				out.write(b);
> > > +			return f_out;
> > > +		} catch (Exception ex) {
> > > +			return null;
> > > +		} finally {
> > > +			if(in!=null) {
> > > +				try {
> > > +					in.close();
> > > +					in = null;
> > > +				} catch(Exception ex) {
> > > +				}
> > > +			}
> > > +			if(out!=null) {
> > > +				try {
> > > +					out.flush();
> > > +					out.close();
> > > +					out = null;
> > > +				} catch(Exception ex) {
> > > +				}
> > > +			}
> > > +		}
> > > +    }
> > > +    /**
> > >       * Finds the specified servlet configuration/initialization
> > >       * parameter, looking first for a servlet-specific
> > > parameter, then
> > >       * for a global parameter, and using the provided
> default if not
> > > @@ -1120,13 +1191,19 @@
> > >       */
> > >      public static String getRealPath(String path)
> > >      {
> > > -        if (path.startsWith("/"))
> > > -        {
> > > -            path = path.substring(1);
> > > +        // try to retrieve the requested resource
> > > +        // using the getTempFileFromResource(String).
> > > +        File resource_file = getTempFileFromResource(path);
> > > +        if(resource_file==null || !resource_file.exists()) {
> > > +        	// oops! Resource is not available which means that
> > > +        	// either we are not currently running within a servlet
> > > +        	// container enviroment or we were unable to retrieve
> > > +        	// the resource via getResourceAsStream() for
> > > some reason.
> > > +        	// Fallback to Turbine's default behaviour;
> > > +			resource_file = new
> > > File(getApplicationRoot(), path.startsWith("/") ?
> > > path.substring(1) : path);
> > >          }
> > > -
> > > -        return new File(getApplicationRoot(),
> > > path).getAbsolutePath();
> > > -    }
> > > +        return resource_file.getAbsolutePath();
> > > +	}
> > >
> > >      /**
> > >       * Return an instance of the currently configured
> Service Manager
> > > --
> > >
> ####################################################################
> > > Filippos Slavik
> > > FORTHnet R&D, Heraklion, Greece
> > > e-mail : fsla@forthnet.gr
> > > phone : (+30) 2811 391230
> > > Key ID: 0xF4B5B375 Filippos Slavik(search pgp.mit.edu)
> > > Key FingerPrint: 81D4 25D0 01EB 9DCA 62E4  B694 20E7 31FB
> F4B5 B375
> > >
> ####################################################################
> > >
> > > "The software said 'runs on Win95 or better,' so I installed it
> > > on Linux..."
> > >
> > >
> > >
> > >
> > >
> ---------------------------------------------------------------------
> > > To unsubscribe, e-mail: turbine-dev-unsubscribe@jakarta.apache.org
> > > For additional commands, e-mail:
> turbine-dev-help@jakarta.apache.org
> >
> >
> ---------------------------------------------------------------------
> > To unsubscribe, e-mail: turbine-dev-unsubscribe@jakarta.apache.org
> > For additional commands, e-mail: turbine-dev-help@jakarta.apache.org
>
> --
> ####################################################################
> Filippos Slavik
> FORTHnet R&D, Heraklion, Greece
> e-mail : fsla@forthnet.gr
> phone : (+30) 2811 391230
> Key ID: 0xF4B5B375 Filippos Slavik(search pgp.mit.edu)
> Key FingerPrint: 81D4 25D0 01EB 9DCA 62E4  B694 20E7 31FB F4B5 B375
> ####################################################################
>
> "The software said 'runs on Win95 or better,' so I installed it
> on Linux..."
>
>
>
>


---------------------------------------------------------------------
To unsubscribe, e-mail: turbine-dev-unsubscribe@jakarta.apache.org
For additional commands, e-mail: turbine-dev-help@jakarta.apache.org


Re: [PATCH] workaround for EAR/WAR deployments

Posted by Filippos Slavik <fs...@forthnet.gr>.
On Wednesday 10 December 2003 10:26, Eric Pugh wrote:
> Filippos,
>
> I think the patch got eaten..  Could you repost to the list and send it to
> me directly?  

Ok, I'm sending the patch again as an attachement this time.
> Also, do you have unit tests demonstrating the functionality?

Nope, I don't have... but I don't know how I can simulate a web-container 
enviroment with a Junit testcase .. Is there any kind of integration with 
junit testcases and tomcat for instance ?

> That would make it easier for us to write unit tests that validate all the
> services.

Slavikos

>
> Eric
>
> > -----Original Message-----
> > From: Filippos Slavik [mailto:fsla@forthnet.gr]
> > Sent: Tuesday, December 09, 2003 9:37 PM
> > To: turbine-dev@jakarta.apache.org
> > Subject: [PATCH] workaround for EAR/WAR deployments
> >
> >
> > I'm sending my patch for Turbine based web-apps that are
> > being deployed as a
> > WAR/EAR modules.
> >
> > This is a workaround and not a complete solution of the
> > issue, since there is
> > a need for a major refactoring in turbine's services which
> > assumes that there
> > is always an "applicationRoot" available.
> >
> > The hack here is based on the fact that fortunately all
> > services (or most of
> > them) and the turbine's main servlet initialization access
> > resources through
> > the turbine's static getRealPath(String) method which returns
> > an absolute
> > path of the resource.
> >
> > The proposed new behaviour is:
> >
> > There are two new methods.
> >
> > [1] java.io.InputStream getResourceAsStream(String) which returns an
> > InputStream, obtained from the servlet's context, to the
> > specified resource.
> >
> > [2] java.io.File getTempFileFromResource(String) which retrieves an
> > InputStream, using the above method, and writes all
> > resource's content to a
> > temporary created file somewhere in the platforms temp directory
> > (File.createTempFile(Stirng, String) is used).
> >
> > Turbine's static method getRealPath(String) is altered as:
> >
> > 1) first an attempt is made to retrieve the requested
> > resource from the
> > servlet's context and if successfull the absolute path of the
> > temporary file
> > is returned to the caller
> >
> > 2) if step (1) is not succesfull then the old behaviour is
> > used instead (which
> > should only happen if we're running junit tests AFAIK)
> >
> > patch against TURBINE_2_3 version.
> >
> > I have succesfully compiled turbine with the patch applied
> > and deployed an WAR
> > turbine based app contained within an EAR module. Certainly
> > this is just a
> > workaround and not all services will run correctly. In my
> > case, the following
> > services were enabled during tests:
> > services.FactoryService.classname=org.apache.turbine.services.
> > factory.TurbineFactoryService
> > services.PoolService.classname=org.apache.turbine.services.poo
> > l.TurbinePoolService
> > services.RunDataService.classname=org.apache.turbine.services.
> > rundata.TurbineRunDataService
> > services.ServletService.classname=org.apache.turbine.services.
> > servlet.TurbineServletService
> > services.AssemblerBrokerService.classname=org.apache.turbine.s
> > ervices.assemblerbroker.TurbineAssemblerBrokerService
> > services.PullService.classname=org.apache.turbine.services.pul
> > l.TurbinePullService
> > services.MimeTypeService.classname=org.apache.turbine.services
> > .mimetype.TurbineMimeTypeService
> > services.GlobalCacheService.classname=org.apache.turbine.servi
> > ces.cache.TurbineGlobalCacheService
> > services.UniqueIdService.classname=org.apache.turbine.services
> > .uniqueid.TurbineUniqueIdService
> > services.SecurityService.classname=gr.forthnet.backgroundftp.w
> > eb.turbine.services.security.BackgroundFTPSecurityService
> > services.TemplateService.classname=org.apache.turbine.services
> > .template.TurbineTemplateService
> > services.VelocityService.classname=org.apache.turbine.services
> > .velocity.TurbineVelocityService
> >
> > And I had no problems at all.
> >
> > If the patch will be accepted I would like to continue and
> > refactor some
> > services which currently requires an "applicationRoot" available.
> >
> > Best Regards
> > Filippos Slavik
> >
> >
> >
> > Index: Turbine.java
> > ===================================================================
> > RCS file:
> > /home/cvspublic/jakarta-turbine-2/src/java/org/apache/turbine/
> > Turbine.java,v
> > retrieving revision 1.45
> > diff -u -r1.45 Turbine.java
> > --- Turbine.java	2 Jul 2003 16:52:24 -0000	1.45
> > +++ Turbine.java	9 Dec 2003 21:14:20 -0000
> > @@ -54,10 +54,15 @@
> >   * <http://www.apache.org/>.
> >   */
> >
> > +import java.io.BufferedInputStream;
> > +import java.io.BufferedOutputStream;
> >  import java.io.File;
> >  import java.io.FileInputStream;
> >  import java.io.FileNotFoundException;
> > +import java.io.FileOutputStream;
> >  import java.io.IOException;
> > +import java.io.InputStream;
> > +import java.io.OutputStream;
> >  import java.util.Properties;
> >
> >  import javax.servlet.ServletConfig;
> > @@ -135,6 +140,7 @@
> >   * @author <a href="mailto:hps@intermeta.de">Henning P.
> > Schmiedehausen</a>
> >   * @author <a href="mailto:quintonm@bellsouth.net">Quinton
> > McCombs</a>
> >   * @author <a href="mailto:epugh@upstate.com">Eric Pugh</a>
> > + * @author <a href="mailto:fsla@forthnet.gr">Filippos Slavik</a>
> >   * @version $Id: Turbine.java,v 1.45 2003/07/02 16:52:24
> > henning Exp $
> >   */
> >  public class Turbine
> > @@ -263,6 +269,9 @@
> >      private void configure(ServletConfig config,
> > ServletContext context)
> >              throws Exception
> >      {
> > +		// Set the Servlet's context right away.
> > +		setTurbineServletContext(context);
> > +
> >          //
> >          // Set up Commons Logging to use the Log4J Logging
> >          //
> > @@ -284,6 +293,14 @@
> >          if (applicationRoot == null ||
> > applicationRoot.equals(WEB_CONTEXT))
> >          {
> >              applicationRoot = webappRoot;
> > +            if(applicationRoot==null) {
> > +            	// if we're running within a servlet container
> > enviroment
> > +            	// the applicationRoot attribute will have a
> > null value, since
> > +            	// the applicationRoot can be a WAR or EAR
> > file. Just set here
> > +            	// a dummy value to avoid NullPointerExceptions
> > with jakarta's
> > +            	// common configuration framework
> > +            	applicationRoot="foo";
> > +            }
> >              // log.info("got empty or 'webContext' Application root.
> > Application root now: " + applicationRoot);
> >          }
> >
> > @@ -390,7 +407,7 @@
> >
> >
> >          setTurbineServletConfig(config);
> > -        setTurbineServletContext(context);
> > +
> >
> >          getServiceManager().setApplicationRoot(applicationRoot);
> >
> > @@ -459,6 +476,60 @@
> >      }
> >
> >      /**
> > +     * Returns the resource located at the named path as an
> > <code>InputStream</code> object.
> > +     *
> > +	 * @param resource_path a <code>String</code>
> > specifying the path to the
> > resource
> > +	 * @return the <code>InputStream</code> returned, or
> > <code>null</code> if no
> > resource exists at the specified path.
> > +	 */
> > +	public static InputStream getResourceAsStream(String
> > resource_path) {
> > +    	return
> > getTurbineServletContext().getResourceAsStream(resource_path);
> > +    }
> > +
> > +    /**
> > +     * Returns a File instance of a given resource. This
> > method is supplied
> > here
> > +     * as a workaround for all turbine specific code which
> > tries to access
> > web-app
> > +     * resources directly with absolute paths (getRealPath()).
> > +     *
> > +     * The tweak here is that the resource is retrieved from an
> > <code>InputStream</code>
> > +     * acquired from the servlet's context and it is written
> > to a temporary
> > file.
> > +     *
> > +	 * @param resource_path a <code>String</code>
> > specifying the path to the
> > resource
> > +	 * @return An <code>File</code> instance pointing to
> > the temp file or
> > <code>null</code>
> > +	 * if the resource couldn't be found.
> > +	 */
> > +	public static File getTempFileFromResource(String
> > resource_path) {
> > +    	InputStream in = null;
> > +    	OutputStream out = null;
> > +    	try {
> > +			File f_out =
> > File.createTempFile("turbine_temp_resource", ".tmp");
> > +			f_out.deleteOnExit();
> > +			in = new
> > BufferedInputStream(getResourceAsStream(resource_path));
> > +			out = new BufferedOutputStream(new
> > FileOutputStream(f_out));
> > +			int b;
> > +			while((b=in.read())!=-1)
> > +				out.write(b);
> > +			return f_out;
> > +		} catch (Exception ex) {
> > +			return null;
> > +		} finally {
> > +			if(in!=null) {
> > +				try {
> > +					in.close();
> > +					in = null;
> > +				} catch(Exception ex) {
> > +				}
> > +			}
> > +			if(out!=null) {
> > +				try {
> > +					out.flush();
> > +					out.close();
> > +					out = null;
> > +				} catch(Exception ex) {
> > +				}
> > +			}
> > +		}
> > +    }
> > +    /**
> >       * Finds the specified servlet configuration/initialization
> >       * parameter, looking first for a servlet-specific
> > parameter, then
> >       * for a global parameter, and using the provided default if not
> > @@ -1120,13 +1191,19 @@
> >       */
> >      public static String getRealPath(String path)
> >      {
> > -        if (path.startsWith("/"))
> > -        {
> > -            path = path.substring(1);
> > +        // try to retrieve the requested resource
> > +        // using the getTempFileFromResource(String).
> > +        File resource_file = getTempFileFromResource(path);
> > +        if(resource_file==null || !resource_file.exists()) {
> > +        	// oops! Resource is not available which means that
> > +        	// either we are not currently running within a servlet
> > +        	// container enviroment or we were unable to retrieve
> > +        	// the resource via getResourceAsStream() for
> > some reason.
> > +        	// Fallback to Turbine's default behaviour;
> > +			resource_file = new
> > File(getApplicationRoot(), path.startsWith("/") ?
> > path.substring(1) : path);
> >          }
> > -
> > -        return new File(getApplicationRoot(),
> > path).getAbsolutePath();
> > -    }
> > +        return resource_file.getAbsolutePath();
> > +	}
> >
> >      /**
> >       * Return an instance of the currently configured Service Manager
> > --
> > ####################################################################
> > Filippos Slavik
> > FORTHnet R&D, Heraklion, Greece
> > e-mail : fsla@forthnet.gr
> > phone : (+30) 2811 391230
> > Key ID: 0xF4B5B375 Filippos Slavik(search pgp.mit.edu)
> > Key FingerPrint: 81D4 25D0 01EB 9DCA 62E4  B694 20E7 31FB F4B5 B375
> > ####################################################################
> >
> > "The software said 'runs on Win95 or better,' so I installed it
> > on Linux..."
> >
> >
> >
> >
> > ---------------------------------------------------------------------
> > To unsubscribe, e-mail: turbine-dev-unsubscribe@jakarta.apache.org
> > For additional commands, e-mail: turbine-dev-help@jakarta.apache.org
>
> ---------------------------------------------------------------------
> To unsubscribe, e-mail: turbine-dev-unsubscribe@jakarta.apache.org
> For additional commands, e-mail: turbine-dev-help@jakarta.apache.org

-- 
####################################################################
Filippos Slavik
FORTHnet R&D, Heraklion, Greece
e-mail : fsla@forthnet.gr
phone : (+30) 2811 391230
Key ID: 0xF4B5B375 Filippos Slavik(search pgp.mit.edu)
Key FingerPrint: 81D4 25D0 01EB 9DCA 62E4  B694 20E7 31FB F4B5 B375
####################################################################

"The software said 'runs on Win95 or better,' so I installed it
on Linux..."



RE: [PATCH] workaround for EAR/WAR deployments

Posted by Eric Pugh <ep...@upstate.com>.
Filippos,

I think the patch got eaten..  Could you repost to the list and send it to
me directly?  Also, do you have unit tests demonstrating the functionality?
That would make it easier for us to write unit tests that validate all the
services.

Eric

> -----Original Message-----
> From: Filippos Slavik [mailto:fsla@forthnet.gr]
> Sent: Tuesday, December 09, 2003 9:37 PM
> To: turbine-dev@jakarta.apache.org
> Subject: [PATCH] workaround for EAR/WAR deployments
>
>
> I'm sending my patch for Turbine based web-apps that are
> being deployed as a
> WAR/EAR modules.
>
> This is a workaround and not a complete solution of the
> issue, since there is
> a need for a major refactoring in turbine's services which
> assumes that there
> is always an "applicationRoot" available.
>
> The hack here is based on the fact that fortunately all
> services (or most of
> them) and the turbine's main servlet initialization access
> resources through
> the turbine's static getRealPath(String) method which returns
> an absolute
> path of the resource.
>
> The proposed new behaviour is:
>
> There are two new methods.
>
> [1] java.io.InputStream getResourceAsStream(String) which returns an
> InputStream, obtained from the servlet's context, to the
> specified resource.
>
> [2] java.io.File getTempFileFromResource(String) which retrieves an
> InputStream, using the above method, and writes all
> resource's content to a
> temporary created file somewhere in the platforms temp directory
> (File.createTempFile(Stirng, String) is used).
>
> Turbine's static method getRealPath(String) is altered as:
>
> 1) first an attempt is made to retrieve the requested
> resource from the
> servlet's context and if successfull the absolute path of the
> temporary file
> is returned to the caller
>
> 2) if step (1) is not succesfull then the old behaviour is
> used instead (which
> should only happen if we're running junit tests AFAIK)
>
> patch against TURBINE_2_3 version.
>
> I have succesfully compiled turbine with the patch applied
> and deployed an WAR
> turbine based app contained within an EAR module. Certainly
> this is just a
> workaround and not all services will run correctly. In my
> case, the following
> services were enabled during tests:
> services.FactoryService.classname=org.apache.turbine.services.
> factory.TurbineFactoryService
> services.PoolService.classname=org.apache.turbine.services.poo
> l.TurbinePoolService
> services.RunDataService.classname=org.apache.turbine.services.
> rundata.TurbineRunDataService
> services.ServletService.classname=org.apache.turbine.services.
> servlet.TurbineServletService
> services.AssemblerBrokerService.classname=org.apache.turbine.s
> ervices.assemblerbroker.TurbineAssemblerBrokerService
> services.PullService.classname=org.apache.turbine.services.pul
> l.TurbinePullService
> services.MimeTypeService.classname=org.apache.turbine.services
> .mimetype.TurbineMimeTypeService
> services.GlobalCacheService.classname=org.apache.turbine.servi
> ces.cache.TurbineGlobalCacheService
> services.UniqueIdService.classname=org.apache.turbine.services
> .uniqueid.TurbineUniqueIdService
> services.SecurityService.classname=gr.forthnet.backgroundftp.w
> eb.turbine.services.security.BackgroundFTPSecurityService
> services.TemplateService.classname=org.apache.turbine.services
> .template.TurbineTemplateService
> services.VelocityService.classname=org.apache.turbine.services
> .velocity.TurbineVelocityService
>
> And I had no problems at all.
>
> If the patch will be accepted I would like to continue and
> refactor some
> services which currently requires an "applicationRoot" available.
>
> Best Regards
> Filippos Slavik
>
>
>
> Index: Turbine.java
> ===================================================================
> RCS file:
> /home/cvspublic/jakarta-turbine-2/src/java/org/apache/turbine/
> Turbine.java,v
> retrieving revision 1.45
> diff -u -r1.45 Turbine.java
> --- Turbine.java	2 Jul 2003 16:52:24 -0000	1.45
> +++ Turbine.java	9 Dec 2003 21:14:20 -0000
> @@ -54,10 +54,15 @@
>   * <http://www.apache.org/>.
>   */
>
> +import java.io.BufferedInputStream;
> +import java.io.BufferedOutputStream;
>  import java.io.File;
>  import java.io.FileInputStream;
>  import java.io.FileNotFoundException;
> +import java.io.FileOutputStream;
>  import java.io.IOException;
> +import java.io.InputStream;
> +import java.io.OutputStream;
>  import java.util.Properties;
>
>  import javax.servlet.ServletConfig;
> @@ -135,6 +140,7 @@
>   * @author <a href="mailto:hps@intermeta.de">Henning P.
> Schmiedehausen</a>
>   * @author <a href="mailto:quintonm@bellsouth.net">Quinton
> McCombs</a>
>   * @author <a href="mailto:epugh@upstate.com">Eric Pugh</a>
> + * @author <a href="mailto:fsla@forthnet.gr">Filippos Slavik</a>
>   * @version $Id: Turbine.java,v 1.45 2003/07/02 16:52:24
> henning Exp $
>   */
>  public class Turbine
> @@ -263,6 +269,9 @@
>      private void configure(ServletConfig config,
> ServletContext context)
>              throws Exception
>      {
> +		// Set the Servlet's context right away.
> +		setTurbineServletContext(context);
> +
>          //
>          // Set up Commons Logging to use the Log4J Logging
>          //
> @@ -284,6 +293,14 @@
>          if (applicationRoot == null ||
> applicationRoot.equals(WEB_CONTEXT))
>          {
>              applicationRoot = webappRoot;
> +            if(applicationRoot==null) {
> +            	// if we're running within a servlet container
> enviroment
> +            	// the applicationRoot attribute will have a
> null value, since
> +            	// the applicationRoot can be a WAR or EAR
> file. Just set here
> +            	// a dummy value to avoid NullPointerExceptions
> with jakarta's
> +            	// common configuration framework
> +            	applicationRoot="foo";
> +            }
>              // log.info("got empty or 'webContext' Application root.
> Application root now: " + applicationRoot);
>          }
>
> @@ -390,7 +407,7 @@
>
>
>          setTurbineServletConfig(config);
> -        setTurbineServletContext(context);
> +
>
>          getServiceManager().setApplicationRoot(applicationRoot);
>
> @@ -459,6 +476,60 @@
>      }
>
>      /**
> +     * Returns the resource located at the named path as an
> <code>InputStream</code> object.
> +     *
> +	 * @param resource_path a <code>String</code>
> specifying the path to the
> resource
> +	 * @return the <code>InputStream</code> returned, or
> <code>null</code> if no
> resource exists at the specified path.
> +	 */
> +	public static InputStream getResourceAsStream(String
> resource_path) {
> +    	return
> getTurbineServletContext().getResourceAsStream(resource_path);
> +    }
> +
> +    /**
> +     * Returns a File instance of a given resource. This
> method is supplied
> here
> +     * as a workaround for all turbine specific code which
> tries to access
> web-app
> +     * resources directly with absolute paths (getRealPath()).
> +     *
> +     * The tweak here is that the resource is retrieved from an
> <code>InputStream</code>
> +     * acquired from the servlet's context and it is written
> to a temporary
> file.
> +     *
> +	 * @param resource_path a <code>String</code>
> specifying the path to the
> resource
> +	 * @return An <code>File</code> instance pointing to
> the temp file or
> <code>null</code>
> +	 * if the resource couldn't be found.
> +	 */
> +	public static File getTempFileFromResource(String
> resource_path) {
> +    	InputStream in = null;
> +    	OutputStream out = null;
> +    	try {
> +			File f_out =
> File.createTempFile("turbine_temp_resource", ".tmp");
> +			f_out.deleteOnExit();
> +			in = new
> BufferedInputStream(getResourceAsStream(resource_path));
> +			out = new BufferedOutputStream(new
> FileOutputStream(f_out));
> +			int b;
> +			while((b=in.read())!=-1)
> +				out.write(b);
> +			return f_out;
> +		} catch (Exception ex) {
> +			return null;
> +		} finally {
> +			if(in!=null) {
> +				try {
> +					in.close();
> +					in = null;
> +				} catch(Exception ex) {
> +				}
> +			}
> +			if(out!=null) {
> +				try {
> +					out.flush();
> +					out.close();
> +					out = null;
> +				} catch(Exception ex) {
> +				}
> +			}
> +		}
> +    }
> +    /**
>       * Finds the specified servlet configuration/initialization
>       * parameter, looking first for a servlet-specific
> parameter, then
>       * for a global parameter, and using the provided default if not
> @@ -1120,13 +1191,19 @@
>       */
>      public static String getRealPath(String path)
>      {
> -        if (path.startsWith("/"))
> -        {
> -            path = path.substring(1);
> +        // try to retrieve the requested resource
> +        // using the getTempFileFromResource(String).
> +        File resource_file = getTempFileFromResource(path);
> +        if(resource_file==null || !resource_file.exists()) {
> +        	// oops! Resource is not available which means that
> +        	// either we are not currently running within a servlet
> +        	// container enviroment or we were unable to retrieve
> +        	// the resource via getResourceAsStream() for
> some reason.
> +        	// Fallback to Turbine's default behaviour;
> +			resource_file = new
> File(getApplicationRoot(), path.startsWith("/") ?
> path.substring(1) : path);
>          }
> -
> -        return new File(getApplicationRoot(),
> path).getAbsolutePath();
> -    }
> +        return resource_file.getAbsolutePath();
> +	}
>
>      /**
>       * Return an instance of the currently configured Service Manager
> --
> ####################################################################
> Filippos Slavik
> FORTHnet R&D, Heraklion, Greece
> e-mail : fsla@forthnet.gr
> phone : (+30) 2811 391230
> Key ID: 0xF4B5B375 Filippos Slavik(search pgp.mit.edu)
> Key FingerPrint: 81D4 25D0 01EB 9DCA 62E4  B694 20E7 31FB F4B5 B375
> ####################################################################
>
> "The software said 'runs on Win95 or better,' so I installed it
> on Linux..."
>
>
>
>
> ---------------------------------------------------------------------
> To unsubscribe, e-mail: turbine-dev-unsubscribe@jakarta.apache.org
> For additional commands, e-mail: turbine-dev-help@jakarta.apache.org


---------------------------------------------------------------------
To unsubscribe, e-mail: turbine-dev-unsubscribe@jakarta.apache.org
For additional commands, e-mail: turbine-dev-help@jakarta.apache.org