Archive

Posts Tagged ‘.NET’

Tellago Technology Updates

May 4, 2011 adglopez and LeandroDG No comments
Tellago announces the new technology webinar series!
The idea is to help organizations to be more effective in their decisions about strategies and evaluations adopting technologies, to achieve this, will be doing  monthly a series of webinars oriented to decision makers, developers and IT professionals.
These will be presented by some of our experts in the different areas and trying to make this as much interactive as possible, for more info you can follow this link.
VN:F [1.9.11_1134]
Rating: 5.0/5 (1 vote cast)
Categories: Uncategorized Tags: , , , ,

Tellago Studios SO-Aware at Microsoft TechReady!

February 15, 2011 adglopez No comments

Tellago Studios’ Chief Architect Jesus Rodriguez will be presenting a session about SOA Governance on the Microsoft platform using SO-Aware at Microsoft TechReady.

This week Microsoft is hosting the first edition of their annual TechReady conference. Even though TechReady is an internal conference, Microsoft invited us to present a session about how to enable Agile SOA Governance on the Microsoft platform using our recently release product: SO-Aware.

As part of our session, we will take a look at the current challenges that organizations face when enabling SOA governance capabilities on the Microsoft platform and how organizations can benefit from  more agile, lightweight and modern SOA governance models.

The session will provide a practical view to the role of Tellago Studios’ SO-Aware as an essential technology to enable native SOA governance on the Microsoft platform. We will explore in detail important capabilities of SO-Aware such as

  • Centralized service repository
  • Centralized configuration management
  • Service testing
  • Monitoring
  • Transparent integration with technologies such as Visual Studio, BizTalk Server, Windows Server & Azure AppFabric among many others

But the fun doesn’t stop there…..

As part of this session, we will showcase for the first time our upcoming SO-Aware Test Workbench product which enables load and functional web service testing capabilities on the Microsoft technology stack.

SO-Aware Test Workbench provides developers with a visually rich environment to model and control the execution of load and functional tests in a SOA infrastructure. This tool includes the first native WCF load testing engine allowing developers to transparently load test applications built on Microsoft’s service oriented technologies such as WCF, BizTalk Server or the Windows Server or Azure AppFabric.

VN:F [1.9.11_1134]
Rating: 0.0/5 (0 votes cast)

Encryption and decryption with X.509 certificates (with MIME Base64 Encoding)

March 29, 2010 LeandroDG and adglopez 6 comments

We’ve been working on the last months with encyption and decryption using certificates for Biztalk, I haven’t found enough documentation out there but after some time we were able to encrypt and decrypt messages with a very little amount of code.

Messages are encrypted using a certificate’s public key, and decrypted using their private key. This way, to send a message to a particular recipient, he needs to have a certificate with a private key deployed on their side, and you need to have the certificate (only the public key is necessary) deployed on your side. No one will be able to decrypt the message without the private key (it’s an asymmetric encryption/decryption method).

We use this code to encrypt/decrypt messages inside Biztalk Server components, so the code we developed for encryption/decryption uses MIME Base64 Encoding, for example:

Content-ID: {F5BBE1D4-D0E3-4CD7-9B51-1129FA3077E1}
Content-Description: body
Bcc:
MIME-Version: 1.0
Content-type: application/x-pkcs7-mime; smime-type=enveloped-data; name="smime.p7m"
Content-Transfer-Encoding: base64

MIAGCSqGSIb3DQEHA6CAMIACAQAxgZEwgY4CAQAwODAkMSIwIAYDVQQDExlSQ0NMIEJpelRhbGsg
q49kxusLITM1r982n2MgZaa8vdgkLBLATSUWDEyDu/B57PZxxxU/AhEyIUppI5fsaxpI7NT+2QPW
8/HT7vfgH0t3ch3AUVglspS/NRYCuaOwG5lIpw9IAAAAAAAAAAAAAA==

How to use the Encrypt method

string messageToEncrypt = "message";
string certificateName = "MyCertificate";
string encryptedMessage = CryptographyHelper.Encrypt(messageToEncrypt, certificateName);

The certificate needs to be deployed on the Personal store inside your Local Machine (the code can be modified in the GetCertificate method to use another store).
To do this deployment, you may want to check this link: http://technet.microsoft.com/en-us/library/cc740068%28WS.10%29.aspx

How to use the Decrypt method

string decryptedMessage =  CryptographyHelper.Decrypt(messageToDecrypt);

This time, the certificate needs to be deployed at the same store but it’ll be necessary to deploy it including the private key. If the method throws an exception “the enveloped data-message does not contain the specified recipient”, this is because the certificate with the private key is not correctly deployed into the current account/local machine personal store.

Source code (download at the bottom)

using System;
using System.Linq;
using System.Text;
using System.Security.Cryptography.X509Certificates;
using System.Security.Cryptography;
using System.Security.Cryptography.Pkcs;
using System.IO;

namespace Logue.Library.Cryptography
{
	public static class CryptographyHelper
	{
		#region Public methods
		public static string Encrypt(string fullMessage, string certificateName)
		{
			X509Certificate2 certificate = GetCertificate(certificateName);

			string base64DecryptedContent = Convert.ToBase64String(Encoding.UTF8.GetBytes(fullMessage));
			base64DecryptedContent = ChunkContent(base64DecryptedContent, 76);
			base64DecryptedContent = EnvelopeBase64(base64DecryptedContent);

			byte[] contentBytes = Encoding.ASCII.GetBytes(base64DecryptedContent);

			Oid contentOid = new Oid("1.2.840.113549.1.7.1", "PKCS 7 Data");
			Oid algorithmOid = new Oid("1.2.840.113549.3.2", "rc2");
			AlgorithmIdentifier algorithmIdentifier = new AlgorithmIdentifier(algorithmOid);
			ContentInfo content = new ContentInfo(contentOid, contentBytes);
			EnvelopedCms envelope = new EnvelopedCms(SubjectIdentifierType.NoSignature, content, algorithmIdentifier);

			envelope.Encrypt(new CmsRecipient(certificate));
			byte[] encryptedBytes = envelope.Encode();

			string encryptedContent = Convert.ToBase64String(encryptedBytes);

			encryptedContent = ChunkContent(encryptedContent, 76);
			string result = EnvelopEncryptedContent(encryptedContent);

			return result;
		}

		public static string Decrypt(string fullMessage)
		{
			string messageContent = GetContentInBase64(fullMessage);

			// Load envelope and decrypt
			EnvelopedCms envelope = new EnvelopedCms();
			envelope.Decode(Convert.FromBase64String(messageContent));
			envelope.Decrypt();

			// Get original bytes
			byte[] decryptedBytes = envelope.ContentInfo.Content;
			string decryptedText = Encoding.ASCII.GetString(decryptedBytes);

			// Get processed Base64 content
			byte[] decryptedContentBytes = Convert.FromBase64String(GetContentInBase64(decryptedText));
			string decryptedContentText = Encoding.UTF8.GetString(decryptedContentBytes);

			return decryptedContentText;
		}
		#endregion

		#region Private Methods
		private static string ChunkContent(string encryptedContent, int chunkSize)
		{
			StringBuilder sb = new StringBuilder();
			StringReader sr = new StringReader(encryptedContent);

			int position = 0;
			char[] buffer = new char[chunkSize];

			while (position < encryptedContent.Length)
			{
				if (encryptedContent.Length - (position + chunkSize) < 0)
				chunkSize = encryptedContent.Length - position;
				sb.Append(encryptedContent.Substring(position, chunkSize));
				sb.Append("rn");
				position += chunkSize;
			}

			return sb.ToString();
		}

		private static string EnvelopEncryptedContent(string encryptedContent)
		{
			return CryptographyResources.ENCRYPTED_TEMPLATE.Replace("[REPLACE]", encryptedContent);
		}

		private static string EnvelopeBase64(string content)
		{
			return CryptographyResources.BASE64_TEMPLATE.Replace("[REPLACE]", content);
		}

		private static X509Certificate2 GetCertificate(string certificateName)
		{
			X509Store store = new X509Store(StoreName.My, StoreLocation.LocalMachine);
			store.Open(OpenFlags.OpenExistingOnly | OpenFlags.ReadOnly);
			X509Certificate2 certificate = store.Certificates.Cast<X509Certificate2>().Where(cert => cert.Subject.IndexOf(certificateName) >= 0).FirstOrDefault();
			if (certificate == null)
			throw new Exception("Certificate " + certificateName + " not found.");

			return certificate;
		}

		private static string GetContentInBase64(string fullMessage)
		{
			string contentSeparator = Environment.NewLine + Environment.NewLine;
			int startIndex = fullMessage.IndexOf(contentSeparator) + contentSeparator.Length;
			int endIndex = fullMessage.Length - 1;
			StringBuilder sb = new StringBuilder();
			string[] lines = fullMessage.Substring(startIndex, endIndex - startIndex).Split(new string[] { Environment.NewLine }, StringSplitOptions.RemoveEmptyEntries);
			foreach (string line in lines)
			sb.Append(line);
			return sb.ToString();
		}
		#endregion
	}
}

Download
Cryptography Helper Source Code (440)

VN:F [1.9.11_1134]
Rating: 5.0/5 (1 vote cast)
Categories: Development Tags: , , ,

Biztalk Custom Functoid Wizard for Biztalk 2004 & 2006

June 29, 2009 LeandroDG 3 comments

First, this release got delayed about 3 years!. But, it still works fine and I’ve used it in many Biztalk Project over the last years, so I think it may be of use for every other BTS developer out there.

The idea behind this project is to be able to build custom Biztalk Functoids through a wizard. When this was built, there was not much information on the web about developing custom functoids, so it was a little hard to work on it. It’s based on Boudewijn van der Zwan and Scott Woodgate‘s Biztalk Adapter Wizard. I’ve also based this development in Martijn Hoogendoorn‘s Biztalk Pipeline Component Wizard. These are the original releases for this components: Adapter Wizard, Pipeline Wizard.

Basically a custom functoid is very similar to a Scripting Functoid with the same code copied once and again. The idea of developing a custom functoid instead of a Scripting Functoid is to avoid code repetition and to be able to modify it in every map that uses it simultaneously. This concept is known as DRY (Don’t repeat yourself).

I’ve built an original version for 2004 for an enormous project which required around 50 custom functoids to be built, of course building them by hand would be very time consuming. Adrian Lopez helped me adapt this version to Biztalk Server 2006, special thanks to him for the help!.

I’m posting both versions here, for Biztalk 2004 (and Visual Studio .NET 2003) and Biztalk 2006 (and Visual Studio .NET 2005).

Installation and usage is quite simple but I’ll show the usage step by step in a simple “Hello world” functoid sample.

  1. Start up Visual Studio, go to File, New Project, and select Biztalk Projects:
    Biztalk Functoid Wizard Project type selection

    Biztalk Functoid Wizard Project type selection

  2. Splash screen

    Biztalk Functoid Wizard Initial wizard splash

    Biztalk Functoid Wizard Initial wizard splash

  3. Now you must select some general properties: class name, namespace, assembly name and assembly key file (.snk), which can be generated by clicking on New or selected by clicking on the browse button. You must select either a key file or a key name (the last one if you’ll be using the Crypto Service Provider).

    Biztalk Functoid Wizard General project properties

    Biztalk Functoid Wizard General project properties

  4. In this screen you must choose the functoid id (this is a unique id that cannot be repeated among functoids, so be careful not to repeat yourself), name, tooltip and description.

    Biztalk Functoid Wizard Functoid properties

    Biztalk Functoid Wizard Functoid properties 1/2

  5. You can choose the category where the functoid will be shown and a default exception message. Also you can select the icon for the functoid (by double clicking on the predefined icon), and select VB.NET or C# as the implementation languages.

    Biztalk Functoid Wizard Functoid properties 2/2

    Biztalk Functoid Wizard Functoid properties 2/2

  6. Then it’s time to select the incoming parameters for the functoid, the return type and the allowed input and output connections for the functoid. Also you can re-order the parameters and define minimum and maximum amount of parameters.

    Biztalk Functoid Wizard Functoid parameters & connection types

    Biztalk Functoid Wizard Functoid parameters & connection types

  7. We are ready, functoid definition is finished.

    Biztalk Functoid Wizard Completion splash

    Biztalk Functoid Wizard Completion splash

  8. Now, into some code. A functoid is nothing more than a function that can be used inside a map. We defined the interface with the wizard, but we need to edit the source code for the implementation. The wizard will have autogenerated the following code:
    public System.String Execute()
    {
    	ResourceManager resmgr = new ResourceManager(ResourceName, Assembly.GetExecutingAssembly());
    	try
    	{
    		// TODO: Implement Functoid Logic
    	}
    	catch (Exception e)
    	{
    		throw new Exception(resmgr.GetString("FunctoidException"), e);
    	}
    }
  9. We add the basic “Hello world” implementation:
    public System.String Execute()
    {
    	ResourceManager resmgr = new ResourceManager(ResourceName, Assembly.GetExecutingAssembly());
    	try
    	{
    		return "Hello world!";
    	}
    	catch (Exception e)
    	{
    		throw new Exception(resmgr.GetString("FunctoidException"), e);
    	}
    }
  10. Now we just build the whole solution, it will automatically generate our file Logue.Biztalk.Functoids.dll inside of Microsoft BizTalk Server 2006Developer ToolsMapper Extensions in the program files folder. We open a map inside of Visual Studio and right-click on the functoids toolbox, and we select “Choose Items”. The following screen appears:

    Functoid toolbox item selection

    Functoid toolbox item selection

  11. We browse for the file. As explained before, it will be inside of Microsoft BizTalk Server 2006Developer ToolsMapper Extensions in the program files folder.

    Browsing for custom functoid assembly

    Browsing for custom functoid assembly

  12. Now the functoid appears in the item selection box, so we check it and click on Ok.

    Our functoid in the toolbox item selection

    Our functoid in the toolbox item selection

  13. Now it appears in the toolbox:

    Functoid toolbox with our functoid

    Functoid toolbox with our functoid

  14. And now we drag&drop it, link it, and we can test the map!

    Our functoid used in a map

    Our functoid used in a map

I hope you find it useful! Please report any bugs or information you think it would be useful to share.

Downloads:

Biztalk Functoid Wizard 2006 Source Code (118)
Biztalk Functoid Wizard 2006 Installer (136)
Biztalk Functoid Wizard 2004 Source Code (82)

Update (2010/01/24): I’ve fixed the download module after moving to a new hosting provider, they are now working again.

VN:F [1.9.11_1134]
Rating: 5.0/5 (3 votes cast)

.NET C#: Recycle current Application Pool programmatically (for IIS 6+)

February 12, 2008 LeandroDG 7 comments

I’ve been working on how to recycle the current application pool for my ASP .NET application.

There are 3 steps for doing this:

  1. Verify if application is running on IIS that supports application pools (if not, there’s nothing to recycle).
  2. Get application pool name (obtained from the DirectoryServices entry corresponding to our virtual directory).
  3. Invoke Recycle method in the DirectoryServices entry corresponding to the application pool.

I divided the code into this 3 steps, the RecycleApplicationPool method can be used separately for recycling any application pool (by knowing only its name). The RecycleCurrentApplicationPool method returns a boolean value indicating if the application pool was recycled.

public static class ApplicationPoolRecycle
{
    /// <summary>Attempts to recycle current application pool</summary>
    /// <returns>Boolean indicating if application pool was successfully recycled</returns>
    public static bool RecycleCurrentApplicationPool()
    {
        try
        {
            // Application hosted on IIS that supports App Pools, like 6.0 and 7.0
            if (IsApplicationRunningOnAppPool())
            {
                // Get current application pool name
                string appPoolId = GetCurrentApplicationPoolId();
                // Recycle current application pool
                RecycleApplicationPool(appPoolId);
                return true;
            }
            else
                return false;
        }
        catch
        {
            return false;
        }
    }

    private static bool IsApplicationRunningOnAppPool()
    {
        // Application is not hosted on IIS
        if (!AppDomain.CurrentDomain.FriendlyName.StartsWith("/LM/"))
            return false;
        // Application hosted on IIS that doesn't support App Pools, like 5.1
        else if (!DirectoryEntry.Exists("IIS://Localhost/W3SVC/AppPools"))
            return false;
        else
            return true;
    }

    private static string GetCurrentApplicationPoolId()
    {
        string virtualDirPath = AppDomain.CurrentDomain.FriendlyName;
        virtualDirPath = virtualDirPath.Substring(4);
        int index = virtualDirPath.Length + 1;
        index = virtualDirPath.LastIndexOf("-", index - 1, index - 1);
        index = virtualDirPath.LastIndexOf("-", index - 1, index - 1);
        virtualDirPath = "IIS://localhost/" + virtualDirPath.Remove(index);
        DirectoryEntry virtualDirEntry = new DirectoryEntry(virtualDirPath);
        return virtualDirEntry.Properties["AppPoolId"].Value.ToString();
    }

    private static void RecycleApplicationPool(string appPoolId)
    {
        string appPoolPath = "IIS://localhost/W3SVC/AppPools/" + appPoolId;
        DirectoryEntry appPoolEntry = new DirectoryEntry(appPoolPath);
        appPoolEntry.Invoke("Recycle");
    }
}

VN:F [1.9.11_1134]
Rating: 5.0/5 (1 vote cast)