我正在开发一个谷歌应用引擎应用程序,我需要使用SOAP连接到Web服务。我正在使用pysimplesoap(使用找到的代码here修补)来解析xml,并使用客户端证书触发请求。 当我在本地环境的简单单元测试中执行此操作时,它可以正常工作,并且我从Web服务获得了适当的响应。 但是,当我从应用程序引擎中运行完全相同的代码时,我得到了这个:
File "/Users/me/Documents/workspace/blixem/model/communicate/communication_channel.py", line 60, in generate_soap_message_pysimplesoap
response = client.SendDocument('LA.XML', 'TESTCASE', 'data')
File "/Users/me/Documents/workspace/blixem/lib/pysimplesoap/client.py", line 152, in <lambda>
return lambda *args, **kwargs: self.wsdl_call(attr,*args,**kwargs)
File "/Users/me/Documents/workspace/blixem/lib/pysimplesoap/client.py", line 320, in wsdl_call
response = self.call(method, *params)
File "/Users/me/Documents/workspace/blixem/lib/pysimplesoap/client.py", line 215, in call
self.xml_response = self.send(method, self.xml_request)
File "/Users/me/Documents/workspace/blixem/lib/pysimplesoap/client.py", line 241, in send
location,"POST", body=xml, headers=headers )
File "/Applications/GoogleAppEngineLauncher.app/Contents/Resources/GoogleAppEngine-default.bundle/Contents/Resources/google_appengine/lib/httplib2/httplib2/__init__.py", line 1457, in request
self.disable_ssl_certificate_validation)
File "/Applications/GoogleAppEngineLauncher.app/Contents/Resources/GoogleAppEngine-default.bundle/Contents/Resources/google_appengine/lib/httplib2/httplib2/__init__.py", line 1143, in __init__
strict, timeout, proxy_info, ca_certs, disable_ssl_certificate_validation)
File "/Applications/GoogleAppEngineLauncher.app/Contents/Resources/GoogleAppEngine-default.bundle/Contents/Resources/google_appengine/lib/httplib2/httplib2/__init__.py", line 1092, in __init__
raise NotSupportedOnThisPlatform()
NotSupportedOnThisPlatform
我做了一些阅读,发现在urlfetch服务中还没有支持客户端证书。这仍然是这样吗?如果是这样,是否有解决方法?
答案 0 :(得分:1)
GAE目前不支持客户端证书。您可以通过HTTPS使用URLFetch服务。但是你不能使用客户端证书。您应该尝试Outbound Sockets Support feature中当前可用的trusted tester program。它可能会将您正在寻找的功能列入白名单。我问a similar question for GAE/J before。
如果您确实需要它,请使用出站套接字功能或在EC2中运行代理。
答案 1 :(得分:0)
现在GAE支持Python SSL - 请参阅https://cloud.google.com/appengine/docs/standard/python/sockets/ssl_support
所以现在可以使用客户端证书了。从那个网页:
# Example of a dynamic key and cert.
datastore_record_k = ndb.Key('Employee', 'asalieri', 'Address', 1)
datastore_record = datastore_record_k.get()
key_str = datastore_record.key_str
cert_str = datastore_record.cert
ssl_server = ssl.wrap_socket(server_sock,
server_side=False,
keyfile=StringIO.StringIO(key_str),
certfile=StringIO.StringIO(cert_str),
cert_reqs=ssl.CERT_REQUIRED,
ssl_version=ssl.PROTOCOL_SSLv23,
ca_certs=CERTIFICATE_FILE)
答案 2 :(得分:0)
要在BooTooMany's answer上进行扩展,只要底层代码正在使用requests
library,现在就可以使用出色的sockets来实现。请按照以下步骤使用它:
requests
安装到您的lib/
目录中。我目前正在使用v2.21.0。确保{strong>不猴子补丁requests
以使用requests-toolbelt
提供的AppEngine适配器,尽管the docs建议这样做。这使得requests
使用urlfetch
而不是套接字,套接字可用于免费应用程序,但当前不支持客户端证书。app.yaml
中,启用SSL库:libraries:
- name: ssl
version: latest
app.yaml
中,为开发服务器启用套接字:env_variables:
GAE_USE_SOCKETS_HTTPLIB: 'yes'
现在您可以使用客户端证书提出请求了:
import requests
def make_request(url):
cert = ('cert_file.pem', 'key_file.pem')
server_cert_file = 'server_cert_file.pem'
return requests.get(url=url, cert=cert, verify=server_cert_file)