Thursday, 23 March 2006
First the good news, there is a cool new method on the string class, instead of having to do the following...

if(astring != null)
   if(astring.Length > 0)
      bstring = astring;

There is the new String.IsNullOrEmpty function that allows you do this...

     bstring = astring;

OK, it doesn't save a lot of code, but it's a 33% savings and it makes for more readable code.  Also it is faster than using the string == ""

if(astring != null)
   if(astring == "")
      bstring = astring;

and it won't throw a null execption that would occur on the following if you don't check for a null first.

   if(astring.length == 0)
      bstring = astring;

Now, for some disturbing news about app recycling when your web app deletes files or directories.  Mike Belcher found this the hard way, his sessions were dying and he didn't know why.  He was deleting some files, which worked fine in 1.1, but if you delete too many in 2.0, hello recycling, good-bye sessions.  Here's some more info.

This is some major foo.  If you are running some intensive logging or doing lots of file uploading, you can blow up your app info, sessions and cache without having a clue why.  The suggested workaround (using junction points) is a little tedious and  is also not viable for shared hosting systems.

A better workaround is buried in one of the comments of Scott's blog...

The App_Data folder of the web app is NOT monitored by the File Change Notification, so if any part of your web app needs to do lots of file or directory manipulation, do it there to prevent sudden AppDomain recycling.

I'm surprised that this new "feature" didn't bite more people on the ass during the beta period.

 In a perfect world, a patch to turn off this behavior will be available soon.

Thursday, 23 March 2006 22:55:17 (Eastern Standard Time, UTC-05:00)   #     Comments [0]  | 
Wednesday, 15 March 2006

Among the many improvements of .NET 2.0 is a subtle but welcome one in GridView, the replacement to the DataGrid control.

The Items have finally left the building.  Any old kinda grid control should have columns and rows.

The DataGrid had Columns and Items?

What in the world is an Item?  It's a row, but it's not called that -- for a very good reason I am sure.

The GridView has Columns and Rows!


Instead of ItemCreated, or ItemDataBound event handlers, there are RowCreated and RowDataBound.  Instead of ItemType there is RowType.

I cannot tell you how confusing this was for developers when first working with the DataGrid.  "How can I access a row?" must have been screamed at monitors from Mountain View to Mumbay.

What things are named can greatly affect how easy/hard it is use someone else's interface or maintain code.  How many times have you written code for something, only to find the same functionality in an obscurely/badly named function or class?

Consistent, meaningful naming makes it much easier for someone else, or the future you (go read some code you haven't touched in a year) to get what you are trying to do.

I must confess that I have not always been the best practioner.  My original programming platform was the Apple II, and variable names were limited to 8 characters (only the first three of which were meaningful -- found that out the HARD way), and I've never fully overcome the combined effects of that and my Modified Hunt & Peck Typing skills. 

This is something I have worked to be better at, but this post from Ryan Olshan really made it hit home.  I will paraphrase his thesis as "Variable names should be like characters in novel, they should be easily identifiable and make the reader care what happens to them". 

Especially with Intellisense and the built-in refactoring tools in Visual Studio (this one especially), there is no reason to skimp on meaningful naming and it's easy to fix past mistakes.

Wednesday, 15 March 2006 12:41:54 (Eastern Standard Time, UTC-05:00)   #     Comments [0]  | 
Tuesday, 07 March 2006
One of those stupid things...

I opened up a 2.0 website I was working on and Visual Studio decided it needed to be converted. Not sure why, unfortunately I wasn't paying attention.  Fortunately, I did tell VS to back up the project.  Went to run the website, which was working yesterday.  I get an allowDefinition='MachineToApplication' error.  What the badword !?!

(BTW, I believe coding -- much like plumbing -- requires lots of swearing to let off steam to save passers-by and inanimate objects from more physical acts of aggression.)

My first, VERY ERRONEOUS, thought was that the stupid project was trying to run under IIS, which I didn't want it to do.  I had been running it under the very handy ASP.NET Development Web Server. But I thought, I'll play along.  I created a virtual directory under my local IIS and pointed it to my website.

Same friggin' error.  More swearing.  Some googling.  What's going on?

Finally, looking at the directory structure, I see the backup folder and decide to just open the old project.  I nuke the "converted" website and copy the old files into the directroy stucture, "wisely" leaving the backup folder intact, just in case.

Same friggin' error.  More swearing. 

Then it hits me.  The backup folder has a web.config file in it. I move the backup folder out of my website tree.  I run the website.

It works. I get the last of the swearing out of my system.

The moral of the story, if you are getting the allowDefinition='MachineToApplication' error, and you have done everything to ensure you have a virtual directory set up with an application, check the rest of the tree to make sure you don't have a friggin' backup web.config file screwing things up. 

Tuesday, 07 March 2006 15:50:17 (Eastern Standard Time, UTC-05:00)   #     Comments [7]  | 
Monday, 06 March 2006
I have a number of code libraries I have created or inherited.  As time allows or urgency requires I am busily converting them into .NET 2.0 projects.  For the most part this is straightforward, but every now and again I run into something interesting that requires a little more digging/coding/swearing.

Today I discovered the XslTransform class has been deprecated in 2.0.  Since I do a fair amount of work with XSLT I decided I should pay attention to the little compilier warning Visual Studio was kind enough to generate and see what I should be using instead.  The new preferred class is XslCompiledTransform and Microsoft has also generated handy guides for using the new beast and to migrating your old XslTransform code.  Clearly there was a fairly meaty change made, so time to do some reading.

The documentation promises increased performance and also states "The new XSLT processor compiles the XSLT style sheet down to a common intermediate format, similar to what the common language runtime (CLR) does for other programming languages. Once the style sheet is compiled, it can be cached and reused."  Very interesting.  I will have to do some side-to-side comparison tests for performance at some point, but what do I have to do now to get my old code using XslCompiledTransform?

The function I need to change takes an XML document, calls another function that returns custom XSLT and then uses this to transform the input document and write it to a  string representation of an XML document.  The transformation simply sorts the document based on a number of supplied parameters.  (There is a better way to do this, but I inherited this particular method and it "works".  Also the need for the method will be removed shortly, so I just want to get it work in 2.0.)

Replacing the XslTransform class with XslCompiledTransfrom causes an error in the .Transform call that is the heart of the procedure...
Dim xTrans as XslCompiledTransform
'1.1 overload (IXPathNavigable, XsltArgument,TextWriter, XmlResolver) - Documentation
InputXMLDoc, Nothing, XMLStringWriter, Nothing)
Looking at the overloads for XslCompiledTransform.Transform reveals that what I want to do is...

'2.0 overload (IXPathNavigable, XsltArgument,TextWriter)
xTrans.Transform(InputXMLDoc, Nothing, XMLStringWriter)

The code wasn't using the
Resolver anyway, which is only used if you need to reference external resources such other DTDs or stylesheet namespaces, which isn't the case here.  If I wanted to use a resolver, I would need to use the one Transform overloads (of 14) that supports it, which requires an XMLReader as an input and an XMLWriter as an output. Fortunately, I don't need to do that much rewriting.  Dropping the unused XmlResolver parm does just what I need.

Monday, 06 March 2006 16:01:38 (Eastern Standard Time, UTC-05:00)   #     Comments [0]  | 
Wednesday, 01 March 2006
I've obviously decided in the affirmative or you wouldn't be reading this.  I knew this entry's title was cliched, but the 309,000+ results from the google search confirmed that there are no original ideas, just loads of sincere flattery -- and loads more laziness.

Surprisingly, the title of the blog only returns about 400 results in Google, showing that there is a not a significant crossover between the programming and hip-hop communities.

But back to why this is here.

I spend an hour or so a day answering all kinds of questions, from intriguing to idiotic on AspNetAnyQuestionIsOk, and I needed a place to write up in longer form some of the Frequently asked questions, so I can just point people to one place.  I could have updated my website, but that seemed like a silly amount of work, when some blog software would make it very simple. 

I'm also ramping up my .NET 2.0 development, and THERE IS SO MUCH NEW COOL-O CRAP in the Framework and Visual Studio 2005 (its Intellisense makes the 2003 version painful to return to). I need a place to write it down so I can remember it when I need it again and my handwriting is horrid.

So here we are.

Not a huge amount of choices for .NET blogging software, but this package was pretty simple to set up, even when having to do it via FTP and my web host's web interface to the file system.

So the first few entries are likely to be some nicely written up answers to questions I have answered far too many times.

Wednesday, 01 March 2006 23:34:22 (Eastern Standard Time, UTC-05:00)   #     Comments [0]  | 
I've been seeing everything as base classes lately. Not sure it is a good thing or a sign of insanity.

Had to do some driving of Excel from a web app -- not really something one should do as a matter of course -- but sometimes business requirements force more insanity than usual.

But I decided as long as I was going go insane, I was only going to do it once, so I created a base class that wrapped up all the goodies to open and close a workbook, get cell values, set cell values, etc. Excel exposes everything via COM.  .NET sets up the InterOp automatically, but if you've worked with automating Office apps, you know they are finicky about closing cleanly, so the destructor handles closing the workbook and quiting the app.  Works very nicely.

.NET | Excel | InterOp
Wednesday, 01 March 2006 22:45:02 (Eastern Standard Time, UTC-05:00)   #     Comments [0]  | 

Theme design by Dean Fiala

Pick a theme: