i have a WCF Service Method which returns XMlDocument i have added the attribut [XmlSerializerFormat]
on the method
Is there any way i can return XmlDocuemnt Object from WCf service
I could get the XmlDocument returned from my WCF Service in the following way.
My WCF service looks as shown below:
[ServiceContract]
[XmlSerializerFormat]
public interface ISampleService
{
[OperationContract]
Test GetXmlData();
}
[AspNetCompatibilityRequirements(RequirementsMode = AspNetCompatibilityRequirementsMode.Required)]
[ServiceBehavior(InstanceContextMode = InstanceContextMode.Single)]
public class SampleService : ISampleService
{
public string GetData()
{
return "Hello World";
}
public Test GetXmlData()
{
XmlDocument doc = new XmlDocument();
doc.Load(#"C:\SampleResponse.xml");
return new Test() {Doc = doc};
}
}
[Serializable]
public class Test
{
public XmlDocument Doc { get; set; }
}
The client adds a reference to the WCF Service and then calls the method GetXmlData() which returns a object Test which has the XmlDocuemnt within it.
Related
I'm trying to port an existing Soap WebService to .NET5 but am having issue with overloading a Soap method parameter.
In NET4 the code looks like this
namespace SoapWebServiceeTest.Soap
{
/// <summary>
/// Summary description for WsgSPServiceOrderService
/// </summary>
[WebService(Namespace = "http://tempuri.org/")]
[WebServiceBinding(ConformsTo = WsiProfiles.BasicProfile1_1)]
[System.ComponentModel.ToolboxItem(false)]
// To allow this Web Service to be called from script, using ASP.NET AJAX, uncomment the following line.
// [System.Web.Script.Services.ScriptService]
public class TextWebService : System.Web.Services.WebService
{
[WebMethod]
public string Test(
[XmlElement("object1", typeof(Object1))]
[XmlElement("object2", typeof(Object2))]
[XmlElement("object3", typeof(Object3))]
object request)
{
return $"{request.GetType().Name}";
}
}
public class Object1 { public string Param1 { get; set; } }
public class Object2 { public string Param2 { get; set; } }
public class Object3 { public string Param3 { get; set; } }
}
How do I achieve this in .NET5?
I have tried following but got reflection exception: System.Reflection.AmbiguousMatchException: 'Multiple custom attributes of the same type found.'
[ServiceContract]
public interface ITestWebService
{
[OperationContract]
string Test(
[XmlElement("object1", typeof(Object1))]
[XmlElement("object2", typeof(Object2))]
[XmlElement("object3", typeof(Object3))]
object request);
}
And also tried this but VS Add Connected Services errored with "More than one message named 'ISampleService_Test_InputMessage' was specified. Each message must have a unique name."
[OperationContract]
string Test(Object1 request);
[OperationContract]
string Test(Object2 request);
Any help would be awesome
You may try this
You can make it post or get based on your need
[OperationContract]
[WebInvoke(UriTemplate = "Test1", Method = "POST"]
string Test(Object1 request);
and
[OperationContract]
[WebInvoke(UriTemplate = "Test2", Method = "POST"]
string Test(Object2 request);
This way you can achieve objective
It is a simple class, I reference it in silverlight project in the same solution. if the operation method returns an integer, it works fine, but if I make it return a DataContract, it just says the servicereference cannot find
In web project
public class UserResult
{
....
}
[ServiceContract(Namespace = "")]
[AspNetCompatibilityRequirements(RequirementsMode = AspNetCompatibilityRequirementsMode.Allowed)]
public class ServiceUser
{
[OperationContract]
public UserResult UserSignIn(string userid, string password)
{
...
} /// doesn't work
public int UserSignIn(string userid, string password)
{
...
} // works
In SilverLight
ServiceReferenceUser.ServiceUserClient srUser =
new ServiceReferenceUser.ServiceUserClient();
Perhaps the UserResult class references some other DataContract. If so, that DataContract needs to be specified as a known type.
I have WCF service which accepts a xmldocument and returns a xml document, Below is the interface code
namespace CreateLabelWS
{
[ServiceContract(Namespace = "http://localhost/Create")]
public interface ICreateLabel
{
[OperationContract,XmlSerializerFormat]
[FaultContract(typeof(CustomException))]
XmlDocument CreateLabelRequestIntoDB(XmlDocument Request);
}
[DataContract(Namespace="")]
public class CustomException
{
[DataMember()]
public string Title;
[DataMember()]
public string ExceptionMessage;
[DataMember()]
public string InnerException;
[DataMember()]
public string StackTrace;
[DataMember()]
public int RowsInserted;
}
}
But when I create a proxy for this and try to access CreateLabelRequestIntoDB from the client application, I found that to be exposed as Xelement type rather than XMLDocument. Could anybody help me here and also tell me if there's any error in my code
Dins
Hopefully this is an easy one. I'm wondering if this is possible - perhaps it is not. I'm attempting to self-host a WCF service (in my example below it is a console application). The service does not have a default constructor. It only contains a single parameter signature constructor. I need the service to be able to handle user sessions. Currently I am using Ninject DI. Here is a simple code solution I came up with to demonstrate my issue:
using System;
using System.ServiceModel;
using System.ServiceModel.Web;
using Ninject.Modules;
namespace ConsoleApplication1
{
public class Program
{
static void Main()
{
using (var webServiceHost = new WebServiceHost(typeof(MyWcf)))
{
var webHttpBinding = new WebHttpBinding();
var uri = new Uri("http://localhost:8000/");
webServiceHost.AddServiceEndpoint(typeof(IMyWcf), webHttpBinding, uri);
webServiceHost.Open();
Console.WriteLine("Service is ready...");
Console.ReadKey();
}
}
}
[ServiceContract]
public interface IMyWcf
{
[OperationContract, WebGet(UriTemplate = "")]
string HelloWorld();
}
[ServiceBehavior(InstanceContextMode = InstanceContextMode.PerSession)]
public class MyWcf : IMyWcf
{
private readonly IMessage _customMessage = new Message("Default Message.");
public MyWcf(IMessage message)
{
_customMessage = message;
}
public string HelloWorld()
{
return _customMessage.Text;
}
}
public interface IMessage
{
string Text { get; }
}
public class Message : IMessage
{
public Message (string message)
{
Text = message;
}
public string Text { get; set; }
}
public class NinjectSetup : NinjectModule
{
public override void Load()
{
Bind<IMessage>().To<Message>()
.WithConstructorArgument("message", "Injected String Message.");
}
}
}
Obviously commenting out the parameterized constructor allows the service to run. But that does me no good. I don't want to use ServiceHostFactory because that apparently requires me to have a .svc/IIS. Is there a way around this? Can I just create a new MyWebServiceHost that inherits from WebServiceHost and override some method that will create a instance for the service?
Using Ruben's suggestion (in the comments) above, I was able to locate a working example within the Ninject.Extensions.Wcf source repository.
I am interested in impersonating well-known Web Services and Wcf Services for integration test purposes. To this end, I would like to capture service metadata, auto-generate service stubs, and host service stubs in a self-hosted environment.
Following this article here, I am able to obtain remote Wcf Service metadata and generate contracts. However, I am having some difficulty doing the same for remote Asmx Web Services.
I have a set of mickey-mouse solutions for vetting this out.
My Asmx solution contains a default "Hello World" web service, found below
[WebService(Namespace = "http://tempuri.org/")]
[WebServiceBinding(ConformsTo = WsiProfiles.BasicProfile1_1)]
[System.ComponentModel.ToolboxItem(false)]
public class SimpleAsmxService : System.Web.Services.WebService
{
[WebMethod]
public string HelloWorld () { return "Hello World"; }
}
My Wcf solution contains a default "Hello World" service, also found below
[ServiceContract]
public interface ISimpleWcfService
{
[OperationContract]
string GetData(int value);
[OperationContract]
CompositeType GetDataUsingDataContract(CompositeType composite);
}
[DataContract]
public class CompositeType
{
[DataMember]
public bool BoolValue { get; set; }
[DataMember]
public string StringValue { get; set; }
}
public class SimpleWcfService : ISimpleWcfService
{
public string GetData(int value)
{
return string.Format("You entered: {0}", value);
}
public CompositeType GetDataUsingDataContract(CompositeType composite)
{
if (composite.BoolValue)
{
composite.StringValue += "Suffix";
}
return composite;
}
}
Finally, the little console-that-could looks like
class Program
{
public const string UrlWcf =
"http://localhost:8731/Design_Time_Addresses/SimpleWcfService/mex";
public const string UrlAsmx =
"http://localhost:1803/SimpleAsmxService.asmx?WSDL";
static void Main(string[] args)
{
EndpointAddress mexAddress = new EndpointAddress (UrlWcf);
MetadataExchangeClient mexClient =
new MetadataExchangeClient (mexAddress);
mexClient.ResolveMetadataReferences = true;
// NOTE: blows up if we use UrlAsmx
MetadataSet metaSet = mexClient.GetMetadata ();
WsdlImporter importer = new WsdlImporter (metaSet);
Collection<ContractDescription> contracts =
importer.ImportAllContracts();
}
}
It seems to me that I should be able to pull Wsdl from a well-known Asmx Web Service and generate contracts [and from contracts to code], but cannot seem to contort the preceding sample to do so. Any help would be much appreciated,
Thanks!
NOTE: the error generated when invoking MetadataSet metaSet = mexClient.GetMetadata(); above is a System.InvalidOperationException with message of
Metadata contains a reference that cannot be resolved : 'http://localhost:1803/SimpleAsmxService.asmx?WSDL'
With a System.InvalidOperationException inner exception with message of
<?xml version="1.0" encoding="utf-16"?>
<Fault xmlns="http://www.w3.org/2003/05/soap-envelope">
<Code>
<Value>Sender</Value>
</Code>
<Reason>
<Text xml:lang="en">
System.Web.Services.Protocols.SoapException: Unable to handle request without a valid action parameter. Please supply a valid soap action.
at System.Web.Services.Protocols.Soap12ServerProtocolHelper.RouteRequest()
at System.Web.Services.Protocols.SoapServerProtocol.RouteRequest(SoapServerMessage message)
at System.Web.Services.Protocols.SoapServerProtocol.Initialize()
at System.Web.Services.Protocols.ServerProtocol.SetContext(Type type, HttpContext context, HttpRequest request, HttpResponse response)
at System.Web.Services.Protocols.ServerProtocolFactory.Create(Type type, HttpContext context, HttpRequest request, HttpResponse response, Boolean& abortProcessing)
</Text>
</Reason>
</Fault>
The way to get it to work with an ASMX web service is to specify the MetadataExchangeClientMode
...
MetadataExchangeClient mexClient =
new MetadataExchangeClient (new Uri(), MetadataExchangeClientMode.HttpGet);
...
using MetadataExchangeClientMode.HttpGet for your ASMX services
and MetadataExchangeClientMode.MetadataExchange for your WCF services.