ImportedPolicyConversionContext.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 / Description / ImportedPolicyConversionContext.cs / 2 / ImportedPolicyConversionContext.cs

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

namespace System.ServiceModel.Description 
{
    using System.Xml; 
    using System.ServiceModel.Channels; 
    using System.ServiceModel.Dispatcher;
    using System.Globalization; 
    using System.Collections;
    using System.Collections.Generic;
    using System.Collections.ObjectModel;
    using WsdlNS = System.Web.Services.Description; 

 
    public abstract partial class MetadataImporter 
    {
        //Consider, [....]: make this public 
        internal static IEnumerable GetPolicyConversionContextEnumerator(ServiceEndpoint endpoint, PolicyAlternatives policyAlternatives)
        {
            return ImportedPolicyConversionContext.GetPolicyConversionContextEnumerator(endpoint, policyAlternatives, MetadataImporterQuotas.Defaults);
        } 

        internal static IEnumerable GetPolicyConversionContextEnumerator(ServiceEndpoint endpoint, PolicyAlternatives policyAlternatives, 
            MetadataImporterQuotas quotas) 
        {
            return ImportedPolicyConversionContext.GetPolicyConversionContextEnumerator(endpoint, policyAlternatives, quotas); 
        }

        internal sealed class ImportedPolicyConversionContext : PolicyConversionContext
        { 
            BindingElementCollection bindingElements = new BindingElementCollection();
            readonly PolicyAssertionCollection endpointAssertions; 
            readonly Dictionary operationBindingAssertions = new Dictionary(); 
            readonly Dictionary messageBindingAssertions = new Dictionary();
            readonly Dictionary faultBindingAssertions = new Dictionary(); 

            ImportedPolicyConversionContext(ServiceEndpoint endpoint, IEnumerable endpointAssertions,
                    Dictionary> operationBindingAssertions,
                    Dictionary> messageBindingAssertions, 
                    Dictionary> faultBindingAssertions,
                    MetadataImporterQuotas quotas) 
                : base(endpoint) 
            {
                int remainingAssertionsAllowed = quotas.MaxPolicyAssertions; 

                this.endpointAssertions = new PolicyAssertionCollection(new MaxItemsEnumerable(endpointAssertions, remainingAssertionsAllowed));

                remainingAssertionsAllowed -= this.endpointAssertions.Count; 

                foreach (OperationDescription operationDescription in endpoint.Contract.Operations) 
                { 
                    this.operationBindingAssertions.Add(operationDescription, new PolicyAssertionCollection());
 
                    foreach (MessageDescription messageDescription in operationDescription.Messages)
                    {
                        this.messageBindingAssertions.Add(messageDescription, new PolicyAssertionCollection());
                    } 

                    foreach (FaultDescription faultDescription in operationDescription.Faults) 
                    { 
                        this.faultBindingAssertions.Add(faultDescription, new PolicyAssertionCollection());
                    } 
                }


                foreach (KeyValuePair> entry in operationBindingAssertions) 
                {
                    this.operationBindingAssertions[entry.Key].AddRange(new MaxItemsEnumerable(entry.Value, remainingAssertionsAllowed)); 
                    remainingAssertionsAllowed -= this.operationBindingAssertions[entry.Key].Count; 
                }
 
                foreach (KeyValuePair> entry in messageBindingAssertions)
                {
                    this.messageBindingAssertions[entry.Key].AddRange(new MaxItemsEnumerable(entry.Value, remainingAssertionsAllowed));
                    remainingAssertionsAllowed -= this.messageBindingAssertions[entry.Key].Count; 
                }
 
                foreach (KeyValuePair> entry in faultBindingAssertions) 
                {
                    this.faultBindingAssertions[entry.Key].AddRange(new MaxItemsEnumerable(entry.Value, remainingAssertionsAllowed)); 
                    remainingAssertionsAllowed -= this.faultBindingAssertions[entry.Key].Count;
                }
            }
 
            //
            // PolicyConversionContext implementation 
            // 

            public override BindingElementCollection BindingElements { get { return this.bindingElements; } } 

            public override PolicyAssertionCollection GetBindingAssertions()
            {
                return this.endpointAssertions; 
            }
 
            public override PolicyAssertionCollection GetOperationBindingAssertions(OperationDescription operation) 
            {
                return this.operationBindingAssertions[operation]; 
            }

            public override PolicyAssertionCollection GetMessageBindingAssertions(MessageDescription message)
            { 
                return this.messageBindingAssertions[message];
            } 
 
            public override PolicyAssertionCollection GetFaultBindingAssertions(FaultDescription message)
            { 
                return this.faultBindingAssertions[message];
            }

            // 
            // Policy Alternative Enumeration code
            // 
 
            public static IEnumerable GetPolicyConversionContextEnumerator(ServiceEndpoint endpoint,
                PolicyAlternatives policyAlternatives, MetadataImporterQuotas quotas) 
            {
                IEnumerable>> messageAssertionEnumerator;
                IEnumerable>> faultAssertionEnumerator;
                IEnumerable>> operationAssertionEnumerator; 
                faultAssertionEnumerator = PolicyIterationHelper.GetCartesianProduct>(policyAlternatives.FaultBindingAlternatives);
                messageAssertionEnumerator = PolicyIterationHelper.GetCartesianProduct>(policyAlternatives.MessageBindingAlternatives); 
                operationAssertionEnumerator = PolicyIterationHelper.GetCartesianProduct>(policyAlternatives.OperationBindingAlternatives); 

                foreach (Dictionary> faultAssertionsSelection in faultAssertionEnumerator) 
                {
                    foreach (Dictionary> messageAssertionsSelection in messageAssertionEnumerator)
                    {
                        foreach (Dictionary> operationAssertionsSelection in operationAssertionEnumerator) 
                        {
                            foreach (IEnumerable endpointAssertionsSelection in policyAlternatives.EndpointAlternatives) 
                            { 
                                ImportedPolicyConversionContext conversionContext;
                                try 
                                {
                                    conversionContext = new ImportedPolicyConversionContext(endpoint, endpointAssertionsSelection,
                                        operationAssertionsSelection, messageAssertionsSelection, faultAssertionsSelection,
                                        quotas); 
                                }
                                catch (MaxItemsEnumeratorExceededMaxItemsException) { yield break; } 
 
                                yield return conversionContext;
                            } 
                        }
                    }
                }
 
            }
 
            internal class MaxItemsEnumerable : IEnumerable 
            {
                IEnumerable inner; 
                int maxItems;

                public MaxItemsEnumerable(IEnumerable inner, int maxItems)
                { 
                    this.inner = inner;
                    this.maxItems = maxItems; 
                } 

                public IEnumerator GetEnumerator() 
                {
                    return new MaxItemsEnumerator(inner.GetEnumerator(), maxItems);
                }
 
                IEnumerator IEnumerable.GetEnumerator()
                { 
                    return (IEnumerator)GetEnumerator(); 
                }
            } 

            internal class MaxItemsEnumerator : IEnumerator
            {
                int maxItems; 
                int currentItem;
                IEnumerator inner; 
 
                public MaxItemsEnumerator(IEnumerator inner, int maxItems)
                { 
                    this.maxItems = maxItems;
                    this.currentItem = 0;
                    this.inner = inner;
                } 

                public T Current 
                { 
                    get { return inner.Current; }
                } 

                public void Dispose()
                {
                    inner.Dispose(); 
                }
 
                object IEnumerator.Current 
                {
                    get { return ((IEnumerator)inner).Current; } 
                }

                public bool MoveNext()
                { 
                    bool moveNext = inner.MoveNext();
                    if (++currentItem > maxItems) 
                    { 
                        throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new MaxItemsEnumeratorExceededMaxItemsException());
                    } 
                    return moveNext;
                }

                public void Reset() 
                {
                    currentItem = 0; 
                    inner.Reset(); 
                }
            } 

            internal class MaxItemsEnumeratorExceededMaxItemsException : Exception{}

            static class PolicyIterationHelper 
            {
                // This method returns an iterator over the cartesian product of a colleciton of sets. 
                //  e.g. If the following 3 sets are provided: 
                //    i) { 1, 2, 3 }
                //   ii) { a, b } 
                //  iii) { x, y, z }
                //
                // You would get an enumerator that returned the following 18 collections:
                // { 1, a, x}, { 2, a, x}, { 3, a, x}, { 1, b, x}, { 2, b, x}, { 3, b, x}, 
                // { 1, a, y}, { 2, a, y}, { 3, a, y}, { 1, b, y}, { 2, b, y}, { 3, b, y},
                // { 1, a, z}, { 2, a, z}, { 3, a, z}, { 1, b, z}, { 2, b, z}, { 3, b, z} 
                // 
                // This method allows us to enumerate over all the possible policy selections in a
                // dictiaonary of policy alternatives. 
                //   e.g. given all the policy alternatives in all the messages in a contract,
                //   we can enumerate over all the possilbe policy selections.
                //
                // Note: A general implementation of this method would differ in that it would probably use a List or an array instead of 
                // a dictionary and it would yield clones of the the counterValue.
                //  - We don't clone because we know that we don't need to based on our useage 
                //  - We use a dictionary because we need to correlate the selections with the alternative source. 
                //
                internal static IEnumerable> GetCartesianProduct(Dictionary> sets) 
                {
                    Dictionary counterValue = new Dictionary(sets.Count);

                    // The iterator is implemented as a counter with each digit being an IEnumerator over one of the sets. 
                    KeyValuePair>[] digits = InitializeCounter(sets, counterValue);
 
                    do 
                    {
                        yield return (Dictionary)counterValue; 
                    } while (IncrementCounter(digits, sets, counterValue));

                }
 
                static KeyValuePair>[] InitializeCounter(Dictionary> sets, Dictionary counterValue)
                { 
                    KeyValuePair>[] digits = new KeyValuePair>[sets.Count]; 

                    // Initialize the digit enumerators and set the counter's current Value. 
                    int i = 0;
                    foreach (KeyValuePair> kvp in sets)
                    {
                        digits[i] = new KeyValuePair>(kvp.Key, kvp.Value.GetEnumerator()); 
                        if (!(digits[i].Value.MoveNext()))
                        { 
                            DiagnosticUtility.DebugAssert("each set must have at least one item in it"); 
                            throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new InvalidOperationException(String.Format(CultureInfo.InvariantCulture, "Each set must have at least one item in it")));
                        } 
                        counterValue[digits[i].Key] = digits[i].Value.Current;
                        i++;
                    }
 
                    return digits;
                } 
 
                static bool IncrementCounter(KeyValuePair>[] digits, Dictionary> sets, Dictionary counterValue)
                { 

                    //
                    // Do rollover and carryying for digits.
                    //  - starting at least significant digit, move digits to  next value. 
                    //    if digit rolls over, carry to next digit and repeat.
                    // 
                    int currentDigit; 
                    for (currentDigit = 0; currentDigit < digits.Length && !digits[currentDigit].Value.MoveNext(); currentDigit++)
                    { 
                        IEnumerator newDigit = sets[digits[currentDigit].Key].GetEnumerator();
                        digits[currentDigit] = new KeyValuePair>(digits[currentDigit].Key, newDigit);
                        digits[currentDigit].Value.MoveNext();
                    } 

                    // 
                    // if we just rolled over on the most significant digit, return false 
                    //
                    if (currentDigit == digits.Length) 
                        return false;

                    //
                    // update countervalue stores for all digits that changed. 
                    //
                    for (int i = currentDigit; i >= 0; i--) 
                    { 
                        counterValue[digits[i].Key] = digits[i].Value.Current;
                    } 
                    return true;
                }
            }
 
        }
 
        internal class PolicyAlternatives 
        {
            public IEnumerable> EndpointAlternatives; 
            public Dictionary>> OperationBindingAlternatives;
            public Dictionary>> MessageBindingAlternatives;
            public Dictionary>> FaultBindingAlternatives;
        } 

    } 
} 

// 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