Get SqlDataSource To Retrieve DefaultValue of Current User (ExpressionBuilder with ASP.NET 2.0)

Posted by Peter Kellner on September 18, 2006 · 6 mins read

Abstract

This article shows how to use Expression Builders in ASP.NET 2.0 to retrieve the current logged in user. DataBinding will not work so Expression Builders is the ticket. A small source file is created, the references to web.config are shown and a simple example is built.

The Problem

I recently was looking at unanswered posts in the asp.net forum, specifically this one: http://forums.asp.net/thread/1402259.aspx. I thought I
understood how databinding and expressions worked, but just wanted to check myself. So, I made a simple example
web page just like the post shows. (see below)

<%@ Page Language=”C#” AutoEventWireup=”true” CodeFile=”Default.aspx.cs” Inherits=”_Default” %>
<!DOCTYPE html PUBLIC-//W3C//DTD XHTML 1.0 Transitional//EN” “http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd>
<html xmlns=”http://www.w3.org/1999/xhtml>
<head id=”Head1? runat=”server>
    <title>Untitled Page</title>
</head>
<body>
    <form id=”form1? runat=”server>
        <div>
            <asp:GridView ID=”GridView1? runat=”serverAutoGenerateColumns=”FalseDataSourceID=”SqlDataSource1?>
                <Columns>
                    <asp:BoundField DataField=”UsernameHeaderText=”UsernameSortExpression=”Username/>
                </Columns>
            </asp:GridView>
            <asp:SqlDataSource ID=”SqlDataSource1? runat=”serverConnectionString=”&lt;%$ ConnectionStrings:CodeCampSV06 %&gt;“
                SelectCommand=”SELECT [Username], [Email] FROM [Attendees] WHERE ([Username] = @Username)”>
                <SelectParameters>
                    <asp:Parameter Name=”UsernameType=”StringDefaultValue=”&lt;% User.Identity.Name %&gt;“  />
                </SelectParameters>
            </asp:SqlDataSource>
        </div>
    </form>
</body>
</html>

Then, I ran it through Lutz Roeder's .NET Reflector and got the following from the code.


private Parameter __BuildControl__control6()
{
    Parameter parameter1 = new Parameter();
    parameter1.Name = “Username”;
    parameter1.Type = TypeCode.String;
    parameter1.DefaultValue = “<% User.Identity.Name %>”;
    return parameter1;
}

It's pretty obvious that unless there is a username of the literal string "<% User.Identity.Name %>" no records will be find. This simply means that the build provider asp.net uses is not generating any code for us with sqldatasource that will help with the DefaultValue of parameters in a SqlDataSource.

The Solution

Expression Builder to the rescue!

To solve the problem, we need to build a simple expression builder. Without going into all the details of what an expression builder is, all you need to do is put the following code in your app_code directory and call it something like ExpressionBuilderIdentity.cs.

using System;
using System.Data;
using System.Configuration;
using System.Web;
using System.Web.Security;
using System.Web.UI;
using System.Web.UI.WebControls;
using System.Web.UI.WebControls.WebParts;
using System.Web.UI.HtmlControls;
using System.Web.Compilation;
using System.CodeDom;
 
public class ExpressionBuilderIdentity : ExpressionBuilder
{
    public override System.CodeDom.CodeExpression GetCodeExpression(
        BoundPropertyEntry entry, object parsedData, ExpressionBuilderContext context)
    {
        CodeTypeReferenceExpression targetClass =
            new CodeTypeReferenceExpression(typeof(ExpressionBuilderIdentity));
        string targetMethod = “GetIdentity”;
        CodeExpression methodParameter =
            new CodePrimitiveExpression(entry.Expression.Trim());
        return new CodeMethodInvokeExpression(
            targetClass, targetMethod, methodParameter);
    }
 
    public static object GetIdentity(string param)
    {
        string returnString = string.Empty;
 
        if (param.ToLower().Equals(“name”))
        {
            returnString = HttpContext.Current.User.Identity.Name;
        }
 
        return returnString;
    }
}

Then, you need to add a reference to it in your web.config as follows:

<compilation debug=“true>
      <expressionBuilders>
        <add expressionPrefix=“UserIdentitytype=“ExpressionBuilderIdentity, __code/>
      </expressionBuilders>

Then, specify the SqlDataSource as follows:

<asp:SqlDataSource ID=”SqlDataSource1runat=”serverConnectionString=”&lt;%$ ConnectionStrings:CodeCampSV06 %&gt;“ SelectCommand=”SELECT [Username], [Email] FROM [Attendees] WHERE ([Username] = @Username)”>
            <SelectParameters>
                <asp:Parameter Name=”UsernameType=”StringDefaultValue=”&lt;%$ UserIdentity:name %&gt;“ />
            </SelectParameters>
        </asp:SqlDataSource>

And, Presto, it works!

Summary

Anytime you are using one of the new datasourceID controls, you need to use expressions rather than databinding if you want to reference outside variables. Creating the code is fairly straight forward and lends itself to lots of cool possibilities.