[英]bad request when using python with suds for sharepoint
我正在使用Suds通过soap访问Sharepoint列表,但我在使用格式错误的肥皂时遇到了一些麻烦。
我使用以下代码:
from suds.client import Client
from suds.sax.element import Element
from suds.sax.attribute import Attribute
from suds.transport.https import WindowsHttpAuthenticated
import logging
logging.basicConfig(level=logging.INFO)
logging.getLogger('suds.client').setLevel(logging.DEBUG)
ntlm = WindowsHttpAuthenticated(username='somedomain\\username', password='password')
url = "http://somedomain/sites/somesite/someothersite/somethirdsite/_vti_bin/Lists.asmx?WSDL"
client = Client(url, transport=ntlm)
result = client.service.GetListCollection()
print repr(result)
每次我运行它,我得到结果Error 400 Bad request。 当我启用调试时,我可以看到生成的信封:
<SOAP-ENV:Envelope xmlns:ns0="http://schemas.xmlsoap.org/soap/envelope/" xmlns:ns1="http://schemas.microsoft.com/sharepoint/soap/" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/">
<SOAP-ENV:Header/>
<ns0:Body>
<ns1:GetListCollection/>
</ns0:Body>
</SOAP-ENV:Envelope>
...出现此错误消息:
DEBUG:suds.client:http failed:
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01//EN""http://www.w3.org/TR/html4/strict.dtd">
<HTML><HEAD><TITLE>Bad Request</TITLE>
<META HTTP-EQUIV="Content-Type" Content="text/html; charset=us-ascii"></HEAD>
<BODY><h2>Bad Request</h2>
<hr><p>HTTP Error 400. The request is badly formed.</p>
</BODY></HTML>
通过SoapUI运行相同的WSDL(以及原始包络数据),请求将按预期返回值。 任何人都可以看到任何明显的原因,为什么我得到不同的结果与Suds作为SoapUI以及我如何纠正这个?
更新:在不同的Sharepoint站点上测试完全相同的代码(即不是名称中有空格的子子站点)和Java(JAX-WS,但同样的站点也存在问题,但是,不同的问题)看起来好像它按预期工作。 结果我想知道这两个问题中的一个是否可能是造成这些问题的原因:
我仍然需要将原始URL与这些问题一起使用,因此任何输入都将受到高度赞赏。 我假设因为SoapUI使用原始URL,所以应该可以纠正任何错误。
我认为我缩小了问题范围,它特定于suds(可能还有其他SOAP实现)。 你的要点:
那就是现场。 打开suds的调试日志记录使我能够获取端点,信封和标题。 使用cURL模仿完全相同的调用会返回一个有效的响应,但suds会抛出错误的请求。
问题是suds接受你的WSDL(url参数)并解析它,但它不包括URL编码的字符串。 这导致调试消息如下:
DEBUG:suds.transport.http:opening (https://sub.site.com/sites/Site Collection with Spaces/_vti_bin/UserGroup.asmx?WSDL)
<snip>
TransportError: HTTP Error 400: Bad Request
通过fiddler代理管理此请求表明它正在运行针对URL https://sub.site.com/sites/Site
的请求,因为它解析了WSDL。 问题是您没有将location参数传递给suds.client.Client。 以下代码每次都给我有效的回复:
from ntlm3 import ntlm
from suds.client import Client
from suds.transport.https import WindowsHttpAuthenticated
# URL without ?WSDL
url = 'https://sub.site.com/sites/Site%20Collection%20with%20Spaces/_vti_bin/Lists.asmx'
# Create NTLM transport handler
transport = WindowsHttpAuthenticated(username='foo',
password='bar')
# We use FBA, so this forces it to challenge us with
# a 401 so WindowsHttpAuthenticated can take over.
msg = ("%s\\%s" % ('DOM', 'foo'))
auth = 'NTLM %s' % ntlm.create_NTLM_NEGOTIATE_MESSAGE(msg).decode('ascii')
# Create the client and append ?WSDL to the URL.
client = Client(url=(url + "?WSDL"),
location=url,
transport=transport)
# Add the NTLM header to force negotiation.
header = {'Authorization': auth}
client.set_options(headers=header)
一个警告:使用urllib
quote
可以工作,但是您无法对整个URL进行编码,或者无法识别URL。 你最好只用%20替换空格。
url = url.replace(' ','%20')
希望这可以防止别人撞到墙上。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.