diff --git a/Samples/Manufacturing/InteropPartner/InteropPartner.csproj b/Samples/Manufacturing/InteropPartner/InteropPartner.csproj
new file mode 100644
index 00000000000..98b64f46ba2
--- /dev/null
+++ b/Samples/Manufacturing/InteropPartner/InteropPartner.csproj
@@ -0,0 +1,65 @@
+
+
+
+ Debug
+ AnyCPU
+ 9.0.30729
+ 2.0
+ {AF9929C8-85B8-4A36-9EC8-E46C17FE3B65}
+ Exe
+ Properties
+ InteropPartner
+ InteropPartner
+ v3.5
+ 512
+
+
+ true
+ full
+ false
+ bin\Debug\
+ DEBUG;TRACE
+ prompt
+ 4
+
+
+ pdbonly
+ true
+ bin\Release\
+ TRACE
+ prompt
+ 4
+
+
+
+
+ 3.5
+
+
+
+ 3.5
+
+
+ 3.5
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/Samples/Manufacturing/InteropPartner/Program.cs b/Samples/Manufacturing/InteropPartner/Program.cs
new file mode 100644
index 00000000000..34ccd5fc5c1
--- /dev/null
+++ b/Samples/Manufacturing/InteropPartner/Program.cs
@@ -0,0 +1,41 @@
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Text;
+using System.Messaging;
+using System.Xml.Serialization;
+
+namespace InteropPartner
+{
+ class Program
+ {
+ static void Main(string[] args)
+ {
+ Console.WriteLine("Using straight xml serialization and msmq to test interop.");
+ Console.WriteLine("To exit, enter 'q'. Press 'Enter' to send a message.");
+
+ string queueName = string.Format("FormatName:DIRECT=OS:{0}\\private$\\messagebus", Environment.MachineName);
+
+ MessageQueue q = new MessageQueue(queueName);
+
+ XmlSerializer serializer = new XmlSerializer(typeof(OrderMessage), new Type[] { typeof(OrderLine) });
+
+ string line = null;
+ while ((line = Console.ReadLine().ToLower()) != "q")
+ {
+ OrderMessage m1 = new OrderMessage();
+ m1.PurchaseOrderNumber = Guid.NewGuid().ToString();
+ m1.ProvideBy = DateTime.Now;
+ m1.PartnerId = Guid.NewGuid();
+ m1.OrderLines = new OrderLine[] { new OrderLine { ProductId = Guid.NewGuid(), Quantity = 10F } };
+ m1.Done = true;
+
+ Message toSend = new Message();
+ serializer.Serialize(toSend.BodyStream, m1);
+
+ q.Send(toSend, MessageQueueTransactionType.Single);
+ Console.WriteLine("Sent order {0}", m1.PurchaseOrderNumber);
+ }
+ }
+ }
+}
diff --git a/Samples/Manufacturing/InteropPartner/Properties/AssemblyInfo.cs b/Samples/Manufacturing/InteropPartner/Properties/AssemblyInfo.cs
new file mode 100644
index 00000000000..0c76a1b928a
--- /dev/null
+++ b/Samples/Manufacturing/InteropPartner/Properties/AssemblyInfo.cs
@@ -0,0 +1,36 @@
+using System.Reflection;
+using System.Runtime.CompilerServices;
+using System.Runtime.InteropServices;
+
+// General Information about an assembly is controlled through the following
+// set of attributes. Change these attribute values to modify the information
+// associated with an assembly.
+[assembly: AssemblyTitle("InteropPartner")]
+[assembly: AssemblyDescription("")]
+[assembly: AssemblyConfiguration("")]
+[assembly: AssemblyCompany("")]
+[assembly: AssemblyProduct("InteropPartner")]
+[assembly: AssemblyCopyright("Copyright © 2008")]
+[assembly: AssemblyTrademark("")]
+[assembly: AssemblyCulture("")]
+
+// Setting ComVisible to false makes the types in this assembly not visible
+// to COM components. If you need to access a type in this assembly from
+// COM, set the ComVisible attribute to true on that type.
+[assembly: ComVisible(false)]
+
+// The following GUID is for the ID of the typelib if this project is exposed to COM
+[assembly: Guid("6e1c25c9-5c7e-4f9c-beee-576f1558a5f8")]
+
+// Version information for an assembly consists of the following four values:
+//
+// Major Version
+// Minor Version
+// Build Number
+// Revision
+//
+// You can specify all the values or you can default the Build and Revision Numbers
+// by using the '*' as shown below:
+// [assembly: AssemblyVersion("1.0.*")]
+[assembly: AssemblyVersion("1.0.0.0")]
+[assembly: AssemblyFileVersion("1.0.0.0")]
diff --git a/Samples/Manufacturing/InteropPartner/schema0.xsd b/Samples/Manufacturing/InteropPartner/schema0.xsd
new file mode 100644
index 00000000000..a8da45d5c2e
--- /dev/null
+++ b/Samples/Manufacturing/InteropPartner/schema0.xsd
@@ -0,0 +1,53 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/Samples/Manufacturing/InteropPartner/schema1.xsd b/Samples/Manufacturing/InteropPartner/schema1.xsd
new file mode 100644
index 00000000000..0b53564abff
--- /dev/null
+++ b/Samples/Manufacturing/InteropPartner/schema1.xsd
@@ -0,0 +1,8 @@
+
+
+
+
+
+
+
+
diff --git a/Samples/Manufacturing/InteropPartner/schema1_schema0.cs b/Samples/Manufacturing/InteropPartner/schema1_schema0.cs
new file mode 100644
index 00000000000..1f76db6c3db
--- /dev/null
+++ b/Samples/Manufacturing/InteropPartner/schema1_schema0.cs
@@ -0,0 +1,260 @@
+//------------------------------------------------------------------------------
+//
+// This code was generated by a tool.
+// Runtime Version:2.0.50727.3053
+//
+// Changes to this file may cause incorrect behavior and will be lost if
+// the code is regenerated.
+//
+//------------------------------------------------------------------------------
+
+using System.Xml.Serialization;
+
+//
+// This source code was auto-generated by xsd, Version=2.0.50727.3038.
+//
+
+
+///
+[System.CodeDom.Compiler.GeneratedCodeAttribute("xsd", "2.0.50727.3038")]
+[System.SerializableAttribute()]
+[System.Diagnostics.DebuggerStepThroughAttribute()]
+[System.ComponentModel.DesignerCategoryAttribute("code")]
+[System.Xml.Serialization.XmlTypeAttribute(Namespace="http://tempuri.net/OrderService.Messages")]
+[System.Xml.Serialization.XmlRootAttribute(Namespace="http://tempuri.net/OrderService.Messages", IsNullable=true)]
+public partial class OrderStatusChangedMessage {
+
+ private string purchaseOrderNumberField;
+
+ private System.Guid partnerIdField;
+
+ private OrderStatusEnum statusField;
+
+ private object[] orderLinesField;
+
+ ///
+ public string PurchaseOrderNumber {
+ get {
+ return this.purchaseOrderNumberField;
+ }
+ set {
+ this.purchaseOrderNumberField = value;
+ }
+ }
+
+ ///
+ public System.Guid PartnerId {
+ get {
+ return this.partnerIdField;
+ }
+ set {
+ this.partnerIdField = value;
+ }
+ }
+
+ ///
+ public OrderStatusEnum Status {
+ get {
+ return this.statusField;
+ }
+ set {
+ this.statusField = value;
+ }
+ }
+
+ ///
+ [System.Xml.Serialization.XmlArrayItemAttribute("OrderLine")]
+ public object[] OrderLines {
+ get {
+ return this.orderLinesField;
+ }
+ set {
+ this.orderLinesField = value;
+ }
+ }
+}
+
+///
+[System.CodeDom.Compiler.GeneratedCodeAttribute("xsd", "2.0.50727.3038")]
+[System.SerializableAttribute()]
+[System.Xml.Serialization.XmlTypeAttribute(Namespace="http://tempuri.net/OrderService.Messages")]
+[System.Xml.Serialization.XmlRootAttribute(Namespace="http://tempuri.net/OrderService.Messages", IsNullable=false)]
+public enum OrderStatusEnum {
+
+ ///
+ Tentative,
+
+ ///
+ Recieved,
+
+ ///
+ Authorized,
+
+ ///
+ Rejected,
+
+ ///
+ Accepted,
+}
+
+///
+[System.CodeDom.Compiler.GeneratedCodeAttribute("xsd", "2.0.50727.3038")]
+[System.SerializableAttribute()]
+[System.Diagnostics.DebuggerStepThroughAttribute()]
+[System.ComponentModel.DesignerCategoryAttribute("code")]
+[System.Xml.Serialization.XmlTypeAttribute(Namespace="http://tempuri.net/OrderService.Messages")]
+[System.Xml.Serialization.XmlRootAttribute(Namespace="http://tempuri.net/OrderService.Messages", IsNullable=true)]
+public partial class OrderMessage {
+
+ private bool doneField;
+
+ private System.DateTime provideByField;
+
+ private object[] orderLinesField;
+
+ private string purchaseOrderNumberField;
+
+ private System.Guid partnerIdField;
+
+ ///
+ public bool Done {
+ get {
+ return this.doneField;
+ }
+ set {
+ this.doneField = value;
+ }
+ }
+
+ ///
+ public System.DateTime ProvideBy {
+ get {
+ return this.provideByField;
+ }
+ set {
+ this.provideByField = value;
+ }
+ }
+
+ ///
+ [System.Xml.Serialization.XmlArrayItemAttribute("OrderLine")]
+ public object[] OrderLines {
+ get {
+ return this.orderLinesField;
+ }
+ set {
+ this.orderLinesField = value;
+ }
+ }
+
+ ///
+ public string PurchaseOrderNumber {
+ get {
+ return this.purchaseOrderNumberField;
+ }
+ set {
+ this.purchaseOrderNumberField = value;
+ }
+ }
+
+ ///
+ public System.Guid PartnerId {
+ get {
+ return this.partnerIdField;
+ }
+ set {
+ this.partnerIdField = value;
+ }
+ }
+}
+
+///
+[System.CodeDom.Compiler.GeneratedCodeAttribute("xsd", "2.0.50727.3038")]
+[System.SerializableAttribute()]
+[System.Diagnostics.DebuggerStepThroughAttribute()]
+[System.ComponentModel.DesignerCategoryAttribute("code")]
+[System.Xml.Serialization.XmlTypeAttribute(TypeName="ArrayOfOrderLine", Namespace="http://tempuri.net/OrderService.Messages")]
+[System.Xml.Serialization.XmlRootAttribute("ArrayOfOrderLine", Namespace="http://tempuri.net/OrderService.Messages", IsNullable=true)]
+public partial class ArrayOfOrderLine1 {
+
+ private object[] orderLineField;
+
+ ///
+ [System.Xml.Serialization.XmlElementAttribute("OrderLine", IsNullable=true)]
+ public object[] OrderLine {
+ get {
+ return this.orderLineField;
+ }
+ set {
+ this.orderLineField = value;
+ }
+ }
+}
+
+///
+[System.CodeDom.Compiler.GeneratedCodeAttribute("xsd", "2.0.50727.3038")]
+[System.SerializableAttribute()]
+[System.Diagnostics.DebuggerStepThroughAttribute()]
+[System.ComponentModel.DesignerCategoryAttribute("code")]
+[System.Xml.Serialization.XmlTypeAttribute(Namespace="http://tempuri.net/OrderService.Messages")]
+[System.Xml.Serialization.XmlRootAttribute(Namespace="http://tempuri.net/OrderService.Messages", IsNullable=true)]
+public partial class OrderLine {
+
+ private System.Guid productIdField;
+
+ private float quantityField;
+
+ ///
+ public System.Guid ProductId {
+ get {
+ return this.productIdField;
+ }
+ set {
+ this.productIdField = value;
+ }
+ }
+
+ ///
+ public float Quantity {
+ get {
+ return this.quantityField;
+ }
+ set {
+ this.quantityField = value;
+ }
+ }
+}
+
+///
+[System.CodeDom.Compiler.GeneratedCodeAttribute("xsd", "2.0.50727.3038")]
+[System.SerializableAttribute()]
+[System.Diagnostics.DebuggerStepThroughAttribute()]
+[System.ComponentModel.DesignerCategoryAttribute("code")]
+[System.Xml.Serialization.XmlTypeAttribute(Namespace="http://tempuri.net/OrderService.Messages")]
+[System.Xml.Serialization.XmlRootAttribute(Namespace="http://tempuri.net/OrderService.Messages", IsNullable=true)]
+public partial class CancelOrderMessage {
+
+ private string purchaseOrderNumberField;
+
+ private System.Guid partnerIdField;
+
+ ///
+ public string PurchaseOrderNumber {
+ get {
+ return this.purchaseOrderNumberField;
+ }
+ set {
+ this.purchaseOrderNumberField = value;
+ }
+ }
+
+ ///
+ public System.Guid PartnerId {
+ get {
+ return this.partnerIdField;
+ }
+ set {
+ this.partnerIdField = value;
+ }
+ }
+}
diff --git a/Samples/Manufacturing/Manufacturing.sln b/Samples/Manufacturing/Manufacturing.sln
index ba7f0fca627..3e60f4ee090 100644
--- a/Samples/Manufacturing/Manufacturing.sln
+++ b/Samples/Manufacturing/Manufacturing.sln
@@ -23,6 +23,8 @@ Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Partner", "Partner\Partner.
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "OrderService.Persistence", "OrderService.Persistence\OrderService.Persistence.csproj", "{C34B917B-14A4-4FFB-A744-F32E9AFBAECD}"
EndProject
+Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "InteropPartner", "InteropPartner\InteropPartner.csproj", "{AF9929C8-85B8-4A36-9EC8-E46C17FE3B65}"
+EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU
@@ -65,6 +67,10 @@ Global
{C34B917B-14A4-4FFB-A744-F32E9AFBAECD}.Debug|Any CPU.Build.0 = Debug|Any CPU
{C34B917B-14A4-4FFB-A744-F32E9AFBAECD}.Release|Any CPU.ActiveCfg = Release|Any CPU
{C34B917B-14A4-4FFB-A744-F32E9AFBAECD}.Release|Any CPU.Build.0 = Release|Any CPU
+ {AF9929C8-85B8-4A36-9EC8-E46C17FE3B65}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
+ {AF9929C8-85B8-4A36-9EC8-E46C17FE3B65}.Debug|Any CPU.Build.0 = Debug|Any CPU
+ {AF9929C8-85B8-4A36-9EC8-E46C17FE3B65}.Release|Any CPU.ActiveCfg = Release|Any CPU
+ {AF9929C8-85B8-4A36-9EC8-E46C17FE3B65}.Release|Any CPU.Build.0 = Release|Any CPU
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
diff --git a/Samples/Manufacturing/Manufacturing.suo b/Samples/Manufacturing/Manufacturing.suo
index 9041f884744..d45ac9a8d01 100644
Binary files a/Samples/Manufacturing/Manufacturing.suo and b/Samples/Manufacturing/Manufacturing.suo differ
diff --git a/Samples/Manufacturing/OrderService.Persistence/TableDefinitions.sql b/Samples/Manufacturing/OrderService.Persistence/TableDefinitions.sql
index 704df57a6cb..6fae6851b34 100644
--- a/Samples/Manufacturing/OrderService.Persistence/TableDefinitions.sql
+++ b/Samples/Manufacturing/OrderService.Persistence/TableDefinitions.sql
@@ -6,7 +6,7 @@ SET ANSI_PADDING ON
GO
CREATE TABLE [dbo].[OrderSagaData](
[Id] [uniqueidentifier] NOT NULL,
- [Originator] [varchar](50) COLLATE Latin1_General_CI_AS NOT NULL,
+ [Originator] [varchar](50) COLLATE Latin1_General_CI_AS,
[PurchaseOrderNumber] [varchar](50) COLLATE Latin1_General_CI_AS NOT NULL,
[PartnerId] [uniqueidentifier] NOT NULL,
[ProvideBy] [datetime] NOT NULL,
diff --git a/src/impl/Serializers/NServiceBus.Serializers.XML/MessageSerializer.cs b/src/impl/Serializers/NServiceBus.Serializers.XML/MessageSerializer.cs
index edb28ca2323..0850067b1e8 100644
--- a/src/impl/Serializers/NServiceBus.Serializers.XML/MessageSerializer.cs
+++ b/src/impl/Serializers/NServiceBus.Serializers.XML/MessageSerializer.cs
@@ -94,13 +94,23 @@ public IMessage[] Deserialize(Stream stream)
}
}
- foreach (XmlNode node in doc.DocumentElement.ChildNodes)
+ if (doc.DocumentElement.Name.ToLower() != "messages")
{
object m = null;
- Process(node, ref m);
+ Process(doc.DocumentElement, ref m);
result.Add(m as IMessage);
}
+ else
+ {
+ foreach (XmlNode node in doc.DocumentElement.ChildNodes)
+ {
+ object m = null;
+ Process(node, ref m);
+
+ result.Add(m as IMessage);
+ }
+ }
defaultNameSpace = null;
@@ -232,7 +242,7 @@ public void Serialize(IMessage[] messages, Stream stream)
for (int i = 0; i < namespaces.Count; i++)
{
- builder.AppendFormat(" xmlns{0}=\"{1}/{2}\"", (i == namespaces.Count - 1 ? ":q" + i : ""), nameSpace, namespaces[i]);
+ builder.AppendFormat(" xmlns{0}=\"{1}/{2}\"", (i != namespaces.Count - 1 ? ":q" + i : ""), nameSpace, namespaces[i]);
namespacesToPrefix[namespaces[i]] = i;
}
@@ -263,7 +273,8 @@ public void Write(StringBuilder builder, Type t, object obj)
public void WriteObject(string name, Type type, object value, StringBuilder builder)
{
string element = name;
- int i = namespacesToPrefix[type.Namespace];
+ int i;
+ namespacesToPrefix.TryGetValue(type.Namespace, out i);
if (i > 0)
element = "q" + i + ":" + name;
diff --git a/src/unicast/NServiceBus.Unicast/UnicastBus.cs b/src/unicast/NServiceBus.Unicast/UnicastBus.cs
index 3be3d9bd8b1..fcbeffa8feb 100644
--- a/src/unicast/NServiceBus.Unicast/UnicastBus.cs
+++ b/src/unicast/NServiceBus.Unicast/UnicastBus.cs
@@ -480,6 +480,12 @@ public ICallback Send(string destination, Action messageConstructor) where
/// The list of messages to send.
public ICallback Send(string destination, params IMessage[] messages)
{
+ if (destination == null)
+ {
+ log.Info("No destination specified. Not sending messages.");
+ return null;
+ }
+
TransportMessage toSend = this.GetTransportMessageFor(destination, messages);
this.transport.Send(toSend, destination);
@@ -530,8 +536,6 @@ public virtual void Start()
this.transport.MessageTypesToBeReceived = this.messageTypes;
- this.transport.Start();
-
this.InitializeSelf();
this.SendReadyMessage(true);
@@ -567,6 +571,8 @@ public virtual void Start()
}
}
+ this.transport.Start();
+
this.started = true;
}
}
@@ -849,6 +855,9 @@ void transport_FinishedMessageProcessing(object sender, EventArgs e)
/// A is used out of convenience as the initialization message.
private bool IsInitializationMessage(TransportMessage msg)
{
+ if (msg.ReturnAddress == null)
+ return false;
+
if (!msg.ReturnAddress.Contains(this.transport.Address))
return false;