1

I wrote a WCF service that returns a JSON response. I then created an html page with some JavaScript code to test the function. When I published the service to the staging environment (which uses SSL to emulate the production environtment), I had to update the web.config file of my service to work over HTTPS. All seems ok when I browse directly to the .svc endpoint (the service page displays in both http and https) and when I call the service in a browser (I am prompted to download the JSON response) however when I change my test page to point to the https version, I get an 'Access Denied' error.

Here is the code for the servicemodel section of my config file:

<system.serviceModel>


    <services>

      <service name="Services.PromotionCodeGeneration" behaviorConfiguration="md">
        <endpoint address="" binding="webHttpBinding" contract="Services.IPromotionCodeGeneration" behaviorConfiguration="webHttp" bindingConfiguration="webBindingSecure"/>
        <endpoint address="" binding="webHttpBinding" contract="Services.IPromotionCodeGeneration" behaviorConfiguration="webHttp"  bindingConfiguration="webBinding"/>
        <endpoint contract="IMetadataExchange" binding="mexHttpBinding" address="mex" />

      </service>

    </services>

    <behaviors>
      <serviceBehaviors>
        <behavior name="md">
          <serviceMetadata httpsGetEnabled="true" />
        </behavior>
      </serviceBehaviors>
      <endpointBehaviors>
        <behavior name="webHttp">
          <webHttp />
        </behavior>
      </endpointBehaviors>
    </behaviors>



    <bindings>

      <webHttpBinding>

        <binding name="webBindingSecure">

          <security mode="Transport"/>

        </binding>

        <binding name="webBinding">

          <security mode="None"></security>

        </binding>

     </webHttpBinding>



    </bindings>

  </system.serviceModel>

Here is the code from my test page:

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" >
<head>
    <title></title>
<script>
    function api_test() {

        var url = "https://test.mydomain.com/Services/PromotionCodeGeneration.svc/contest/useremail@mydomain.com";

        var client = new XMLHttpRequest();
        client.open("GET", url, false);
        client.setRequestHeader("Authentication-Key", "LK589-JIJO-SHG9-0987-65TG-HJKU-Y$GH");
        client.send();
        var responseText = client.responseText;

        var result = JSON.parse(responseText); 


        document.writeln("Id: " + result.Id + "<br/>");
        document.writeln("Code: " + result.Code + "<br/>");
        var expiryDate = "";
        if (result.Expires != null){expiryDate = result.Expires;} 
        document.writeln("Expires: " + expiryDate + "<br/>");
        document.writeln("Status: " + result.Status + "<br/>");
    }
</script>
</head>
<body onload="api_test();">

</body>
</html>

I have been researching the problem for 2 days. I find alot of people saying you can't use the 'XMLHttpRequest' method across domains but it works find for me over basic http so I find that hard to believe. I have also tried MANY different servicemodel configuration suggestions however none worked for the https communication. Does anyone see anyything in my config or calling page that is causing the 'Access Denied' response over https?

Any help would be appreciated.

John
  • 35
  • 1
  • 7
  • the mention of the multiple domains makes me think there not hosted on the same domain? is that correct? it not you might want to take a look around jsonp - http://stackoverflow.com/questions/2055186/json-and-xmlhttprequest – Mike Miller Jun 09 '11 at 22:45

1 Answers1

2

Do the HTML page and the service conform to the Same Origin Policy?

  • The domain name must be the same, including subdomains (so you couldn't, for example, load a file hosted on test1.example.com in a page on test2.example.com).

  • The protocol (e.g. http or https) must be the same.

  • The port must be the same (for example, you can't load a file at example.com:8080 from a page at example.com).

All AJAX requests need to meet this policy - otherwise, as @Mike Miller suggested, you may need to look at JSONP.

nrabinowitz
  • 55,314
  • 10
  • 149
  • 165
  • Thanks for the suggested reading - I'll take a look. The service will eventually be hosted on one of our corporate web sites (the wish was for one of our SSL domains) and be accessed by a flash application hosted on facebook. At the moment, I'm hosting the test page on my local machine and accessing the service on a stage server. It works fine over http but I get the access denied error when I try to access it over https. If it was the different domain, why does it work over http? – John Jun 10 '11 at 00:54
  • It looks like you guys were right about the cross domain issue - it must have been working from my localhost over http because I am on the same network domain as the web server even though it doesn't appear in the localhost url. Then chaning the host to https violated the Same Origin Policy. When I moved the test file to the web server, and also viewed it over https the call to the WCF service succeeded. – John Jun 10 '11 at 15:17
  • At first I thought this would be a problem for the eventual Flash client on Facebook however it turns out Adobe has come up with a policy file concept where you put an xml policy file in the service directory which allows the communication. I can't figure out how to post a link in this comment (kills the add functionality) but if you google 'adobe cross domain policy' the first result should be a link to Adobe's page describing the policy file concept and it's specifications. – John Jun 10 '11 at 15:26