从JQuery调用WCF服务:跨源选项请求给出错误400

从JQuery调用WCF服务:跨源选项请求给出错误400,jquery,wcf,web-services,soap,cross-domain,Jquery,Wcf,Web Services,Soap,Cross Domain,我正试图从JQuery调用C#wcfsoapweb服务 该服务托管在端口80上的IIS上,客户端从端口81上的Apache运行,两者都从本地主机运行。因此,我陷入了跨源请求中 使用Chrome,我得到了预期的结果,但是查看网络流量,它显示选项请求返回错误400错误请求,但是下一个POST请求成功: 使用Firefox会引发错误(JavaScript警报显示null | error |)。POST请求似乎没有发送,因为选项请求失败: 使用IE,一切都很好,就好像它来自同一个来源。。。我没有看到

我正试图从JQuery调用C#wcfsoapweb服务

该服务托管在端口80上的IIS上,客户端从端口81上的Apache运行,两者都从本地主机运行。因此,我陷入了跨源请求中

  • 使用Chrome,我得到了预期的结果,但是查看网络流量,它显示
    选项
    请求返回错误
    400错误请求
    ,但是下一个
    POST
    请求成功:

  • 使用Firefox会引发错误(JavaScript警报显示
    null | error |
    )。
    POST
    请求似乎没有发送,因为
    选项
    请求失败:

  • 使用IE,一切都很好,就好像它来自同一个来源。。。我没有看到任何
    选项
    请求:

  • 从接口公开的函数:

    namespace Test
    {
        [ServiceContract]
        public interface IMathService
        {
            [OperationContract]
            String HelloWorld();
        }
    }
    
    服务配置(Web.config):

    
    [...]
    
    JQuery代码:

    $('#btn_helloworld').click(function () {
        var soapRequest = '<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/" xmlns:tem="http://tempuri.org/">' +
                            '<soapenv:Header/>' +
                            '<soapenv:Body>' +
                                '<tem:HelloWorld/>' +
                            '</soapenv:Body>' +
                            '</soapenv:Envelope>';
        $.ajax({
            type: 'POST',
            url: 'http://localhost/WCFtest/service.svc/soap',
            crossDomain: true,
            contentType: 'text/xml',
            dataType: 'xml',
            data: soapRequest,
            beforeSend: function (xhr) {
                xhr.setRequestHeader('SOAPAction', 'http://tempuri.org/IMathService/HelloWorld');
            },
            success: function (data) {
                $('#outputHelloWorld').val($(data).find('HelloWorldResponse').text());
            },
            error: function (jqxhr, textStatus, errorThrown) {
                alert(jqxhr.responseXML + ' | ' + textStatus + ' | ' + errorThrown);
            }
        });
    });
    
    $('btn_helloworld')。单击(函数(){
    var soapRequest=''+
    '' +
    '' +
    '' +
    '' +
    '';
    $.ajax({
    键入:“POST”,
    网址:'http://localhost/WCFtest/service.svc/soap',
    跨域:是的,
    contentType:'text/xml',
    数据类型:“xml”,
    数据:soapRequest,
    发送前:函数(xhr){
    setRequestHeader('SOAPAction','http://tempuri.org/IMathService/HelloWorld');
    },
    成功:功能(数据){
    $('#outputHelloWorld').val($(data.find('HelloWorldResponse').text());
    },
    错误:函数(jqxhr、textStatus、errorshown){
    警报(jqxhr.responseXML+'|'+textStatus+'|'+errorshown);
    }
    });
    });
    
    如果从同一来源调用该服务,则该服务工作正常


    我错过了什么吗?

    我自己花了两天时间追踪鬼魂(浏览器对CORS的各种版本的“解释”)之后,我认为结论是:这里的问题是选项请求-FF和Opera正在发送它,但我认为IE不会。此外,我认为在IIS、IIS express等默认情况下,选项是不允许使用的动词。 我在my global.asax中添加了应用程序_BeginRequest:

    void Application_BeginRequest(Object sender, EventArgs e)
    {
        HttpContext.Current.Response.AddHeader("Access-Control-Allow-Origin", "*");
    
        if (HttpContext.Current.Request.HttpMethod == "OPTIONS")
        {
            HttpContext.Current.Response.AddHeader("Access-Control-Allow-Methods", "GET, POST, OPTIONS");
            HttpContext.Current.Response.AddHeader("Access-Control-Allow-Headers", "*");
    
            HttpContext.Current.Response.End();
        }
    }
    

    因此,我设法通过FF完成了我的请求。

    你有没有让这项工作正常?没有,但如果我必须回到问题并找到解决方案,我肯定会更新我的帖子。
    void Application_BeginRequest(Object sender, EventArgs e)
    {
        HttpContext.Current.Response.AddHeader("Access-Control-Allow-Origin", "*");
    
        if (HttpContext.Current.Request.HttpMethod == "OPTIONS")
        {
            HttpContext.Current.Response.AddHeader("Access-Control-Allow-Methods", "GET, POST, OPTIONS");
            HttpContext.Current.Response.AddHeader("Access-Control-Allow-Headers", "*");
    
            HttpContext.Current.Response.End();
        }
    }