此Web API未启用CORS;我怎么用呢?

时间:2014-08-14 18:42:58

标签: ajax xml web-services jsonp cors

我想从我正在制作的网络应用程序向ChemSpider Web Api发出Ajax请求 - 例如,使用GetCompoundInfo搜索功能。

此API以XML格式返回其数据。例如,搜索吡啶:

GetCompoundInfo?CSID=1020&token=redacted-security-token

结果

<?xml version="1.0" encoding="utf-8"?>
<CompoundInfo xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns="http://www.chemspider.com/">
  <CSID>1020</CSID>
  <InChI>InChI=1S/C5H5N/c1-2-4-6-5-3-1/h1-5H</InChI>
  <InChIKey>JUJWROOIHBZHMG-UHFFFAOYSA-N</InChIKey>
  <SMILES>C1=CC=NC=C1</SMILES>
</CompoundInfo>

看起来很简单。这是我的Ajax请求:

$.ajax({
  crossDomain: true,
  type: 'GET',
  url: "http://www.chemspider.com/Search.asmx/GetCompoundInfo",
  data: {
    "CSID": 1020,
    "token": "redacted-security-token",
  },
  success: function(xmlstring, st, x) {
    success_stuff(xmlstring);
  },
  failure: function(xmlstring, st, x) {
    failure_stuff(xmlstring);
  }
});

但是,服务器似乎没有启用跨源资源共享。

Cross-Origin Request Blocked: The Same Origin Policy disallows reading the remote resource at http://www.chemspider.com/Search.asmx/CompoundInfo?CSID=1020&token=redacted-security-token. This can be fixed by moving the resource to the same domain or enabling CORS.

我无法使用JSONP,因为数据是以XML格式返回的,而不是JSON格式。并且设置crossDomain = true似乎无法正常工作。

如何向此Web API发出简单的GET请求?

1 个答案:

答案 0 :(得分:1)

首先,与ChemSpider开发团队取得联系。询问他们是否打开了针对CORS请求的API。他们可能很乐意提供帮助。

如果这不是一个选项,您需要设置一个代理,直接将调用作为GET请求而不是ajax请求。然后让你的ajax请求命中代理而不是API的域。

如果你是一个python程序员,uwsgi&amp; urllib让这很简单。将以下代码保存为 ajaxproxy.py

请注意以下代码仅用于演示其工作原理,并未解决安全问题。它有效地运行开放代理。除非您希望在托管此服务器的服务器名称中完成各种有趣的业务,否则不要将其原样用于生产。

"""
Run with:
    uwsgi --http :9090 --wsgi-file ajaxproxy.py
"""
import urllib2

def application(env, start_response):
    # Get the resource url from the proxy's url & query string.
    resource_base_url = env['PATH_INFO'].split('/getresource/')[-1]
    if resource_query == '':
        resource_url = resource_base_url
    else:
        resource_url = '{}?{}'.format(resource_base_url, resource_query)

    # Get the resource.
    print('Getting resource: {}'.format(resource_url))
    resource_response = urllib2.urlopen(resource_url)
    resource_content = resource_response.read()

    # Return the resource to the requester.
    start_response('200 OK', [('Content-Type','text/html'), ('Access-Control-Allow-Origin', '*')])
    return [resource_content]

可以使用

轻松安装uwsgi
pip install wsgi

你的ajax请求中所有改变的都是url:

$.ajax({
   url: 'http://127.0.0.1:9090/getresource/http://www.chemspider.com/Search.asmx/GetCompoundInfo',
...
});

当然除了开发之外还有其他任何东西。测试您需要在公共服务器上运行代理并将127.0.0.1更改为其地址。