posts - 103, comments - 4, trackbacks - 37

My Links

News

Tag Cloud

Archives

Wednesday, October 11, 2006

West Michigan .NET User Group Meeting CodeSmith Presentation Resources

Last night, I gave my talk on Code Generation and CodeSmith, and I think it went fairly well. I promised I would post the templates I created as well as my slides, which you can get here. The slides are relatively useless. as there's not much details about what I talked about, but there are notes in the powerpoint, so you can get an idea of what I said.

There's also a text file in the zip which contains the command lines I used to do batch generation and the "Keep" region example.

Here's a listing of the resources I had on the last slides, in case you're just looking for those.

There's nothing in here about CodeSmith 4.0, but here's the email I got, as posted by Tim Rayburn.

Technorati Tags: |

posted @ Wednesday, October 11, 2006 7:09 AM | Feedback (0) |

Sunday, October 08, 2006

Designed vs. Open Inheritence

Martin Fowler has a post title DesignedInheritence which talks about the reasoning behind only allowing inheritence where the library developer specifies versus allowing inheritence anywhere. The reasoning for only allowing inheritence where the library developer specifies is the argument that library developers are experts and library users aren't.

He basically goes on to say that he believes in open inheritence, where you rely on the developers using your library to be smart enough to not screw things up - basically, don't get a big ego about how good you are. When you use Designed Inheritence, you're basically putting yourself on a pedastal and saying, "Look at me, all you lowly coders. I have deemed you worthy to use my perfect software."

That's not how the world works. When we build libraries, we have to understand that we don't know how it will be used. That's the whole idea of it being a seperate library. You recognize how you need it, but you're also opening it up to let others use it. The best libraries out there are the ones that get used in ways the original developer didn't take into account - but wrote the library in such a way that it was flexible enough to support those alternate ways.

Recently, I've been involved in building a framework, and this article was right on point with the philosophy that we used when building the framework. It's designed to be a business entity layer that can be used on just about any type of project, and what you get out of the box is huge. But that doesn't mean we can take everything into account that will be needed on any given project. So we took an open inheritence approach - our classes are wide open. You can override just about anything you want, and not one single class is sealed. Not only that, but we also have a whole set of events that you can hook into to manipulate data. Oh, and whoever's using the framework, they get the source to the framework. Not only that, they get the templates that generate the framework.

Can't get much farther from Designed Inheritence than that!

Technorati Tags: | |

posted @ Sunday, October 08, 2006 7:10 PM | Feedback (0) |

Thursday, October 05, 2006

I'm Speaking At The West Michigan .NET User Group

On Tuesday, I agreed to fill in for a colleague and speak at the next West Michigan .NET User Group meeting, which happens to be next Tuesday (October 10th). It's short notice, but I'm sure I'll have time to throw together a pretty decent presentation on code generation and more specifically, CodeSmith. I thought someone had already done something on CodeSmith, but looking back, it appears that's not the case - a couple of years ago, there was a talk about useful tools, where CodeSmith was mentioned, but not covered in detail.

I've been deep into CodeSmith for the past couple of months, so I think I have a fairly good grasp of what it's capable of, and can put together a pretty compelling demo. And since I found out, I've been digging deeper and found a few more things that I can show. And more importantly, I'll start using them now that I know about them!

On the down side, since I found out, I've come down with a cold which is making it difficult to speak too much. Hopefully I'll be over that by next week. I guess the big test will be tomorrow, when I have a presentation at NuSoft - oddly enough, based around CodeSmith too!

Technorati Tags: | |

posted @ Thursday, October 05, 2006 5:57 PM | Feedback (0) |

Monday, August 28, 2006

TeamCI Released - For Free!

I've been helping a client upgrade from Visual SourceSafe to Team System over the past couple of weeks, and one of our requirements is to ensure that we still have an automated build process. Well, TFS does not have an automated build system out of the box, and finding something has been a challenge.

Until now! On Friday, Notion Solutions released TeamCI, a free CI tool that works with Team System. I got it installed today, but haven't had much of a chance to work with it. Hopefully, it will work out nicely for us. I'll update as I get more experience with it.

FYI, our solution to this point has been to use the CruiseControl.NET plug-in for TFS. That's worked out fine for us - it's convenient because we can use the same build files in our current process. But the down side is that we don't get build reporting directly into TFS, and since consolidation of all of our third party tools was a goal, this doesn't exactly fit. It's better than no CI, but not what we were hoping for. Hopefully, once we get TeamCI up and running, it'll work out for us.

[via Greg's Cool Thing Of The Day]

posted @ Monday, August 28, 2006 7:59 PM | Feedback (0) |

Thursday, July 27, 2006

Sandcastle - NDoc's Replacement?

This week, the lead developer on a major open source project, NDoc, resigned. His reasons are valid, if not disappointing (not in him, in the community of NDoc users), but that's not the point. Coming on the heels of this announcement is the announcement about the pending availability of Sandcastle.

What's Sandcastle? Well, the preliminary announcement is a little light on details, but there's a few tidbits that give you a clue that it could be a replacement for the now defunct NDoc: Produces MSDN-like documentation, Build Assember includes syntax generation, and that it's used internally to generate .NET Framework documentation.

I'm interested - if for no other reason than it supports Generics! Anywya, a CTP should be released shortly.

Technorati Tags: |

posted @ Thursday, July 27, 2006 7:40 PM | Feedback (0) |

SSW's Rules For Successful .NET Projects

SSW has a list of 41 rules that they've put out there that can be used as guidelines for running successful projects. I perused the list, and for the most part, they're spot on.

One item I hadn't seen was number 5 - about synching up development vs. production web.config settings. SSW uses an approach based on machine name - so if you have a key for WebServiceUrl, you'd have DevLaptop_WebServiceUrl for your local machine, and DevServer_WebServiceUrl as the key for your dev server. I've never done it that way, but it's an interesting approach - and could see some use for it in the future. I've typically used either the ability to have a developer.config file that's not checked into source control (file attribute for appSettings), or, more recently, using a web deployment project to make our dev, staging, and production builds, and use the built-in ability to swap out sections with other files - we have a production.appSettings.config, staging.appSettings.config, and dev.appSettings.config, and those get put into the appSettings section in our web.config when the build happens.

Others that I hadn't seen? Database tools. I use Red Gate's SQL Compare to do our database upgrades, but it's not part of our build process. Having some sort of SQL deployment tool in our build process is a goal, but a lofty one at this point.

I like the point about referencing projects over DLLs. Even for stable DLLs, if I have access to the project, I'd rather have the project reference, if for no other reason than when I'm debugging, I can still step through the code if I need to - not swap out my reference for a debug DLL - because if you reference a DLL directly, it should be the release version!

By the way, the actual author of this list looks like it's Adam Cogan, who's been on dnrTV for the past four weeks talking about SQL Reporting Services (part 1part 2part 3) and Visual Studio Team System (part 1).

Technorati Tags: | | | |

posted @ Thursday, July 27, 2006 7:09 PM | Feedback (0) |

Monday, May 22, 2006

SQL Intellisense For Free

If you've used Visual Studio, and ever switched to SQL Server (Query Analyzer, for example), you've probably wished for Intellisense. I know I have. Now, Red Gate, makers of the best SQL products (besides the server itself) out there, is offering SQL Prompt for free until September 2006. I've downloaded it, and will be installing it soon, considering I work with SQL stored procedures on a daily basis right now. It adds intellisense to a whole slew of products, including Query Analyzer and Visual Studio.

I wonder if the whole free until September will end up like Microsoft's free for one year offer they had on the express products...

Technorati Tags: | |

posted @ Monday, May 22, 2006 8:09 PM | Feedback (1) |

Thursday, May 04, 2006

All Mix '06 Content Available

Mike Swanson's got the news that all of the sessions from the 72 hour conversation known as Mix '06 is online, and will be for at least 6 months.

Time to get the downloaders going. When will Microsoft get on board and start distributing this stuff via torrents?

Technorati Tags: |

posted @ Thursday, May 04, 2006 8:00 AM | Feedback (0) |

Wednesday, April 12, 2006

Multiple Property Sorting Of Generic Collections

Dave Donaldson prodded me this morning to get off my butt and post an update to my previous multi-sorting comparer, and I'm going to do that now. Man, Dave, get off my back!

Ok. He didn't prod. He asked if I'd updated it to support Generics, which I had. If you look at the previous one, not a lot has changed, so let's just highlight the changes. First, instead of using an ArrayList to store the internal sorting classes, I'm using a Generics (it really wouldn't be a good upgrade if I didn't use generics in my implementation, would it?), and instead of using objects in the comparison class, it can now be typed, which means better compile time checks. This changes both the Compare method, and the CheckSort method (CheckSort is what Compare calls to perform the recursive sorting, which is what allows you to sort and subsort your collections). Here's the updated code:

   1:  public int Compare(T x, T y) {
   2:      if(SortClasses.Count == 0) {
   3:          return 0;
   4:      }
   5:      return CheckSort(0, x, y);
   6:  }
   7:   
   8:  private int CheckSort(int SortLevel, T MyObject1, T MyObject2) {
   9:      int returnVal = 0;
  10:              
  11:      if(SortClasses.Count - 1 >= SortLevel) {
  12:          object valueOf1 = MyObject1.GetType().GetProperty(SortClasses[SortLevel].SortColumn).GetValue(MyObject1, null);
  13:          object valueOf2 = MyObject2.GetType().GetProperty(SortClasses[SortLevel].SortColumn).GetValue(MyObject2, null);
  14:   
  15:          if(SortClasses[SortLevel].SortDirection == SortDirection.Ascending) {
  16:              returnVal = ((IComparable) valueOf1).CompareTo(valueOf2);
  17:          } 
  18:          else {
  19:              returnVal = ((IComparable) valueOf2).CompareTo(valueOf1);
  20:          }
  21:   
  22:          if(returnVal == 0){
  23:              returnVal = CheckSort(SortLevel + 1, MyObject1, MyObject2);
  24:          }
  25:      }
  26:      return returnVal;
  27:  }

So now, you can sort your generic collections easily and flexibly. This could be used in conjunction with an ObjectDataSource pretty easily, and I may post an example of that at a later date.

The full code snippet is on CodeKeep and is available here.

While I'm on the subject of CodeKeep, Dave added a new feature where you can link to your Code snippets using a nice little icon. Here's my code snippets - there's only five right now, but I plan to add more in the near future (once I get some time!):

Technorati Tags: | |

posted @ Wednesday, April 12, 2006 4:59 PM | Feedback (0) |

Tuesday, April 11, 2006

West Michigan .NET User Group Meeting - Tonight!

And I'll be there! It's at the Watermark Country Club at 6:00 PM. It should be a very good meeting, with Sahil Malik speaking about ADO.NET and John Cripe (of NuSoft) talking about SQL Server 2005.

If you're there, say hi. I'll be wearing a black NationalCityHomeLoans.com shirt.

Technorati Tags: | |

posted @ Tuesday, April 11, 2006 10:10 AM | Feedback (0) |

Tuesday, March 28, 2006

Interested In Web Content Management 2007?

If so, then this'll be of interest to you. For those not in the know, Web Content Management is the next version of Microsoft Content Management Server, and should bve a solid replacement.

Anyway, if you want to get a look at it before it's released, Andrew Connell will be doing a webcast on April 18th, and he'll go into what's new (everything, it seems!) and how to migrate from CMS 2002 (the last major release) to the latest and greatest.

If you're interested, check out Andrew's post for some more information, or skip that, and just register!

Technorati Tags: | |

posted @ Tuesday, March 28, 2006 5:46 PM | Feedback (0) |

Friday, March 24, 2006

A Possible Issue With Website Deployment in Visual Studio 2005?

I've harped on Visual Studio 2005's website projects quite a bit lately, and I'm going to move to the web application model now that it's been officially released. But, I did want to talk about one last issue I've seen, because it's a doozy.

Some background: We have three projects that we're building and deploying. One is at the root of the website, and the other are sub applications (virtual directories) under the root. Of the two sub applications, one was set to compile all of the code into one DLL, and one was left like it was - compiling each code file into a randomly named DLL. The root site used the default compilation, but that part didn't seem to matter, because we changed that to compile to one DLL and still had the same issue that I'm going to lay out.

Basically, whenever the root application was deployed, it broke the sub application that used the default compilation model. We got errors saying it couldn't find the necessary DLLs. The sub app would remain broken until I uploaded the same exact files again. I don't know if this is a problem with ASP.NET 2.0, something we were doing, or possibly WebHost4Life's shared hosting environment.

What led us to fault the default compilation model? Well, the other sub application was unaffected by deployments of the root application. So our solution was to switch the problematic sub application to compile to one DLL. Once we did that, our issues went away, and I stopped trying to figure out what was going on. But if you ever run into this, now you'll know how to fix it!

Technorati Tags: | |

posted @ Friday, March 24, 2006 8:13 PM | Feedback (2) |

Mix06 Sessions Coming

Mike Swanson is reporting that about 50 sessions from Mix06 will be available online for free - for everyone. Microsoft did the same thing for PDC '05, so I was hoping this was going to happen. Expect to see it in three to four weeks.

I spoke with Brian, who was there, and he told me this was the best conference he's ever been to - and he's been to a few Tech Eds and PDCs. I'm looking forward to downloading a few of these.

Technorati Tags:

posted @ Friday, March 24, 2006 6:22 PM | Feedback (0) |

Thursday, March 23, 2006

Viewstate On The Server

We're going through an existing application with an eye on performance. One of the first things we noticed was viewstate. We had quite a few pages that were pretty heavy, so we started looking at what we could do about it.

The obvious choice was to reduce the size, but that takes time to determine what can be excluded, and with a lot of pages, that would be a fairly large undertaking. We plan to do that over time, but we wanted a speed increase now. So we started looking at alternatives to storing the viewstate on the client. Our application is hosted in the midwest, but the users are primarily on the left coast, and it's accessed over a T1 - it's not available on the 'Net, so the pipe is limited. With 300 or so users, it's important for us to limit the sheer amount of data passed over the line. We eventually settled on storing viewstate in the database. We looked at some alternatives - cache, session, etc., but settled on the database because, while it isn't as fast as the other two, it is less memory intensive, and still faster than passing it over the wire.

So how did we do it? Well, we were smart and put in a base page that all pages in our application use, so we only had to modify one file, and all pages benefited. Then we added a web.config option to turn it on and off, and left it flexible enough that we could add other storage mechanisms in the future.

With that, here's the code to save it to the database:

   1:  protected override void SavePageStateToPersistenceMedium(object state)
   2:  {
   3:      switch (ConfigurationManager.AppSettings["ViewStateMode"].ToLower())
   4:      {
   5:          case "database":
   6:              LosFormatter los = new LosFormatter();
   7:              System.IO.StringWriter writer = new System.IO.StringWriter();
   8:              los.Serialize(writer, state);
   9:              string viewState = writer.ToString();
  10:   
  11:              string key = ViewStateManager.InsertViewState(viewState);
  12:   
  13:              RegisterHiddenField("__VIEWSTATE_KEY", key);
  14:              break;
  15:   
  16:          default:
  17:          case "normal":
  18:              base.SavePageStateToPersistenceMedium(state);
  19:              break;
  20:      } 
  21:  }

When storing viewstate in cache or session, you don't have to worry about serializing the data - you can throw it in, and pull it out as an object without issue. When you throw it in the database, you need to serialize it to a string, so you have to use a LosFormatter to do that for you. Our ViewStateManager takes a string and returns a key - we use a GUID for our key, but I've also seen using the session ID combined with the current page name and time. It doesn't really matter what you use, as long as it't unique. Then, you register that key as a hidden field. So instead of passing the whole viewstate to the client, you only pass a pointer to it. Now, when a page posts back, you use that key to load it from the database:

   1:  protected override object LoadPageStateFromPersistenceMedium()
   2:  {
   3:      switch (ConfigurationManager.AppSettings["ViewStateMode"].ToLower())
   4:      {
   5:          case "database":
   6:              string key = Request.Form["__VIEWSTATE_KEY"];
   7:              string viewState = ViewStateManager.GetViewState(key);
   8:   
   9:              LosFormatter los = new LosFormatter();
  10:              return los.Deserialize(viewState);
  11:          
  12:          case "normal":
  13:          default:
  14:              return base.LoadPageStateFromPersistenceMedium();
  15:      }
  16:  }

As you can see, we can easily turn it off in the web.config and have viewstate back in the page. We considered using our configuration table to manage this value so we could change viewstate persistence on the fly, but determined that would actually be a bad thing. Imagine this scenario:

  1. User loads a page and viewstate is stored in the database
  2. The configuration is changed to persist viewstate to the page
  3. User posts back

So what happens? When the user posts back, the load viewstate method will be looking for the viewstate in the page, when it's actually in the database. Not good. At least with storing it in the web.config, it will force the application to restart, which gives us a little more protection - plus, it requires a developer to make the change, who should know the consequences of making that change.

The last thing to touch on is the viewstate table itself. Not the structure - that's pretty easy. Three fields: key, value, and a timestamp. Simple, but the most important thing to consider about this table is clean up. When do you delete the records in this table? Our initial thought was to delete it when you retrieve it. Once you've used it, it's no longer valid, right? Have you ever posted a form, had something go wrong, and just hit F5 to repost the data? I have, and if after thefirst post, the viewstate was deleted, hitting F5 would cause an error because the viewstate would be gone. That's a problem. So we decided to go with a nightly job to purge old records from the table. Since it's an internal application, we could reliably remove records at night knowing that most of the time, no users are currently using the site.

So while this is all technically possible, was it worth it? Using Fiddler, I went through a few different scenarios and my quick eye ball glance says page size was reduced by about 25% on a lot of pages, and on a few pages, the size was reduced by more than half. And this was after we've already implemented HTTP compression. Also, by not having to compress the viewstate reduces the tax on the server too - less data to compress.

Overall, we've been happy with the performance increase.

posted @ Thursday, March 23, 2006 6:20 PM | Feedback (2) |

Sunday, March 05, 2006

Differing Opinions on Differencing Disks

After reading my post on how I use virtual machines, Andrew Connell pointed me to an article he wrote about his extensive use of Virtual PC, including how he uses Differencing disks to his advantage. He also says he doesn't see the huge differencing disks that I'd heard about in the past. I'm now rethinking my plan, and when I update my base image to have Visual Studio 2005, I may give it a try.

My biggest hang up with using differencing disks wasn't the size - I really do find it hard to believe that a disk plus two differencing disks would be larger than 3 seperate disks - it was the patching. But, whenever I need a new disk, I could always create a new differencing disk on top of my existing base disk which just has the patches and any updated software I want to install. Then I'd use that new disk as my new base. Right now, my base disk does not have Visual Studio 2005 on it, and as soon as I have a new project, I'll probably give it a try.

Technorati Tags: |

posted @ Sunday, March 05, 2006 8:53 PM | Feedback (0) |

Powered by: