[ComponentCategory(CategoryTypes.CATID_PipelineComponent)]
[System.Runtime.InteropServices.Guid("a06fc47a-8349-4ed0-a3b3-e2de3f13beaa")]
[ComponentCategory(CategoryTypes.CATID_DisassemblingParser)]
public class XmlDecomposer :
Microsoft.BizTalk.Component.Interop.IDisassemblerComponent,
IBaseComponent, IPersistPropertyBag, IComponentUI
{
public virtual void Save(Microsoft.BizTalk.Component.Interop.IPropertyBag pb, bool fClearDirty, bool fSaveAllProperties)
this.WritePropertyBag(pb, "EnforeValidatation", this.EnforeValidatation);
this.WritePropertyBag(pb, "MessagePropertyName", this.MessagePropertyName);
this.WritePropertyBag(pb, "PartPropertyName", this.PartPropertyName);
this.WritePropertyBag(pb, "MessagePropertyNameSpace", this.MessagePropertyNameSpace);
this.WritePropertyBag(pb, "PartPropertyNameSpace", this.PartPropertyNameSpace);
#error please implement IPersistPropertyBag.Save for property "Schemas"
}
public void Disassemble(Microsoft.BizTalk.Component.Interop.IPipelineContext pc,
Microsoft.BizTalk.Message.Interop.IBaseMessage inmsg)
//
// TODO: implement message retrieval logic
_msgs.Enqueue(inmsg);
public string Convert(Schema s)
using (MemoryStream ms = new MemoryStream())
BinaryFormatter f = new BinaryFormatter();
f.Serialize(ms, s);
return System.Convert.ToBase64String(ms.ToArray());
public Schema Convert(string s)
using (MemoryStream ms = new MemoryStream(System.Convert.FromBase64String(s)))
return (Schema)f.Deserialize(ms);
public string Convert(SchemaList sl)
StringBuilder sb = new StringBuilder();
int len = sl.Count;
for (int i = 0; i < len; ++i)
sb.Append(SchemaUtil.Instance.Convert(sl[i]));
if ((i + 1) != len) sb.Append(r_Separator);
return sb.ToString();
public SchemaList Convert(string s)
SchemaList sl = new SchemaList();
string[] schemaList = s.Split(new char[] { r_Separator });
foreach (string schema in schemaList)
sl.Add(SchemaUtil.Instance.Convert(schema));
return sl;
val = this.ReadPropertyBag(pb, "Schemas");
if (val != null)
Schemas = SchemaListUtil.Instance.Convert(val.ToString());
this.WritePropertyBag(pb, "Schemas", SchemaListUtil.Instance.Convert(Schemas));
foreach (Schema schema in schemas)
if (s.ContainsKey(schema))
continue;
IDocumentSpec documentSpecByName = pc.GetDocumentSpecByName(schema.SchemaName);
s.Add(schema, documentSpecByName.GetSchemaCollection());
Dictionary<string, Assembly> Assemblies = new Dictionary<string, Assembly>();
if (string.IsNullOrEmpty(schema.AssemblyName)) continue;
if (!Assemblies.ContainsKey(schema.AssemblyName))
Assemblies.Add(schema.AssemblyName, Assembly.Load(schema.AssemblyName));
SchemaBase baseSchema = (SchemaBase)
Activator.CreateInstance(Assemblies[schema.AssemblyName].GetType(schema.DocSpecName));
s.Add(schema, baseSchema.SchemaCollection);
// not supported otherwise
if (inmsg.PartCount != 1)
return;
Dictionary<Guid, Pair<Schema, Stream>> dvn = XmlValidableNodesFinder.Instance.Find(
inmsg.BodyPart.GetOriginalDataStream(), this.Schemas);
if (EnforeValidatation)
Dictionary<Schema, XmlSchemaCollection> s =
XmlValidableNodesFinder.Instance.Convert(pc, this.Schemas);
XmlValidableNodesFinder.Instance.ValidateXmlDocumentsAgainstSchema(dvn, s);
IBaseMessageFactory bmf = pc.GetMessageFactory();
IBaseMessage bm = bmf.CreateMessage();
//! body part must be added first !
bm.AddPart(Guid.Empty.ToString(), BuildMessagePart(bmf, dvn[Guid.Empty], pc), true);
//add validated sub xml as new parts if any
foreach (KeyValuePair<Guid, Pair<Schema, Stream>> kvp in dvn)
if (kvp.Key == Guid.Empty)
bm.AddPart(kvp.Key.ToString(), BuildMessagePart(bmf, kvp.Value, pc), false);
bm.Context = PipelineUtil.CloneMessageContext(inmsg.Context);
if (!string.IsNullOrEmpty(MessagePropertyName) &&
MessagePropertyName != r_DefaultMessagePropertyName &&
!string.IsNullOrEmpty(MessagePropertyNameSpace) &&
MessagePropertyNameSpace != r_DefaultMessagePropertyNameSpace)
bm.Context.Promote(this.MessagePropertyName, this.MessagePropertyNameSpace, true);
_msgs.Enqueue(bm);
rivate IBaseMessagePart BuildMessagePart(IBaseMessageFactory bmf, Pair<Schema, Stream> pair, IPipelineContext pc)
if (null == bmf || null == pair.Right)
return null;
IBaseMessagePart bmp = bmf.CreateMessagePart();
if (!string.IsNullOrEmpty(PartPropertyName) &&
PartPropertyName != r_DefaultPartPropertyName &&
!string.IsNullOrEmpty(PartPropertyNameSpace) &&
PartPropertyNameSpace != r_DefaultPartPropertyNameSpace)
bmp.PartProperties.Write(this.PartPropertyName, this.PartPropertyNameSpace, pair.Left.DocSpecName);
bmp.Data = pair.Right;
pc.ResourceTracker.AddResource(pair.Right);
bmp.Data.Position = 0;
return bmp;