Microsoft StreamInsight CTP2 is available

It was bound to happen. The very day I fly off on vacation is the day that Microsoft posts the first public CTP of StreamInsight. This is CTP2. CTP1 was for private distribution inside Microsoft only, and I couldn’t convince or bribe anyone to slip me a copy. So, I just noticed now, and I haven’t had a chance to look at it yet. Can’t wait, though.

CTP2 can be downloaded from http://www.microsoft.com/downloads/details.aspx?FamilyID=a3faa562-b6dc-4702-90c6-bf8e08df3b8b&displaylang=en

Executing OLEDB SQL statement from C#

Here is a way to execute a sql statement that returns one column of one row. If there is more than one row returned, it will return nothing.

        public static string CreateReader(string connectionString, string queryString)
        {
            string result="";
            int rowCount = 0;
            using (System.Data.OleDb.OleDbConnection connection = new System.Data.OleDb.OleDbConnection(connectionString))
            {
                System.Data.OleDb.OleDbCommand command = new System.Data.OleDb.OleDbCommand(queryString, connection);
                connection.Open();
                System.Data.OleDb.OleDbDataReader reader = command.ExecuteReader();
                while (reader.Read())
                {
                    rowCount = rowCount + 1;
                    result = reader[0].ToString();
                }
                reader.Close();
                return (rowCount == 0 || rowCount > 1) ? "" : result;
            }
        }

WCF Intermediaries with Binding Switching

I have been working on a WCF intermediary that receives messages from a 3rd party and routes this onto another WCF service. The intermediary service uses basicHttpBinding whereas the destination service is netTcpBinding. I have worked on similar patterns before, but they always had the same binding on each service and they worked well, therefore I hadn’t anticipated any problems.


However, once I had this all set-up I started receiving the following error on the intermediary service: “Addressing Version ‘AddressingNone (http://schemas.microsoft.com/ws/2005/05/addressing/none)’ does not support adding WS-Addressing headers.”


This error appears to stem from the fact that basicHttpBinding is using SOAP 1.1 for the message version and no WS-Addressing, whereas netTcpBinding is using SOAP 1.2 for the message version with WS-Addressing. I had originally attempted to use custom bindings to get over this hurdle without much success so adopted to implement a message conversion in the intermediary service instead.


Your typical intermediary service would tend to have a service contract that is defined as so:


[ServiceContract]


public interface IMyIntermediaryService


{


   [OperationContract(


      IsOneWay = false,


      IsInitiating = true,


      IsTerminating = false,


      Action = “*”,


      ReplyAction = “*”)]


   [FaultContract(


      typeof(MyCustomFault),


      Namespace = “http://mydomain.com/myapplication/2009/08”)]


  


   Message ProcessMessage(Message message);


}


The implementation of the ProcessMessage method would be something like the following. Note that this is a very basic example to be succinct, you would need to include error handling etc. In addition we are defining the destination endpoint in the web.config using the name “destination” as the identifier.


public Message ProcessMessage(Message message)


{


   var channelFactory = new ChannelFactory<IMyIntermediaryService>(“destination”);


 


   IMyIntermediaryService forwardingChannel = channelFactory.CreateChannel();


 


   Message responseMessage = forwardingChannel.ProcessMessage(message);


   channelFactory.Close();


 


   return responseMessage;


}


Now, in order to handle the message conversion you would supplement the above code so that it identifies the message version received. Note that we are solely checking for netTcpBinding here, but this code could be modified to expand upon this to make it more generic.


public Message ProcessMessage(Message message)


{


   // Get the message version


   MessageVersion returnMessageVersion = message.Version;


   bool messageConverted = false;


 


   var channelFactory = new ChannelFactory<IMyIntermediaryService>(“destination”);


 


   IMyIntermediaryService forwardingChannel = channelFactory.CreateChannel(); 


 


   // If we are using NetTcpBinding make sure that the message we are sending is


   // Soap 1.2 WS-Addressing if it is not already


   if (channelFactory.Endpoint.Binding.GetType() == typeof(NetTcpBinding)


       && message.Version != MessageVersion.Soap12WSAddressing10)


   {


      message = CreateMessageCopy(message, MessageVersion.Soap12WSAddressing10);


      messageConverted = true;


   }


 


   Message responseMessage = forwardingChannel.ProcessMessage(message);


   channelFactory.Close();


 


   // Convert the message type back to that of the original if necessary


   if (messageConverted)


   {


      responseMessage = CreateMessageCopy(responseMessage, returnMessageVersion);


   }


   return responseMessage;


}


Note that you must also covert the result back to the original format if a conversion has taken place otherwise the client will throw an exception “An error occurred while receiving the HTTP response to http://myserver/myservice.svc. This could be due to the service endpoint binding not using the HTTP protocol. This could also be due to an HTTP request context being aborted by the server (possibly due to the service shutting down). See server logs for more details.”


The conversion method would be something like the following


private static Message CreateMessageCopy(


   Message message,


   MessageVersion newMessageVersion)


{


   Message copy = Message.CreateMessage(


      newMessageVersion,


      message.Headers.Action,


      message.GetReaderAtBodyContents());


   copy.Properties.CopyProperties(message.Properties);


   return copy;


}

Selecting all rows from a stored procedure

I needed to use a select to return data, however the data resided via a call to a stored procedure.

For a simple example, I will use the the following stored procedure

exec sp_who 'sa'

So how do I select * from a stored a procedure?

Use OPENROWSET

select *
from openrowset('sqloledb','Server=(local);TRUSTED_CONNECTION=YES','set fmtonly off exec master.sys.sp_who ''sa''')

which returns this result

Which means that I can filter what I want:

select *
from openrowset('sqloledb','Server=(local);TRUSTED_CONNECTION=YES','set fmtonly off exec master.sys.sp_who ''sa''') [x]
where x.status='sleeping'