RE: io path information in servlets

2002-07-22 Thread Shapira, Yoav

Howdy,

OK, so my question - if I want to do this, where in the file system
should
I stick the xml file so it doesn't get overwritten if the war is
redeployed?  A user's home directory?  That will force the user to mess
with the configuration.

I'm a out of my league on this, so I'd appreciate any advice.  Of of
course, I could give up on file storage and go with jdbc, but that
seems
like overkill for this little app I am writing.

If you don't need the XML files to be persisted, you can read/write them
from the context's temporary directory (javax.servlet.context.tempdir
property).

If you do need them persisted, you have some options:

1) Pass in an init-param to one of your servlets a directory where these
files will be stored.  

2) Use JDBC and write the files to a database.  (This is not that bad a
solution, especially if your schema is easy and the files aren't huge).

3) Use JNDI and have a bean or service persist the files for you.

Good luck,

Yoav Shapira
Millennium ChemInformatics

--
To unsubscribe, e-mail:   mailto:[EMAIL PROTECTED]
For additional commands, e-mail: mailto:[EMAIL PROTECTED]




Re: io path information in servlets

2002-07-18 Thread Craig R. McClanahan



On Thu, 18 Jul 2002, Will Hartung wrote:


 This all came out of the fact that it seems essentially impossible to create
 a webapp according to the 2.3 spec that uses file based storage and have it
 be usable out of the box with zero basic configuration to start up. For
 example, I don't think that there is a (portable) way for a servlet to
 change its own parameters. Say the webapp comes with some reasonable
 default for File pathnames, but a user wishes to change them. They cannot
 do that using the servlet itself (through some HTML Form/GUI mechanism), in
 a portable way.


The approach I would use for this is to pass the default pathname as an
env-entry in the web.xml file, and access it via JNDI calls in the
servlet.  Containers that support JNDI resources for webapps (which means
Tomcat 4 plus every J2EE server in the world) provide mechanisms for the
administrator to change the value of environment entries, either in a
configuration file (like server.xml for Tomcat) or as part of the process
of deploying the application, with zero changes to the WAR itself.

The mechanism to do the configuration customizaton is not portable in
the sense of being identical on every server, but it is available.

 Even with a databased app, there's no way for a servlet to change its
 default JDBC URL and persist that change, it has to be done through the
 configuration files or in the webapp itself.


That's actually a good thing (changing it via configuration).

Consider an environment with three servers (development, test, and
production).  Naturally, each is connected to a different database.  The
last thing you want to do is have to change JDBC strings in your webapp
depending on which server you are deploying to.

Using a resource-ref to declare a reference to a connection pool that is
configured for you by the server administrator is much less tedious and
error prone -- and you don't have to do anything at all to your
application itself.

JNDI resources are your friend.

 That would be a nice bit to concentrate on in the future I think.

 Best Regards,

 Will Hartung
 ([EMAIL PROTECTED])


Craig


--
To unsubscribe, e-mail:   mailto:[EMAIL PROTECTED]
For additional commands, e-mail: mailto:[EMAIL PROTECTED]




Re: io path information in servlets

2002-07-18 Thread Will Hartung

From: Craig R. McClanahan [EMAIL PROTECTED]
Sent: Wednesday, July 17, 2002 11:19 PM
Subject: Re: io path information in servlets


 On Wed, 17 Jul 2002, Will Hartung wrote:

  It has CONVENTIONALLY been done this way, as it's a fairly obvious
  optimization to handle a web app (who wants to constantly grind through
a
  jar file for crying out loud). However, what is convention, and what is
  specification are two completely different things.

 Be sure you run some benchmarks before complaining too loudly about
 constantly grind through a jar file.  You will find, for example, that
 Tomcat will never do that more than once to load a class or JAR file, and
 for most static resources in the WAR it will also unpack them once and
 only once.

 In the very large majority of cases, whether a webapp is unpacked or not
 will have zero impact on performance for typical installations of Tomcat.

Yes, this was a premature statement, and I didn't actually expect a
container to literally continually access the files from the jar files.

  So, specifically, if you are relying upon the fact that getRealPath will
  give you a location that you can actually perform read/write file I/O
upon,
  then you are relying on a Container specific behavior that MAY not be
  portable to other containers.
 
  A simple contrived example is that if you were deploying your WAR to,
say,
  an Oracle Application Server, then Oracle can easily deploy the WAR
into
  DBMS Tables and not use a file system at all, and this behavior is
perfectly
  legal within the specification. (Mind you, I don't know what Oracle
does.
  Like I said, a contrived example).

 As a matter of fact, Oracle has web containers that do exactly this --
 funny thing, they run *faster* than the filesystem in many cases, because
 they take advantage of the DBMS's optimized I/O and caching capabilities
 :-).

Yeah, it makes you wonder about things like Oracle's Internet File System.

  Another example is that your WAR may be deployed into a container where
the
  webapp is exploded in an area where you may only have READ permission,
and
  not WRITE. Also legal.
 
  It's actually a bit of a nit of mine that by specification, there is no
  guaranteed, portable way for a Servlet to get access to some writeable
area
  for file I/O. It can be a parameter, say in the WAR, but the container
  itself is not guaranteed to have to deliver this kind of functionality
to a
  Servlet.
 

 Not true.

   File workdir = (File)
  getServletContext().getAttribute(javax.servlet.context.tempdir);

 You don't get any assurances about the persistence of any files you store
 here, but this returns a perfectly useful directory for temporary files
 that you might need to create during execution of your business logic.
 (See section 3.7.1).

Ah good! This is really necessary I think. I also like how they required
that it contain File objects, thus you're able to get Streams and Writers as
necessary. Pity about persistence, however.

This all came out of the fact that it seems essentially impossible to create
a webapp according to the 2.3 spec that uses file based storage and have it
be usable out of the box with zero basic configuration to start up. For
example, I don't think that there is a (portable) way for a servlet to
change its own parameters. Say the webapp comes with some reasonable
default for File pathnames, but a user wishes to change them. They cannot
do that using the servlet itself (through some HTML Form/GUI mechanism), in
a portable way.

Even with a databased app, there's no way for a servlet to change its
default JDBC URL and persist that change, it has to be done through the
configuration files or in the webapp itself.

That would be a nice bit to concentrate on in the future I think.

Best Regards,

Will Hartung
([EMAIL PROTECTED])




--
To unsubscribe, e-mail:   mailto:[EMAIL PROTECTED]
For additional commands, e-mail: mailto:[EMAIL PROTECTED]




io path information in servlets

2002-07-17 Thread Paul Phillips

I have a webapp that stores some data in an xml file. (I am using jdom to 
read and write the xml files.)

Right now I am using a construct like:

String prefix = sc.getRealPath(/) + /WEB-INF/dirName/;

to get the path.  I then concatonate that with the file name and it works 
fine.

However, in the javadocs for javax.servlet I read:

This method returns null if the servlet container cannot translate the 
virtual path to a real path for any reason (such as when the content is 
being made available from a .war archive).

I am not exactly sure what this means.  If I deploy this application as a 
.war, does the sc.getRealPath stop working?

Thanks
Paul Phillips


--
To unsubscribe, e-mail:   mailto:[EMAIL PROTECTED]
For additional commands, e-mail: mailto:[EMAIL PROTECTED]




Re: io path information in servlets

2002-07-17 Thread Will Hartung

From: Paul Phillips [EMAIL PROTECTED]
Sent: Wednesday, July 17, 2002 5:20 PM
Subject: io path information in servlets


 I have a webapp that stores some data in an xml file. (I am using jdom to
 read and write the xml files.)

 Right now I am using a construct like:

 String prefix = sc.getRealPath(/) + /WEB-INF/dirName/;

 to get the path.  I then concatonate that with the file name and it works
 fine.

 However, in the javadocs for javax.servlet I read:

 This method returns null if the servlet container cannot translate the
 virtual path to a real path for any reason (such as when the content is
 being made available from a .war archive).

 I am not exactly sure what this means.  If I deploy this application as a
 .war, does the sc.getRealPath stop working?

What it is refering to is the fact that there is nothing in the
specification that says when a WAR is deployed into a server, that the WAR
is actually exploded into something resembling a filesystem, much less
something that you may actually have write access too (or, heck, even READ
access for that matter).

It has CONVENTIONALLY been done this way, as it's a fairly obvious
optimization to handle a web app (who wants to constantly grind through a
jar file for crying out loud). However, what is convention, and what is
specification are two completely different things.

So, specifically, if you are relying upon the fact that getRealPath will
give you a location that you can actually perform read/write file I/O upon,
then you are relying on a Container specific behavior that MAY not be
portable to other containers.

A simple contrived example is that if you were deploying your WAR to, say,
an Oracle Application Server, then Oracle can easily deploy the WAR into
DBMS Tables and not use a file system at all, and this behavior is perfectly
legal within the specification. (Mind you, I don't know what Oracle does.
Like I said, a contrived example).

Another example is that your WAR may be deployed into a container where the
webapp is exploded in an area where you may only have READ permission, and
not WRITE. Also legal.

It's actually a bit of a nit of mine that by specification, there is no
guaranteed, portable way for a Servlet to get access to some writeable area
for file I/O. It can be a parameter, say in the WAR, but the container
itself is not guaranteed to have to deliver this kind of functionality to a
Servlet.

I think that for PORTABILITY, you should make the path that you save your
XML file to be a ENV-ENTRY in the WAR, that, at least in TC 4, can be
overridden by the Context that deploys the WAR. This gives the person
deploying your application the control over where your webapp can write to
its disk.

For those containers that do not have the ability to override the ENV-ENTRY
in the Context, they're stuck unpacking the WAR and fixing it there (so much
for validating the integrity of your WAR buy signing it, though to be honest
I don't know if the specification mentions anything about signed WARs).
Which is another nit. Something like the ENV-ENTRY override needs to be
standardized.

Also, if you're writing stuff to the exploded webapp directory, then
remember that it can go away if the container, for whatever reason,
decided to redeploy your WAR.

Basically, what you're doing with TC is probably fine, even semi-long term,
but it's not portable behavior as documented in the specification.

These limitations are not there specifically to screw up your code, they're
in the spec to let the container developers have a lot more flexibility in
how they build their containers.

Best Regards,

Will Hartung
([EMAIL PROTECTED])




--
To unsubscribe, e-mail:   mailto:[EMAIL PROTECTED]
For additional commands, e-mail: mailto:[EMAIL PROTECTED]




Re: io path information in servlets

2002-07-17 Thread Jacob Kjome

With Tomcat, normally when you deploy a .war file, it gets expanded and the 
context is run out of the directory created upon expansion, not the .war 
file itself.  For intance if you put a myapp.war file in 
TOMCAT_HOME/webapps (and haven't defined the context in server.xml because, 
if defined, it doesn't expand for some reason...known bug...) Tomcat 
automatically extracts the contents of the .war file to a directory called 
myapp.  Then the context is run from that directory.

However, you can specify your appbase as the myapp.war file itself.  Tomcat 
can serve your entire application out of the archive.  Given this, 
myapp/WEB-INF is not on the file system.  It exists ony iside the archive 
where no file IO is possible.  So, a call to getRealPath/) will return 
null because there is no real system file path to be found.

You can avoid this issue by always making sure to use your .war archive to 
distribute the app and make sure that the system is set up to expand the 
archive so the app is run out of a directory on the file system.

Hope that helps.

Jake

At 07:20 PM 7/17/2002 -0500, you wrote:
I have a webapp that stores some data in an xml file. (I am using jdom to 
read and write the xml files.)

Right now I am using a construct like:

String prefix = sc.getRealPath(/) + /WEB-INF/dirName/;

to get the path.  I then concatonate that with the file name and it works 
fine.

However, in the javadocs for javax.servlet I read:

This method returns null if the servlet container cannot translate the 
virtual path to a real path for any reason (such as when the content is 
being made available from a .war archive).

I am not exactly sure what this means.  If I deploy this application as a 
.war, does the sc.getRealPath stop working?

Thanks
Paul Phillips


--
To unsubscribe, e-mail:   mailto:[EMAIL PROTECTED]
For additional commands, e-mail: mailto:[EMAIL PROTECTED]



Re: io path information in servlets

2002-07-17 Thread Craig R. McClanahan



On Wed, 17 Jul 2002, Paul Phillips wrote:

 Date: Wed, 17 Jul 2002 19:20:00 -0500
 From: Paul Phillips [EMAIL PROTECTED]
 Reply-To: Tomcat Users List [EMAIL PROTECTED]
 To: Tomcat Users List [EMAIL PROTECTED]
 Subject: io path information in servlets

 I have a webapp that stores some data in an xml file. (I am using jdom to
 read and write the xml files.)

 Right now I am using a construct like:

 String prefix = sc.getRealPath(/) + /WEB-INF/dirName/;

 to get the path.  I then concatonate that with the file name and it works
 fine.

 However, in the javadocs for javax.servlet I read:

 This method returns null if the servlet container cannot translate the
 virtual path to a real path for any reason (such as when the content is
 being made available from a .war archive).

 I am not exactly sure what this means.  If I deploy this application as a
 .war, does the sc.getRealPath stop working?


Yes; assuming that Tomcat doesn't unpack the WAR into a directory, this
definitely stops working.  In that case, getRealPath() will return null
because there is no such thing as a real path to this resource path.

Note that the ability to run an application from an unpacked directory at
all is *not* a feature that the servlet spec requires -- the only
requirement is to accept a WAR.

If you want to do this kind of thing in a manner guaranteed to be
portable, you should make your servlet accept an initialization parameter
of some sort that identifies the directory in which output files should be
stored.

 Thanks
 Paul Phillips


Craig


--
To unsubscribe, e-mail:   mailto:[EMAIL PROTECTED]
For additional commands, e-mail: mailto:[EMAIL PROTECTED]




Re: io path information in servlets

2002-07-17 Thread Craig R. McClanahan



On Wed, 17 Jul 2002, Will Hartung wrote:

 It has CONVENTIONALLY been done this way, as it's a fairly obvious
 optimization to handle a web app (who wants to constantly grind through a
 jar file for crying out loud). However, what is convention, and what is
 specification are two completely different things.


Be sure you run some benchmarks before complaining too loudly about
constantly grind through a jar file.  You will find, for example, that
Tomcat will never do that more than once to load a class or JAR file, and
for most static resources in the WAR it will also unpack them once and
only once.

In the very large majority of cases, whether a webapp is unpacked or not
will have zero impact on performance for typical installations of Tomcat.

 So, specifically, if you are relying upon the fact that getRealPath will
 give you a location that you can actually perform read/write file I/O upon,
 then you are relying on a Container specific behavior that MAY not be
 portable to other containers.

 A simple contrived example is that if you were deploying your WAR to, say,
 an Oracle Application Server, then Oracle can easily deploy the WAR into
 DBMS Tables and not use a file system at all, and this behavior is perfectly
 legal within the specification. (Mind you, I don't know what Oracle does.
 Like I said, a contrived example).


As a matter of fact, Oracle has web containers that do exactly this --
funny thing, they run *faster* than the filesystem in many cases, because
they take advantage of the DBMS's optimized I/O and caching capabilities
:-).

 Another example is that your WAR may be deployed into a container where the
 webapp is exploded in an area where you may only have READ permission, and
 not WRITE. Also legal.

 It's actually a bit of a nit of mine that by specification, there is no
 guaranteed, portable way for a Servlet to get access to some writeable area
 for file I/O. It can be a parameter, say in the WAR, but the container
 itself is not guaranteed to have to deliver this kind of functionality to a
 Servlet.


Not true.

  File workdir = (File)
 getServletContext().getAttribute(javax.servlet.context.tempdir);

You don't get any assurances about the persistence of any files you store
here, but this returns a perfectly useful directory for temporary files
that you might need to create during execution of your business logic.
(See section 3.7.1).

 I think that for PORTABILITY, you should make the path that you save your
 XML file to be a ENV-ENTRY in the WAR, that, at least in TC 4, can be
 overridden by the Context that deploys the WAR. This gives the person
 deploying your application the control over where your webapp can write to
 its disk.


That's one reasonable way to do it.  All J2EE containers, by the way, need
to provide mechanisms for defining the values corresponding env-entry
resources.

 For those containers that do not have the ability to override the ENV-ENTRY
 in the Context, they're stuck unpacking the WAR and fixing it there (so much
 for validating the integrity of your WAR buy signing it, though to be honest
 I don't know if the specification mentions anything about signed WARs).
 Which is another nit. Something like the ENV-ENTRY override needs to be
 standardized.


It is ... across every J2EE container.

 Also, if you're writing stuff to the exploded webapp directory, then
 remember that it can go away if the container, for whatever reason,
 decided to redeploy your WAR.

 Basically, what you're doing with TC is probably fine, even semi-long term,
 but it's not portable behavior as documented in the specification.


Well, there's always databases ... last I heard they are pretty good at
long term storage :-).

 These limitations are not there specifically to screw up your code, they're
 in the spec to let the container developers have a lot more flexibility in
 how they build their containers.

 Best Regards,

 Will Hartung
 ([EMAIL PROTECTED])


Craig McClanahan



--
To unsubscribe, e-mail:   mailto:[EMAIL PROTECTED]
For additional commands, e-mail: mailto:[EMAIL PROTECTED]