The problem with resources

R

Roedy Green

I was considering converting a giant switch statement in my code to a
resource array lookup. Then I realised if anyone used my code, they
would have to MANUALLY ensure the resource were included in the jar.
They would fail to do so, and curse my code for not working.

What we need is something like a resource, but more tightly linked so
that it would be automatically be included in a jar, the way ANT
genjar automatically pulls in dependent class files.

Another way of looking at it, is we need a more efficient class file
format where you can include compressed data inside the class file for
initialisation.

There is a commercial product called Cramfull that does this, but you
can't very well use it in Open Source software. see
http://mindprod.com/jgloss/cramfull.html

We need something open source. You would use it like this:


HashMap<String,String h = (HashMap<String,String)
HolderClass.readResourceObject();

It would behave like readObject.

To prepare a resource you would do a writeObject to a *.ser file.

The prepare program would read it, gzip it, and somehow encode as a
giant string in a class file or some other more efficient format.

There are some tools for creating class files on the byte level. see
http://mindprod.com/jgloss/bcel.html

Any takers?


--
Roedy Green Canadian Mind Products
http://mindprod.com
Refactor early. If you procrastinate, you will have
even more code to adjust based on the faulty design.
..
 
R

Roedy Green

You mean like... genjar?




Done!

<http://download.oracle.com/javase/tutorial/deployment/webstart/index.html>


Seriously Roedy, you re-invent the wheel WAY too much. Try to work with
existing solutions please.

GenJar does NOT automatically include resources. That is the problem.
It can only automatically include classes. What I was calling for was
a way to masquerade resources as classes so that GenJar would
automatically include them.

Resources are only loosely tied to a program, the way dynamically
loaded classes are, by a name revealed only at run time. Classes on
the other hand have a link that can be resolved at compile time.
GenJar is aware of this link and thus can automatically include
dependencies.

Java web start has nothing to with building jars. I don't see how it
is relevant to the problem of ensuring necessary resources are
automatically included in jars.

I think when you skimmed my post you presumed I was calling for
something quite different than I was. Basically I am calling for a
simplified open source Cramfull clone.


--
Roedy Green Canadian Mind Products
http://mindprod.com
Refactor early. If you procrastinate, you will have
even more code to adjust based on the faulty design.
..
 
M

markspace

GenJar does NOT automatically include resources. That is the problem.
I think when you skimmed my post you presumed I was calling for
something quite different than I was.


I find it hard to believe there's no way to include resources in a Jar
task. I'll look at the docs later (it's Saturday), but my guess is the
task just needs to be configured correctly.
 
R

Roedy Green

I find it hard to believe there's no way to include resources in a Jar
task. I'll look at the docs later (it's Saturday), but my guess is the
task just needs to be configured correctly.

Manually including them is easy. The problem is remembering to add the
lines to your ant script, or people using library code you write
remembering to add them.

To include the resources from some dependent package you need
something like this is your ant script:

<resource>
<!-- include all the *.ser index files -->
<fileset dir="${basedir}">
<include name="com/mindprod/qf/*.ser" />
</fileset>
</resource>

I don't need anything similar to include dependent CLASSES from the qf
package.

The other thing that is neat about genjar class inclusion, is it won't
include EVERYTHING, just the classes in a package you actually use
(or more precisely reference). It would be nice if Genjar could be
were similarly clever about resources.

For that, we need a way to tighten the compile time link to the
necessary resources.

Image if Java ONLY had explicit dynamic class loading. Resources
should have both kinds of loading too.
--
Roedy Green Canadian Mind Products
http://mindprod.com
Refactor early. If you procrastinate, you will have
even more code to adjust based on the faulty design.
..
 
L

Lew

Roedy said:
GenJar does NOT automatically include resources. That is the problem.
It can only automatically include classes. What I was calling for was
a way to masquerade resources as classes so that GenJar would
automatically include them.

I have no trouble including resources in the JARs I make. I simply put the
resources directory in the source path. For example, with either Eclipse or
NetBeans, I can put a "resources/" under "web/WEB-INF/" or "src/" and it will
wind up in the constructed application WAR/JAR.
Resources are only loosely tied to a program, the way dynamically
loaded classes are, by a name revealed only at run time. Classes on
the other hand have a link that can be resolved at compile time.
GenJar is aware of this link and thus can automatically include
dependencies.

I think I haven't yet grokked your use case.
 
A

Arne Vajhøj

Manually including them is easy. The problem is remembering to add the
lines to your ant script, or people using library code you write
remembering to add them.

To include the resources from some dependent package you need
something like this is your ant script:

<resource>
<!-- include all the *.ser index files -->
<fileset dir="${basedir}">
<include name="com/mindprod/qf/*.ser" />
</fileset>
</resource>

I don't need anything similar to include dependent CLASSES from the qf
package.

The other thing that is neat about genjar class inclusion, is it won't
include EVERYTHING, just the classes in a package you actually use
(or more precisely reference). It would be nice if Genjar could be
were similarly clever about resources.

What is the point?

You want to create a tool for people that:
1) change source in projects
2) forget to update the build file appropriately
3) does not test if the code is still working
?

That seems like a rather futile exercise to me.

They will get into so many other problems.

Arne
 
M

markspace

You want to create a tool for people that:
1) change source in projects
2) forget to update the build file appropriately


I took a look at the <jar> task for any. There doesn't seem to be a way
to do EXACTLY what Roedy wants, but there's a pretty easy work-around.
Just use two <jar> tasks, the second of which is an update.

So if your .class files go to build/classes/, and your source file
directory is named src/, you can just use this pair of <jar> tasks:

<jar destfile="dist/Some.jar" basedir="./build/classes" />
<jar destfile="dist/Some.jar" basedir="./src"
excludes="**/*.java **/package.html"
update="true" />

The second task is an update. It excludes all *.java (source) files as
well as the older style package.html Javadoc tool file. It includes
everything else, which is the way most IDEs work and is very convenient.
Don't have to remember to add anything to your build file, it just
grabs everything that you've added to your source tree.

Caveat: lightly tested.
 
M

Mike Schilling

markspace said:
I took a look at the <jar> task for any. There doesn't seem to be a way
to do EXACTLY what Roedy wants, but there's a pretty easy work-around.
Just use two <jar> tasks, the second of which is an update.

So if your .class files go to build/classes/, and your source file
directory is named src/, you can just use this pair of <jar> tasks:

<jar destfile="dist/Some.jar" basedir="./build/classes" />
<jar destfile="dist/Some.jar" basedir="./src"
excludes="**/*.java **/package.html"
update="true" />

The second task is an update. It excludes all *.java (source) files as
well as the older style package.html Javadoc tool file. It includes
everything else, which is the way most IDEs work and is very convenient.
Don't have to remember to add anything to your build file, it just grabs
everything that you've added to your source tree.

Caveat: lightly tested.

The solution I've used for years is to copy the resources to the classes
directory before calling <jar>. This doesn't cause any unnecessary work
because ant's <copy> task won't bother copying files that are identical in
the source and destination directories.
 
D

Daniele Futtorovic

The solution I've used for years is to copy the resources to the classes
directory before calling <jar>. This doesn't cause any unnecessary work
because ant's <copy> task won't bother copying files that are identical
in the source and destination directories.

This has the advantage of working in "exploded" mode, too.
 
M

markspace

This has the advantage of working in "exploded" mode, too.


I thought about this, but it seemed that one copy of the resources was
better than two. However if your app needs to run from the raw .class
files directly, sure.
 
D

Daniele Futtorovic

I thought about this, but it seemed that one copy of the resources was
better than two.

What, you mean not including the resources in the build hierarchy? On
the contrary, it would seem better to me that the packaging packaged
only the final product, without additional trickery. This makes problems
easier to track. I vaguely thought this was /lege artis/.
 
M

markspace

I vaguely thought this was /lege artis/.


I don't know that it's not. However, it seems to me that there no
difference between "trickery" building the Jar file vs. "trickery" in
copying various files into one build hierarchy.

Both are equally documented in the build.xml file. I can't think of a
reason, personally, to strongly prefer one to the other. It seems a
matter of preference, and perhaps saving a few bytes of disc space.

Class files need to be built, but if a file is used whole and
untransformed, why copy it twice?
 
A

Arne Vajhøj

The solution I've used for years is to copy the resources to the classes
directory before calling <jar>. This doesn't cause any unnecessary work
because ant's <copy> task won't bother copying files that are identical
in the source and destination directories.

What does that do that multiple filesets in the jar element
does not?

Arne
 
M

Mike Schilling

Arne Vajhøj said:
What does that do that multiple filesets in the jar element
does not?

As mentioned upthread, it allows running tests before building the jar
(without needing to specify the resources directory in the classpath).
 
A

Arne Vajhøj

As mentioned upthread, it allows running tests before building the jar
(without needing to specify the resources directory in the classpath).

How does the content of the jar file differ with the two jar elements
one with update and one jar element with two filesets??

Arne
 
M

Mike Schilling

Arne Vajhøj said:
How does the content of the jar file differ with the two jar elements
one with update and one jar element with two filesets??

It doesn't.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,968
Messages
2,570,153
Members
46,699
Latest member
AnneRosen

Latest Threads

Top