Click here to Skip to main content
15,896,557 members
Articles / Web Development / HTML

Implementing WS-SecureConversation in Microsoft IssueVision

Rate me:
Please Sign up or sign in to vote.
4.61/5 (12 votes)
27 Sep 20056 min read 73.3K   776   38  
Adding secure communications to the Microsoft IssueVision sample application using WSE 2.0.
using System;
using System.Configuration;
using System.Data;
using System.Net;
using System.Web.Services.Protocols;
using System.Windows.Forms;
using Microsoft.Web.Services2;
using Microsoft.Web.Services2.Security;
using Microsoft.Web.Services2.Security.Tokens;
using IssueVision.localhost;

namespace IssueVision
{
	public enum WebServicesExceptionType
	{
		WebExceptionFirstUse = 0,
		WebException = 1,
		SoapException = 2,
		Exception = 3,
		None = 4,
	}

	public class WebServicesLayer
	{
		public const string IV_WEBEXCEPTION_TEXT = "The server is not responding. Please try again.";
		public const string IV_WEBEXCEPTION_TITLE = "Network Error";
		public const string IV_WEBEXCEPTIONOFFLINEOK_TEXT = "The server is not responding. Starting IssueVision in offline mode.";
		public const string IV_WEBEXCEPTIONOFFLINEOK_TITLE = "Network Error - Working Offline";
		public const string IV_SOAPEXCEPTION_TEXT = "The system could not log you on.";
		public const string IV_SOAPEXCEPTION_TITLE = "Login Error";
		public const string IV_EXCEPTION_TEXT = "An unknown error has occurred";
		public const string IV_EXCEPTION_TITLE = "Unknown Error";

		public static void HandleWebServicesException(WebServicesExceptionType exceptionType)
		{
			switch (exceptionType)
			{
				case WebServicesExceptionType.WebException:
					MessageBox.Show(IV_WEBEXCEPTION_TEXT, IV_WEBEXCEPTION_TITLE, MessageBoxButtons.OK, MessageBoxIcon.Error);
					break;

				case WebServicesExceptionType.SoapException:
					MessageBox.Show(IV_SOAPEXCEPTION_TEXT, IV_SOAPEXCEPTION_TITLE, MessageBoxButtons.OK, MessageBoxIcon.Error);
					break;

				case WebServicesExceptionType.Exception:
					MessageBox.Show(IV_EXCEPTION_TEXT, IV_EXCEPTION_TITLE, MessageBoxButtons.OK, MessageBoxIcon.Error);
					break;
			}
		}

		public static WebServicesExceptionType Authenticate()
		{
			return Authenticate(UserSettings.Instance.Username, UserSettings.Instance.Password);
		}

		public static WebServicesExceptionType Authenticate(string username, string password)
		{
			WebServicesExceptionType exceptionType = WebServicesExceptionType.None;
			
			try
			{
				Wse2HelperClient.RequestSCTByUsername(username, password);
			}
			catch (WebException)
			{
				exceptionType = WebServicesExceptionType.WebException;
			}
			catch (SoapException soapEx)
			{
				if (soapEx.Actor == "Security")
				{
					exceptionType = WebServicesExceptionType.SoapException;
				}
				else
				{
					exceptionType = WebServicesExceptionType.WebException;
				}
			}
			catch (Exception)
			{
				exceptionType = WebServicesExceptionType.Exception;
			}
			
			return exceptionType;
		}

		// The GetLookupTables method is used to fetch lookup data such as Staffer information.  
		// The lookup data is refreshed each time the application is started while online.  
		// Unlike issue data, it is not updated in the background.
		public static IVDataSet GetLookupTables()
		{
			IVDataSet data = null;
			IssueVisionServicesWse dataService = GetWebServiceReference();
			
			try
			{
				// Request the security context token
				SecurityContextToken sct = Wse2HelperClient.RequestSCTByUsername(UserSettings.Instance.Username, UserSettings.Instance.Password);

				// Use the security context token to sign and encrypt a request to the Web service
				SoapContext requestContext = dataService.RequestSoapContext;
				requestContext.Security.Tokens.Add(sct);
				requestContext.Security.Elements.Add( new MessageSignature( sct ) );
				requestContext.Security.Elements.Add( new EncryptedData( sct ) );

				data = dataService.GetLookupTables();
			}
			catch (WebException)
			{
				HandleWebServicesException(WebServicesExceptionType.WebException);
			}
			catch (SoapException soapEx)
			{
				if (soapEx.Actor == "Security")
				{
					HandleWebServicesException(WebServicesExceptionType.SoapException);
				}
				else
				{
					HandleWebServicesException(WebServicesExceptionType.WebException);
				}
			}
			catch (Exception)
			{
				HandleWebServicesException(WebServicesExceptionType.Exception);
			}
						
			return data;
		}

		// SendReceiveIssues is a batch processing method that 1) sends data updates to 
		// the server, and 2) returns updated issue data since the last synchronization. 
		// When the application is set to Work Online, this method is called every few
		// seconds from the IssuesSubject and processed on a background thread.
		public static IVDataSet SendReceiveIssues(DataSet changedIssues, DateTime lastAccessed)
		{
			IVDataSet data = null;
			IssueVisionServicesWse dataService = GetWebServiceReference();
			
			try
			{
				// Request the security context token
				SecurityContextToken sct = Wse2HelperClient.RequestSCTByUsername(UserSettings.Instance.Username, UserSettings.Instance.Password);

				// Use the security context token to sign and encrypt a request to the Web service
				SoapContext requestContext = dataService.RequestSoapContext;
				requestContext.Security.Tokens.Add(sct);
				requestContext.Security.Elements.Add( new MessageSignature( sct ) );
				requestContext.Security.Elements.Add( new EncryptedData( sct ) );

				data = dataService.SendReceiveIssues(changedIssues, lastAccessed);
			}
			catch (WebException)
			{
				HandleWebServicesException(WebServicesExceptionType.WebException);
			}
			catch (SoapException soapEx)
			{
				if (soapEx.Actor == "Security")
				{
					HandleWebServicesException(WebServicesExceptionType.SoapException);
				}
				else
				{
					HandleWebServicesException(WebServicesExceptionType.WebException);
				}
			}
			catch (Exception)
			{
				HandleWebServicesException(WebServicesExceptionType.Exception);
			}
			
			return data;
		}

		// In IssueVision 1.0, this method returns an instance of the web reference for 
		// the IssueVisionService, with credentials attached as a custom SOAP header.
		// In version 1.1, the section marked below will be replaced with WSE 2.0 logic.
		private static IssueVisionServicesWse GetWebServiceReference()
		{
			IssueVisionServicesWse dataService = new IssueVisionServicesWse();
			
			string urlSetting = ConfigurationSettings.AppSettings["DataServiceUrl"];
			
			if (urlSetting != null)
			{
				dataService.Url = urlSetting;
			}
			else
			{
				dataService.Url = "http://localhost/IssueVisionWebWseCS/IssueVisionServices.asmx";
			}
			
			// wire up the default credentials in case the app is being run in a network
			// that requires authentication to a proxy server
			dataService.Credentials = (NetworkCredential)CredentialCache.DefaultCredentials;
			
			return dataService;
		}
	}
}

By viewing downloads associated with this article you agree to the Terms of Service and the article's licence.

If a file you wish to view isn't highlighted, and is a text file (not binary), please let us know and we'll add colourisation support for it.

License

This article has no explicit license attached to it but may contain usage terms in the article text or the download files themselves. If in doubt please contact the author via the discussion board below.

A list of licenses authors might use can be found here


Written By
Software Developer (Senior)
United States United States
Weidong has been an information system professional since 1990. He has a Master's degree in Computer Science, and is currently a MCSD .NET

Comments and Discussions