Use JQuery AJAX to call WCF Service with multiple bindings - wcf

I have a WCF service with three endpoints with different bindings (basicHttpBinding for soap clients, webHttpBinding for jquery ajax client, and mex).
I can access the service via SOAP (by adding a Service Reference then):
ServiceRef.IService service = new ServiceClient("BasicHttpBinding_IService");
Response.Write(service.TestMethod("hi"));
But why I call from Jquery Ajax I get a 404 error.
If I copy the service into a test project and define only one webHttpBinding, I can call the service via jquery.
IService.cs
[ServiceContract]
public interface IService
{
[OperationContract]
[WebInvoke(Method = "POST",
ResponseFormat = WebMessageFormat.Json)]
Response TestMethod(string Id);
....
Service.cs
[AspNetCompatibilityRequirements(RequirementsMode = AspNetCompatibilityRequirementsMode.Allowed)]
[ServiceBehavior]
public class Service : IService
{
[OperationBehavior]
public Response TestMethod(string Id)
{
Response resp = new Response();
resp.Message = "hello";
return resp;
}
....
Web.Config
<system.serviceModel>
<serviceHostingEnvironment multipleSiteBindingsEnabled="false" aspNetCompatibilityEnabled="true" />
<services>
<service
name="eBooks.Presentation.Wcf.Service"
behaviorConfiguration="eBooks.Presentation.Wcf.ServiceBehavior">
<!-- use base address provided by host -->
<!-- specify BasicHttp binding and a binding configuration to use -->
<endpoint address="soap"
binding="basicHttpBinding"
bindingConfiguration="Binding1"
contract="eBooks.Presentation.Wcf.IService" />
<endpoint address="mex" binding="mexHttpBinding" contract="IMetadataExchange"/>
<endpoint address="" binding="webHttpBinding"
contract="eBooks.Presentation.Wcf.IService" behaviorConfiguration="EndpBehavior"/>
</service>
</services>
<bindings>
<!--
Following is the expanded configuration section for a BasicHttpBinding.
Each property is configured with the default value.
See the TransportSecurity, and MessageSecurity samples in the
Basic directory to learn how to configure these features.
-->
<basicHttpBinding>
<binding name="Binding1"
hostNameComparisonMode="StrongWildcard"
receiveTimeout="00:10:00"
sendTimeout="00:10:00"
openTimeout="00:10:00"
closeTimeout="00:10:00"
maxReceivedMessageSize="65536"
maxBufferSize="65536"
maxBufferPoolSize="524288"
transferMode="Buffered"
messageEncoding="Text"
textEncoding="utf-8"
bypassProxyOnLocal="false"
useDefaultWebProxy="true" >
<security mode="None" />
</binding>
</basicHttpBinding>
</bindings>
<behaviors>
<serviceBehaviors>
<behavior name="eBooks.Presentation.Wcf.ServiceBehavior">
<!-- To avoid disclosing metadata information, set the value below to false and remove the metadata endpoint above before deployment -->
<serviceMetadata httpGetEnabled="true"/>
<!-- To receive exception details in faults for debugging purposes, set the value below to true. Set to false before deployment to avoid disclosing exception information -->
<serviceDebug includeExceptionDetailInFaults="true"/>
</behavior>
</serviceBehaviors>
<endpointBehaviors>
<behavior name="EndpBehavior">
<webHttp/>
</behavior>
</endpointBehaviors>
</behaviors>
Jquery
function CallService() {
$.ajax({
type: "POST", //GET or POST or PUT or DELETE verb
url: "http://localhost:888/Service.svc/TestMethod", // Location of the service
data: '{"Id": "1"}', //Data sent to server
contentType: "application/json; charset=utf-8", // content type sent to server
dataType: "json", //Expected data format from server
processdata: ProcessData, //True or False
success: function (msg) {//On Successfull service call
ServiceSucceeded(msg);
},
error: ServiceFailed// When Service call fails
});
}
In my endpoint configuration I have set the address for the webHttp endpoint to be "" as I dont know how to select a specific endpoint when calling from jquery.
Anyone have any ideas why I am getting this 404 error?

1) Make sure your Service.svc is in the root directory.
2) Add the
[WebInvoke(Method = "POST", ResponseFormat = WebMessageFormat.Json)]
To the place where you instantiate your TestMethod. like this:
[OperationBehavior]
[WebInvoke(Method = "POST", ResponseFormat = WebMessageFormat.Json)]
public Response TestMethod(string Id)
{
Response resp = new Response();
resp.Message = "hello";
return resp;
}
Either of those help?

Related

WCF JSON Format - while consuming in Client side getting an error message

Client side Code
I have created web application and added service reference to the Client Project
I tried creating a client Object like this:
Service1Client a = new Service1Client();
but getting an error message :
Could not find default endpoint element that references contract 'ServiceReference_test.IService1' in the ServiceModel client
configuration section. This might be because no configuration file was
found for your application, or because no endpoint element matching
this contract could be found in the client element.
Could you please let me know what mistake am I doing, I am new to WCF please help me
WCF service which returns JSON Format:
namespace WcfService1
{
public class Service1 : IService1
{
public string GetData(string Id)
{
return ("You entered: " + Id);
}
}
}
namespace WcfService1
{
[ServiceContract]
public interface IService1
{
[OperationContract]
[WebInvoke(Method = "GET", UriTemplate = "/GetData/{Id}",
RequestFormat = WebMessageFormat.Json,
ResponseFormat = WebMessageFormat.Json,
BodyStyle = WebMessageBodyStyle.Wrapped
)]
string GetData(string Id);
// TODO: Add your service operations here
}
}
Web.Config file
<system.serviceModel>
<services>
<service name="WcfService1.Service1" behaviorConfiguration="ServiceBehaviour">
<endpoint address="" behaviorConfiguration="web" binding="webHttpBinding" contract="WcfService1.IService1"/>
<endpoint contract="IMetadataExchange" binding="mexHttpBinding" address="mex"/>
</service>
</services>
<behaviors>
<endpointBehaviors>
<behavior name="web">
<webHttp helpEnabled="true" automaticFormatSelectionEnabled="false" />
</behavior>
</endpointBehaviors>
<serviceBehaviors>
<behavior name="ServiceBehaviour">
<serviceMetadata httpGetEnabled="true" httpsGetEnabled="true"/>
<serviceDebug includeExceptionDetailInFaults="false"/>
</behavior>
</serviceBehaviors>
</behaviors>
<!--<protocolMapping>
<add binding="basicHttpsBinding" scheme="https" />
</protocolMapping>-->
<serviceHostingEnvironment aspNetCompatibilityEnabled="true" multipleSiteBindingsEnabled="true" />
</system.serviceModel>
You should add following tags in your client App.config or Web.config:
<system.serviceModel>
<bindings>
<webHttpBinding>
<binding name="WebHttpBinding" />
</webHttpBinding>
</bindings>
<client>
<endpoint address="http://localhost:8733/Design_Time_Addresses/fine_service/FineService/soap"
binding="webHttpBinding" bindingConfiguration="WebHttpBinding"
contract="ServiceReference1.IService1" name="WebHttpBinding" />
</client>
</system.serviceModel>
if you have this tags in your cofig file then make sure that client endpoint contract name should be the same as it is in your service endpoint. In your case contract name is IService1
EDIT:
also see this

WCF Rest service not working

ILeaveManagement class
[ServiceContract]
public interface ILeaveManagement
{
[OperationContract]
[WebInvoke(Method = "GET", ResponseFormat = WebMessageFormat.Xml,
BodyStyle = WebMessageBodyStyle.Bare, UriTemplate = "get")]
List<ServiceReference1.LeaveRequest> GetLeaveDetails();
}
LeaveManagement class
public class LeaveManagement : ILeaveManagement
{
public List<ServiceReference1.LeaveRequest> GetLeaveDetails()
{
try
{
var entities = new ServiceReference1.leaverequest_Entities(new Uri(serviceUrl));
var result = entities.LeaveRequestCollection;
return result.ToList();
}
catch
{
return new List<ServiceReference1.LeaveRequest>();
}
}
}
configuration
<service behaviorConfiguration="DRLExternalList.LeaveManagementBehavior" name="DRLExternalList.LeaveManagement">
<endpoint address="" binding="wsHttpBinding" contract="DRLExternalList.ILeaveManagement"/>
<endpoint address="mex" binding="mexHttpBinding" contract="IMetadataExchange"/>
</service>
<behavior name="DRLExternalList.LeaveManagementBehavior">
<serviceMetadata httpGetEnabled="true" />
<serviceDebug includeExceptionDetailInFaults="false" />
</behavior>
I have deployed the project in IIS 7.5. When i run the application , it is saying BadRequest.
I have verrified in fiddler. i saw 400 error.
Please help me on this.
Try using webHttpBinding in your endpoint instead of the wsHttpBinding, or add it as an additional one and change the address. I use a bindingNamespace in my project, but I don't think you need it.
<endpoint address="XMLService"
binding="webHttpBinding"
behaviorConfiguration="restXMLBehavior"
contract="DRLExternalList.ILeaveManagement">
</endpoint>
Add an Endpoint Behavior
<endpointBehaviors>
<!-- Behavior for the REST endpoint -->
<behavior name="restXMLBehavior">
<webHttp helpEnabled="true"/>
</behavior>
</endpointBehaviors>
I also annotate the OperationContract slightly differently, but it shouldn't make all that much of a difference. I'll give it to you just in case...
[WebGet(UriTemplate = "/GetLeaveDetails", ResponseFormat = WebMessageFormat.Xml)]
To call the service, it would look like this using the XMLService endpoint name:
http://myWebHost.com/WebService/MyService.svc/XMLService/GetLeaveDetails
Hosting an wcf service into a website issue : System.ArgumentException: ServiceHost only supports class service types
the above link helped me to solve my issue.
<%# ServiceHost Language="C#" Debug="true" Service="restleave.ProductRESTService" %>

wcf rest service consumption in c# console application

I made wcf rest service by going New->projects->WCF Service Application
I am unable to use methods in console application while i have hosted wcf rest service and referenced wcf rest service in application
My Application code is below :
IRestServiceImpL
[ServiceContract]
public interface IRestServiceImpL
{
[OperationContract]
[WebInvoke(Method = "GET", ResponseFormat = WebMessageFormat.Xml,
RequestFormat = WebMessageFormat.Xml, UriTemplate = "XmlData/{id}")]
string XmlData(string id);
[OperationContract]
[WebInvoke(Method = "GET", ResponseFormat = WebMessageFormat.Json,
RequestFormat = WebMessageFormat.Json, UriTemplate = "JsonData/{id}")]
string JsonData(string id);
}
RestServiceImpL.svc.cs
[AspNetCompatibilityRequirements(RequirementsMode
= AspNetCompatibilityRequirementsMode.Allowed)]
public class RestServiceImpL : IRestServiceImpL
{
public string XmlData(string id)
{
return "you requested for " + id;
}
public string JsonData(string id)
{
return "you requested for " + id;
}
}
Config File
<system.web>
<compilation debug="true" targetFramework="4.0" />
</system.web>
<system.serviceModel>
<bindings>
<webHttpBinding>
<binding name="StreamedRequestWebBinding"
bypassProxyOnLocal="true"
useDefaultWebProxy="false"
hostNameComparisonMode="WeakWildcard"
sendTimeout="10:15:00"
openTimeout="10:15:00"
receiveTimeout="10:15:00"
maxReceivedMessageSize="2147483647"
maxBufferSize="2147483647"
maxBufferPoolSize="2147483647"
transferMode="StreamedRequest"
crossDomainScriptAccessEnabled="true"
>
<readerQuotas maxArrayLength="2147483647"
maxStringContentLength="2147483647" />
</binding>
</webHttpBinding>
</bindings>
<services>
<service name="RestService.RestServiceImpL" behaviorConfiguration="ServiceBehaviour">
<!--<endpoint address="" binding="basicHttpBinding" contract="RestService.IRestServiceImpL"></endpoint>-->
<endpoint address="" binding="webHttpBinding" name="StreamedRequestWebBinding" bindingConfiguration="StreamedRequestWebBinding" contract="RestService.IRestServiceImpL" behaviorConfiguration="web"></endpoint>
</service>
</services>
<behaviors>
<serviceBehaviors>
<behavior name="ServiceBehaviour">
<!-- To avoid disclosing metadata information, set the value below to false and remove the metadata endpoint above before deployment -->
<serviceMetadata httpGetEnabled="true"/>
<!-- To receive exception details in faults for debugging purposes, set the value below to true. Set to false before deployment to avoid disclosing exception information -->
<serviceDebug includeExceptionDetailInFaults="false"/>
</behavior>
</serviceBehaviors>
<endpointBehaviors>
<behavior name="web">
<webHttp/>
</behavior>
</endpointBehaviors>
</behaviors>
<serviceHostingEnvironment multipleSiteBindingsEnabled="true" aspNetCompatibilityEnabled="true" />
</system.serviceModel>
<system.webServer>
<httpProtocol>
<customHeaders>
<add name="Access-Control-Allow-Origin" value="*"/>
</customHeaders>
</httpProtocol>
<modules runAllManagedModulesForAllRequests="true"/>
</system.webServer>
I host this service application in IIS
Now after giving reference to console application when i call its methods
by using proxy class then i got error of Invalid Operation Contract Exception
that endpoint not specified
calling code is below :
ServiceClient oServiceClient = new ServiceClient();<br/>
oServiceClient.JsonData("123");
Please suggest what is problem in the code.
Thanks stack overflow for support...I did it..
The calling Wcf Rest Service code is written below :
//code for xml Response consumption from WCF rest Service[Start]
WebRequest req = WebRequest.Create(#"http://RestService.com/WcfRestService/RestServiceImpL.svc/XmlData/sad");
req.Method = "GET";
req.ContentType = #"application/xml; charset=utf-8";
HttpWebResponse resp = req.GetResponse() as HttpWebResponse;
if (resp.StatusCode == HttpStatusCode.OK)
{
XmlDocument myXMLDocument = new XmlDocument();
XmlReader myXMLReader = new XmlTextReader(resp.GetResponseStream());
myXMLDocument.Load(myXMLReader);
Console.WriteLine(myXMLDocument.InnerText);
}
//code for xml Response consumption from WCF rest Service[END]
//****************************************************************************
//code for json Response consumption from WCF rest Service[Start]
WebRequest req2 = WebRequest.Create(#"http://RestService.com/WcfRestService/RestServiceImpL.svc/JsonData/as");
req2.Method = "GET";
req2.ContentType = #"application/json; charset=utf-8";
HttpWebResponse response = (HttpWebResponse)req2.GetResponse();
string jsonResponse = string.Empty;
using (StreamReader sr = new StreamReader(response.GetResponseStream()))
{
jsonResponse = sr.ReadToEnd();
Console.WriteLine(jsonResponse);
}
//code for json Response consumption from WCF rest Service[END]

WCF Windows authentication issue with REST service

I'm having some difficulty setting up a WCF service to run under Windows authentication. The service is only consumed via jQuery using ajax.
IIS (version 6 on server 2003) is set to only allow Windows Authentication.
web.config has the <authentication mode="Windows" /> tag.
Here's the service section of the web.config:
<system.serviceModel>
<behaviors>
<endpointBehaviors>
<behavior name="AspNetAjaxBehavior">
<webHttp />
</behavior>
</endpointBehaviors>
<serviceBehaviors>
<behavior name="ServiceBehavior">
<serviceMetadata httpGetEnabled="true"/>
</behavior>
</serviceBehaviors>
</behaviors>
<serviceHostingEnvironment aspNetCompatibilityEnabled="true"/>
<services>
<service name="SearchService" behaviorConfiguration="ServiceBehavior">
<endpoint address="http://localhost:9534/SearchService.svc" behaviorConfiguration="AspNetAjaxBehavior"
binding="webHttpBinding" bindingConfiguration="webWinBinding"
name="searchServiceEndpoint" contract="MyApp.Services.ISearchService">
</endpoint>
</service>
</services>
<bindings>
<webHttpBinding>
<binding name="webWinBinding" maxBufferSize="2147483647" maxReceivedMessageSize="2147483647">
<security mode="TransportCredentialOnly">
<transport clientCredentialType="Windows"/>
</security>
<readerQuotas maxArrayLength="100000" maxStringContentLength="2147483647" />
</binding>
</webHttpBinding>
</bindings>
The interface looks like this:
[ServiceContract(Namespace = "http://MyService.ServiceContracts/2012/02", Name = "SearchService")]
public interface ISearchService
{
[WebGet(ResponseFormat = WebMessageFormat.Json, BodyStyle = WebMessageBodyStyle.Bare, UriTemplate = "GetSomeData?filter={filter}")]
[OperationContractAttribute(Action = "GetSomeData")]
string GetSomeData(string filter);
}
And the implementation:
[ServiceBehavior(IncludeExceptionDetailInFaults = true)]
[AspNetCompatibilityRequirements(RequirementsMode = AspNetCompatibilityRequirementsMode.Required)]
public class SearchService : ISearchService
{
public string GetSomeData(string filter)
{
// Call Database and get some results
// return the results
return "";
}
}
When I navigate to the service in Internet Explorer, it prompts me for my username and password, despite having Windows Authentication turned on.
As soon as I enable Anonymous Authentication, the service loads just fine and everything works. Problem is, I have other things going on in the web application that require anonymous to be turned off.
I've scoured the web and can't find anything on this problem.

WCF 405 webmethod not found issue

I have a requirement of creating a webservice where the client and the service will talk in Simple Soap (that request and response will be soap), I tried all to find a sample example on net where this thing is already done or some code sample so that I can get started but I think I am bad in searching google, that is why can't find any one so far, Some one suggested to use WCF so get an article
http://csharping.com/wcf/building-a-soap-response-envelope-manually-with-the-message-class/
But again my problem is not solved, I tried to create an application with this sample (with so many issues :( )
Created a console application and the Program.cs is
using System;
using System.IO;
using System.Net;
using System.ServiceModel;
using System.ServiceModel.Channels;
using System.ServiceModel.Description;
using System.Text;
using System.Runtime.Serialization;
namespace ServiceConsole
{
public class Program
{
static void Main(string[] args)
{
using (ServiceHost serviceHost = new ServiceHost(typeof(ServiceClient), new Uri("http://localhost:2000/")))
{
ServiceEndpoint serviceEndpoint = new ServiceEndpoint(
ContractDescription.GetContract(typeof(IService)));
ServiceEndpoint metadataEndpoint = new ServiceEndpoint(
ContractDescription.GetContract(typeof(IMetadataExchange)));
ServiceMetadataBehavior metadataBehavior = serviceHost.Description.Behaviors.Find<ServiceMetadataBehavior>();
if (metadataBehavior == null)
{
metadataBehavior = new ServiceMetadataBehavior();
metadataBehavior.HttpGetEnabled = true;
serviceHost.Description.Behaviors.Add(metadataBehavior);
}
serviceHost.AddServiceEndpoint(typeof(IService), new BasicHttpBinding(), "http://localhost:2000/");
serviceHost.AddServiceEndpoint(typeof(IMetadataExchange), MetadataExchangeBindings.CreateMexHttpBinding(), "http://localhost:2000/WCFService/mex");
serviceHost.Open();
string requestData = "<s:Envelope xmlns:s=\"http://schemas.xmlsoap.org/soap/envelope/\"><s:Header><h:HeaderItem xmlns:h=\"http://tempuri.org/\">a header item</h:HeaderItem><ActivityId CorrelationId=\"090c553b-bfcc-4e4f-94cd-1b4333fe82a9\" xmlns=\"http://schemas.microsoft.com/2004/09/ServiceModel/Diagnostics\">377a454b-b543-4c6f-b4ac-3981029b60e6</ActivityId></s:Header><s:Body><string xmlns=\"http://schemas.microsoft.com/2003/10/Serialization/\">a body item</string></s:Body></s:Envelope>";
byte[] requestDataBytes = Encoding.UTF8.GetBytes(requestData);
HttpWebRequest request = (HttpWebRequest)WebRequest.Create("http://localhost/WCFService/");
request.Method = "POST";
request.ContentType = "text/xml; charset=utf-8";
request.Headers.Add("SOAPAction", "http://tempuri.org/IWebService/GetMessage");
request.ContentLength = requestDataBytes.Length;
StreamWriter streamWriter = new StreamWriter(request.GetRequestStream());
streamWriter.Write(requestData);
streamWriter.Flush();
streamWriter.Close();
HttpWebResponse response = (HttpWebResponse)request.GetResponse();
StreamReader streamReader = new StreamReader(response.GetResponseStream());
string responseBody = streamReader.ReadToEnd();
Console.WriteLine("Service returned the following response...");
Console.WriteLine("");
Console.WriteLine(responseBody);
Console.ReadKey();
serviceHost.Close();
}
}
}
}
the app.config which I generated using svcutil.exe is like this
<?xml version="1.0" encoding="utf-8"?>
<configuration>
<system.serviceModel>
<bindings>
<basicHttpBinding>
<binding name="BasicHttpBinding_IService" closeTimeout="00:01:00"
openTimeout="00:01:00" receiveTimeout="00:10:00" sendTimeout="00:01:00"
allowCookies="false" bypassProxyOnLocal="false" hostNameComparisonMode="StrongWildcard"
maxBufferSize="65536" maxBufferPoolSize="524288" maxReceivedMessageSize="65536"
messageEncoding="Text" textEncoding="utf-8" transferMode="Buffered"
useDefaultWebProxy="true">
<readerQuotas maxDepth="32" maxStringContentLength="8192" maxArrayLength="16384"
maxBytesPerRead="4096" maxNameTableCharCount="16384" />
<security mode="None">
<transport clientCredentialType="None" proxyCredentialType="None"
realm="" />
<message clientCredentialType="UserName" algorithmSuite="Default" />
</security>
</binding>
</basicHttpBinding>
</bindings>
<client>
<endpoint address="http://localhost:2000/WebService/Service.svc"
binding="basicHttpBinding" bindingConfiguration="BasicHttpBinding_IService"
contract="IService" name="BasicHttpBinding_IService" />
</client>
</system.serviceModel>
</configuration>
My webservioce is like (it is a WCF website in which the port is provided by me and is 2000
Service contract is
[ServiceContract]
public interface IService
{
[OperationContract]
Message GetMessage(Message s);
}
[ServiceBehavior]
public class Service : IService
{
public Message GetMessage(Message message)
{
string body = message.GetBody<string>();
return Message.CreateMessage(MessageVersion.Soap11, "http://tempuri.org/IWebService/GetMessageResponse", "body is " + body);
}
}
and the web.config is
<system.serviceModel>
<services>
<service behaviorConfiguration="ServiceBehavior" name="Service">
<endpoint address="http://localhost:2000/WebService/Service.svc" binding="basicHttpBinding" bindingConfiguration=""
contract="IService" >
<identity>
<dns value="localhost" />
</identity>
</endpoint>
<endpoint address="mex" binding="mexHttpBinding" contract="IMetadataExchange" />
<host>
<timeouts closeTimeout="00:01:10" />
</host>
</service>
</services>
<behaviors>
<serviceBehaviors>
<behavior name="ServiceBehavior">
<serviceMetadata httpGetEnabled="true" policyVersion="Policy15" />
<serviceDebug includeExceptionDetailInFaults="false" />
</behavior>
</serviceBehaviors>
</behaviors>
</system.serviceModel>
My issue is 405 webmethod not body can anyone please tell me what is an issue in this, I am new to WCF before this created a sample and this is my second application
You do not need to create the SOAP message manually, just use basic http binding and that will rturn SOAP.
When you have a WCF service, the whole point is that you can define e.g. parameters like strings, int and so forth - and you don't have to mess with loads of XML and SOAP headers and bodies.
So basically, your service contract should be something like:
[ServiceContract]
public interface IService
{
[OperationContract]
int DoSomeMathAddTowNumbers(int num1, int num2);
}
and your service implementation would then just implement that method, add the two numbers, and return the result:
public class Service : IService
{
int DoSomeMathAddTowNumbers(int num1, int num2)
{
return num1 + num2;
}
}
No mess with Message or XML manipulation or anything.
A client that wants to call your service would create a WCF client-side proxy using svcutil or the Visual Studio Add Service Reference method, and it would get a proxy class that has the same methods as the service it connects to - and you would call them, using the straight, easy parameters - something like:
ServiceClient client = new ServiceClient();
int result = client.DoSomeMathAddTwoNumbers(42, 100);
So basically, I think you need to get back to the drawing board and read up on the WCF basics again - it should not be that difficult, really! (that's the whole point - it should make services easy ...)
Check out the Beginner's Guide at the WCF Developer Center at MSDN - it contains lots of really good videos, screencasts, articles on how to get started with WCF.-
You might also want to check out the DotNet Rocks TV episode #135: Keith Elder Demystifies WCF