/// <summary>
        /// Infers service operations from domain service description.
        /// </summary>
        /// <param name="domainServiceDescription">Domain service description.</param>
        private void CollectServiceOperations(DomainServiceDescription domainServiceDescription)
        {
            foreach (var operationEntry in domainServiceDescription.DomainOperationEntries)
            {
                DomainDataServiceOperation op = null;

                if ((operationEntry.Operation == DomainOperation.Query && !DomainDataServiceMetadata.IsRootQueryOperation(operationEntry)) ||
                    operationEntry.Operation == DomainOperation.Invoke)
                {
                    op = this.CreateServiceOperation(operationEntry);
                }

                if (op != null)
                {
                    this.serviceOperations.Add(op.Name, op);
                }
            }
        }
        /// <summary>
        /// Create a service operation based on a domain operation entry.
        /// </summary>
        /// <param name="operation">Domain operation corresponding to the service operation.</param>
        /// <returns>ServiceOperation instance mapping to the domain operation.</returns>
        private DomainDataServiceOperation CreateServiceOperation(DomainOperationEntry operation)
        {
            List <ServiceOperationParameter> operationParameters = new List <ServiceOperationParameter>();

            foreach (DomainOperationParameter p in operation.Parameters)
            {
                // Only allow primitive type parameters for service operations.
                ResourceType parameterType = ResourceType.GetPrimitiveResourceType(p.ParameterType);
                if (parameterType == null)
                {
                    return(null);
                }

                operationParameters.Add(new ServiceOperationParameter(p.Name, parameterType));
            }

            ServiceOperationResultKind resultKind = ServiceOperationResultKind.Void;
            ResourceType resultResourceType       = null;

            if (operation.ReturnType != null)
            {
                bool isEnumeration;
                resultResourceType = this.ResolveResourceType(operation.ReturnType, out isEnumeration);

                if (resultResourceType == null)
                {
                    // Ignore service operations for which the appropriate resource type could not be inferred.
                    return(null);
                }

                if (isEnumeration)
                {
                    // Will need to distinguish between ServiceOperationResultKind.Enumeration and
                    // ServiceOperationResultKind.QueryWithMultipleResults once we support composition.
                    resultKind = ServiceOperationResultKind.Enumeration;
                }
                else
                {
                    resultKind = ServiceOperationResultKind.DirectValue;
                }
            }

            bool hasSideEffects = false;

            switch (operation.Operation)
            {
            case DomainOperation.Invoke:
                hasSideEffects = (operation.OperationAttribute as InvokeAttribute).HasSideEffects;
                break;

            case DomainOperation.Query:
                hasSideEffects = (operation.OperationAttribute as QueryAttribute).HasSideEffects;
                break;

            default:
                break;
            }

            ResourceSet resultSet = null;

            if (resultResourceType.ResourceTypeKind == ResourceTypeKind.EntityType)
            {
                resultSet = this.sets.Values.SingleOrDefault(s => s.ResourceType.InstanceType.IsAssignableFrom(resultResourceType.InstanceType));
                if (resultSet == null)
                {
                    // Only support those service query operations which have a corresponding entity set.
                    return(null);
                }
            }

            DomainDataServiceOperation op = new DomainDataServiceOperation(
                operation.Name,
                resultKind,
                resultResourceType,
                resultSet,
                hasSideEffects ? ServiceUtils.HttpPostMethodName : ServiceUtils.HttpGetMethodName,
                operationParameters,
                operation.Operation);

            return(op);
        }