private static BundleEntry loadEntry(XElement entry) { BundleEntry result; try { if (entry.Name == XTOMBSTONE + XATOM_DELETED_ENTRY) { result = new DeletedEntry(); result.Id = SerializationUtil.UriValueOrNull(entry.Attribute(XATOM_DELETED_REF)); } else { XElement content = entry.Element(XATOMNS + XATOM_CONTENT); var id = SerializationUtil.UriValueOrNull(entry.Element(XATOMNS + XATOM_ID)); if (content != null) { var parsed = getContents(content); if (parsed != null) { result = ResourceEntry.Create(parsed); } else { throw Error.Format("BundleEntry has a content element without content", XmlDomFhirReader.GetLineInfo(content)); } } else { result = SerializationUtil.CreateResourceEntryFromId(id); } result.Id = id; } result.Links = getLinks(entry.Elements(XATOMNS + XATOM_LINK)); result.Tags = TagListParser.ParseTags(entry.Elements(XATOMNS + XATOM_CATEGORY)); if (result is DeletedEntry) { ((DeletedEntry)result).When = SerializationUtil.InstantOrNull(entry.Attribute(XATOM_DELETED_WHEN)); } else { ResourceEntry re = (ResourceEntry)result; re.Title = SerializationUtil.StringValueOrNull(entry.Element(XATOMNS + XATOM_TITLE)); re.LastUpdated = SerializationUtil.InstantOrNull(entry.Element(XATOMNS + XATOM_UPDATED)); re.Published = SerializationUtil.InstantOrNull(entry.Element(XATOMNS + XATOM_PUBLISHED)); re.AuthorName = entry.Elements(XATOMNS + XATOM_AUTHOR).Count() == 0 ? null : SerializationUtil.StringValueOrNull(entry.Element(XATOMNS + XATOM_AUTHOR) .Element(XATOMNS + XATOM_AUTH_NAME)); re.AuthorUri = entry.Elements(XATOMNS + XATOM_AUTHOR).Count() == 0 ? null : SerializationUtil.StringValueOrNull(entry.Element(XATOMNS + XATOM_AUTHOR) .Element(XATOMNS + XATOM_AUTH_URI)); } } catch (Exception exc) { throw Error.Format("Exception while reading entry: " + exc.Message, XmlDomFhirReader.GetLineInfo(entry)); } return(result); }
public static string ToXml(this ITypedElement source, FhirXmlSerializationSettings settings = null) => SerializationUtil.WriteXmlToString(writer => source.WriteTo(writer, settings), settings?.Pretty ?? false, settings?.AppendNewLine ?? false);
public static byte[] ToXmlBytes(this ITypedElement source, FhirXmlSerializationSettings settings = null) => SerializationUtil.WriteXmlToBytes(writer => source.WriteTo(writer, settings));
#pragma warning disable 612, 618 public static string ToXml(this IElementNavigator source, FhirXmlSerializationSettings settings = null) => SerializationUtil.WriteXmlToString(writer => source.WriteTo(writer, settings), settings?.Pretty ?? false);
private void build(ITypedElement source, XContainer parent) { var xmlDetails = source.GetXmlSerializationDetails(); var sourceComments = (source as IAnnotated)?.Annotation <SourceComments>(); if (!MustSerializeMember(source, out var serializationInfo)) { return; } bool hasTypeInfo = serializationInfo != null; var value = source.Value != null? PrimitiveTypeConverter.ConvertTo <string>(source.Value) : null; // xhtml children require special treament: // - They don't use an xml "value" attribute to represent the value, instead their Value is inserted verbatim into the parent // - They cannot have child nodes - the "Value" on the node contains all children as raw xml text var isXhtml = source.InstanceType == "xhtml" || serializationInfo?.Representation == XmlRepresentation.XHtml || xmlDetails?.Namespace?.GetName("div") == XmlNs.XHTMLDIV; if (isXhtml && !String.IsNullOrWhiteSpace(value)) { // The value *should* be valid xhtml - however if people just provide a plain // string, lets add a <div> around it. if (!value.TrimStart().StartsWith("<div")) { value = $"<div xmlns='http://www.w3.org/1999/xhtml'>{value}</div>"; } var sanitized = SerializationUtil.SanitizeXml(value); XElement xe = XElement.Parse(sanitized); // The div should be in the XHTMLNS namespace, correct if it // is not the case. xe.Name = XmlNs.XHTMLNS + xe.Name.LocalName; parent.Add(xe); //using (var divWriter = parent.CreateWriter()) //using (var nodeReader = SerializationUtil.XmlReaderFromXmlText(value)) // divWriter.WriteNode(nodeReader, false); return; } var usesAttribute = serializationInfo?.Representation == XmlRepresentation.XmlAttr || (xmlDetails?.NodeType == XmlNodeType.Attribute); var ns = serializationInfo?.NonDefaultNamespace ?? xmlDetails?.Namespace.NamespaceName ?? (usesAttribute ? "" : XmlNs.FHIR); bool atRoot = parent is XDocument; var localName = serializationInfo?.IsChoiceElement == true ? source.Name + source.InstanceType.Capitalize() : source.Name; // If the node is represented by an attribute (e.g. an "id" child), write // an attribute with the child's name + the child's Value into the parent if (usesAttribute && !String.IsNullOrWhiteSpace(value) && !atRoot) { parent.Add(new XAttribute(XName.Get(localName, ns), value)); return; } // else: fall through - value will be serialized as an element var me = new XElement(XName.Get(localName, ns)); if (xmlDetails?.SchemaLocation != null) { me.Add(new XAttribute(XmlNs.XSCHEMALOCATION, xmlDetails.SchemaLocation)); } // If the node has a value, add the standard FHIR value attribute if (value != null) { me.Add(new XAttribute("value", value)); } // If this needs to be serialized as a contained resource, do so var containedResourceType = atRoot ? null : (serializationInfo?.IsResource == true ? source.InstanceType : source.Annotation <IResourceTypeSupplier>()?.ResourceType); XElement containedResource = null; if (containedResourceType != null) { containedResource = new XElement(XName.Get(containedResourceType, ns)); } var childParent = containedResource ?? me; // Now, do the same for the children // xml requires a certain order, so let's make sure we serialize in the right order var orderedChildren = source.Children().OrderBy(c => c.Definition?.Order ?? 0); foreach (var child in orderedChildren) { build(child, childParent); } if (serializationInfo?.Representation == XmlRepresentation.XmlText || xmlDetails?.NodeText != null) { childParent.Add(new XText(value ?? xmlDetails.NodeText)); } if (sourceComments?.ClosingComments != null) { writeComments(sourceComments.ClosingComments, me); } // Only really add this contained resource to me when it has contents if (containedResource != null && (containedResource.HasAttributes || containedResource.HasElements)) { me.Add(containedResource); } // Only add myself to my parent if I have content, or I am the root if (value != null || me.HasElements || atRoot) { if (sourceComments?.CommentsBefore != null) { writeComments(sourceComments.CommentsBefore, parent); } parent.Add(me); } if (atRoot && parent.Elements().Any() && sourceComments?.DocumentEndComments != null) { writeComments(sourceComments.DocumentEndComments, parent); } }
public static string ToJson(this IElementNavigator source, FhirJsonSerializationSettings settings = null) => SerializationUtil.WriteJsonToString(writer => source.WriteTo(writer, settings), settings?.Pretty ?? false, settings?.AppendNewLine ?? false);
public static string ToJson(this ISourceNode source, FhirJsonSerializationSettings settings = null) => SerializationUtil.WriteJsonToString(writer => source.WriteTo(writer, settings), settings?.Pretty ?? false);
private static JObject createEntry(BundleEntry entry, bool summary) { JObject result = new JObject(); if (entry is ResourceEntry) { ResourceEntry re = (ResourceEntry)entry; if (!String.IsNullOrEmpty(re.Title)) { result.Add(new JProperty(BundleXmlParser.XATOM_TITLE, re.Title)); } if (SerializationUtil.UriHasValue(entry.Id)) { result.Add(new JProperty(BundleXmlParser.XATOM_ID, entry.Id.ToString())); } if (re.LastUpdated != null) { result.Add(new JProperty(BundleXmlParser.XATOM_UPDATED, re.LastUpdated)); } if (re.Published != null) { result.Add(new JProperty(BundleXmlParser.XATOM_PUBLISHED, re.Published)); } if (!String.IsNullOrWhiteSpace(re.AuthorName)) { result.Add(jsonCreateAuthor(re.AuthorName, re.AuthorUri)); } } else { DeletedEntry de = (DeletedEntry)entry; if (de.When != null) { result.Add(new JProperty(BundleJsonParser.JATOM_DELETED, de.When)); } if (SerializationUtil.UriHasValue(entry.Id)) { result.Add(new JProperty(BundleXmlParser.XATOM_ID, entry.Id.ToString())); } } if (entry.Links != null && entry.Links.Count() > 0) { result.Add(new JProperty(BundleXmlParser.XATOM_LINK, jsonCreateLinkArray(entry.Links))); } if (entry.Tags != null && entry.Tags.Count() > 0) { result.Add(TagListSerializer.CreateTagCategoryPropertyJson(entry.Tags)); } if (entry is ResourceEntry) { ResourceEntry re = (ResourceEntry)entry; if (re.Resource != null) { result.Add(new JProperty(BundleXmlParser.XATOM_CONTENT, getContentsAsJObject(re.Resource, summary))); } // Note: this is a read-only property, so it is serialized but never parsed if (entry.Summary != null) { result.Add(new JProperty(BundleXmlParser.XATOM_SUMMARY, entry.Summary)); } } return(result); }
internal static Bundle Load(JsonReader reader) { JObject feed; try { reader.DateParseHandling = DateParseHandling.None; reader.FloatParseHandling = FloatParseHandling.Decimal; feed = JObject.Load(reader); if (feed.Value <string>(JsonDomFhirReader.RESOURCETYPE_MEMBER_NAME) != "Bundle") { throw Error.Format("Input data is not an json FHIR bundle", null); } } catch (Exception exc) { throw Error.Format("Exception while parsing feed: " + exc.Message, null); } Bundle result; try { result = new Bundle() { Title = feed.Value <string>(BundleXmlParser.XATOM_TITLE), LastUpdated = instantOrNull(feed[BundleXmlParser.XATOM_UPDATED]), Id = SerializationUtil.UriValueOrNull(feed[BundleXmlParser.XATOM_ID]), Links = getLinks(feed[BundleXmlParser.XATOM_LINK]), Tags = TagListParser.ParseTags(feed[BundleXmlParser.XATOM_CATEGORY]), AuthorName = feed[BundleXmlParser.XATOM_AUTHOR] as JArray != null ? feed[BundleXmlParser.XATOM_AUTHOR] .Select(auth => auth.Value <string>(BundleXmlParser.XATOM_AUTH_NAME)) .FirstOrDefault() : null, AuthorUri = feed[BundleXmlParser.XATOM_AUTHOR] as JArray != null ? feed[BundleXmlParser.XATOM_AUTHOR] .Select(auth => auth.Value <string>(BundleXmlParser.XATOM_AUTH_URI)) .FirstOrDefault() : null, TotalResults = intValueOrNull(feed[BundleXmlParser.XATOM_TOTALRESULTS]) }; } catch (Exception exc) { throw Error.Format("Exception while parsing json feed attributes: " + exc.Message, null); } var entries = feed[BundleXmlParser.XATOM_ENTRY]; if (entries != null) { if (!(entries is JArray)) { throw Error.Format("The json feed contains a single entry, instead of an array", null); } result.Entries = loadEntries((JArray)entries, result); } return(result); }
private static BundleEntry loadEntry(JObject entry) { BundleEntry result; try { if (entry[JATOM_DELETED] != null) { result = new DeletedEntry(); result.Id = SerializationUtil.UriValueOrNull(entry[BundleXmlParser.XATOM_ID]); } else { var content = entry[BundleXmlParser.XATOM_CONTENT]; var id = SerializationUtil.UriValueOrNull(entry[BundleXmlParser.XATOM_ID]); if (id == null) { throw Error.Format("BundleEntry found without an id", null); } if (content != null) { var parsed = getContents(content); if (parsed != null) { result = ResourceEntry.Create(parsed); } else { throw Error.Format("BundleEntry {0} has a content element without content", null, id); } } else { result = SerializationUtil.CreateResourceEntryFromId(id); } result.Id = id; } result.Links = getLinks(entry[BundleXmlParser.XATOM_LINK]); result.Tags = TagListParser.ParseTags(entry[BundleXmlParser.XATOM_CATEGORY]); if (result is DeletedEntry) { ((DeletedEntry)result).When = instantOrNull(entry[JATOM_DELETED]); } else { var re = (ResourceEntry)result; re.Title = entry.Value <string>(BundleXmlParser.XATOM_TITLE); re.LastUpdated = instantOrNull(entry[BundleXmlParser.XATOM_UPDATED]); re.Published = instantOrNull(entry[BundleXmlParser.XATOM_PUBLISHED]); re.AuthorName = entry[BundleXmlParser.XATOM_AUTHOR] as JArray != null ? entry[BundleXmlParser.XATOM_AUTHOR] .Select(auth => auth.Value <string>(BundleXmlParser.XATOM_AUTH_NAME)) .FirstOrDefault() : null; re.AuthorUri = entry[BundleXmlParser.XATOM_AUTHOR] as JArray != null ? entry[BundleXmlParser.XATOM_AUTHOR] .Select(auth => auth.Value <string>(BundleXmlParser.XATOM_AUTH_URI)) .FirstOrDefault() : null; } } catch (Exception exc) { throw Error.Format("Exception while reading entry: " + exc.Message, null); } return(result); }
// [WMR 20160421] Note: StringReader, XmlReader and JsonReader don't require explicit disposal // JsonTextReader overrides Close method => explicitly dispose public static XmlReader XmlReaderFromXmlText(string xml) { return(WrapXmlReader(XmlReader.Create(new StringReader(SerializationUtil.SanitizeXml(xml))))); }
public static XDocument XDocumentFromXmlText(string xml) { return(XDocument.Parse(SerializationUtil.SanitizeXml(xml))); }