[Scons-dev] File-based build tools will never handle Java
Mark A. Flacy
mflacy at verizon.net
Thu Sep 6 15:09:04 EDT 2012
On Thursday 06 September 2012 13:47:02 Greg Ward wrote:
> On 06 September 2012, Gary Oberbrunner said:
> > I don't think this is really a problem, or doesn't have to be. In
> > SCons there are no dependencies *between* source files; only from
> > object (.class files) to source (the object depends on the source(s)).
> >
> > And the jar depends on the class files. So I don't see how call
> >
> > graph complexities lead to build dependency cycles. If any of the
> > source files change, certain objects and jars depend on those and have
> > to be rebuilt. The real problem (at least as I understand it, I'm not
> > a Java guy) is the fact that each .java produces unpredictable
> > outputs. Am I correct about this, or are there actually real
> > unavoidable build dependency cycles?
>
> As Mark Flacy said, you are unfortunately incorrect here. Let me give
> a concrete example (taken from the little hg repository I mentioned
> earlier today: http://hg.gerg.ca/sample-java, in cycle/).
>
> Container.java:
> """
> package cycle;
>
> class Container {
> void add(Item item) {
> }
> }
> """
>
> Item.java:
> """
> package cycle;
>
> class Item {
> Container parent;
> }
> """
>
> You cannot compile these two files independently. Either javac will
> discover the other source file and compile it implicitly, or you must
> list both files on the javac command line. (IMHO the latter is by far
> preferable. javac's implicit compilation might have seemed like a good
> idea at the time, but I'm convinced that it's a bad thing to rely on.)
>
> What's really funny is that the DAG depends on how you run javac. No,
> seriously. I *believe* that javac's default results in this DAG:
>
> Container.class <---------------> Item.class
>
> v v
> Container.java Item.java
>
> * Container.class depends on Container.java
> * Container.class depends on Item.class
> * Item.class depends on Item.java
> * Item.class depends on Container.class
>
> However, if you run "javac -Xprefer:source", I *think* it looks like
> this:
>
> Container.class-------+ +-----Item.class
>
> v +----|-----+ v
> Container.java <-+ +---------> Item.java
>
> I have no idea why anyone would want to compile Java this way. I only
> learned about that option earlier today, browsing the archives of the
> tup-users mailing list. (Yes, tup also has problems with Java. I
> gather from the list that other languages/compilers play similar
> tricks, e.g. Vala and Erlang.)
>
> Greg
If you run "javac -X" on the command line, you'll see (among other things)...
-Xprefer:{source,newer} Specify which file to read when both a source file
and class file are found for an implicitly compiled class
...and I assume that some version control systems may set the source to be
older than the compiled version if you updated a checkout or decided to go
back to an earlier version in the same workspace.
More information about the Scons-dev
mailing list