Object Reference .NET

ref this.Object

NHibernate and Execution Plans

clock October 26, 2009 11:29 by author Naz

Lately we have been investigating ORM’s (Object Relational Mapping) frameworks for use on a large enterprise level website which we been given the rare opportunity to rebuild from the ground up in Microsoft MVC.

I’ve used Subsonic in the past while working with dashCommerce and more recently on my latest project based on the wonderful Subsonic 3.0. We decided we needed something more robust and proven with a large enterprise level system like ours which currently comprises with hundreds of tables and store procedures all managed by a team of professional DBA’s who do a pretty good job at optimising and tuning the Microsoft SQL 2005 database.

After much deliberation we managed to convince the DBAs and Developer Head to give NHibernate a shot. It seemed to be the most mature fully featured ORM for .NET and rated highly whitin the .NET community as is apparent by the huge number of blog posts about it, so we felt more secure choosing it over the premature Entity Framework.

NHibernate and MVC brought us to reconsider our architecture and after finally getting my head around to the S#harp Architecture I managed to convince the team it was the way to go and gave us a good foundation to build our application on.

After a few weeks we got a really good prototype working. We mapped some of our core tables using FluentNhibernate, wrote some simple LinqToNHibernate queries, religiously followed Test Driven Development and Domain Driven Design until we stumbled across our first major issue.

Queries run by NHibernate were not re-using SQL Server execution plans This was causing us some major performance issues since some queries were taking a few seconds just to generate a plan. We quickly managed to figure out the problem caused viewing the queries using SQL Profiler. NHibernate was passing parameter sizes dynamically based on the length of the value rather than from the mapping which was causing SQL Server to create new execution plans for each unique query.

We found a good explanation and “fix” setting prepare_sql to true in the NHibernate config.

This seemed to fix the parameter size issue but now the queries were being sent using exec sp_prepexec which even had the DBA’s scratching their heads over as it’s documented as a system procedure used to facilitate cursors within SQL Server. The DBAs later informed us that running queries like this causes the execution plans to only be re-used per open connection so for every connection it would still have to create new execution plans.

Carsten Hess wrote a good comment on Ayende’s Blog explaning the issue to which no follow up was made but helped us find and fix the issue. I’ve attached the file for those interested in the fix as to why this isn’t the default behaviour of NHibernate has us perplexed. I've just commenting out an if statement in \Driver\SQLClientDriver.cs found in NHibernate source code thus forcing it to call SetParameterSizes() all the time regardless of the prepare_sql setting alowing us to set it to false so queries are sent normally and excecution plans being issued and re-used correctly.

The whole experience left us feeling weary, had we not discovered the issue beforehand it almost certainly would have brought down our application if we went live with NHibernate. In the end we decided to hold off on implementing the ORM to give it more investigation.

Our journey wasn’t a waste of time as it has brought us to learn about many new skills along the way that has already had an affect on our programming. Test Driven Development, Dependency Injection, Inversion of Control, Domain Driven Design all of which has given us an understanding of some techniques we can use to better develop our system.

Attached: SqlClientDriver.cs

EDIT: Andrei Volkov has posted a good followup in which he explains the history of this issue and an alternative fix to create your own driver. NHibernate parameter sizes controversy

kick it on DotNetKicks.com Shout it



Learning new Programmming Languages and Technologies

clock June 11, 2009 09:31 by author DaveTheKnave

These days, it seems there are so many new programming languages and technologies to learn I’m starting to find it difficult to even keep track.

Recently, I’ve read article after article about how part of being a good software developer is about being open to new technologies, and to “learn new things” – and I’d be foolish not to agree. The classic example is that of the COBOL programer – the dinosaur – who never updated their skills, and slowly became unemployable as the market changed around them.
How could an 80’s COBOL programmer have stayed relivant? The most probable answer back then would have been “Learn C++”, or, at least “Learn Pascal”.

However, I feel that software developers of the current age are facing a slightly different problem. I’m starting to feel like we’re approaching a kind of “Software Development Singularity” – where things are starting to move too quickly than is possible to keep track.

Currently, outside of my day-job and any projects I’m working on in my spare time, I consider learning the following list of things (at least to a passable level) essential to placing myself in a position where I’m moving forward, so as to avoid becoming extinct.

  1. .Net 4.0
  2. MVC
  3. LINQ
  4. IronRuby
  5. IronPython
  6. F#
  7. Entity Framework
  8. nHibernate
  9. Azure
  10. Windows 7 Development
  11. Silverlight 3.0
  12. WCF, WPF, WF


But wait! That’s just a Microsoft based list! I’m a .Net developer, sure – but I should really broaden my horizons to the open-source community and any Microsoft competitors. (not to mention vendor-ambiguous technologies)

  1. HTML 5.0
  2. Javascript 2.0
  3. Python
  4. Ruby
  5. Google App Engine
  6. Google Gears
  7. Mono
  8. jQuery
  9. CSS 3.0
  10. Google Wave?
  11. iPhone Development


I’m sure there are many more things I could add to these lists.

Whilst I do have some experience with a lot of things on this list – it’s becoming harder for me to refer to myself as an “expert”, or even “well versed” in some of these emerging, and in some cases established technologies.

It’s starting to become scary.

So – I guess the motivation of this article was simply to ask if anyone else is starting to feel things are moving a little faster than they did, well, only a few years ago – and more importantly to ask how you go about choosing the technologies you are going to explore, and to master.

Wish me luck.

kick it on DotNetKicks.com



Construct a comma delimited list from table column with SQL

clock January 15, 2009 15:44 by author Magz

How many times have you had to create a comma delimited list from a table column? Do you ever remember how to do it? I don’t. Here is a little snippet I find useful:

-- this will be a comma delimited list of location ids
DECLARE @LocationIds Varchar(Max)
-- set it to an empty string to start with
SET @LocationIds = ''
 
--add commas 
SELECT @LocationIds = COALESCE(@LocationIds + ',','') + CAST(Location_ID AS VARCHAR) FROM Locations_Table
--get rid of the comma at the front of the string
SELECT SUBSTRING(@LocationIds, 2, Len(@LocationIds))



Result: 1234,3445,6778,6789,…

kick it on DotNetKicks.com



RegEx Multiple Matches with Lookahead Assertion

clock November 27, 2008 09:41 by author Magz

This is a quick article where I would like to show how to use regular expression to get all matches of a particular pattern from the string.

Example of a string:

string strHTML = "<span>key1<span>value1
                  <span>key2</span>value2
                  <span>key3</span>value3";


To get the list of key-value pairs we need to parse the above string and return a list of matches, where each match will contain key in Group[1].Value and value in Group[2].Value. The first part of the pattern is clear: (.+?)(.+?) but the tricky bit is to know how to define an end match condition. Here I suggest to use an operator (?=exp) that will match any position preceding a suffix exp, in our case we want to stop the match if we find another occurrence of tag or reach the end of the string ($)

MatchCollection mc = Regex.Matches(strHTML, @"<span>(.+?)</span>(.+?)(?=(<span>|$))");
foreach(Match m in mc)
   Response.Write(m.Groups[1].Value + " " + m.Groups[2].Value + "</br>");

Result:
key1 value1
key2 value2
key3 value3

What will happen if you don’t include (?=exp) operator? You will lose the middle pair and the result will be:

key1 value1
key3 value3

kick it on DotNetKicks.com



SQL: Find last week date range

clock November 24, 2008 08:59 by author Magz

The other day we needed to write a report on online sales for the last week. SQL doesn’t offer developers many predefined functions to work with date ranges unlike the C# programming language. Here is a little example how to query SQL for some data between the dates for the last week.

By default the first day of the week is set to Sunday (default value 7), so if you need it to be Monday run the following command:

SET DATEFIRST 1

SQL Last Week Date Range

DECLARE @TodayDayOfWeek INT
DECLARE @EndOfPrevWeek DateTime
DECLARE @StartOfPrevWeek DateTime
 
--get number of a current day (1-Monday, 2-Tuesday... 7-Sunday)
SET @TodayDayOfWeek = datepart(dw, GetDate())
--get the last day of the previous week (last Sunday)
SET @EndOfPrevWeek = DATEADD(dd, -@TodayDayOfWeek, GetDate())
--get the first day of the previous week (the Monday before last)
SET @StartOfPrevWeek = DATEADD(dd, -(@TodayDayOfWeek+6), GetDate())


Now we can use above expressions in our query:

SELECT …. FROMWHERE Sale_Date BETWEEN 
CONVERT(VARCHAR, @StartOfPrevWeek,7)
AND
CONVERT(VARCHAR, @EndOfPrevWeek+1,7)


Note that we had to convert dates in order to reset minutes/hours/seconds to 00:00:00, but it also means that if we want to include the whole Sunday into our week report we need to set the dates BETWEEN Monday AND Monday 00:00:00.

kick it on DotNetKicks.com



ListBox Extension Method for Get and Set Selected Values

clock August 11, 2008 11:01 by author Magz

ASP.Net ListBox control allows two types of selection mode: single and multiple. Working in single selection mode is similar to working with DropDown list control. Use ListBox.SelectedValue to get the value that was selected by a user. In order to set a selection SelectedIndex property can be used or Selected property of a particular item should be set to true.

Example:

string selectedValue = MyListBox.SelectedValue; //get selected value
        
MyListBox.SelectedIndex = 0; //set the first item to  be selected
MyListBox.Items.FindByValue("val2").Selected = true; //select the item with value="val2"


However when using ListBox with SelectionMode="Multiple" ListBox.SelectedValue will return only the first selected item, not all of them. The code below shows how to create a simple extension method for a ListBox that will allow to get and set multiple selected items.

public static class ListBoxExtensions
{
    //return ArrayList of selected values
    public static ArrayList SelectedValues(this ListBox lbox)
    {
        ArrayList selectedValues = new ArrayList();
 
        int[] selectedIndeces = lbox.GetSelectedIndices();
        foreach (int i in selectedIndeces)
           selectedValues.Add(lbox.Items[i].Value);
        return selectedValues;
    }
    
    /// <summary>
    /// Select multiple items in a ListBox
    /// </summary>
    /// <param name="values">Values of the items that need to appear selected</param>
    public static void SelectedValues(this ListBox lbox, string[] values)
    {
        foreach (string value in values)
        {
            ListItem item = lbox.Items.FindByValue(value);
            if (item != null)
                item.Selected = true;
        }        
    }
}


Example:

<asp:ListBox ID="MyListBox" runat="server" SelectionMode="Multiple">
        <asp:ListItem Text="ItemText1" Value="val1"></asp:ListItem>
        <asp:ListItem Text="ItemText2" Value="val2"></asp:ListItem>
        <asp:ListItem Text="ItemText3" Value="val3"></asp:ListItem>
        <asp:ListItem Text="ItemText4" Value="val4"></asp:ListItem>
        <asp:ListItem Text="ItemText5" Value="val5"></asp:ListItem>
</asp:ListBox>    


List Box Example
To set items to be selected use

MyListBox.SelectedValues(new string[] {"val1", "val3"});


To get selected values call

ArrayList selectedValues = MyListBox.SelectedValues();


kick it on DotNetKicks.com



BlogEngine Flaws

clock July 27, 2008 21:46 by author Naz

Get Blog Engine I'm part of the small open source team for dashCommerce an .NET shopping cart system so please don't get me wrong this article isn't about dissing the hard work and time developers have put into BlogEngine it is just to highlight some of the the design flaws I've encountered which we should help to improve on in future versions. I will still continue to use blogengine as it's still the best out there but it can be better...

This site is currently distributed across multiple web servers sometimes referred to as “Cloud Hosting”. Many large popular websites work of this kind of architecture to keep up with demand of resources required to process user requests. I’ve read somewhere Facebook currently has around 200 distributed web servers for hosting their site at various parts of the world.

BlogEngine runs of a singleton caching model where it caches posts and comments into an static object and then reads and writes that object to either an XML or Database when required. A common problem with this design is each server does not have direct access to the in memory object. Due to this when a comment is posted on server 1 gets saved to database, server 2 doesn't know that there has been change so you wont see the update until server 2 updates itself. However there are some work-rounds the simplest is just using the standard .NET caching model instead of singleton caching as you can specify an expiration times and also set-up things like cache dependency enabling your servers can get back to sync.

Recently I’ve been having problems as the site has gotten more popular I’ve had comments and even posts disappearing randomly, sometimes re-appearing you might have experienced this yourself either on my site or in your own so after divulging into the code to see what was happening found something I thought was shocking. When you add a comment, or Rating, Approving and Remove Comments this is what BlogEngine DbBlogProvider actually does...

  1. UPDATE The post
  2. DELETE All Tags for that post
  3. INSERT All Tags for that post
  4. DELETE All Posts Categories
  5. INSERT All Posts Categories
  6. DELETE All existing comments for that post
  7. INSERT All comments back in including the new comment
  8. DELETE All post notifications
  9. INSERT All post notifications


Remember all this when all it needed to do is INSERT into Comments table the new Comment!

From what I can see (I could be wrong) it is doing it without an SqlTransaction so if something where to go wrong it wont rollback changes. This can also cause concurrancy issues say if two people are adding comments at the same time i'm not sure if it will lock it. So instead of just getting delayed updates my web servers are actually in constant battle with each other overwriting each others changes when they save content every time someone post's a comment or rates an article.

I hacked a workaround so Add Comment just does what it needs to by adding new Abstract Methods to BlogProvider but this meant I had to write the same methods for XMLProvider but XML's and relational databases are completely different so I just stubbed them out.

I hope the developers take note about this for future versions there might have been a reason for this the only thing I can think of is they tried to reduce the number of methods a BlogProvider requires.

kick it on DotNetKicks.com



Web developers. You suck.

clock July 15, 2008 16:54 by author DaveTheKnave

Well, JavaScript developers, specifically.

In order to aid in development of my own websites, I enabled JavaScript debugging in Internet Explorer a few weeks back.

To my horror, I have quickly experienced what seems to be complete disregard for serving syntactically correct JavaScript on the open internet.

No, I’m not just talking about a few niche websites, run by amateur programmers. I am talking about industry-leading nerd-friendly powerhouse websites that should know better.

To list a few examples of websites coated with syntax errors (at the time of writing):

  1. http://slashdot.org/. Slashdot for god’s sake!! On the homepage!
  2. http://digg.com/. Try posting a new dig article with a thumbnail.
  3. http://www.computerworld.com/ come on.
  4. http://www.somethingawful.com/
  5. http://www.pcmag.com/
  6. http://www.washingtonpost.com


The list really does go on. With script debugging enabled, the internet becomes an almost unusable, frustrating place. Especially if you couple this with a delightful bug in Internet Explorer, that causes it to freeze if two of your open and loading tabs both have a modal JavaScript error box waiting for a response.

Anyone who writes production JavaScript should always have script debugging enabled. If not just to help catch your own mistakes - but also to see how infuriating it can be to simply use the internet while being forced to close millions of error dialogs.
This alone should convince you to write better JavaScript.

To enable script debugging:

Tools/Internet Options/Advanced/ - Un-check "Disable Script Debugging"



When disabled, this will cause a small error box to show if there is a syntax (or execution) error in any JavaScript code.


Slashdot: 15 July 2008

If you wish, you can click the “Debug” option, and this will offer you the option of opening visual studio, letting you step through the broken code.

I’m sure you’ll all agree that correct JavaScript should not be a lofty goal to aim for.

Dave

kick it on DotNetKicks.com



Get Checked Repeater Items Extension Method

clock June 16, 2008 17:24 by author Magz

Imagine you have a list of some items and checkboxes next to each item providing the ability for a user to make multiple choices and submit a result in one go. Weather you are implementing a news groups subscription, user survey or online products catalogue - the code behind is the same: we bind some object list to a data control like Repeater, add a checkbox to every item, set checkbox value to item ID.

Here is an example with list of books available for order

Repeater with checkboxes

<table>
    <asp:Repeater ID="rptBooks" runat="server"> 
        <ItemTemplate>
            <tr>     
                <td><input type="checkbox" runat="server" value='<%# Eval("BookID")%>' ID="chkBox" /></td>
                <td><%# Eval("Title")%></td>
                <td><%# Eval("Author")%> </td>
            </tr>
        </ItemTemplate>  
    </asp:Repeater>
</table>
<asp:Button ID="btnOrder" OnClick="btnOrder_Click" runat="server" Text="Order" />


When “Order” button is clicked we need get all selected book IDs (we store them in a value field of each checkbox). I suggest that we create an extension method that will do all the work and when we need to get selected items in any repeater in our code we will have to call only one method GetSelectedItems

public static class RepeaterExt
{
    /// <summary>
    /// Returns selected items array list in a repeater rpt
    /// </summary>
    /// <param name="chkBoxId">ID of a checkbox used in repeater to store the value of each item</param>
    public static ArrayList GetSelectedItems(this Repeater rpt, string chkBoxId)
    {
        var selectedValues = new ArrayList();
        for (int i = 0; i < rpt.Items.Count; i++)
        {
            var chkBox = rpt.Items[i].FindControl(chkBoxId) as HtmlInputCheckBox;
 
            if (chkBox != null && chkBox.Checked)
                selectedValues.Add(chkBox.Value);
        }
        return selectedValues;
    }
}


Now if we go back to our page with books catalog we can right the following:

protected void btnOrder_Click(object sender, EventArgs e)
{

using extenstion method to get checked items
selectedValues array will contain BookIDs that were ordered and you can store them in the database or process as required by your code.

Note that this example assumes that you need to use <input runat=”server”…  to be able to pre-polulate checked values or keep the state of the checkboxes after the postback. If none of this functionality is needed, the simplest way to get selected values is to use standard html

<input type="checkbox" value='<%# Eval("BookID")%>' name="chkBox" />


When the “Order” button is clicked Request["chkBox"] will return comma delimited list of selected BookIDs.

kick it on DotNetKicks.com



enum to friendly string extension method

clock June 3, 2008 12:05 by author Naz

We use enums quite extensively in our application as they are great for representing integral values in a strongly typed way using symbolic names eg.

if (Status == UserStatus.NotLoggedInAYear)
    ArchiveRecord();


is a lot more clearer and meaningful making it easier to maintain than

if (Status == 3)
    ArchiveRecord()


The enum names are not very friendly to the user and I recently read a some good articles creating user friendly strings for enum values and Enum description values which tried to solve this problem.

I think i've found a better solution to this problem using extension methods.

public enum RemovalType
{
    None,
    ManAndVan,
    FullRemoval,
    FullRemovalsAndPacking
}
 
public static class RemovalTypeEnum
{
    /// <summary>
    /// Returns a friendly enum name
    /// </summary>
    public static string ToFriendlyString(this RemovalType removalType)
    {
        switch (removalType)
        {
            case RemovalType.ManAndVan:
                return "Man & Van Service";
            case RemovalType.FullRemoval:
                return "Standerd removals service";
            case RemovalType.FullRemovalsAndPacking:
                return "Full removals and packing service";
            default:
                return removalType.ToString();
        }
    }
}

 

RemovalType removalType = RemovalType.ManAndVan;
removalType.ToFriendlyString()


This implementation creates an extension method on the actual enum "RemovalType" which then allows you to call a ToFriendlyString() on the instance of all enums of that type I think this a more fluid implementation and also means better performance compared to the other implementations as it doesn't need to use reflection.

You will notive i've decided to leave the default return value to call ToString() on the enum value which means you only need to implement the values that need to be made friendlier.

You can also call it easily inside databinded controls in the aspx page.

<%# ((RemovalType)Eval("ServiceType")).ToFriendlyString() %>



kick it on DotNetKicks.com



TextBox


RecentComments

Comment RSS

Sign in