Programatically signing in to site using Basic Authentication using .Net

This week I was evaluating a help desk application to use for our site. One of the key factors in decision making was ability to connect to application's API using some form of web service. It turns out that this application supported REST API. First thing I needed to look for was how do I authenticate request to extract data. This application uses BASIC authetication. That would not be my first preference to use any application that uses BASIC authentication because of concerns related to user credentials being exposed in clear text in request. In this post I will discuss how to submit a HTTP request with Basic Authentication.

Basic Authentication Protocol

Basic authentication protocol manadates that HTTP request should include Authorization header that contains user credentials in the following format.

        Authorization = Basic UserCredentials
        where
        UserCrdentials = Base64 encoded value of Login":"Password string
    

Now you can see why this mechanism is not safe because credentials are exposed in the header directly and it does not take any effort to decode this Base64 encoded pair. Thats the besides the point for this discussion.

Basic Authentication With .Net

Here is code snippet from my evaluation application. There is nothing fancy in this code. The code that relates to authentication has been highlighted.

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Net;
using System.Web;

namespace FreshdeskConsole
{
    class Program
    {
        const string BaseUrl = "https://{0}.freshdesk.com/";
        const string CompanyName = "byteblocks";
        const string LoginUrl = "login";
        const string TicketsUrl = "helpdesk/tickets.xml";
        const string LoginEmail = "xyz@byteblocks.com";
        const string Password = "mypassword";

        static void Main(string[] args)
        {
            GetAllTickets();
        }

        static void GetAllTickets()
        {
            var baseUrl = string.Format(BaseUrl, CompanyName);
            var ticketsUrl = string.Format("{0}{1}", baseUrl, TicketsUrl);

            var webReq = WebRequest.Create(ticketsUrl);
        
            var credentialsCache = new CredentialCache();
            credentialsCache.Add(new Uri(baseUrl), "Basic", GetUserCredentials());
            webReq.Credentials = credentialsCache;
            webReq.Headers.Add("Authorization", GetBasicAuthenticationData());
        
            webReq.Method = "GET";
            webReq.PreAuthenticate = true;
            webReq.ContentType = "application/x-www-form-urlencoded";

            var response = webReq.GetResponse();
            ProcessWebResponse(response);
        }

        static void ProcessWebResponse(WebResponse response)
        {
        }

        static NetworkCredential GetUserCredentials()
        {
            var credentials = new NetworkCredential(LoginEmail, Password);
            return credentials;
        }

        static string GetBasicAuthenticationData()
        {
            var authInfo = string.Format("{0}:{1}", LoginEmail, Password);
            var bytes = new UTF8Encoding().GetBytes(authInfo);
            var encodedInfo = Convert.ToBase64String(bytes);
            return string.Format("Basic {0}", encodedInfo);
        }
    }
}
    

NetworkCredentials and CredentialsCache

.Net framework exposes NetworkCredentials and CredentialsCache classes that you can use to set a user's credentials to attach to a web request. You can from the code above how this is done.

Authorization Header

This is something that I found out after spending couple of hours on trying to figure out why credentials were not being sent to web service. Although I had set CredentialsCache to WebRequest, the information was not being sent to server. So I had to go back to basics and do it old fashioned way of explicitly setting Authorization header.

If you have any questions about Basic authentication use in .Net, feel free to post a comment in this post and I will try to get back to you as soon as I can.

comments powered by Disqus

Search

Social

Weather

19.9 °C / 67.9 °F

weather conditions Clouds

Monthly Posts

Blog Tags