Attention: We are retiring the ASP.NET Community Blogs. Learn more >

Fear and Loathing

Gonzo blogging from the Annie Leibovitz of the software development world.

  • SharePoint beyond the Intranet

    Okay, let's face it. SharePoint (when appropriately used) kicks as a collaboration tool. I don't know how many times I've been asked about sharing knowledge only to say "well SharePoint can do this". I don't know how many times I've seen teams wanting to cobble together a website with FrontPage or throw up a forum tool or something when "SharePoint can do it" (the struggle with the evil IT empire [our strategy and architecture guys] and how we can't just do what's right vs. correct is a whole 'nuther conversation). Grant you, SharePoint isn't all things to all people, but from a collaboration viewpoint it's pretty nifty.

    My fellow SharePoint lover (hmm, that didn't come out quite right) Amanda Murphy (and a Canadian to boot), posed the question of Virtual SharePoint User Groups. While we're all squibbing away building our intranet solutions, it seems that we might be missing the one thing that SharePoint is great for and the one thing that might bring some order to this chaos. The internet is a big ugly place (as I put on all my blueprints, a nasty stormcloud with the words "big bad interweb") and trying to filter information out at the same time balancing what's worthy is just as ugly. I've got I don't know how many bookmarks that I use to hunt down things, a few dozen RSS feeds, countless forum userids and passwords, yet still information fall through the cracks and I'll stumble across a "wow, I didn't know that" each day.

    Microsoft is making some headway in building Technical Community Sites where like people with like thoughts can meet and swap good stuff. We all know User Groups are a great thing (the .NET one here in Cowtown has some great events and is very value-added IMHO). So Amanda puts in my head the notion of a more global User Group. Still a special interest group around that thing we call SharePoint (or SPS, WSS, or whatever acronym you want to throw out there) but why not extend the very tool itself we use each day to accomodate this? Exactly how to get things going, I'm not sure. I do have a passion for this though and would like to see where it goes.

    Anyways, some food for thought and perhaps an evolution towards a more unified collaboration across virtual boundaries that might make life a little bit easier one day for some of us.

  • Hodgepodge of some (hopefully) useful .NET links and sites

    Was doing some research over the weekend and gathed together some links on patterns and practices and other stuff. Hope you guys find these useful.
     
    Good site with all kinds of patterns around user interface (both web and other). Lots of good ideas here.
     
    I was going through some options of providing online help in web apps and came across this. It's a study done on different techniques applied to providing online help for web application users. Some good ideas and information here on what worked and what didn't.
     
    This may seem silly but tables have TH tags for a reason and web readers (the type blind folks use to read webpages for them) rely on it. One of my biggest beef is the fact that the ASP.NET DataGrid doesn't spit out HTML code that's compliant with these readers. This KB article talks about resolving the problem via a hotfix that went out sometime ago. Just information to watch out for and contains a good link to Watchfire, a website that can check your page for accessibility compliance.
     
    Sample Applications
    Microsoft (and others) have gone to some extents to put together sample applications, reference architecture apps, and other resources to learn from. Some good (some not so good) stuff here if you haven't already seen any of these. That make for great reference when you're looking at how to implement some ideas.
     
    ASP.NET 1.0/1.1 Starter Kits
    Home
     
    ASP.NET 2.0 Starter Kits
    Home
     
    Peer to Peer - .NET Framework 1.0/1.1
    Terrarium
     
     
    Service Orientation Architecture
    Generico
     
    Smart Client - .NET Framework 1.0/1.1
    IssueVision
    FotoVision
    TaskVision
  • The dumbness of a Domain Object

    I've been mulling over some ideas for the past couple of days as I work on a project and came to a bit of a head with regards to the dumbness of a Domain Object. There are some base principles that I try to follow with application architecture:

    • The data access layer only creates or accepts domain objects
    • The service layer is responsible for creating or converting data transfer objects to real domain objects
    • Only data transfer objects are sent between the service layer and user interface

    So first off, maybe some of these principles are not correct. Hey, principles can always be changed (as long as you reapply them everywhere if they do change and adjust accordingly). I'll leave that to the reader to discuss.

    Given these norms, there's a problem (or maybe a question). If the DAL only creates Domain Objects, then it needs to know how to assemble them. After all, it's retrieving data from a source and populating *something*. You could hide the creation in an Assembler or maybe a Factory but still, at some point some data needs to be set as an attribute in a Domain Object meaning that the DAL knows something about the contruction of a Domain Object. The other option is that everything gets assembled in the service layer. If this is the case then why do we even need collections in a Domain Object? They can be dumb and just hold properties that relate to themselves and not worry about things like collections of children.

    So here's an example to try to make sense of what I'm talking about. Imagine you have a Media Center tool where users can view album information, list tracks on an album and update the track information. This gives us some simple objects like so (C# pseudo-code):

    class Album
    {
      int AlbumId;
      string Title;
      string Artist;   
    }

    class Track
    {
      int TrackId;
      string Title;
      int Length;
    }

    In order to know what Track belongs to what Album, I could have Domain Objects that look like this:

    class Album
    {
      int AlbumId;
      string Title;
      string Artist;   
      ArrayList Tracks;
    }

    class Track
    {
      int TrackId;
      string Title;
      int Length;
    }

    Or maybe this:

    class Album
    {
      int AlbumId;
      string Title;
      string Artist;   
    }

    class Track
    {
      int TrackId;
      int AlbumId;
      string Title;
      int Length;
    }

    In the case where I have an ArrayList of Tracks in my Album, I don't need the AlbumId to know which Track belongs where. However, if I have to create an Album object out of my DAL, I now know that I have to create Tracks as well. Am I not putting logic of structure of the application in my data layer now? In the last example, I can have some Assembler make calls to the data layer (1 for the album and 1 for the tracks) and put together an object myself. And if the only reason I'm doing this is so that I can show the user at the UI layer an album and it's related tracks, why does my Album Domain Object even need to know about Tracks?

    This also brings up the question around using IDs everywhere. Remember we have a principle (right or wrong) that the UI only deals with DTOs and knows nothing about the domain or (gasp) the data access layer. End users don't need to know that "Like a Virgin" has an ID of 4532 in the database. However, if they update the title to a track on the album and want the tool to save that information, it means the UI needs to keep track of all this junk in order to send it back to the system for updating (there's no guarantee that two tracks won't have the same name, even on the same album). So going back to our example where I only want to update one single Track.Title property with a new name the user typed in, do I send back an entire AlbumDTO (with an Array of TrackDTOs). Probably not. I only want to update one track so I only send back one TrackDTO which leads me to the idea that:

    • A TrackDTO must be able to exist on its own (for updating the backend from the UI)
    • It needs to keep track of the Album it belongs to (otherwise how do we know what Album it's for when we update it)

    Given this, why should a Domain Object (Album in this case) even bother to have a collection of children (Tracks). So all assembling should be done somewhere other than in the domain objects or data access layer? While this might not be the rule for all Domain Objects, I thought it was something that didn't seem to have a very clear answer (or maybe there is but I'm just missing it).

  • Happy Thanksgiving Canada!

    "As God is my witness, I thought Turkeys could fly!"

    - Arthur Carlson, (WKRP Station Manager) 1978 - after a Thanksgiving promotional stunt went horribly wrong

  • InstallShield AutoUpdate

    I'm not one to usually go non-techie and go down the dark sales path, but I saw something I wanted to mention.

    I picked up a copy of Jasc's Paint Shop Pro Studio. It's basically an uber-version of their Paint Shop Pro product. Anyways, after the install, I ran it for the first time and up came what looked like the Windows Installer Update site. I was a little thrown for a sec because I wasn't sure what was going on? Was I missing a critical update? If so, why was Jasc telling me this? Then I realized that it wasn't Studio but an Install Shield feature. Install Shield Corp has a nice Update Service. It basically gives you a nice web-based interface (like WUS) to check for components of your application and an integration piece to install them. They offer both an Install Shield-Hosted service or you can host it on your own infrastructure. Pretty nifty (although when they don't talk about how much it is online, I'm sure it's a big-ticket item).

    Here's to more installers (especially the free ones like Inno Setup that I highly recommend) to combining these concepts. It would be nice if products built in more updaters themselves like Visual Studio (there is a "Check for Service Updates" but I've never got it to work and you have to go through the Add/Remove Programs to access it). Of course here's an opportunity to maybe build a component that does this easily for people.

  • SharePoint Service Architecture and site updates

    Found this on TheServerSide.NET and felt it was worthy to post:

    A new paper on MSDN looks at the architecture of SharePoint Services beginning with a high level overview of the web server and drilling down to using managed and unmanaged code. This paper is a “must read” for anybody looking to develop applications built using SharePoint Services.

    There’s quite a bit going on under the covers of SharePoint services. SharePoint Services is implemented primarily through an ISAPI filter installed in IIS which accesses unmanaged DLLs installed on the web server. The ASPX pages that make up a SharePoint site are actually a relatively thin veneer over those same DLLs. All of the data is then stored in an MSDE or SQL Server Database. And this is the high level view!

    To read more about SharePoint Services Architecture look
    here.

    For this site, a few new links in the SharePoint and Scrum sections. The site is filling out nicely since I started it 6 months ago, although I wish I could post everyday as there's a lot of great stuff to share. Please feel free to let me know if I've missed anything important or you have something to share.

    Also I've taken a couple of blogs and turned them into articles so you can find them in the sidebar. These were ones where I got some feedback and people were asking a lot of questions so there was interest to keep it around and to the forefront (migration of sites, branding SPS, etc.) I'll add more as they become a reality.

  • Defeated by CVS, Windows, and IIS

    Okay, I'll admit it. I've come up against a techno-combo that just has drained me (and bugs the crap out of me). I'm throwing in the towel and picking up a new one.

    We setup CVSNT at work for team source control in order to adapt to a more agile development lifecycle (PVCS just doesn't work when everyone is refactoring and checking in all the time). We're still using PVCS for our enteprise SCM and when things are ready, they're labeled at checked into our corporate repository (well, that's the plan anyways). It's a nice setup and works well.

    I've been struggling with getting some kind of web interface for CVS working with IIS. Yes, I'm tied down to IIS as our corporate web servers which is fine. So I went out to hunt down all the tools I could find and make work (the ultimate goal is to turn our Projects Portal running on SharePoint into something like SourceForge where you can access the source code from a project website). Talk about painful.

    CVSWebNT was the first stop. After installing ActivePerl I was okay burning through the setup. However Perl really isn't a friendly thing to debug, especially when it's an out-of-process cgi-bin script. So after many tries at hanging IIS and rebooting the server, I gave up. Next seemed like a nice gem called CVS4IIS. VB, ASP, and COM (blech) but okay let's give it a try. Not bad but didn't seem to work and it can't support multiple repositories. Finally I took at look at ViewCVS for Windows. Well, not really official but Russ is doing a good job of getting things going there. Problem is that now I would have to install Python, and the Python for Windows extensions and whatever else is thrown in there. In a corporate environment when you're somewhat limited to using a core set of technologies (Python is not one of them) it's tricky. Pain and suffering all before my 2nd cup of coffee this morning.

    So why isn't there a nice project out there that does this easily? I mean, CVSNT is great. Works well, actually has an installer, and doesn't seem to fall over when you look at it. I'm throwing in the towel on trying to get these things working in our environment but there might be hope. Now I'm charged with looking at writing what should hopefully be a fairly simple ASP.NET application to do this. I mean, how frickin' hard can it be? (famous last words). Here comes NCVSWeb coming soon to a SourceForge site near you.

    I so wish for a Linux server at work. Just one. Just a little one. A copy of Debian and a call to apt install cvs and I'm done.

  • The Mysteries of SharePoint Search

    There's a myth in town. SharePoint searches documents. While the search feature of the SharePoint products is a key element, it's not entirely true that it actually does any searching. Walk with me on this one.

    SharePoint, like a conductor in an orchestra, really just orchestrates a search request. As a conductor doesn't play an instrument, SharePoint doesn't actually do the mechanics of a search, it just makes the request. It's really all about IFilters and the search capabilities they provide. The SharePoint search pages, object model and web services are just facades to access the real workers.

    This conversation came up because, out of the box, SharePoint only searches the following content types: .txt, .htm, .doc, .xls, and .ppt. And this search is not SharePoint but rather SQL Servers full-text search engine. After all, a binary file type (like PDF) can't really be searched unless the searcher knows how to read the format. SQL Server knows how to read the base types and with the addition of new iFilters, you can extend that. You can get additional IFilters for PDF, RTF, MSG, ZIP and other formats from various sources (Microsoft has a few free ones like for RTF). A good source of commercial IFilters is the IFilterShop.

    So next time you try searching for content check to make sure your SQL Server (all content for SharePoint is stored in SQL) has an IFilter that recognizes the format you're looking for. Also a catch is when you do need to add a new search type, make sure you install the IFilter on the SQL Server and not the SharePoint one as it's the mechanic that's actually performing the search and just providing results to SharePoint to present to the user.

  • SPS Customization

    I see (and get) a lot of questions about customizing the look and feel of SharePoint Portal Server. More often than not, this leads to an answer of directly modifying the SPS.CSS files on the server. This always leads to the caveat that this file may be updated with a service pack install or software upgrade. There is a much easier and safer way to do this which will never break.

    In your SharePoint setup, Microsoft has provided a way to specify your own custom style sheet. If you know how style sheets work when a page is rendered, the last style specified (no matter how many style sheet files get loaded) always wins. This is by design but knowing this, and how SharePoint works, is a powerful combo that will let you cleanly mod your portal as much as you want without having to backup/restore files everytime your do an upgrade.

    When SharePoint renders it's portal pages it renders all of it's own internal stylesheets. These are (in order):

    1. ows.ccs
    2. menu.css
    3. sps.css

    Next, it renders any stylesheet you specify in the Site Settings page. Finally it renders the page content. Knowing this means that any style you put into your own stylesheet will override those specified in the Microsoft ones. So now you don't have to go modifying the base files to get the effect you want. Here's a simple example.

    Create a blank stylesheet. Put a single style in it. Let's override .ms-WPTitle which is the style used to render Web Part titles. Your stylesheet should contain this:

    .ms-WPTitle
    {
      background-color: black;
      font-weight: bold;
      font-family: verdana, arial, helvetica, sans-serif;
      color: white;
      padding-left: 6px;
      padding-right: 7px;
      padding-top: 2px;
      padding-bottom: 2px;
      font-size: 8pt;
      text-transform: uppercase;
    }

    This creates a style for the web part titles that displays a white uppercase title against a black background using Verdana as a font. Save this file as "mystyle.css" (or whatever name you want).

    Now you need to tell SharePoint to use this stylesheet.

    1. Select "Site Settings" from your portal
    2. Click on "Change portal site properties and SharePoint site creation settings" from the General Settings section
    3. The last option is for a Custom Cascading Style Sheet. Put in the location of your stylesheet you created above. An additional trick is to use SharePoint to store your own stylesheet so put it in the Document Library of your own portal. That way you don't have to deal with server administrators whenever you want to change your sites look and it gives you a simple document management process to keep tabs on who's working on this file. So our entry would look like this: "/Document%20Library/mystyle.css" (assuming you uploaded it to the site, otherwise use a fully qualilfied UNC to locate the stylesheet, maybe from your corporate web servers)
    4. Click OK to save the changes

    Now refresh the site in your browser. You should see the changes applied to all web parts on your site (Press F5 to refresh or you might have to do a "deep" refresh with Ctrl+F5). Continue to edit this file, making changes with your favorite style sheet editor like TopStyle (or Notepad if you prefer). In no time you'll have a custom stylesheet with the branding you want on your site.

    A variation on creating styles from scratch is to take a copy of SPS.CSS and modify the styles you want by changing your copy of this file. This uses the same technique as above (not modifying the file directly) but gives you a list of all the styles that SharePoint uses rather than building up from scratch. Pick whichever method works for you but the important thing to remember is that you don't have to touch the base SharePoint files.

    Two more quick tips. There's a list of the styles used with a visual reference in the SDK documentation available here. Also in that file is a short piece of Javascript that you can create and put into a content editor webpart to display the styles on the page when you hover your mouse over them. Both are valuable resources to help you when you're customizing your look.

    Here's a full set of MSDN articles published on the subject of customizing SPS:

    Part 1 : Introduction
    Part 2 : Using Templates and Site Definitions
    Part 3: Style Sheet Class Reference Tables

  • Migrating SharePoint Sites

    One thing that comes up quite often is "How do I keep all the work I've done in development and move it to acceptance/production" with SharePoint? Luckily there's a nice command line tool that's bundled with SharePoint to do this.

    SMIGRATE is a tool that can restore sites and move them from SharePoint Team Services (STS) into the new 2003 versions. It can also help you migrate sites from one server to another (or to the same server) in 2003 directly. This blog talks about using it for migration from a development environment to your production one (or test if you prefer).

    SMIGRATE works wonders because a) it migrates all your data, including security and subsites b) you can execute it from any SharePoint server and restore to any server (you have to be SPS/WSS admin on both) c) is simple for moving all your hard work in development into acceptance or production. Using SMIGRATE is pretty straight forward.

    To backup a website:

    1. Enter the following at the command line:
      smigrate -w http://server[/site] -f filename.fwp -u domain\id -pw *
    2. This will prompt you for your NT password. Enter it at the prompt.
    3. Grab a coffee and wait.

    To restore a site:

    1. Create a new site through the portal site creation wizard. Note what the site url is.
    2. When you get to the point of applying a template, stop and close the browser.
    3. Enter the following at the command line from any SharePoint server (where siteurl is the url you used in step #1):
      smigrate -r -w siteurl -f filename.fwp -u domain\id -pw *
    4. Enter your password, grab a coffee, go for lunch or have a siesta.

    There are a couple of gotchas you should be aware of.

    1. When you migrate a site, the new site has to exist. If you've gone through the trouble of creating the site using something like the SPS site creation wizard you'll find you get the site created then try to migrate and it tells you a template has already been applied. The trick is that when you to the screen in SPS where you apply the template to the site, the site is already created. Go ahead and start your migration now and when you're done, the site will be there and ready to use.
    2. Make sure all your dataview web parts and 3rd party components are on the target server. There's nothing like migrating the site then trying to access it, only to find yourself staring at the maintenance page trying to remove invalid web parts. This is especially true of dataview web parts as they are sometimes picky about the pathing to the datasource, especially if you have it pointing at another list on the same site.

    In any case, the tool is a good friend to have so get used to it, try it out and make sure you understand what's going on before you start moving gigabytes of documents and lists onto your production boxes. There's also a good writeup on using the tool here and the online version of the Windows SharePoint Administrators Guide here.

    For those that are afflicticted with GUI-Itis and fear the command line, there's a graphical interface that Renauld Comte created. You can download the file directly from here (note, you still have to run this on your SharePoint server).