Code:
/ Dotnetfx_Vista_SP2 / Dotnetfx_Vista_SP2 / 8.0.50727.4016 / DEVDIV / depot / DevDiv / releases / Orcas / QFE / ndp / fx / src / DataWeb / Server / System / Data / Services / Serializers / PlainXmlDeserializer.cs / 1 / PlainXmlDeserializer.cs
//---------------------------------------------------------------------- //// Copyright (c) Microsoft Corporation. All rights reserved. // //// Provides a deserializer for plain XML content. // // // @owner [....] //--------------------------------------------------------------------- namespace System.Data.Services.Serializers { using System; using System.Diagnostics; using System.IO; using System.Text; using System.Xml; using System.Data.Services.Parsing; using System.Data.Services.Providers; ///Provides a deserializer for plain XML content. internal class PlainXmlDeserializer : Deserializer { ///reader to read xml from the request stream private readonly XmlReader xmlReader; ///Whether private readonly bool xmlReaderOwned; ///is owned and should be disposed of. Initializes a new /// Input stream reader from which POX content must be read. /// Encoding to use for the stream (null to auto-discover). /// Data service for which the deserializer will act. /// Indicates whether this is a PUT operation (rather than POST). /// Tracker to use for modifications. internal PlainXmlDeserializer(Stream stream, Encoding encoding, IDataService dataService, bool update, UpdateTracker tracker) : base(update, dataService, tracker) { Debug.Assert(stream != null, "stream != null"); this.xmlReader = XmlUtil.CreateXmlReader(stream, encoding); this.xmlReaderOwned = true; } ///for the specified stream. Initializes a new /// Reader for content. /// Parent deserializer. internal PlainXmlDeserializer(XmlReader reader, Deserializer deserializer) : base(deserializer) { Debug.Assert(reader != null, "reader != null"); this.xmlReader = reader; // this.xmlReaderOwned = false; } ///based on the settings for another one. Returns the content format for the deserializer. protected override ContentFormat ContentFormat { get { return ContentFormat.PlainXml; } } ///Applies properties from the reader to the specified resource. /// Deserializer which is driving the. /// XmlReader to read from. /// Type of resource. /// Resource to set value on. /// current object count for this operation. /// /// This method will end as soon as it find something that is not an /// XML element to process. /// internal static void ApplyContent(Deserializer deserializer, XmlReader reader, ResourceType resourceType, object resource, int currentObjectCount) { Debug.Assert(deserializer != null, "deserializer != null"); Debug.Assert(reader != null, "reader != null"); using (PlainXmlDeserializer xml = new PlainXmlDeserializer(reader, deserializer)) { // Initialize the new deserializer instance with the current object count xml.UpdateObjectCount(currentObjectCount); // load all the properties xml.ApplyContent(xml.xmlReader, resourceType, resource); // After all the properties have been loaded, initialize the current deserializer value with the object count deserializer.UpdateObjectCount(xml.MaxObjectCount); } } ////// Converts the given value to the expected type as per XML serializer rules. /// Make sure these rules are in [....] with PlainXmlSerializer. /// /// value to the converted /// name of the property whose value is getting converted /// clr type to which the value needs to be converted to ///object which is in [....] with the properties type internal static object ConvertValuesForXml(object value, string propertyName, Type typeToBeConverted) { Debug.Assert(WebUtil.IsPrimitiveType(typeToBeConverted), "WebUtil.IsPrimitiveType(typeToBeConverted)"); string stringValue = value as string; if (stringValue != null) { try { value = WebConvert.StringToPrimitive(stringValue, typeToBeConverted); } catch (FormatException e) { throw DataServiceException.CreateBadRequestError(Strings.BadRequest_ErrorInConvertingPropertyValue(propertyName, typeToBeConverted), e); } } return value; } ////// Assumes the payload to represent a single object and processes accordingly /// /// info about the object being created ///the newly formed object that the payload represents protected override object CreateSingleObject(SegmentInfo segmentInfo) { Debug.Assert( #if ASTORIA_OPEN_OBJECT segmentInfo.TargetKind == RequestTargetKind.OpenProperty || #endif segmentInfo.TargetKind == RequestTargetKind.ComplexObject || segmentInfo.TargetKind == RequestTargetKind.Primitive, segmentInfo.TargetKind + " is one of open property; complex object; primitive -- otherwise the wrong serializer was chosen"); if (!WebUtil.XmlReaderEnsureElement(this.xmlReader)) { throw DataServiceException.CreateBadRequestError(Strings.PlainXml_PayloadLacksElement); } if (HasNullAttributeWithTrueValue(this.xmlReader)) { return null; } ResourceType resourceType; string propertyName; #if ASTORIA_OPEN_OBJECT if (segmentInfo.TargetKind == RequestTargetKind.OpenProperty) { bool typeNameSpecified; resourceType = this.ReadOpenPropertyTypeAttribute(this.xmlReader, out typeNameSpecified); if (resourceType.ResourceTypeKind == ResourceTypeKind.EntityType) { throw DataServiceException.CreateBadRequestError( Strings.PlainXml_EntityTypeNotSupported(resourceType.Type)); } Debug.Assert(resourceType != null, "resourceType != null"); propertyName = this.xmlReader.LocalName; } else #endif { Debug.Assert(segmentInfo.ProjectedProperty != null, "segmentInfo.ProjectedProperty != null"); resourceType = segmentInfo.ProjectedProperty.ResourceType; propertyName = segmentInfo.ProjectedProperty.Name; if (propertyName != this.xmlReader.LocalName) { throw DataServiceException.CreateBadRequestError( Strings.PlainXml_IncorrectElementName(propertyName, this.xmlReader.LocalName)); } } object result = this.ReadPropertyWithType(this.xmlReader, propertyName, resourceType); return result; } ///Provides an opportunity to clean-up resources. /// /// Whether the call is being made from an explicit call to /// IDisposable.Dispose() rather than through the finalizer. /// protected override void Dispose(bool disposing) { base.Dispose(disposing); if (disposing && this.xmlReaderOwned) { this.xmlReader.Close(); } } ////// Get the resource referred by the uri in the payload /// ///resource referred by the uri in the payload. protected override string GetLinkUriFromPayload() { if (!WebUtil.XmlReaderEnsureElement(this.xmlReader)) { throw DataServiceException.CreateBadRequestError(Strings.PlainXml_PayloadLacksElement); } string uri = null; bool skipped; do { skipped = false; switch (this.xmlReader.NodeType) { case XmlNodeType.Element: string localName = this.xmlReader.LocalName; string elementNamespace = this.xmlReader.NamespaceURI; if (elementNamespace != XmlConstants.DataWebMetadataNamespace || localName != XmlConstants.UriElementName) { this.xmlReader.Skip(); skipped = true; continue; } if (uri != null) { throw DataServiceException.CreateBadRequestError(Strings.BadRequest_MoreThanOneUriElementSpecified); } uri = ReadElementString(this.xmlReader, localName); if (String.IsNullOrEmpty(uri)) { throw DataServiceException.CreateBadRequestError(Strings.BadRequest_MissingUriForLinkOperation); } break; default: break; } } while (skipped || this.xmlReader.Read()); Debug.Assert( this.xmlReader.NodeType != XmlNodeType.Element, "reader.NodeType != XmlNodeType.Element -- otherwise we should have kept processing"); if (String.IsNullOrEmpty(uri)) { throw DataServiceException.CreateBadRequestError(Strings.BadRequest_MissingUriForLinkOperation); } return uri; } ////// returns true if the null attribute is specified and the value is true /// /// xml reader from which attribute needs to be read ///true if the null attribute is specified and the attribute value is true private static bool HasNullAttributeWithTrueValue(XmlReader reader) { Debug.Assert(reader != null, "reader != null"); Debug.Assert(reader.NodeType == XmlNodeType.Element, "reader.NodeType == XmlNodeType.Element"); string elementValue = reader.GetAttribute(XmlConstants.AtomNullAttributeName, XmlConstants.DataWebMetadataNamespace); // If the null attribute is specified and the value is true, then set the property value to null, // otherwise set the value to empty string if ((null != elementValue) && XmlConvert.ToBoolean(elementValue)) { string elementName = reader.LocalName; if (!reader.IsEmptyElement) { reader.Read(); if (reader.NodeType != XmlNodeType.EndElement) { throw DataServiceException.CreateBadRequestError( Strings.BadRequest_CannotSpecifyValueOrChildElementsForNullElement(elementName)); } } return true; } return false; } ////// Reads the value from the given element. This leaves the reader in the EndElement. /// /// xml reader from which the value needs to be read /// name of the element whose value is getting read ///returns the xml string values as specified in the payload private static string ReadElementString(XmlReader reader, string elementName) { Debug.Assert(reader != null, "reader != null"); Debug.Assert(XmlNodeType.Element == reader.NodeType, "not positioned on Element"); string elementValue = null; if (HasNullAttributeWithTrueValue(reader)) { return null; } else if (reader.IsEmptyElement) { return String.Empty; } StringBuilder builder = null; bool done = false; while (!done && reader.Read()) { switch (reader.NodeType) { case XmlNodeType.EndElement: done = true; break; case XmlNodeType.CDATA: case XmlNodeType.Text: case XmlNodeType.SignificantWhitespace: if (elementValue == null) { elementValue = reader.Value; } else if (builder == null) { string newValue = reader.Value; builder = new StringBuilder(newValue.Length + elementValue.Length); builder.Append(elementValue); builder.Append(newValue); } else { builder.Append(reader.Value); } break; case XmlNodeType.Comment: case XmlNodeType.Whitespace: break; #region XmlNodeType error case XmlNodeType.None: case XmlNodeType.XmlDeclaration: case XmlNodeType.Attribute: case XmlNodeType.EndEntity: case XmlNodeType.EntityReference: case XmlNodeType.Entity: case XmlNodeType.Document: case XmlNodeType.DocumentType: case XmlNodeType.DocumentFragment: case XmlNodeType.Notation: case XmlNodeType.ProcessingInstruction: default: throw DataServiceException.CreateBadRequestError(Strings.BadRequest_InvalidValue(elementName)); #endregion } } if (builder != null) { elementValue = builder.ToString(); } else if (elementValue == null) { elementValue = String.Empty; } return elementValue; } ///Applies properties from the reader to the specified resource. /// XmlReader to read from. /// Type of resource. /// Resource to set value on. ////// This method will end as soon as it find something that is not an /// XML element to process. /// private void ApplyContent(XmlReader reader, ResourceType resourceType, object resource) { Debug.Assert(resourceType != null, "resourceType != null"); Debug.Assert(resource != null, "resource != null"); if (!WebUtil.XmlReaderEnsureElement(reader)) { return; } this.RecurseEnter(); bool skipped; do { skipped = false; switch (reader.NodeType) { case XmlNodeType.Element: string localName = reader.LocalName; string elementNamespace = reader.NamespaceURI; if (elementNamespace != XmlConstants.DataWebNamespace) { reader.Skip(); skipped = true; continue; } this.ApplyProperty(reader, localName, resourceType, resource); break; default: break; } } while (skipped || reader.Read()); Debug.Assert( reader.NodeType != XmlNodeType.Element, "reader.NodeType != XmlNodeType.Element -- otherwise we should have kept processing"); this.RecurseLeave(); } ///Applies a property from the reader to the specified resource. /// XmlReader to read from. /// Name of property to set on the specified resource. /// Type of resource. /// Resource to set value on. private void ApplyProperty(XmlReader reader, string propertyName, ResourceType resourceType, object resource) { Debug.Assert(reader != null, "reader != null"); Debug.Assert(propertyName != null, "propertyName != null"); Debug.Assert(resourceType != null, "resourceType != null"); Debug.Assert(resource != null, "resource != null"); ResourceProperty property = resourceType.TryResolvePropertyName(propertyName); ResourceType propertyType; bool ignoreValue = false; if (property == null) { #if ASTORIA_OPEN_OBJECT if (resourceType.OpenTypeKind != OpenTypeKind.CompletelyOpen) #endif { throw DataServiceException.CreateBadRequestError(Strings.BadRequest_InvalidPropertyNameSpecified(propertyName, resourceType.FullName)); } #if ASTORIA_OPEN_OBJECT bool typeNameSpecified; propertyType = this.ReadOpenPropertyTypeAttribute(reader, out typeNameSpecified); #endif } else { propertyType = property.ResourceType; if (this.Update && property.IsOfKind(ResourcePropertyKind.Key)) { ignoreValue = true; } } object propertyValue = this.ReadPropertyWithType(reader, propertyName, propertyType); if (!ignoreValue) { this.Service.Provider.SetValue(resource, propertyName, propertyValue); } } #if ASTORIA_OPEN_OBJECT ///Gets the type attribute and resolves the type. /// reader from which type attribute needs to be read /// true if the reader contains a type attribute otherwise false ///resolved type private ResourceType ReadOpenPropertyTypeAttribute(XmlReader reader, out bool typeNameSpecified) { Debug.Assert(reader != null, "reader != null"); string typeName = reader.GetAttribute(XmlConstants.AtomTypeAttributeName, XmlConstants.DataWebMetadataNamespace); ResourceType resourceType = null; // If the type is not specified in the payload, we assume the type to be the expected type if (String.IsNullOrEmpty(typeName)) { typeNameSpecified = false; resourceType = this.Service.Provider.GetResourceType(typeof(string)); } else { typeNameSpecified = true; // try and resolve the name specified in the payload resourceType = this.Service.Provider.TryResolveTypeName(typeName); if (resourceType == null) { throw DataServiceException.CreateBadRequestError(Strings.BadRequest_InvalidTypeName(typeName)); } } return resourceType; } #endif ///Reads a typed property from the specified XmlReader. /// XmlReader to read from. /// Name of property to read. /// Type of property to read. ///The instance read, possibly null. private object ReadPropertyWithType(XmlReader reader, string propertyName, ResourceType propertyType) { Debug.Assert(reader != null, "reader != null"); Debug.Assert(propertyName != null, "propertyName != null"); Debug.Assert(propertyType != null, "propertyType != null"); object propertyValue; switch (propertyType.ResourceTypeKind) { case ResourceTypeKind.ComplexType: this.CheckAndIncrementObjectCount(); if (HasNullAttributeWithTrueValue(reader)) { propertyValue = null; } else { propertyValue = this.Service.Provider.CreateResource(null, propertyType.FullName); if (!reader.IsEmptyElement) { // Step inside the complex type, apply its properties, and pop back out. using (XmlReader propertyReader = reader.ReadSubtree()) { if (!WebUtil.XmlReaderEnsureElement(propertyReader)) { throw DataServiceException.CreateBadRequestError( Strings.PlainXml_PropertyLacksElement(propertyName)); } propertyReader.ReadStartElement(); ApplyContent(propertyReader, propertyType, propertyValue); } Debug.Assert( reader.NodeType == XmlNodeType.EndElement, "reader.NodeType == XmlNodeType.EndElement -- otherwise ReadSubtree left outer read in incorrect position."); } } break; case ResourceTypeKind.EntityType: throw DataServiceException.CreateBadRequestError( Strings.PlainXml_NavigationPropertyNotSupported(propertyName)); default: Debug.Assert( propertyType.ResourceTypeKind == ResourceTypeKind.Primitive, "property.TypeKind == ResourceTypeKind.Primitive -- metadata shouldn't return " + propertyType.ResourceTypeKind); string stringValue = ReadElementString(reader, propertyName); propertyValue = PlainXmlDeserializer.ConvertValuesForXml(stringValue, propertyName, propertyType.Type); break; } return propertyValue; } } } // File provided for Reference Use Only by Microsoft Corporation (c) 2007. //---------------------------------------------------------------------- //// Copyright (c) Microsoft Corporation. All rights reserved. // //// Provides a deserializer for plain XML content. // // // @owner [....] //--------------------------------------------------------------------- namespace System.Data.Services.Serializers { using System; using System.Diagnostics; using System.IO; using System.Text; using System.Xml; using System.Data.Services.Parsing; using System.Data.Services.Providers; ///Provides a deserializer for plain XML content. internal class PlainXmlDeserializer : Deserializer { ///reader to read xml from the request stream private readonly XmlReader xmlReader; ///Whether private readonly bool xmlReaderOwned; ///is owned and should be disposed of. Initializes a new /// Input stream reader from which POX content must be read. /// Encoding to use for the stream (null to auto-discover). /// Data service for which the deserializer will act. /// Indicates whether this is a PUT operation (rather than POST). /// Tracker to use for modifications. internal PlainXmlDeserializer(Stream stream, Encoding encoding, IDataService dataService, bool update, UpdateTracker tracker) : base(update, dataService, tracker) { Debug.Assert(stream != null, "stream != null"); this.xmlReader = XmlUtil.CreateXmlReader(stream, encoding); this.xmlReaderOwned = true; } ///for the specified stream. Initializes a new /// Reader for content. /// Parent deserializer. internal PlainXmlDeserializer(XmlReader reader, Deserializer deserializer) : base(deserializer) { Debug.Assert(reader != null, "reader != null"); this.xmlReader = reader; // this.xmlReaderOwned = false; } ///based on the settings for another one. Returns the content format for the deserializer. protected override ContentFormat ContentFormat { get { return ContentFormat.PlainXml; } } ///Applies properties from the reader to the specified resource. /// Deserializer which is driving the. /// XmlReader to read from. /// Type of resource. /// Resource to set value on. /// current object count for this operation. /// /// This method will end as soon as it find something that is not an /// XML element to process. /// internal static void ApplyContent(Deserializer deserializer, XmlReader reader, ResourceType resourceType, object resource, int currentObjectCount) { Debug.Assert(deserializer != null, "deserializer != null"); Debug.Assert(reader != null, "reader != null"); using (PlainXmlDeserializer xml = new PlainXmlDeserializer(reader, deserializer)) { // Initialize the new deserializer instance with the current object count xml.UpdateObjectCount(currentObjectCount); // load all the properties xml.ApplyContent(xml.xmlReader, resourceType, resource); // After all the properties have been loaded, initialize the current deserializer value with the object count deserializer.UpdateObjectCount(xml.MaxObjectCount); } } ////// Converts the given value to the expected type as per XML serializer rules. /// Make sure these rules are in [....] with PlainXmlSerializer. /// /// value to the converted /// name of the property whose value is getting converted /// clr type to which the value needs to be converted to ///object which is in [....] with the properties type internal static object ConvertValuesForXml(object value, string propertyName, Type typeToBeConverted) { Debug.Assert(WebUtil.IsPrimitiveType(typeToBeConverted), "WebUtil.IsPrimitiveType(typeToBeConverted)"); string stringValue = value as string; if (stringValue != null) { try { value = WebConvert.StringToPrimitive(stringValue, typeToBeConverted); } catch (FormatException e) { throw DataServiceException.CreateBadRequestError(Strings.BadRequest_ErrorInConvertingPropertyValue(propertyName, typeToBeConverted), e); } } return value; } ////// Assumes the payload to represent a single object and processes accordingly /// /// info about the object being created ///the newly formed object that the payload represents protected override object CreateSingleObject(SegmentInfo segmentInfo) { Debug.Assert( #if ASTORIA_OPEN_OBJECT segmentInfo.TargetKind == RequestTargetKind.OpenProperty || #endif segmentInfo.TargetKind == RequestTargetKind.ComplexObject || segmentInfo.TargetKind == RequestTargetKind.Primitive, segmentInfo.TargetKind + " is one of open property; complex object; primitive -- otherwise the wrong serializer was chosen"); if (!WebUtil.XmlReaderEnsureElement(this.xmlReader)) { throw DataServiceException.CreateBadRequestError(Strings.PlainXml_PayloadLacksElement); } if (HasNullAttributeWithTrueValue(this.xmlReader)) { return null; } ResourceType resourceType; string propertyName; #if ASTORIA_OPEN_OBJECT if (segmentInfo.TargetKind == RequestTargetKind.OpenProperty) { bool typeNameSpecified; resourceType = this.ReadOpenPropertyTypeAttribute(this.xmlReader, out typeNameSpecified); if (resourceType.ResourceTypeKind == ResourceTypeKind.EntityType) { throw DataServiceException.CreateBadRequestError( Strings.PlainXml_EntityTypeNotSupported(resourceType.Type)); } Debug.Assert(resourceType != null, "resourceType != null"); propertyName = this.xmlReader.LocalName; } else #endif { Debug.Assert(segmentInfo.ProjectedProperty != null, "segmentInfo.ProjectedProperty != null"); resourceType = segmentInfo.ProjectedProperty.ResourceType; propertyName = segmentInfo.ProjectedProperty.Name; if (propertyName != this.xmlReader.LocalName) { throw DataServiceException.CreateBadRequestError( Strings.PlainXml_IncorrectElementName(propertyName, this.xmlReader.LocalName)); } } object result = this.ReadPropertyWithType(this.xmlReader, propertyName, resourceType); return result; } ///Provides an opportunity to clean-up resources. /// /// Whether the call is being made from an explicit call to /// IDisposable.Dispose() rather than through the finalizer. /// protected override void Dispose(bool disposing) { base.Dispose(disposing); if (disposing && this.xmlReaderOwned) { this.xmlReader.Close(); } } ////// Get the resource referred by the uri in the payload /// ///resource referred by the uri in the payload. protected override string GetLinkUriFromPayload() { if (!WebUtil.XmlReaderEnsureElement(this.xmlReader)) { throw DataServiceException.CreateBadRequestError(Strings.PlainXml_PayloadLacksElement); } string uri = null; bool skipped; do { skipped = false; switch (this.xmlReader.NodeType) { case XmlNodeType.Element: string localName = this.xmlReader.LocalName; string elementNamespace = this.xmlReader.NamespaceURI; if (elementNamespace != XmlConstants.DataWebMetadataNamespace || localName != XmlConstants.UriElementName) { this.xmlReader.Skip(); skipped = true; continue; } if (uri != null) { throw DataServiceException.CreateBadRequestError(Strings.BadRequest_MoreThanOneUriElementSpecified); } uri = ReadElementString(this.xmlReader, localName); if (String.IsNullOrEmpty(uri)) { throw DataServiceException.CreateBadRequestError(Strings.BadRequest_MissingUriForLinkOperation); } break; default: break; } } while (skipped || this.xmlReader.Read()); Debug.Assert( this.xmlReader.NodeType != XmlNodeType.Element, "reader.NodeType != XmlNodeType.Element -- otherwise we should have kept processing"); if (String.IsNullOrEmpty(uri)) { throw DataServiceException.CreateBadRequestError(Strings.BadRequest_MissingUriForLinkOperation); } return uri; } ////// returns true if the null attribute is specified and the value is true /// /// xml reader from which attribute needs to be read ///true if the null attribute is specified and the attribute value is true private static bool HasNullAttributeWithTrueValue(XmlReader reader) { Debug.Assert(reader != null, "reader != null"); Debug.Assert(reader.NodeType == XmlNodeType.Element, "reader.NodeType == XmlNodeType.Element"); string elementValue = reader.GetAttribute(XmlConstants.AtomNullAttributeName, XmlConstants.DataWebMetadataNamespace); // If the null attribute is specified and the value is true, then set the property value to null, // otherwise set the value to empty string if ((null != elementValue) && XmlConvert.ToBoolean(elementValue)) { string elementName = reader.LocalName; if (!reader.IsEmptyElement) { reader.Read(); if (reader.NodeType != XmlNodeType.EndElement) { throw DataServiceException.CreateBadRequestError( Strings.BadRequest_CannotSpecifyValueOrChildElementsForNullElement(elementName)); } } return true; } return false; } ////// Reads the value from the given element. This leaves the reader in the EndElement. /// /// xml reader from which the value needs to be read /// name of the element whose value is getting read ///returns the xml string values as specified in the payload private static string ReadElementString(XmlReader reader, string elementName) { Debug.Assert(reader != null, "reader != null"); Debug.Assert(XmlNodeType.Element == reader.NodeType, "not positioned on Element"); string elementValue = null; if (HasNullAttributeWithTrueValue(reader)) { return null; } else if (reader.IsEmptyElement) { return String.Empty; } StringBuilder builder = null; bool done = false; while (!done && reader.Read()) { switch (reader.NodeType) { case XmlNodeType.EndElement: done = true; break; case XmlNodeType.CDATA: case XmlNodeType.Text: case XmlNodeType.SignificantWhitespace: if (elementValue == null) { elementValue = reader.Value; } else if (builder == null) { string newValue = reader.Value; builder = new StringBuilder(newValue.Length + elementValue.Length); builder.Append(elementValue); builder.Append(newValue); } else { builder.Append(reader.Value); } break; case XmlNodeType.Comment: case XmlNodeType.Whitespace: break; #region XmlNodeType error case XmlNodeType.None: case XmlNodeType.XmlDeclaration: case XmlNodeType.Attribute: case XmlNodeType.EndEntity: case XmlNodeType.EntityReference: case XmlNodeType.Entity: case XmlNodeType.Document: case XmlNodeType.DocumentType: case XmlNodeType.DocumentFragment: case XmlNodeType.Notation: case XmlNodeType.ProcessingInstruction: default: throw DataServiceException.CreateBadRequestError(Strings.BadRequest_InvalidValue(elementName)); #endregion } } if (builder != null) { elementValue = builder.ToString(); } else if (elementValue == null) { elementValue = String.Empty; } return elementValue; } ///Applies properties from the reader to the specified resource. /// XmlReader to read from. /// Type of resource. /// Resource to set value on. ////// This method will end as soon as it find something that is not an /// XML element to process. /// private void ApplyContent(XmlReader reader, ResourceType resourceType, object resource) { Debug.Assert(resourceType != null, "resourceType != null"); Debug.Assert(resource != null, "resource != null"); if (!WebUtil.XmlReaderEnsureElement(reader)) { return; } this.RecurseEnter(); bool skipped; do { skipped = false; switch (reader.NodeType) { case XmlNodeType.Element: string localName = reader.LocalName; string elementNamespace = reader.NamespaceURI; if (elementNamespace != XmlConstants.DataWebNamespace) { reader.Skip(); skipped = true; continue; } this.ApplyProperty(reader, localName, resourceType, resource); break; default: break; } } while (skipped || reader.Read()); Debug.Assert( reader.NodeType != XmlNodeType.Element, "reader.NodeType != XmlNodeType.Element -- otherwise we should have kept processing"); this.RecurseLeave(); } ///Applies a property from the reader to the specified resource. /// XmlReader to read from. /// Name of property to set on the specified resource. /// Type of resource. /// Resource to set value on. private void ApplyProperty(XmlReader reader, string propertyName, ResourceType resourceType, object resource) { Debug.Assert(reader != null, "reader != null"); Debug.Assert(propertyName != null, "propertyName != null"); Debug.Assert(resourceType != null, "resourceType != null"); Debug.Assert(resource != null, "resource != null"); ResourceProperty property = resourceType.TryResolvePropertyName(propertyName); ResourceType propertyType; bool ignoreValue = false; if (property == null) { #if ASTORIA_OPEN_OBJECT if (resourceType.OpenTypeKind != OpenTypeKind.CompletelyOpen) #endif { throw DataServiceException.CreateBadRequestError(Strings.BadRequest_InvalidPropertyNameSpecified(propertyName, resourceType.FullName)); } #if ASTORIA_OPEN_OBJECT bool typeNameSpecified; propertyType = this.ReadOpenPropertyTypeAttribute(reader, out typeNameSpecified); #endif } else { propertyType = property.ResourceType; if (this.Update && property.IsOfKind(ResourcePropertyKind.Key)) { ignoreValue = true; } } object propertyValue = this.ReadPropertyWithType(reader, propertyName, propertyType); if (!ignoreValue) { this.Service.Provider.SetValue(resource, propertyName, propertyValue); } } #if ASTORIA_OPEN_OBJECT ///Gets the type attribute and resolves the type. /// reader from which type attribute needs to be read /// true if the reader contains a type attribute otherwise false ///resolved type private ResourceType ReadOpenPropertyTypeAttribute(XmlReader reader, out bool typeNameSpecified) { Debug.Assert(reader != null, "reader != null"); string typeName = reader.GetAttribute(XmlConstants.AtomTypeAttributeName, XmlConstants.DataWebMetadataNamespace); ResourceType resourceType = null; // If the type is not specified in the payload, we assume the type to be the expected type if (String.IsNullOrEmpty(typeName)) { typeNameSpecified = false; resourceType = this.Service.Provider.GetResourceType(typeof(string)); } else { typeNameSpecified = true; // try and resolve the name specified in the payload resourceType = this.Service.Provider.TryResolveTypeName(typeName); if (resourceType == null) { throw DataServiceException.CreateBadRequestError(Strings.BadRequest_InvalidTypeName(typeName)); } } return resourceType; } #endif ///Reads a typed property from the specified XmlReader. /// XmlReader to read from. /// Name of property to read. /// Type of property to read. ///The instance read, possibly null. private object ReadPropertyWithType(XmlReader reader, string propertyName, ResourceType propertyType) { Debug.Assert(reader != null, "reader != null"); Debug.Assert(propertyName != null, "propertyName != null"); Debug.Assert(propertyType != null, "propertyType != null"); object propertyValue; switch (propertyType.ResourceTypeKind) { case ResourceTypeKind.ComplexType: this.CheckAndIncrementObjectCount(); if (HasNullAttributeWithTrueValue(reader)) { propertyValue = null; } else { propertyValue = this.Service.Provider.CreateResource(null, propertyType.FullName); if (!reader.IsEmptyElement) { // Step inside the complex type, apply its properties, and pop back out. using (XmlReader propertyReader = reader.ReadSubtree()) { if (!WebUtil.XmlReaderEnsureElement(propertyReader)) { throw DataServiceException.CreateBadRequestError( Strings.PlainXml_PropertyLacksElement(propertyName)); } propertyReader.ReadStartElement(); ApplyContent(propertyReader, propertyType, propertyValue); } Debug.Assert( reader.NodeType == XmlNodeType.EndElement, "reader.NodeType == XmlNodeType.EndElement -- otherwise ReadSubtree left outer read in incorrect position."); } } break; case ResourceTypeKind.EntityType: throw DataServiceException.CreateBadRequestError( Strings.PlainXml_NavigationPropertyNotSupported(propertyName)); default: Debug.Assert( propertyType.ResourceTypeKind == ResourceTypeKind.Primitive, "property.TypeKind == ResourceTypeKind.Primitive -- metadata shouldn't return " + propertyType.ResourceTypeKind); string stringValue = ReadElementString(reader, propertyName); propertyValue = PlainXmlDeserializer.ConvertValuesForXml(stringValue, propertyName, propertyType.Type); break; } return propertyValue; } } } // File provided for Reference Use Only by Microsoft Corporation (c) 2007.
Link Menu
This book is available now!
Buy at Amazon US or
Buy at Amazon UK
- codemethodreferenceexpression.cs
- TextAutomationPeer.cs
- ClientConfigurationHost.cs
- XmlReflectionImporter.cs
- Vector3DCollection.cs
- ServiceOperationDetailViewControl.cs
- DragStartedEventArgs.cs
- TextSelectionProcessor.cs
- DataViewListener.cs
- Context.cs
- StorageAssociationSetMapping.cs
- HttpContextWrapper.cs
- TabPanel.cs
- BitArray.cs
- Transform3DGroup.cs
- SRDisplayNameAttribute.cs
- Header.cs
- ObjectAnimationUsingKeyFrames.cs
- SiteMapDataSourceView.cs
- CatalogZone.cs
- SchemaTypeEmitter.cs
- HeaderedContentControl.cs
- UIElement.cs
- PropertyOverridesDialog.cs
- XmlSchemaCollection.cs
- DataGridColumn.cs
- TreeViewEvent.cs
- DependencyObjectProvider.cs
- ValidationVisibilityAttribute.cs
- CircleHotSpot.cs
- Maps.cs
- GetParentChain.cs
- WebBrowserHelper.cs
- CodeSnippetCompileUnit.cs
- WorkflowDesignerColors.cs
- XmlAttribute.cs
- RequestNavigateEventArgs.cs
- ImageAutomationPeer.cs
- SessionStateContainer.cs
- ObjectDataSourceDisposingEventArgs.cs
- StyleSelector.cs
- DrawListViewSubItemEventArgs.cs
- XPathDocumentNavigator.cs
- PointCollectionConverter.cs
- GridErrorDlg.cs
- SchemaImporterExtensionsSection.cs
- AutomationEventArgs.cs
- MemoryStream.cs
- IPAddressCollection.cs
- PingOptions.cs
- XmlNamedNodeMap.cs
- FilterQueryOptionExpression.cs
- MutexSecurity.cs
- SourceFileBuildProvider.cs
- BitSet.cs
- FilteredAttributeCollection.cs
- WebPartEditorCancelVerb.cs
- StylusPointDescription.cs
- SqlProcedureAttribute.cs
- RangeBase.cs
- CodeAttributeDeclarationCollection.cs
- Registry.cs
- TypeDescriptionProviderAttribute.cs
- DesignBindingEditor.cs
- DataGridViewDataConnection.cs
- ArraySet.cs
- DurationConverter.cs
- PriorityBindingExpression.cs
- DictionaryKeyPropertyAttribute.cs
- ListSortDescriptionCollection.cs
- TagMapInfo.cs
- EllipseGeometry.cs
- CodeTypeParameterCollection.cs
- DbConnectionPool.cs
- AssociationType.cs
- MenuItemBindingCollection.cs
- WrapPanel.cs
- DesignerTransaction.cs
- DrawListViewSubItemEventArgs.cs
- CodePageUtils.cs
- IndexedWhereQueryOperator.cs
- TaskFormBase.cs
- DataProtection.cs
- DbConvert.cs
- HScrollProperties.cs
- XmlBaseWriter.cs
- FormsAuthentication.cs
- Drawing.cs
- FileCodeGroup.cs
- TraceUtils.cs
- SqlInternalConnection.cs
- WebPartEventArgs.cs
- InputMethodStateTypeInfo.cs
- AuthenticatingEventArgs.cs
- OpenTypeCommon.cs
- PartManifestEntry.cs
- UIElement.cs
- TripleDES.cs
- CompilerGeneratedAttribute.cs
- ListBoxItemWrapperAutomationPeer.cs