1

I have a WCF service which is run on a port (25537) and also I have a MVC application. From MVC application I make post call to WCF service.

I got error :

OPTIONS http://mylocal.com:25537/Authentication Request header field Content-Type is not allowed by Access-Control-Allow-Headers.

I had try to many options but nothing changed.

To Global.asax

protected void Application_BeginRequest(object sender, EventArgs e)
        {
            Response.AppendHeader("Access-Control-Allow-Origin", "*");
            Response.AppendHeader("Access-Control-Allow-Headers", "Origin, X-Requested-With, Content-Type, Accept");
            if (HttpContext.Current.Request.HttpMethod == "OPTIONS" )
            {
                Response.AppendHeader("Access-Control-Allow-Methods", "GET, POST");
                Response.AppendHeader("Access-Control-Allow-Headers", "Origin, X-Requested-With, Content-Type, Accept");
                Response.AppendHeader("Access-Control-Max-Age", "1728000");
                HttpContext.Current.Response.End();
            } 
        }

To Web.Config

<httpProtocol>
  <customHeaders>
    <add name="Access-Control-Allow-Origin" value="*" />
    <add name="Access-Control-Allow-Headers" value="Origin, X-Requested-With, Content-Type, Accept" />
  </customHeaders>
</httpProtocol>

Nothing changed.

Any idea?

Thanks in advance.

2
  • did you put the customHeaders in the web.config for the WCF service? Commented Jun 27, 2014 at 13:19
  • There's a blog article out today (not my blog) about setting up WCF with CORS. You may find it useful Commented Jun 27, 2014 at 13:56

2 Answers 2

1

You should make some configuration both on js-side and wcf-side

on js:

function post(type, data, timeout) {
    return $.ajax({
        url: createUrl(POST, type),
        type: POST,
        data: JSON.stringify(data),
        contentType: "application/json",
        crossDomain: true,//<<<<-------------It`s here!
        processData: false,
        dataType: "json",
        timeout: timeout
    });
}

app.config on wcf-side:

  <system.serviceModel>

    <extensions>
      <behaviorExtensions>
        <add name="crossOriginResourceSharingBehavior" type="Nelibur.ServiceModel.Behaviors.EnableCrossOriginResourceSharingBehavior, Nelibur" />
      </behaviorExtensions>
    </extensions>
...
    <services>
      <service name="Nelibur.ServiceModel.Services.Default.JsonServicePerCall">
        <host>
          <baseAddresses>
            <add baseAddress="http://127.0.0.1:61111/webhost" />
            <add baseAddress="https://127.0.0.1:61112/webhost" />
          </baseAddresses>
        </host>
        <endpoint binding="webHttpBinding"
                  contract="Nelibur.ServiceModel.Contracts.IJsonService" behaviorConfiguration="jsonBehavior" bindingConfiguration="webHttpBinding"/>
      </service>
    </services>
    <behaviors>
      <endpointBehaviors>
        <behavior name="jsonBehavior">
          <webHttp />
          <crossOriginResourceSharingBehavior />
        </behavior>
      </endpointBehaviors>
    </behaviors>
  </system.serviceModel>

Behavior class on WCF-service side:

using System;
using System.Collections.Generic;
using System.ServiceModel.Channels;
using System.ServiceModel.Configuration;
using System.ServiceModel.Description;
using System.ServiceModel.Dispatcher;

namespace Nelibur.ServiceModel.Behaviors
{
    /// <summary>
    ///     Provides CORS support.
    /// </summary>
    public class EnableCrossOriginResourceSharingBehavior : BehaviorExtensionElement, IEndpointBehavior
    {
        /// <summary>
        ///     Gets the type of behavior.
        /// </summary>
        /// <returns>
        ///     A <see cref="T:System.Type" />.
        /// </returns>
        public override Type BehaviorType
        {
            get { return typeof (EnableCrossOriginResourceSharingBehavior); }
        }

        /// <summary>
        ///     Implement to pass data at runtime to bindings to support custom behavior.
        /// </summary>
        /// <param name="endpoint">The endpoint to modify.</param>
        /// <param name="bindingParameters">The objects that binding elements require to support the behavior.</param>
        public void AddBindingParameters(ServiceEndpoint endpoint, BindingParameterCollection bindingParameters)
        {
        }

        /// <summary>
        ///     Implements a modification or extension of the client across an endpoint.
        /// </summary>
        /// <param name="endpoint">The endpoint that is to be customized.</param>
        /// <param name="clientRuntime">The client runtime to be customized.</param>
        public void ApplyClientBehavior(ServiceEndpoint endpoint, ClientRuntime clientRuntime)
        {
        }

        /// <summary>
        ///     Implements a modification or extension of the service across an endpoint.
        /// </summary>
        /// <param name="endpoint">The endpoint that exposes the contract.</param>
        /// <param name="endpointDispatcher">The endpoint dispatcher to be modified or extended.</param>
        public void ApplyDispatchBehavior(ServiceEndpoint endpoint, EndpointDispatcher endpointDispatcher)
        {
            var requiredHeaders = new Dictionary<string, string>();

            requiredHeaders.Add("Access-Control-Allow-Origin", "*");
            requiredHeaders.Add("Access-Control-Request-Method", "POST,GET,OPTIONS");
            requiredHeaders.Add("Access-Control-Allow-Headers", "X-Requested-With,Content-Type");

            endpointDispatcher.DispatchRuntime.MessageInspectors.Add(new CustomHeaderMessageInspector(requiredHeaders));
        }

        /// <summary>
        ///     Implement to confirm that the endpoint meets some intended criteria.
        /// </summary>
        /// <param name="endpoint">The endpoint to validate.</param>
        public void Validate(ServiceEndpoint endpoint)
        {
        }

        /// <summary>
        ///     Creates a behavior extension based on the current configuration settings.
        /// </summary>
        /// <returns>
        ///     The behavior extension.
        /// </returns>
        protected override object CreateBehavior()
        {
            return new EnableCrossOriginResourceSharingBehavior();
        }
    }
}

You also have to include next operation in your service contract:

/// <summary>
/// Helper method for CORS support.
/// </summary>
[OperationContract]
[WebInvoke(Method = "OPTIONS", UriTemplate = "*")]
void GetOptions();

That`s all. Hope this help.

Sign up to request clarification or add additional context in comments.

Comments

0

To access WCF service across the cross domain you must have to allow crossDomainScriptAccessEnabled="true" for your binding.

I am sharing a very good blog and I am sure that, this will help you to understand access WCF service across the cross domain and difference between Jquery Ajax and Jsonp method.

http://www.bendewey.com/index.php/186/using-jsonp-with-wcf-and-jquery

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.