ServiceModelExtensionCollectionElement.cs source code in C# .NET

Source code for the .NET framework in C#

                        

Code:

/ WCF / WCF / 3.5.30729.1 / untmp / Orcas / SP / ndp / cdf / src / WCF / ServiceModel / System / ServiceModel / Configuration / ServiceModelExtensionCollectionElement.cs / 1 / ServiceModelExtensionCollectionElement.cs

                            //------------------------------------------------------------------------------ 
// Copyright (c) Microsoft Corporation.  All rights reserved.
//-----------------------------------------------------------------------------

namespace System.ServiceModel.Configuration 
{
    using System; 
    using System.ServiceModel.Channels; 
    using System.ServiceModel;
    using System.Collections.Generic; 
    using System.Configuration;
    using System.Globalization;
    using System.Xml;
    using System.ServiceModel.Diagnostics; 
    using System.Diagnostics;
    using System.Security; 
 

    public abstract class ServiceModelExtensionCollectionElement : ConfigurationElement, ICollection, IConfigurationContextProviderInternal 
        where TServiceModelExtensionElement : ServiceModelExtensionElement
    {
        /// 
        ///   Critical - stores information used in a security decision 
        /// 
        [SecurityCritical] 
        EvaluationContextHelper contextHelper; 

        string extensionCollectionName = null; 
        bool modified = false;
        List items = null;
        ConfigurationPropertyCollection properties = null;
 
        internal ServiceModelExtensionCollectionElement(string extensionCollectionName)
        { 
            this.extensionCollectionName = extensionCollectionName; 
        }
 
        public TServiceModelExtensionElement this[int index]
        {
            get {return this.Items[index]; }
        } 

        public TServiceModelExtensionElement this[Type extensionType] 
        { 
            get
            { 
                if (extensionType == null)
                {
                    throw DiagnosticUtility.ExceptionUtility.ThrowHelperArgumentNull("extensionType");
                } 

                if (!this.CollectionElementBaseType.IsAssignableFrom(extensionType)) 
                { 
#pragma warning disable 56506 //[....]; Variable 'extensionType' checked for null previously
                    throw DiagnosticUtility.ExceptionUtility.ThrowHelperArgument("extensionType", 
                        SR.GetString(SR.ConfigInvalidExtensionType,
                        extensionType.ToString(),
                        this.CollectionElementBaseType.FullName,
                        this.extensionCollectionName)); 
#pragma warning restore
                } 
                TServiceModelExtensionElement retval = null; 

                foreach (TServiceModelExtensionElement collectionElement in this) 
                {
                    if (null != collectionElement)
                    {
                        if (collectionElement.GetType() == extensionType) 
                        {
                            retval = collectionElement; 
                        } 
                    }
                } 

                return retval;
            }
        } 

        public int Count 
        { 
            get {return this.Items.Count; }
        } 

        bool ICollection.IsReadOnly
        {
            get {return this.IsReadOnly(); } 
        }
 
        internal List Items 
        {
            get 
            {
                if (this.items == null)
                {
                    this.items = new List(); 
                }
                return this.items; 
            } 
        }
 
        protected override ConfigurationPropertyCollection Properties
        {
            get
            { 
                if (this.properties == null)
                { 
                    this.properties = new ConfigurationPropertyCollection(); 
                }
                return this.properties; 
            }
        }

        public virtual void Add(TServiceModelExtensionElement element) 
        {
            if (this.IsReadOnly()) 
            { 
                throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ConfigurationErrorsException(SR.GetString(SR.ConfigReadOnly)));
            } 
            if (element == null)
            {
                throw DiagnosticUtility.ExceptionUtility.ThrowHelperArgumentNull("element");
            } 

            element.ExtensionCollectionName = this.extensionCollectionName; 
 
            if (this.Contains(element))
            { 
                throw DiagnosticUtility.ExceptionUtility.ThrowHelperArgument("element", SR.GetString(SR.ConfigDuplicateKey, element.ConfigurationElementName));
            }
            else if (!this.CanAdd(element))
            { 
                throw DiagnosticUtility.ExceptionUtility.ThrowHelperArgument("element",
                    SR.GetString(SR.ConfigElementTypeNotAllowed, 
                    element.ConfigurationElementName, 
                    this.extensionCollectionName));
            } 
            else
            {
                element.ContainingEvaluationContext = ConfigurationHelpers.GetEvaluationContext(this);
                ConfigurationProperty configProperty = new ConfigurationProperty(element.ConfigurationElementName, element.GetType(), null); 
                this.Properties.Add(configProperty);
                this[configProperty] = element; 
                this.Items.Add(element); 
                this.modified = true;
            } 
        }

        public virtual bool CanAdd(TServiceModelExtensionElement element)
        { 
            if (null == element)
            { 
                throw DiagnosticUtility.ExceptionUtility.ThrowHelperArgumentNull("element"); 
            }
 
            bool retval = false;
            Type elementType = element.GetType();

            if (!this.IsReadOnly()) 
            {
                if (!this.ContainsKey(elementType)) 
                { 
                    retval = element.CanAdd(this.extensionCollectionName, ConfigurationHelpers.GetEvaluationContext(this));
                } 
                else if (DiagnosticUtility.ShouldTraceWarning)
                {
                    TraceUtility.TraceEvent(TraceEventType.Warning,
                        TraceCode.ExtensionElementAlreadyExistsInCollection, 
                        this.CreateCanAddRecord(this[elementType]), this, null);
                } 
            } 
            else if (DiagnosticUtility.ShouldTraceWarning)
            { 
                TraceUtility.TraceEvent(TraceEventType.Warning,
                    TraceCode.ConfigurationIsReadOnly,
                    null, this, null);
            } 
            return retval;
        } 
 
        DictionaryTraceRecord CreateCanAddRecord(TServiceModelExtensionElement element)
        { 
            return this.CreateCanAddRecord(element, new Dictionary(3));
        }

        DictionaryTraceRecord CreateCanAddRecord(TServiceModelExtensionElement element, Dictionary values) 
        {
            values["ElementType"] = DiagnosticTrace.XmlEncode(typeof(TServiceModelExtensionElement).AssemblyQualifiedName); 
            values["ConfiguredSectionName"] = element.ConfigurationElementName; 
            values["CollectionName"] = ConfigurationStrings.ExtensionsSectionPath + "/" + this.extensionCollectionName;
            return new DictionaryTraceRecord(values); 
        }

        public void Clear()
        { 
            if (this.IsReadOnly())
            { 
                throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ConfigurationErrorsException(SR.GetString(SR.ConfigReadOnly))); 
            }
            if (this.Properties.Count > 0) 
            {
                this.modified = true;
            }
 
            List propertiesToRemove = new List(this.Items.Count);
            foreach (TServiceModelExtensionElement item in this.Items) 
            { 
                propertiesToRemove.Add(item.ConfigurationElementName);
            } 

            this.Items.Clear();

            foreach (string name in propertiesToRemove) 
            {
                this.Properties.Remove(name); 
            } 
        }
 
        internal Type CollectionElementBaseType
        {
            get { return typeof(TServiceModelExtensionElement); }
        } 

        public bool Contains(TServiceModelExtensionElement element) 
        { 
            if (element == null)
            { 
                throw DiagnosticUtility.ExceptionUtility.ThrowHelperArgumentNull("element");
            }
            return this.ContainsKey(element.GetType());
        } 

        public bool ContainsKey(Type elementType) 
        { 
            if (elementType == null)
            { 
                throw DiagnosticUtility.ExceptionUtility.ThrowHelperArgumentNull("elementType");
            }
            return (this[elementType] != null);
        } 

        public bool ContainsKey(string elementName) 
        { 
            if (string.IsNullOrEmpty(elementName))
            { 
                throw DiagnosticUtility.ExceptionUtility.ThrowHelperArgumentNull("elementName");
            }
            bool retval = false;
            foreach (TServiceModelExtensionElement element in this) 
            {
                if (null != element) 
                { 
                    string configuredSectionName = element.ConfigurationElementName;
                    if (configuredSectionName.Equals(elementName, StringComparison.Ordinal)) 
                    {
                        retval = true;
                        break;
                    } 
                }
            } 
            return retval; 
        }
 
        public void CopyTo(TServiceModelExtensionElement[] elements, int start)
        {
            if (elements == null)
            { 
                throw DiagnosticUtility.ExceptionUtility.ThrowHelperArgumentNull("elements");
            } 
            if (start < 0 || start >= elements.Length) 
            {
                throw DiagnosticUtility.ExceptionUtility.ThrowHelperArgument("start", 
                    SR.GetString(SR.ConfigInvalidStartValue,
                    elements.Length - 1,
                    start));
            } 

            foreach (TServiceModelExtensionElement element in this) 
            { 
                if (null != element)
                { 
                    string configuredSectionName = element.ConfigurationElementName;

                    TServiceModelExtensionElement copiedElement = this.CreateNewSection(configuredSectionName);
                    if (start < elements.Length) 
                    {
                        copiedElement.CopyFrom(element); 
                        elements[start] = copiedElement; 
                        ++start;
                    } 
                }
            }
        }
 
        TServiceModelExtensionElement CreateNewSection(string name)
        { 
            if (this.ContainsKey(name)) 
            {
                throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ConfigurationErrorsException(SR.GetString(SR.ConfigDuplicateItem, 
                    name,
                    this.GetType().Name),
                    this.ElementInformation.Source,
                    this.ElementInformation.LineNumber)); 
           }
 
            TServiceModelExtensionElement retval = null; 

            Type elementType = GetExtensionType(ConfigurationHelpers.GetEvaluationContext(this), name); 
            if (null != elementType)
            {
                if (this.CollectionElementBaseType.IsAssignableFrom(elementType))
                { 
                    retval = (TServiceModelExtensionElement)Activator.CreateInstance(elementType);
                    retval.ExtensionCollectionName = this.extensionCollectionName; 
                    retval.InternalInitializeDefault(); 
                }
                else 
                {
                    throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ConfigurationErrorsException(SR.GetString(SR.ConfigInvalidExtensionElement,
                        name,
                        this.CollectionElementBaseType.FullName), 
                        this.ElementInformation.Source,
                        this.ElementInformation.LineNumber)); 
                } 
            }
            else 
            {
                throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ConfigurationErrorsException(SR.GetString(SR.ConfigInvalidExtensionElementName,
                    name,
                    this.extensionCollectionName), 
                    this.ElementInformation.Source,
                    this.ElementInformation.LineNumber)); 
            } 

            return retval; 
        }

        /// 
        /// Critical - calls SecurityCritical method UnsafeLookupCollection which elevates in order to load config 
        /// Safe - does not leak any config objects
        ///  
        [SecurityCritical, SecurityTreatAsSafe] 
        Type GetExtensionType(ContextInformation evaluationContext, string name)
        { 
            ExtensionElementCollection collection = ExtensionsSection.UnsafeLookupCollection(this.extensionCollectionName, evaluationContext);
            if (collection.ContainsKey(name))
            {
                ExtensionElement element = collection[name]; 
                Type elementType = Type.GetType(element.Type, false);
                if (null == elementType) 
                { 
                    throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ConfigurationErrorsException(SR.GetString(SR.ConfigInvalidType, element.Type, element.Name),
                        this.ElementInformation.Source, 
                        this.ElementInformation.LineNumber));
                }
                return elementType;
            } 
            return null;
        } 
 
        /// 
        /// Critical - uses the critical helper SetIsPresent 
        /// Safe - controls how/when SetIsPresent is used, not arbitrarily callable from PT (method is protected and class is sealed)
        /// 
        [SecurityCritical, SecurityTreatAsSafe]
        protected override void DeserializeElement(XmlReader reader, bool serializeCollectionKey) 
        {
            SetIsPresent(); 
            DeserializeElementCore(reader); 
        }
 
        private void DeserializeElementCore(XmlReader reader)
        {
            if (reader.HasAttributes && 0 < reader.AttributeCount)
            { 
                while (reader.MoveToNextAttribute())
                { 
                    if (this.Properties.Contains(reader.Name)) 
                    {
                        this[reader.Name] = this.Properties[reader.Name].Converter.ConvertFromString(reader.Value); 
                    }
                    else
                    {
                        this.OnDeserializeUnrecognizedAttribute(reader.Name, reader.Value); 
                    }
                } 
            } 

            if (XmlNodeType.Element != reader.NodeType) 
            {
                reader.MoveToElement();
            }
 
            XmlReader subTree = reader.ReadSubtree();
            if (subTree.Read()) 
            { 
                while (subTree.Read())
                { 
                    if (XmlNodeType.Element == subTree.NodeType)
                    {
                        // Create new child element and add it to the property collection to
                        // associate the element with an EvaluationContext.  Then deserialize 
                        // XML further to set actual values.
                        TServiceModelExtensionElement collectionElement = this.CreateNewSection(subTree.Name); 
                        this.Add(collectionElement); 
                        collectionElement.DeserializeInternal(subTree, false);
                    } 
                }
            }
        }
 
        /// 
        /// Critical - calls ConfigurationHelpers.SetIsPresent which elevates in order to set a property 
        ///  
        [SecurityCritical]
        void SetIsPresent() 
        {
            ConfigurationHelpers.SetIsPresent(this);
        }
 
        public System.Collections.Generic.IEnumerator GetEnumerator()
        { 
            for (int index = 0; index < this.Items.Count; ++index) 
            {
                TServiceModelExtensionElement currentValue = items[index]; 
                yield return currentValue;
            }
        }
 
        protected override bool IsModified()
        { 
            bool retval = this.modified; 
            if (!retval)
            { 
                for (int i = 0; i < this.Items.Count; i++)
                {
                    TServiceModelExtensionElement element = this.Items[i];
                    if (element.IsModifiedInternal()) 
                    {
                        retval = true; 
                        break; 
                    }
                } 
            }
            return retval;
        }
 
        protected override bool OnDeserializeUnrecognizedElement(string elementName, XmlReader reader)
        { 
            // When this is used as a DefaultCollection (i.e. CommonBehaviors) 
            // the element names are unrecognized by the parent tag, which delegates
            // to the collection's OnDeserializeUnrecognizedElement.  In this case, 
            // an unrecognized element may be expected, simply try to deserialize the
            // element and let DeserializeElement() throw the appropriate exception if
            // an error is hit.
            this.DeserializeElement(reader, false); 
            return true;
        } 
 
        public bool Remove(TServiceModelExtensionElement element)
        { 
            if (element == null)
            {
                throw DiagnosticUtility.ExceptionUtility.ThrowHelperArgumentNull("element");
            } 
            bool retval = false;
            if (this.Contains(element)) 
            { 
                string configuredSectionName = element.ConfigurationElementName;
 
                TServiceModelExtensionElement existingElement = (TServiceModelExtensionElement)this[element.GetType()];
                this.Items.Remove(existingElement);
                this.Properties.Remove(configuredSectionName);
                this.modified = true; 
                retval = true;
            } 
            return retval; 
        }
 
        /// 
        ///   Critical - accesses critical field contextHelper
        /// 
        [SecurityCritical] 
        protected override void Reset(ConfigurationElement parentElement)
        { 
            ServiceModelExtensionCollectionElement collection = 
                (ServiceModelExtensionCollectionElement) parentElement;
            foreach (TServiceModelExtensionElement collectionElement in collection.Items) 
            {
                this.Items.Add(collectionElement);
            }
            // Update my properties 
            this.UpdateProperties(collection);
 
            this.contextHelper.OnReset(parentElement); 

            base.Reset(parentElement); 
        }

        protected override void ResetModified()
        { 
            for (int i = 0; i < this.Items.Count; i++)
            { 
                TServiceModelExtensionElement collectionElement = this.Items[i]; 
                collectionElement.ResetModifiedInternal();
            } 
            this.modified = false;
        }

        protected void SetIsModified() 
        {
            this.modified = true; 
        } 

        protected override void SetReadOnly() 
        {
            base.SetReadOnly();

            for (int i = 0; i < this.Items.Count; i++) 
            {
                TServiceModelExtensionElement element = this.Items[i]; 
                element.SetReadOnlyInternal(); 
            }
        } 

        System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator()
        {
            return this.GetEnumerator(); 
        }
 
        protected override void Unmerge(ConfigurationElement sourceElement, ConfigurationElement parentElement, ConfigurationSaveMode saveMode) 
        {
            if (sourceElement == null) 
            {
                return;
            }
 
            ServiceModelExtensionCollectionElement sourceCollectionElement = (ServiceModelExtensionCollectionElement) sourceElement;
 
            this.UpdateProperties(sourceCollectionElement); 
            base.Unmerge(sourceElement, parentElement, saveMode);
        } 

        void UpdateProperties(ServiceModelExtensionCollectionElement sourceElement)
        {
            foreach (ConfigurationProperty property in sourceElement.Properties) 
            {
                if (!this.Properties.Contains(property.Name)) 
                { 
                    this.Properties.Add(property);
                } 
            }
            foreach (TServiceModelExtensionElement extension in this.Items)
            {
                string configuredSectionName = extension.ConfigurationElementName; 

                if (!this.Properties.Contains(configuredSectionName)) 
                { 
                    ConfigurationProperty configProperty = new ConfigurationProperty(configuredSectionName, extension.GetType(), null);
                    this.Properties.Add(configProperty); 
                }
            }
        }
 
        ContextInformation IConfigurationContextProviderInternal.GetEvaluationContext()
        { 
            return this.EvaluationContext; 
        }
 
        /// 
        ///   Critical -- accesses critical field contextHelper
        ///   RequiresReview -- the return value will be used for a security decision -- see comment in interface definition
        ///  
        [SecurityCritical]
        ContextInformation IConfigurationContextProviderInternal.GetOriginalEvaluationContext() 
        { 
            return this.contextHelper.GetOriginalContext(this);
        } 
    }
}


// File provided for Reference Use Only by Microsoft Corporation (c) 2007.
// Copyright (c) Microsoft Corporation. All rights reserved.
                        

Link Menu

Network programming in C#, Network Programming in VB.NET, Network Programming in .NET
This book is available now!
Buy at Amazon US or
Buy at Amazon UK