Top posting as I just wanted to say:  Can people do more editing of the
quoted parts of emails.  There are 4 pages of previous material here
before getting to anything new and almost all of the quoted material has
been seen before about seven times.

Thanks.

On Wed, 2008-08-27 at 08:44 +0200, Hans Dockter wrote:
> On Aug 26, 2008, at 12:47 PM, Adam Murdoch wrote:
> 
> >
> >
> > Adam Murdoch wrote:
> >>
> >>
> >> Hans Dockter wrote:
> >>>
> >>> On Aug 7, 2008, at 1:22 PM, Adam Murdoch wrote:
> >>>
> >>>>
> >>>>
> >>>> Hans Dockter wrote:
> >>>>>
> >>>>> On Aug 6, 2008, at 12:12 PM, Adam Murdoch wrote:
> >>>>>
> >>>>>>
> >>>>>>
> >>>>>> Hans Dockter wrote:
> >>>>>>>
> >>>>>>> What about doing things differently?
> >>>>>>>
> >>>>>>> We could introduce a Configuration class which implements  
> >>>>>>> Task. One can add dependencies to a configuration. Executing  
> >>>>>>> such a task means resolving its dependencies. Such a task  
> >>>>>>> would offer also methods to get a path, list of files,  
> >>>>>>> etc ... The compile task for example would depends on its  
> >>>>>>> configuration task(s). A project dependency would establish a  
> >>>>>>> depends relation between the configuration it belongs to and  
> >>>>>>> the configuration of the other project. The artifact  
> >>>>>>> producing configuration of the other project would depend on  
> >>>>>>> the corresponding artifact task(s).
> >>>>>>>
> >>>>>>> This would remove unnecessary elements from our API. It  
> >>>>>>> decreases the learning curve and simplifies the design. Last  
> >>>>>>> but not least we have finally our Configuration object to  
> >>>>>>> express this important domain concept.
> >>>>>>
> >>>>>> I think this is an excellent idea. We already do something  
> >>>>>> similar (conceptually) for bundles: A task is added to the  
> >>>>>> project for each bundle produced by the project, and I can ask  
> >>>>>> that a bundle be built from the command-line, add dependencies  
> >>>>>> on it, query it for its location, etc. We could probably come  
> >>>>>> up with a common approach for configurations and bundles.
> >>>>>
> >>>>> A bundle is a task and at the same time a container for archive  
> >>>>> tasks on which it depends. Your analogy is that a configuration  
> >>>>> is a container for dependencies, right?
> >>>> Sorry, I meant to say archives instead of bundles, ie we do  
> >>>> something similar for archives (make them available as tasks  
> >>>> which other tasks can depend on).  Hopefully that makes more sense.
> >>>>
> >>>>>>
> >>>>>>
> >>>>>> I'm not sure if Configuration should implement Task, or  
> >>>>>> whether adding a Configuration would trigger the adding of a  
> >>>>>> Task that resolves it.  The problem with implementing Task is  
> >>>>>> that there are (at least) 2 interpretations of 'executing' a  
> >>>>>> configuration: resolving it, and producing/publishing it. By  
> >>>>>> adding a task instead, we have the option of adding both a  
> >>>>>> resolve task and a publish task for a configuration. I guess  
> >>>>>> another option would be to have 2 types of Configuration: one  
> >>>>>> for incoming dependencies and one for produced artifacts.
> >>>>>>
> >>>>>
> >>>>> In Ivy itself all configurations are equals. They may contain  
> >>>>> only external dependencies or only artifacts produced by the  
> >>>>> project or both (e.g. a configuration that exposes the  
> >>>>> artifacts of a projects plus its external dependencies). I'm  
> >>>>> not sure if Ivy misses to model an important concept.
> >>>>>
> >>>>> Our configurations could take the same approach as Ivy. The  
> >>>>> fact that a configuration contains artifacts to be produced by  
> >>>>> the project can be expressed by the fact that this  
> >>>>> configuration depends on the respective archive task. A resolve  
> >>>>> could be simply defined by calling an Ivy resolve for the  
> >>>>> underlying Ivy ocnfiguration.
> >>>>>
> >>>> This makes sense. So, for example, if I have a project that  
> >>>> produces an artifact and includes it in a configuration, I add  
> >>>> an Archive (task) to produce the artifact, then add a  
> >>>> Configuration (task) with a dependency on the archive task.  
> >>>> Adding this dependency declares that the archive is a  
> >>>> publication included in the configuration.
> >>>>
> >>>> If I want to use the configuration in my project, I add another  
> >>>> task with a dependency on the configuration task.  Adding this  
> >>>> dependency declares that the task uses the configuration. Before  
> >>>> my task is executes, the archive is built, the configuration is  
> >>>> resolved, and my task can query the Configuration object for the  
> >>>> files that make up the configuration.
> >>>>
> >>>> If I want to include artifacts from another project, I can add a  
> >>>> dependency from the configuration task to a configuration task  
> >>>> in the other project.
> >>>
> >>> Right. With the current design we would use an intermediary for  
> >>> doing this. A project dependency would establish the dependency  
> >>> between the two configurations of the respective projects. The  
> >>> project dependency has the additional job to translate this  
> >>> dependency into ivy language.
> >>>
> >>>> I can add more artifacts to the configuration by adding more  
> >>>> dependencies on archive tasks (or any file producing task,  
> >>>> really). I can add external dependencies (log4j, say) by adding  
> >>>> them directly to the configuration task.
> >>>>
> >>>> Where do you think publishing would happen in all this?
> >>>
> >>> Publishing in the sense of adding an artifact to a repository  
> >>> happens in the uploadLibs and uploadDists tasks.
> >> I'm interested in how this happens generically, so assume I'm not  
> >> using the java plugin. In my example above, then, I would add an  
> >> upload task which depends on the configuration it uploads.  Adding  
> >> the dependency declares that the upload task publishes the config  
> >> to a repository. So, the dependency graph ends up like: upload ->  
> >> config -> archive. The upload task could potentially be  
> >> automatically added when the configuration is added to the project.
> >>
> >> If I want to use the config from another project in the same multi- 
> >> project build, I really want to depend on the config rather than  
> >> the upload task (ie I want to depend on the thing I use, rather  
> >> than the step that happens to produce it). So, then ideally I have  
> >> a dependency graph like a:task -> a:config -> b:config ->  
> >> b:archive.  Would we do an implicit publish when b:config is  
> >> executed, or would a:config reach in to project b and resolve the  
> >> archive from there?
> >>
> >>> I'm not sure if it was a good idea to introduce a new term  
> >>> 'upload' for this instead of using the term 'publish'.
> >>>
> >>> The remaining open issue is how to deal with cleaning. Building a  
> >>> dependency without cleaning is not that reliable.  This is a  
> >>> (modified) quote from one of my earlier emails:
> >>>> One more point we need to think about. If we do a partial build  
> >>>> of project A which has a project dependency on project B. Let's  
> >>>> say we execute 'gradle clean libs'. Project A is cleaned before  
> >>>> its libs are created, not so project B. Only the artifact  
> >>>> producing task is executed. We could declare an additional  
> >>>> dependsOn('projectB') in project A. Such a dependsOn establishes  
> >>>> task dependencies between tasks with similar names of both  
> >>>> projects. Now the clean is done for both projects but also the  
> >>>> libs task is executed for project B which would neutralize our  
> >>>> effort to become more fine-grained regarding project  
> >>>> dependencies artifacts.
> >> Not sure yet.  When you execute 'gradle clean libs', you're really  
> >> saying 'rebuild the libs and its dependencies', so I think a good  
> >> solution is going to allow me to 1. ask gradle to do this from the  
> >> command-line, and 2. declare in the build scripts how to do this.
> >>
> >
> > Thinking about it, there are a two things you might want gradle to  
> > do when you execute 'gradle clean libs':
> > - rebuild the libs and all their dependencies
> > - rebuild this lib only.
> >
> > It would be good to handle both these cases.
> 
> Definitely. Specially in large builds people want to be able to say:  
> I know the project dependencies haven't change. So please rebuild  
> this project only to save time.
> 
> Right now the jars of the project dependencies are copied to  
> the .gradle/build-resolver dir, which is always removed before and  
> after a build execution. To make the above work I guess we must not  
> remove this directory and think about whether this can lead to  
> problems with stale jar's.
> 
> >
> >> Given that cleaning and rebuilding are concepts that pretty much  
> >> every build has, it is tempting to bake this concept into the  
> >> build tool's domain model. Something like (I haven't thought this  
> >> through, its just an example), a project can declare which task  
> >> should be run before doing a rebuild of its artifacts (eg a Clean  
> >> task). Then, using the configuration dependencies, gradle can  
> >> decorate the dependency graph to add in the clean tasks if a  
> >> rebuild is being done.
> >>
> >
> > Some other options:
> >
> > - We add some way to specify a dependency like: "this task depends  
> > on the 'clean' task of each project which this project uses  
> > artifacts from". You can then attach such a dependency to your  
> > project's 'clean' task. Or 'rebuild' task.
> >
> > - We change the Clean task so that it automatically has such a  
> > dependency, so that you just use the Clean task in your project and  
> > it figures it all out. Alternatively we could add a Rebuild task  
> > which does this.
> >
> > - We add a command-line option (--rebuild, say) which executes the  
> > 'clean' task for all projects whose artifacts are going to be used  
> > during the build.
> 
> Yet another approach would be to add a property to the  
> dependencyManager, let's call it cleanTask. The default behavior of a  
> ProjectDependency would be to create a dependency from the  
> configuration (future implementation!) to the cleanTask of the  
> dependencyProject's dependency manager. This approach would confine  
> the notion of cleaning a dependency project to the domain model of  
> dependency management.
> 
> - Hans
> 
> --
> Hans Dockter
> Gradle Project lead
> http://www.gradle.org
> 
> 
> 
> 
> 
> ---------------------------------------------------------------------
> To unsubscribe from this list, please visit:
> 
>     http://xircles.codehaus.org/manage_email
> 
> 
-- 
Russel.
====================================================
Dr Russel Winder                 Partner

Concertant LLP                   t: +44 20 7585 2200, +44 20 7193 9203
41 Buckmaster Road,              f: +44 8700 516 084
London SW11 1EN, UK.             m: +44 7770 465 077

Attachment: signature.asc
Description: This is a digitally signed message part

Reply via email to