开发者

Message or a type that has MessageContractAttribute and other parameters of different types

I'm developing WCF services where some classes have the [MessageContract] attribute, and some don't.

When I try to run the services I get this error message below:

The operation 'ProcessOperation' could not be loaded because it has a parameter or return type of type System.ServiceModel.Channels.Message or a type that has MessageContractAttribute and other parameters of different types. When using System.ServiceModel.Channels.Message or types with MessageContractAttribute, the method must 开发者_运维知识库not use any other types of parameters.

Does it mean that all the services must have [MessageContract] although they are not related?


No, it means that you have multiple parameters on the method and some of them are not messages. Try posting the interface to your service.

This blog post explains:

... problem is that message contracts cannot be used at the same time as other parameter types. In this case, the return value of the operation is a string. Return values are just another output parameter, so this operation is mixing a message contract message with a primitive parameter type. This fails because message contracts give you control of the layout of the SOAP message, preventing the system from melding in these additional parameters.

Important note:

By the way, the error message you get when you try to mix message contracts looks like this.


This basically means that a particular operation is using a combination of message contract types and primitive types in any of the following combinations:

MixType1: Contract type and primitive types as operation parameters
MixType2: Contract type as a parameter and primitive type as return type
MixType3: Primitive type as a parameter and Contract type as return type

Any of the scenarios listed above would generate the error.


Solved!

I can't return String, I have return Greeting object to the client.

using System;
using System.ServiceModel;
using System.Net.Security;

namespace com.blogspot.jeanjmichel.model
{
    [MessageContract]
    public class Greeting
    {
        private String userGreeting;

        private void SetGreeting()
        {
            DateTime now = DateTime.Now;

            if (now.Hour >= 7 && now.Hour <= 11)
            {
                this.userGreeting = "Good morning";
            }
            else if (now.Hour >= 12 && now.Hour <= 17)
            {
                if (now.Hour == 12 || now.Hour == 13)
                {
                    this.userGreeting = "Good afternoon, it's lunch time!";
                }
                else
                {
                    this.userGreeting = "Good afternoon";
                }
            }
            else if (now.Hour >= 18 && now.Hour <= 20)
            {
                this.userGreeting = "Good evening";
            }
            else
            {
                this.userGreeting = "Good night";
            }
        }

        [MessageBodyMember(Order = 1, ProtectionLevel = ProtectionLevel.EncryptAndSign)]
        public String UserGreeting
        {
            get { return this.userGreeting; }
        }

        public Greeting()
        {
            this.SetGreeting();
        }
    }
}

using System;
using System.ServiceModel;
using com.blogspot.jeanjmichel.model;

namespace com.blogspot.jeanjmichel.services.contract
{
    [ServiceContract(Namespace = "http://jeanjmichel.blogspot.com/services/v0.0.1")]
    public interface IGetGreeting
    {
        [OperationContract]
        Greeting GetGreeting(Credential credential);
    }
}

using System;
using System.ServiceModel;
using com.blogspot.jeanjmichel.services.contract;
using com.blogspot.jeanjmichel.model;

namespace com.blogspot.jeanjmichel.services
{
    [ServiceBehavior(InstanceContextMode = InstanceContextMode.PerCall,
                     Namespace = "http://jeanjmichel.blogspot.com/services/v0.0.1")]
    public class GetGreetingService: IGetGreeting
    {
        public Greeting GetGreeting(Credential credential)
        {
            if (String.IsNullOrEmpty(credential.Token))
            {
                throw new FaultException("Inform the security phrase, and try again.");
            }
            else
            {
                if (credential.Token.Equals("mySeCuriTyP@ss"))
                {
                    Greeting g = new Greeting();
                    return g;
                }
                else
                {
                    throw new FaultException("Wrong password.");
                }
            }
        }
    }
}


When you are using Message object as a parameter, the method should return void


If you have the issue with mixed types of primitive(such as string) and MessageContract as the other type, i.e. one class as return and a string parameter, one way I solved this was switching from MessageContract to DataContract.

The other way to solve this would be to create a class to hold your primitive type as a property, so that both your return and parameter can implement MessageContract.


I ran into this error while maintaining an API in our code. The API suddenly began returning this error for all endpoints. I had upgraded the initialization method for Ninject to move away from a method that it said was obsolete.

Obsolete method: NinjectWebServiceHostFactory (no error) 
New method:      NinjectServiceHostFactory    (returns error)

The error went away when I reverted the change.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜