XML Literals - (VB.NET only)

After I learned about lambda statements that they are supported only in C# 3.5 and not in VB.NET 9.0, I got curious and thought why not to find something that is available only for VB.NET and not for C#, and found this interesting thing which is called XML Literals. Using this nice features which is a part of LINQ to XML API, we can embed XML directly within Visual Basic 9.0 code.

To illustrate its power let's have a look at the below XML that we will produce using XML Literal.


<books>
<book>
<title>LINQ IN ACTION</title>
<author>FABRICE MARGUERIE</author>
<author>STEVE EICHERT</author>
<author>JIM WOOLEY</author>
<publisher>Manning</publisher>
</book>
</books>

now take a look at Listing 1.1 below, which shows the code for creating the XML using the XML literal syntax offered by VB9.

Listing 1.1

Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load

Dim booksElement As XElement = <books>
<book>
<title>LINQ IN ACTION</title>
<author>FABRICE MARGUERIE</author>
<author>STEVE EICHERT</author>
<author>JIM WOOLEY</author>
<publisher>Manning</publisher>
</book>
</books>
End Sub

Note that in the above code we are using XElement which is a new class introduced in .NET 3.5 which represents an XML element. According to MSDN:
"XElement can be used to create elements; change the content of the element; add, change, or delete child elements; add attributes to an element; or serialize the contents of an element in text form"
The XML fragment in listing 1.1 above is static. When building real applications we might need to create XML using expressions stored in a set of local variables. XML Literal allows us to do so through expression holes which is expressed with the .

Listing 1.2

Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load

Dim xml = LoadXML("LINQ IN ACTION", "Manning", "FABRICE MARGUERIE", "STEVE EICHERT", "JIM WOOLEY")

End Sub

Private Sub LoadXML(ByVal title As String, ByVal publisher As String, ByVal ParamArray authours() As String)

Dim booksElement As XElement = <books>
<book>
<title><%= title %></title>
<author><%= authours(0) %></author>
<author><%= authours(1) %></author>
<author><%= authours(2) %></author>
<publisher><%= publisher %></publisher>
</book>
</books>

End Sub

XML Literals allows us to embed XML directly within the code without having to learn the details of XML API. It's a great addition to VB9.0 and hope that it will get added to C# as well in future.



HTH,

From Delegates to Lambda Expressions

Delegates:

Delegate was a wonderful addition to .NET 1.1 in early 2000. It is a type that can store a pointer to a function. The below snippet shows the way we would use delegates in our everyday programming.
Listing 1.1

delegate DataTable GetUserDetailsDelegate(int userID);

class Program
{
static void Main(string[] args)
{
GetUserDetailsDelegate GetUserDetails = new GetUserDetailsDelegate(GetUserDetailsByUserID);
DataTable dt = GetUserDetails(1);
}

private DataTable GetUserDetailsByUserID(int userID)
{
return new DataTable();
}
}

Anonymous Methods

C#2.0 was improved to allow working with delegates through anonymous methods. I said C#, because VB.NET doesn’t offer support for anonymous methods. These anonymous methods allow us to write shorter code and avoid the need for explicitly named methods. Let's modify the code in Listing1.1 and re-write it using anonymous methods.
Listing 1.2
delegate DataTable GetUserDetailsDelegate(int userID);

class Program
{
static void Main(string[] args)
{
GetUserDetailsDelegate GetUserDetails = delegate(int userID) { return new DataTable(); };
var dt = GetUserDetails(1);
}

Lambda Expressions

Now, Starting with C# 3.0, instead of anonymous methods we can use lambda expressions.
Listing 1.3
C#
var GetUserDetails = userID => { return new DataTable(); };
var dt = GetUserDetails(1);
VB.NET
Dim GetUserDetails = Function(x) New DataTable()
Dim dt = GetUserDetails(1)

The anonymous method introduced in C#2.0 is verbose and imperative in nature. In contrast, lambda expressions provide a more concise syntax, providing much of the expressive power of functional programming languages. It is a superset of anonymous methods with additional functionalities like inferring types, using both statement blocks and expression as bodies etc.

Note that, In the above lambda expression left hand side variable is of anonymous type. Anonymous type is a new language enhancement that enable us to declare types without names. If you are concerned about their limitations and don't want to use them then you can use Func<T, TResult> generic delegate in lieu of anonymous types.

Listing 1.4
C#
Func<int,DataTable> GetUserDetails = userID => { return new DataTable(); };
var dt = GetUserDetails(1);
VB.NET

Dim GetUserDetails As Func(Of Integer, DataTable) = Function(x) New DataTable
Dim dt = GetUserDetails(1)



HTH,

Server.URLEncode an Encrypted String - do it twice my friend!!

Query string is a very important part of a web application which needs to be prevented from being sniffed or changed when it carries sensitive data. We do not have a magic wand that upon waving will hide the sensitive portion of the query string across multiple requests, but we do have powerful encryption algorithms that come as a rescue and encrypt everything which turns out to look like a toddler's handwriting. And, if it contains characters that are prohibited in a query string e.g. ('+','?',':','&','/','='), then we can encode it using Server.URLEncoding API which comes as part of .NET class library.

var encryptedString = CommonUtils.Encrypt("clientid=1980&code=alphabravo", lKey);
var encodedEncrypted = Server.URLEncode(encryptedString);

In the above code, CommonUtils is my homegrown encryption utility (symmetric key encryption) that takes lKey to encrypt/decrypt large quantities of data. But wait, I notice it's throwing an exception on the receiving side and not showing my properly URLEncoded query string that i generated while sending. Why o why!!

After a small research I found that I need to do Server.URLEncoding twice but not just once before sending it out. By just doing it once, I witnessed that all my URL encoded characters for ('+') were getting lost somehow. Anyways, the final correct sequence that I have come to know about encoding an encrypted string and decoding it is this:
  1. Encrypt it
  2. Encode it twice
  3. Decode it once
  4. Decrypt it
Happy coding!!

LINQ to SQL - Multiple result shapes

Working with LINQ to SQL, you might come across a situation where your stored procedure looks something like this:

CREATE PROCEDURE [dbo].[GetAllProductsAndCustomers]
@CompanyID INT
AS
SELECT [Code, Category] FROM Products
SELECT [Name, Email,Contact] FROM Customers

This SP returns multiple result sets which LINQ supports quite efficiently. However, If you work with auto-generated object relational mapper (*.dbml), you must have noticed that CLR cannot automatically determine which stored procedure returns multiple result shapes, hence creates a wrapper function with ISingleResult as a return type, which represents the result of a mapped function that has a single return sequence. For the above SP, it generated the below method signature:

<FunctionAttribute(Name:="GetAllProductsAndCustomers")> _
Public Function GetAllProductsAndCustomers(<Parameter(Name:="CompanyID", DbType:="Int")> ByVal CompanyID As System.Nullable(Of Integer)) As ISingleResult(Of GetAllProductsAndCustomersResult)
Dim result As IExecuteResult = Me.ExecuteMethodCall(Me, CType(MethodInfo.GetCurrentMethod,MethodInfo), companyID)
Return CType(result.ReturnValue,ISingleResult(Of GetAllProductsAndCustomersResult))
End Function

In order to turn this situation into our favor and handle multiple result shapes returned by the stored proc, all we need to do is replace the ISingleResult with IMultipleResults and supply the appropriate result types. If in case there is no specific result type, which is quite possible if stored proc is generating columns from multiple tables as a result of join, you can provide any names and LINQ will treat them as anonymous types. In the method signature below, I have created two classes GetAllProductsAndCustomersResult1 and GetAllProductsAndCustomersResult2 along with the properties Code and Category in the first and Name, Email, Contact in the second class.

One important thing, for the kind of SP we are using we need to read the result shapes in the same sequence as the SP returns the results. The order of IMultipleResults.GetResult() should be same as the order of SELECT statements in SP in order to avoid getting unexpected results or errors and exceptions if our IEnumerable result set is bound to a data source control.

The modified method signature will look like:

<FunctionAttribute(Name:="GetAllProductsAndCustomers"), _
ResultType(GetType(GetAllProductsAndCustomersResult1)), _
ResultType(GetType(GetAllProductsAndCustomersResult2))> _
Public Function GetAllProductsAndCustomers(<Parameter(Name:="DataBridgeQueueID", DbType:="Int")> ByVal companyID As System.Nullable(Of Integer)) As IMultipleResults
Dim result As IExecuteResult = Me.ExecuteMethodCall(Me, CType(MethodInfo.GetCurrentMethod,MethodInfo), companyID)
Return CType(result.ReturnValue,IMultipleResults)
End Function

HTH,