Welcome

You have reached the blog of Keith Elder. Thank you for visiting! Feel free to click the twitter icon to the right and follow me on twitter.

CodeMash: Scott Guthrie Keynote on LINQ

Posted by Keith Elder | Posted in Asp.Net, Programming | Posted on 19-01-2007

0

Scott Guthrie opened up CodeMash day 2 today with the keynote this morning and covered LINQ (Language Integrated Query).   I first saw LINQ over a year ago and it is just as exciting today to see it again as it was then.

 

I’m sitting at a table with some of my fellow team members and other conference attendees.  Most of them haven’t seen a LINQ demo and it was interesting to watch their reactions to LINQ for the first time.  As Scott showed different examples you could tell he had their attention as their heads turned around to each other nodding with approval.  Since we only had an hour the time went by fast and I was left wanting more LINQ goodness.  If you haven’t seen LINQ in action, check out this screen shot.

 

Take Securing Web Services With Username and Password One Step Further With a Custom SoapExtension

Posted by Keith Elder | Posted in Asp.Net, Programming | Posted on 09-01-2007

22

In a previous posts I showed how to secure your web services with a username and a password.  One of the readers added a comment and mentioned using an extension to provide authentication so I thought I would expand on how that is done.  If you haven’t read the previous posts do that first, then pickup with this.  And before we get started, thanks for the idea Kevin!

Have you ever wanted to intercept a web service method because you wanted to maybe log it or even as we are about to do authenticate a user?  Did you know you can intercept any incoming SoapMessage that is sent to your web service?  This is all possible because of the SoapExtension class in .Net. Not only can you intercept the incoming message but you can do it within one of four stages:

  1. AfterDeserialize
  2. AfterSerialize
  3. BeforeDeserialize
  4. BeforeSerialize

This allows us a lot of flexibility obviously.  In our example we are going to work with the AfterDeserialize stage which is after the message has been sent across the wire and serialized into a SoapMessage object.  Since we will have a full blown SoapMessage object, we can inspect the headers of the SoapMessage and take care of authentication then.  Our end goal with taking this approach is to allow us to authenticate a user with a WebMethod simply by adding an authentication attribute to the WebMethod like this highlighted in bold.

    1     [WebMethod]

    2     [SoapHeader(“CustomSoapHeader”)]

    3     [AuthenticatonSoapExtensionAttribute] (magic here)

    4     public int AddTwoNumbers(int x, int y)

    5     {

    6         return x + y;

    7     }

You’ll notice in this example we do not have to remember to call the code to authenticate the user manually as we saw in the previous article.  Instead by adding the attribute to the method it knows to call the authentication method.  To do this we need to first create a custom object that extends SoapExtensionAttribute and then another that extends SoapExtension.

Create a Custom SoapExtensionAttribute

In order to have the method call our custom SoapExtension we need to create an object that extends SoapExtensionAttribute.  It is a farily simple class with two overridden properties.  Here’s the code:

    1     [AttributeUsage(AttributeTargets.Method)]

    2     public class AuthenticatonSoapExtensionAttribute : SoapExtensionAttribute

    3     {

    4         private int _priority;

    5 

    6         public override int Priority

    7         {  

    8             get { return _priority; }

    9             set { _priority = value; }

   10         }

   11 

   12         public override Type ExtensionType

   13         {

   14             get { return typeof(AuthenticatonSoapExtension); }

   15         }

   16     }

You’ll notice about the only thing of real substance is the Extension type property which simply returns to us our custom extension.

Create a Custom SoapExtension

The last piece to pull this all together is a custom class which extends the SoapExtension class.  In this class we are going to write the code that does the actual authentication.  We are going to check for the AfterDeserialize stage and then first make sure we have a valid SoapHeader.   Once we do that we are going to call the static validation method and pass in the SoapHeader as we did above. 

    1 /// <summary>

    2     /// Custom SoapExtension that authenticates the method being called.

    3     /// </summary>

    4     public class AuthenticatonSoapExtension : SoapExtension

    5     {

    6 

    7         /// <summary>

    8         /// When overridden in a derived class, allows a SOAP extension to initialize data specific to an XML Web service method using an attribute applied to the XML Web service method at a one time performance cost.

    9         /// </summary>

   10         /// <param name=”methodInfo”></param>

   11         /// <param name=”attrib”></param>

   12         public override object GetInitializer(LogicalMethodInfo methodInfo, SoapExtensionAttribute attrib)

   13         {

   14             return null;

   15         }

   16 

   17         /// <summary>

   18         /// When overridden in a derived class, allows a SOAP extension to initialize data specific to a class implementing an XML Web service at a one time performance cost.

   19         /// </summary>

   20         /// <param name=”WebServiceType”></param>

   21         public override object GetInitializer(Type WebServiceType)

   22         {

   23             return null;

   24         }

   25 

   26         /// <summary>

   27         /// When overridden in a derived class, allows a SOAP extension to initialize itself using the data cached in the GetInitializer method.

   28         /// </summary>

   29         /// <param name=”initializer”></param>

   30         public override void Initialize(object initializer)

   31         {

   32 

   33         }

   34 

   35         /// <summary>

   36         /// After the message is deserialized we authenticate it.

   37         /// </summary>

   38         /// <param name=”message”></param>

   39         public override void ProcessMessage(SoapMessage message)

   40         {

   41            

   42             if (message.Stage == SoapMessageStage.AfterDeserialize)

   43             {

   44                 Authenticate(message);

   45             }

   46         }

   47 

   48         public void Authenticate(SoapMessage message)

   49         {

   50             ServiceAuthHeader header = message.Headers[0] as ServiceAuthHeader;

   51             if (header != null)

   52             {

   53                 ServiceAuthHeaderValidation.Validate(header);

   54             }

   55             else

   56             {

   57                 throw new ArgumentNullException(“No ServiceAuthHeader was specified in SoapMessage.”);

   58             }

   59         }

   60     }

The method that we are really concerned with is the ProcessMessage which checks for the stage and then calls the Authenticate method.  This in turn calls our static validation method which checks for authentication.  At this point light bulbs should be going off!   Since we have a SoapMessage object do we not know which method is being called?  Yes!  Could we modify the ServiceAuthHeaderValidation to check for a database instead of hard coding things?  Yes!  Now you are starting to see where this could really go.   SoapExtensions are powerful and only limited to your imagination. 

When I Test It, It Doesn’t Work, Why?

Once you get your SoapExtension in your solution setup and press F5 to debug it within Visual Studio  it will launch a new web server on a random port and bring you to your service.  You enter the parameters and submit the form and it by passes your validation.  Why!? 

This is suppose to happen and here is why. If you go to the service invoked from VS through the browser interface it will not invoke the authentication and it isn’t suppose to either. The reason is you are not invoking the service via SOAP but rather just a standard POST from a form. Therefore, the SOAP extension is never going to fire. This should be disabled when you publish your web service to production as only SOAP messages should be allowed. If you have a case where you need to allow GET and POST calls then the method of a custom SoapExtension isn’t going to work. Go back to the previous way outlined that I talked about.

As a benefit, Visual Studio builds the form for you automatically when you press F5 and allows you to pass parameters to the web method, but it does it via POST. If you invoke the web method from a console application or a real client making a SOAP call, you have to pass in the username and password.  I actually consider this behavior a feature.  If we didn’t use the SoapExtension to secure the method, we’d be forced to pass in username and password all the time which would mean we’d have to always call the secured web method from a test client.   Speaking from experience this isn’t fun.  Of course you should have Unit Tests for each web method anyway but it is really easy to pass in the params to a web form while debugging.

I hope you find this useful and now don’t feel so daunted because your team leader asked you how you were going to authenticate web service methods via a database.  The only thing left is for you to implement your required features.  Of course, if you are on an Intranet, instead of using username and password as we did in the previous post you could at the point of Authenticate(SoapMessage message) use the user’s integrated credentials and check for various groups in Active Directory or even using Enterprise Library Security Block. 

Like this article?  Then kick it on DotNetKicks.com

Securing Web Services With Username and Password

Posted by Keith Elder | Posted in .Net, Asp.Net, Programming | Posted on 06-01-2007

32

I was going through my news feeds this morning and stumbled across this article about securing web services.  The article is short and doesn’t give any examples of one of the methods I use a lot.  I thought I would elaborate on one of the topics it touches on which is securing a web service with a Username and a Password.  While there are other ways to secure web services I find this particular method works really well when dealing with internal systems that may not speak .Net.  It is also simple to implement on both sides.  These systems could be in Java, PHP or even 4GL.  If you are a .Net developer and want to secure a web service with a username, password, or even other information, here is what you need to get going.

1.  Create an object that extends SoapHeader

The first thing you need to do is create an object that extends the built-in SoapHeader object.   The object can be simple or complex. Add the tokens you want to authenticate against.  Here is a sample:

    1 /// <summary>

    2 /// Extends from SoapHeader and provides a username / password

    3 /// for web methods that need authentication.

    4 /// </summary>

    5 public class ServiceAuthHeader : SoapHeader

    6 {

    7     public string Username;

    8     public string Password;

    9 }

2.  Add a property to your service class that uses the class above

Once you’ve created your base soap header class, add it as a property to your service class.

    // SoapHeader for authentication

    public ServiceAuthHeader CustomSoapHeader;

3.  Attribute the method you want to secure

Add the SoapHeader attribute to each or certain methods you wish to secure pass in the name of the property that is defined as the SoapHeader object in step 2.

    1     [WebMethod]

    2     [SoapHeader(“CustomSoapHeader”)]

    3     public int AddTwoNumbers(int x, int y)

    4     {

    5        

    6         return x + y;

    7     }

4.  Create a method to process your SoapHeader for authentication

The last big step is to create a static method that will take in your custom soap header class and process it for validation.  The first thing we want to do is make sure that some type of credentials were passed in the SoapHeader and that the properties we are looking for are not null.  Finally we want to validate each property contains the information we are looking for. This could be read from the web.config file, database, or other places.

 

    1 public class ServiceAuthHeaderValidation

    2 {

    3     /// <summary>

    4     /// Validates the credentials of the soap header.

    5     /// </summary>

    6     /// <returns></returns>

    7     public static bool Validate(ServiceAuthHeader soapHeader)

    8     {

    9         if (soapHeader == null)

   10         {

   11             throw new NullReferenceException(“No soap header was specified.”);

   12         }

   13         if (soapHeader.Username == null)

   14         {

   15             throw new NullReferenceException(“Username was not supplied for authentication in SoapHeader.”);

   16         }

   17         if (soapHeader.Password == null)

   18         {

   19             throw new NullReferenceException(“Password was not supplied for authentication in SoapHeader.”);

   20         }

   21 

   22         if (soapHeader.Username != “myusername” || soapHeader.Password != “mypassword”)

   23         {

   24             throw new Exception(“Please pass the proper username and password for this service.”);

   25         }

   26         return true;

   27     }

   28 }

5.  Add validation to service method

 

    1     [WebMethod]

    2     [SoapHeader(“CustomSoapHeader”)]

    3     public int AddTwoNumbers(int x, int y)

    4     {

    5         // Test to see if the proper credentials were passed in.

    6         ServiceAuthHeaderValidation.Validate(CustomSoapHeader);

    7 

    8         // If we get this far the user has been validated.

    9         return x + y;

   10     }

 

That’s it. You now have all the pieces of the puzzle to process a request and validate the credentials of the calling client via a username and or password.  If we launch the solution we will see that our XML for our service has been updated and now contains an XML Node called ServiceAuthHeader which contains two sub nodes: username, password.

Passing SoapHeader Credentials To Your Service

Now that we have our service secured, we need to now call the service and pass the credentials expected from a client.  Based on the example above, once you add a web reference to the service and instantiate the service in code, the thing you want to look for is a new property of your service proxy called ServiceAuthHeader. This is converted into a property called ServiceAuthHeaderValue.  This property needs to be an instantiation of the ServiceAuthHeader class where you set the username and password properties.  Here is an example of a console application calling our service and passing the required information to authenticate.

    1 using System;

    2 using System.Collections.Generic;

    3 using System.Text;

    4 

    5 namespace ConsoleApplication1

    6 {

    7     class Program

    8     {

    9         static void Main(string[] args)

   10         {

   11             localhost.Service service = new ConsoleApplication1.localhost.Service();

   12             localhost.ServiceAuthHeader header = new ConsoleApplication1.localhost.ServiceAuthHeader();

   13             header.Username = “myusername”;

   14             header.Password = “mypassword”;

   15             service.ServiceAuthHeaderValue = header;

   16             int x = service.AddTwoNumbers(1, 1);

   17             Console.WriteLine(x);

   18             Console.ReadLine();

   19         }

   20     }

   21 }

 The return result will be 2 of course and from the client side it is rather trivial to pass the credentials as you see.   That’s it.   Happy authenticating!

[Related Link]
To take authenticating one step further with a custom SoapExtension read this follow up article.
http://keithelder.net/blog/archive/2007/01/09/Take-Securing-Web-Services-With-Username-and-Password-One-Step.aspx

 

SubText vs DasBlog (Part 1)

Posted by Keith Elder | Posted in .Net, Asp.Net | Posted on 30-10-2006

6

This weekend I spent some time investigating two of the top blog packages: SubText and DasBlog in preparing for a new site I launched (http://www.keithelder.net).  I’ve heard of each app equally it seems and each seem to be the top two players in the .Net blog space.  After downloading both of them and poking around the source and trying to get them to build I am no where further along in my evaluation this evening than I was when I started. 

 

DasBlog Installation Stumps Me

For starters DasBlog is still using VS2003 for its solution.  For me, this was a huge turn off right out of the gate.   I had to configure lots more out of the box to get DasBlog configured.  Ultimately I had something configured improperly with IIS and kept getting this error:

 

Server Error in ‘/’ Application.


Configuration Error

Description: An error occurred during the processing of a configuration file required to service this request. Please review the specific error details below and modify your configuration file appropriately.
Parser Error Message: It is an error to use a section registered as allowDefinition=’MachineToApplication’ beyond application level.  This error can be caused by a virtual directory not being configured as an application in IIS.
Source Error:

Line 109:        <!-- <httpCookies httpOnlyCookies="false"/> -->
Line 110:        
Line 111:        <authentication mode="Forms">
Line 112:			<!-- NOTE: If you want to run MULTIPLE dasBlogs on the SAME Domain Name
Line 113:			     include the path in each blog's Web.Config like path="/dasblog1" and path="/yoursite"

Source File: C:\Inetpub\wwwroot\DasBlog\source\newtelligence.DasBlog.Web\web.config    Line: 111

After a stint of digging around and trying to trouble shoot things I gave up and decided to try to get SubText going.  I honestly don’t care which one I wind up with but I ultimately want to use one that I can contribute too. 

SubText Installation Stumps Me

After getting defeated by the DasBlog installation I decided to give SubText a whirl.  As soon as I opened the solution I had errors.  While SubText works with VS2005, it requires you have the web project addition installed, which also requires a VS2005 update to be installed.  After going through all of the required updates I thought I was on my way when I pressed F5 in VS2005 and it launched a web site that took me to the installation pages as outlined in the videos.  It was here where things got shaky because I started running into dbo.subtext_version issues.  I pulled up RssBandit and went to Phil Haack’s blog and found this entry.   It turns out I wasn’t the only one that had a SQL Server installation problems.  It is late and I have to work on Monday so I am off to bed.  I plan on trying the update tomorrow evening and I’ll let you know how it goes. 

Job Openings: .Net Engineers Needed

Posted by Keith Elder | Posted in .Net, Asp.Net | Posted on 27-09-2006

1

It isn’t everyday that you can say you work for #1 but I can.  Actually I have said that for the past 2 years.  Would you like to work for #1 as well? If you are a .Net Developer / Engineer who is passionate, self-motivated, loves being able to set and manage your own goals and you are looking to work for THE best company to work for in the IT industry in the US, we in turn are looking for you!

This is the first time I have tried posting job openings on my blog so we’ll see how this works.  If it works, great, if not, there was nothing lost. 

Quicken Loans is seeking talented .Net developers and engineers.  If you have some or all of the following skills, please contact me so I can get you started down the interview path.

  1. .Net Framework 2.0
  2. Visual Studio 2005
  3. Asp.Net
  4. Web Services
  5. Smart Client
    1. ClickOnce
    2. Winform experience
  6. Enterprise Library
  7. Smart Client Software Factory
  8. Web Service Software Factory
  9. Biztalk
  10. SQL Server 2005
  11. Reporting Services

I am sure you will check out our web site, and you should.  There is TONS of information about the company, the awards we’ve won, about our culture and our outstanding benefits.  If you want to find out more about us and what type of work you would be doing, CONTACT ME with the information found on the About page.  Call or email it doesn’t matter.  We are moving fast so act now while supplies last. 🙂