为什么我会收到阻止的跨源请求:同源策略不允许读取远程资源

时间:2014-12-01 16:40:47

标签: javascript jquery ajax webforms form-submit

好的,所以我正在使用API​​,目前我使用的是geonames api。我的问题是它工作正常,直到......

让我解释一下,当我这样编写代码时

$(document).ready(function() {


        Date.prototype.dateToString = function() {
               var yyyy = this.getFullYear().toString();
               var mm = (this.getMonth()+1).toString(); // getMonth() is zero-based
               var dd  = this.getDate().toString();
               return yyyy + '-' + (mm[1]?mm:"0"+mm[0]) + '-' + (dd[1]?dd:"0"+dd[0]); // padding
        };

        var d = new Date();
        var date = d.dateToString();


        $.ajax({
            dataType: "json",
            url: url
        }).then(function(data){

            var latitude = data.geonames[0].lat;
            var longitude = data.geonames[0].lng;

            var north = parseFloat(latitude) + 1;
            var south = parseFloat(latitude) - 1;
            var east = parseFloat(longitude) + 1;
            var west = parseFloat(longitude) - 1;

            var uri = encodeURI("http://api.geonames.org/earthquakesJSON?north=" + north + "&south=" + south + "&east=" + east + "&west=" + west + "&date=" + date +"&username=demo"); 

            $.ajax({
                dataType: "json",
                url: uri
            }).then(function(eData){

                var myLatlng = new google.maps.LatLng(parseFloat(data.geonames[0].lat), parseFloat(data.geonames[0].lng));

                function initialize() {

                    var mapProp = {
                        center : myLatlng,
                        minzoom: 1,
                        maxzoom: 20,
                        zoom : 7,
                        mapTypeId : google.maps.MapTypeId.ROADMAP
                    };

                    var map = new google.maps.Map(document.getElementById("googleMap"),
                        mapProp);

                    var marker = new google.maps.Marker({
                        position: myLatlng,
                        map: map,
                        title: 'Search Location\nLatitude: ' + data.geonames[0].lat + '\nLongitude: ' + data.geonames[0].lng  
                    }); 

                    for(item = 0; item < eData.earthquakes.length; item++){

                        if (eData.earthquakes.length > 0){
                            var eLat = eData.earthquakes[item].lat, eLng = eData.earthquakes[item].lng;
                        } else {
                            var eLat = '', eLng = '';
                        }
                        new google.maps.Marker({
                            position: new google.maps.LatLng(eLat,eLng),
                            map: map,
                            title: 'Date and Time: '+eData.earthquakes[item].datetime+'\nMagnitude: '+eData.earthquakes[item].magnitude+'\nDepth: '+eData.earthquakes[item].depth+'\nLat: '+eData.earthquakes[item].lat+'\nLong: '+eData.earthquakes[item].lng 
                        });
                    }
                }
                initialize();

                });
            });
        });

它会正常工作,当页面出现时会加载,但是如果我将它包装在这样的函数中

 function getSearch(url){
    $(document).ready(function() {


        Date.prototype.dateToString = function() {
               var yyyy = this.getFullYear().toString();
               var mm = (this.getMonth()+1).toString(); // getMonth() is zero-based
               var dd  = this.getDate().toString();
               return yyyy + '-' + (mm[1]?mm:"0"+mm[0]) + '-' + (dd[1]?dd:"0"+dd[0]); // padding
        };

        var d = new Date();
        var date = d.dateToString();


        $.ajax({
            dataType: "json",
            url: url
        }).then(function(data){

            var latitude = data.geonames[0].lat;
            var longitude = data.geonames[0].lng;

            var north = parseFloat(latitude) + 1;
            var south = parseFloat(latitude) - 1;
            var east = parseFloat(longitude) + 1;
            var west = parseFloat(longitude) - 1;

            var uri = encodeURI("http://api.geonames.org/earthquakesJSON?north=" + north + "&south=" + south + "&east=" + east + "&west=" + west + "&date=" + date +"&username=demo"); 

            $.ajax({
                dataType: "json",
                url: uri
            }).then(function(eData){

                var myLatlng = new google.maps.LatLng(parseFloat(data.geonames[0].lat), parseFloat(data.geonames[0].lng));

                function initialize() {

                    var mapProp = {
                        center : myLatlng,
                        minzoom: 1,
                        maxzoom: 20,
                        zoom : 7,
                        mapTypeId : google.maps.MapTypeId.ROADMAP
                    };

                    var map = new google.maps.Map(document.getElementById("googleMap"),
                        mapProp);

                    var marker = new google.maps.Marker({
                        position: myLatlng,
                        map: map,
                        title: 'Search Location\nLatitude: ' + data.geonames[0].lat + '\nLongitude: ' + data.geonames[0].lng  
                    }); 

                    for(item = 0; item < eData.earthquakes.length; item++){

                        if (eData.earthquakes.length > 0){
                            var eLat = eData.earthquakes[item].lat, eLng = eData.earthquakes[item].lng;
                        } else {
                            var eLat = '', eLng = '';
                        }
                        new google.maps.Marker({
                            position: new google.maps.LatLng(eLat,eLng),
                            map: map,
                            title: 'Date and Time: '+eData.earthquakes[item].datetime+'\nMagnitude: '+eData.earthquakes[item].magnitude+'\nDepth: '+eData.earthquakes[item].depth+'\nLat: '+eData.earthquakes[item].lat+'\nLong: '+eData.earthquakes[item].lng 
                        });
                    }
                }
                initialize();

                });
            });
        });
}

我收到此错误....

Cross-Origin Request Blocked: The Same Origin Policy disallows reading the remote 
resource at http://api.geonames.org/searchJSON?q=Fukushima&maxRows=10&username=demo. 
This can be fixed by moving the resource to the same domain or enabling CORS.

我没有做足够的服务器端或使用API​​来确切地知道这意味着什么,或者为什么它唯一发生的时间是我试图从表单中调用此方法。

EDIT :::

在键入此内容时,我意识到这不是函数中的包装,而是在提交表单时更改URL因此在错误中提及域名时,我应该放慢速度读得好一点。但是因为我在javascript和ajax中这样做我想知道,因为我知道表单处理可以在不调用服务器的情况下完成,我将如何去做。

我理解,如果没有人给出直接答案,我实际上更喜欢没有人这样做,而是指向我使用javascript和ajax进行客户端表单处理的文档方向,并简要说明或使用它的历史。

谢谢大家!

1 个答案:

答案 0 :(得分:1)

CORS(跨域资源共享)规定从浏览器触发的AJAX请求只能联系其同一主机。这意味着在disney.com上运行的JavaScript只能向其他disney.com端点发出AJAX请求。

您的问题是您向api.geonames.org发送请求,即使您可能在自己的主机上运行,​​而不是在api.geonames.org网站上运行。

服务器可以启用CORS,这意味着它们将接受来自其他域的请求。但是,每个服务器都不同,大多数API仍然不允许跨源请求。看起来api.geonames.org就是其中之一,不支持CORS。

请注意,CORS仅适用于从浏览器发送的请求。从后端服务器(如Node或Rails)访问该API将正常工作。