Derik Whittaker

Syndication

News


Depends vs Call, Do you know and understand the difference in NAnt?

This past week I was taking a look at one of our build scripts as it appeared to be taking a bit longer than everyone wanted.  Because I am very close to the file (authored about 50% of it) I decided that in place of just diving in and looking at the raw source I would instead run the script with the given options I needed and record the output (nant.exe -buildfile:Demo.xml SomeTargetName > Log.txt) and once the run was complete I would take a look at the output and look for ‘out of normal items’.  Within a few minutes of scanning the file I noticed something ODD, we were compiling all of our code twice (just to be double sure it compiled correctly of course).

Now that I knew the issue, double compiling 5 solutions for each build, it was time to determine why we were doing this.  As I started to follow the call chain I noticed something that was a bit interesting to me.  It appeared that were we calling a target via a <Call> command vs a Depends command the entire call stack would be re-executed.  A quick google search lead me to this page (here) which had the answer to my problem.  Per the Nant documentation:

A target gets executed only once, even when more than one target depends on it (see the previous example). However, when the <call> task is used to execute a target, both the target and all its dependent targets will be re-executed.

Hum.. problem found, root caused determined.  Now it was simply a matter of resolving the issue. SWEET

To better illustrate this scenario I have created a simple example (with screenshots to boot).

Imagine you have the following Nant script (sorry, could not get the XML to not be ‘xml’ and rather be code/text)

image

If you take a look at the script above you will see 2 things.

  1. I have a few targets that use Depends to call other targets
  2. I have one target (Target_Z) which simply does a call out to the other targets it needs

 

In order to understand how ‘Depends’ works and the fact that it will NOT double call a target lets take a look at the call stack if we invoke Target_A directly.

image

As you can see from the image, each target is only invoked once even though that Target_C is referenced by both Target_A and Target_B

 

Now, to understand how ‘<Call>’ works and the fact that it will double call targets let take a look at the call stack if were to invoke Target_Z directly.

image

As you can see from the image above, Since Z calls both A & B we get the repeating of each of their targets, so Target_B and Target_C are each called multiple times and this could be really bad on performance.

Now that you understand the difference between <Call> and ‘Depends’ use this information wisely and with caution. 

Oh, by not double calling our compile for all 5 solutions we shaved about 4-5 minutes off of our CI build… NOT TOO BAD

Till next time,


Posted 11-20-2009 5:32 AM by Derik Whittaker

[Advertisement]

Comments

Andriy Buday wrote re: Depends vs Call, Do you know and understand the difference in NAnt?
on 11-20-2009 8:58 AM

Great article.

So in order to have all executed once I just need make Target_Z depend on Target_A and Target_B and do not call them... great...

Rob Reynolds wrote re: Depends vs Call, Do you know and understand the difference in NAnt?
on 11-22-2009 4:06 PM

Great article!

Did Dru ever talk you into trying UppercuT?

Derik Whittaker wrote re: Depends vs Call, Do you know and understand the difference in NAnt?
on 11-22-2009 4:50 PM

@Rob,

yes, i am planing on it.  However for work we are way too in bed with Nant

About The CodeBetter.Com Blog Network
CodeBetter.Com FAQ

Our Mission

Advertisers should contact Brendan

Subscribe
Google Reader or Homepage

del.icio.us CodeBetter.com Latest Items
Add to My Yahoo!
Subscribe with Bloglines
Subscribe in NewsGator Online
Subscribe with myFeedster
Add to My AOL
Furl CodeBetter.com Latest Items
Subscribe in Rojo

Member Projects
DimeCasts.Net - Derik Whittaker

Friends of Devlicio.us
Red-Gate Tools For SQL and .NET

NDepend

SlickEdit
 
SmartInspect .NET Logging
NGEDIT: ViEmu and Codekana
LiteAccounting.Com
DevExpress
Fixx
NHibernate Profiler
Unfuddle
Balsamiq Mockups
Scrumy
JetBrains - ReSharper
Umbraco
NServiceBus
RavenDb
Web Sequence Diagrams
Ducksboard<-- NEW Friend!

 



Site Copyright © 2007 CodeBetter.Com
Content Copyright Individual Bloggers

 

Community Server (Commercial Edition)