On 22/02/2013, at 3:32 AM, Adam Murdoch <[email protected]> wrote:
>
> On 22/02/2013, at 2:10 PM, Adam Murdoch wrote:
>
>> Hi,
>>
>> So we're starting to build out a graph of build items, with our source sets
>> and jvm binaries (and publications). At the moment, this is pretty basic,
>> where you can define some source sets and define some jvm binaries and
>> attach the source sets as inputs to the binaries. Or you can attach a
>> component as input to a publication.
>>
>> There are a few different types of build items that we need to model:
>>
>> 1. Something that already exists and does not need building. These things
>> are only consumed in the current project. You need to be able to define it
>> and configure some stuff about how to use it. For example: here is a java
>> source set and it includes java source from this directory and that
>> directory.
>>
>> 2. Something that is produced outside the project. Again, these things are
>> only consumed in the current project. You need to be able to define a
>> dependency on the thing and resolve it into something usable. For example:
>> give me a jvm binary for 'org:gradle:gradle-core:1.5+' so that I can use it
>> in my compile classpath, or give me the source set for project(':other') so
>> I can generate some aggregate javadoc from it.
>>
>> 3. Something that is produced by the project. You need to be able to define
>> it and configure some stuff about how to build it. For example, please
>> produce a jvm binary into this classes directory, built from these input
>> source sets and targeting this jvm version.
>>
>> 4. Something that is produced and consumed within the project. As above,
>> where the configuration that describes how to build it also implies how to
>> use it.
>>
>> 5. Something that is a view over some other things. For example, a composite
>> or a filtered source set. These things are only consumed.
>>
>
> Another question is how to represent the work that need to be done to make
> the build item usable. Each thing is usable in a bunch of different ways, and
> each of these require different work to be done. Some of these ways of using
> an item are cross-cutting, and some are type specific. Here are some examples:
>
> * In order to refer a thing, to pass it around, I don't need to do anything
> more than define it (ie here is a java source set called 'mainJava').
>
> * In order to use a java source set's compile classpath as a set of
> dependency definitions, I need to make sure the source set has been
> configured. This might mean configuring the current project, which might mean
> running some tasks to build some other project that is used to configure the
> project, which might mean configuring that other project, and so on.
>
> * In order to use a java source set's compile classpath as a set of files
> that will be built (for example, say I'm generating a classpath manifest
> file), I need to make sure the source set has been configured (as above) and
> I need to resolve any dependency definitions referenced in the classpath,
> which might mean configuring each project referenced by a project dependency
> or resolving the meta-data for a thing from a repository. I don't need to
> build or download the files themselves.
>
> * In order to zip up a java source set's source, I need to make sure the
> source set has been configured (as above), and I need to make sure the source
> has been generated (if required). I don't need to do anything with the
> classpath.
>
> * In order to compile a jave source set, I need to make source the source set
> has been configured, the source has been generated, the compile classpath has
> been resolved to files, and the classpath files built or downloaded.
>
> In other words, Buildable isn't going to cut it. I don't think we necessarily
> need to go quite as fine grained as the above, but we need something better
> than 'configure and build and resolve and download all the things that might
> be required to use this thing in any way'.
>
> Suggestions?
It's becoming obvious that we need to formalise the idea of “configured”. Or at
least, formalise the notion of there being a configuration lifecycle. Perhaps
though this is not really a separate concept. That is, building (aka
configuring) the model is not inherently different to building files for
example.
One idea is just to go fine grained with the types and modelling. So strongly
model the specification of source as a buildable thing and separately model the
actual physical files, having both of these things express some kind of opaque
dependency like Buildable. So if you just need to know when it's configured,
you'd use the specification's buildable. It may be hard to find the concepts to
break apart here sometimes though. So something like…
class JavaSourceSet {
SourceDirectorySetSpec getSrcDirs()
ClasspathSpec getCompileClasspath()
}
class SourceDirectorySetSpec implements Buildable {
SourceDirectorySet getBuilt()
}
The general idea being instead of introducing a protocol that allows us to
depend on something in a certain state, we introduce more fine grained
modelling.
I need to think on this some more.
--
Luke Daley
Principal Engineer, Gradleware
http://gradleware.com
---------------------------------------------------------------------
To unsubscribe from this list, please visit:
http://xircles.codehaus.org/manage_email