Why doesn't setting document.domain work to al

2019-02-10 01:32发布

问题:

I have two files, domain.com/test2.php:

<div id="testDiv"></div>

<script src="http://domain.com/packages/jquery.js"></script>
<script>$("#testDiv").load("http://domain.com/test3.php", {var1:1, var2:2});</script>

and domain.com/test3.php:

<b>var1: <?php echo $var1; ?> , var2: <?php echo $var2; ?></b>

In this case domain.com/test2.php outputs var1: 1 , var2: 2 as one would expect, but let's now say I want to make a test2.php in a subdomain. To stop problems with cross-domain scripting, I would add this extra line to the start of sub.domain.com/test2.php:

<script>document.domain = "domain.com";</script>

This extra line stops the cross-domain error from showing up, but now the file no longer outputs var1: 1 , var2: 2. Why is this and how can I fix this?

回答1:

The document.domain mechanism is intended for allowing client-side communication between frames, rather than client-to-server communication. If you have one frame containing a page from example.com and another frame containing a page from foo.example.com then the two cannot access each other's DOM unless the latter sets document.domain to example.com as you showed in your example.

The modern preferred mechanism for cross-domain AJAX requests is Cross-Origin Resource Sharing, or "CORS". This mechanism involves having the target resource return a special HTTP response header that indicates that cross-domain requests are allowed. In your scenario you'd make your test3.php return the following HTTP response header:

Access-Control-Allow-Origin: sub.domain.com

In PHP you'd do this as follows:

header("Access-Control-Allow-Origin: sub.domain.com");

You can also set this header value to just * in order to allow cross-domain requests from any origin, but be aware that this will allow requests from sites you don't control.

Requests from client-side JavaScript libraries often also include the additional header X-Requested-With that is not in the standard set allowed by CORS, so it may be necessary to explicitly allow this header via an additional response header:

Access-Control-Allow-Headers: X-Requested-With

CORS is only supported in modern browsers. For older browsers the common convention is to use JSON-P, which is a trick exploiting the fact that a page on one server is able to load and execute a script file from another server. This technique requires that the target resource be a valid JavaScript program that calls a function in the page, so it's not as elegant and seamless as CORS but it should work in any browser that supports JavaScript.