I'm copying components between versions of essentially the same schema, of which the latter has a stricter XSLT attached to it's RTF field.
The code (TOM.Net):
value = ((TextField)oldField).Value;
var def = (XhtmlFieldDefinition)field.Definition;
var tfm = new XslCompiledTransform();
tfm.Load(def.FilterXslt);
var settings = new XmlReaderSettings();
settings.ConformanceLevel = ConformanceLevel.Fragment;
using (var sw = new StringWriter())
{
using (var sr = new StringReader(value))
{
using (var reader = XmlReader.Create(sr, settings))
{
tfm.Transform(reader, null, sw);
field.Value = sw.ToString();
}
}
}
The problems i'm getting:
If it runs "as is", all XML is trippedstripped off. That's likely because input value has xmlns="http://www.w3.org/1999/xhtml" declaration on some (not all, by the way) of it's HTML tags, but in XSLT these tags are not bound to anything but default xmlns="http://www.w3.org/1999/XSL/Transform".
If i do an unfair move by exterminating "xmlns" in content, say, like this: new StringReader(value.Replace(@" xmlns=""http://www.w3.org/1999/xhtml""", string.Empty)), then transform works fine, but upon calling component.Save(), it says something like this:
XML validation error. Reason: The element 'text' in namespace 'http://www.unilever.com/general' has invalid child element 'h2'. List of possible elements expected: any element in namespace 'http://www.w3.org/1999/xhtml'..
As i understand, the proper way of tackling my problem would be to alter XSLT in such a way as to: 1. Declare XHTML namespace, 2. Modify XPath expressions to use FQ names.
Unfortunately, modifying field's XSLT is not an option.
Also, ILSpy cannot find any references of XhtmlFieldDefinition.FilterXslt to get an idea how Tridion itself does it.
How to transform XHtmlField value according to attached filter XSLT?
EDIT
LinqPad snipped that demonstrates the transformation (but not the behavior during Save!): https://gist.github.com/esteewhy/6248993