我在设置WCF(.NET 4.0)Web服务以调用Axis2 Rampart Web服务时遇到了一些问题。 我是WCF的新手,我没有找到完全符合这种特殊情况的教程。 以下是事实:
我必须拨打的网络服务是Axis2 Ramart服务。 我需要构建的客户端使用WCF / .NET 4.0。 Webservice使用SOAP 1.1和WS-Security(Messagesecurity)。
WS-Securtity应该像这样工作:
服务器提供带有公钥的证书。 客户端生成秘密对称密钥。 客户端使用服务器公钥加密此密钥。 此加密密钥将写入Soap-header。 客户端使用密钥加密Soap请求的主体。 (事实上,我从网络服务提供商处获得的结构表明主体是使用服务器公钥加密的,但在他们提供的示例请求中,加密方法表示为aes128-cbc,它是对称密钥AFAIK)
所以这就是我必须要做的。 到目前为止我所做的是尝试从几个教程中的一些自定义绑定。 但是我发现的所有样本都使用服务器和客户端证书,我没有设法以适合我的方式调整这些绑定。
所以这是一个示例请求,显示请求的外观:
<soapenv:Envelope
xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/"
xmlns:xenc="http://www.w3.org/2001/04/xmlenc#">
<soapenv:Header>
<wsse:Security xmlns:wsse="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd" soapenv:mustUnderstand="1">
<xenc:EncryptedKey Id="EncKeyId-Cl6B57CC684EEpm8E6E61WBp3421878712">
<xenc:EncryptionMethod Algorithm="http://www.w3.org/2001/04/xmlenc#rsa-1_5" />
<ds:KeyInfo xmlns:ds="http://www.w3.org/2000/09/xmldsig#">
<wsse:SecurityTokenReference>
<wsse:KeyIdentifier EncodingType="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-soap-message-security-1.0#Base64Binary" ValueType="http://docs.oasis-open.org/wss/oasis-wss-soap-message-security-1.1#ThumbprintSHA1">D99lKi5jizWOxThG6yZXw6llwq4FdM=</wsse:KeyIdentifier>
</wsse:SecurityTokenReference>
</ds:KeyInfo>
<xenc:CipherData>
<xenc:CipherValue>Ab5i63RFNPNXcoEn6PqflaoPjsUI3E5EZh668621xkMcEDz9Jcm204A5Ecn8WQamxKX7UYEG8gPwn66X+pOj0DiWD4ShKVJIOD5gCliobcGgjVB1Uihj8Xk5MGesi8atuy9RFA=</xenc:CipherValue>
</xenc:CipherData>
</xenc:EncryptedKey>
<wsc:DerivedKeyToken xmlns:wsc="http://docs.oasis-open.org/ws-sx/ws-secureconversation/200512" xmlns:wsu="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsd" wsu:Id="derivedKeyId-1">
<wsse:SecurityTokenReference>
<wsse:Reference URI="#EncKeyId-Cl6B57CC684EEpm8E6E61WBp3421878712"
ValueType="http://docs.oasis-open.org/wss/oasis-wss-soap-message-security-1.1#EncryptedKey" />
</wsse:SecurityTokenReference>
<wsc:Offset>0</wsc:Offset>
<wsc:Length>16</wsc:Length>
<wsc:Nonce>wQ9oyLHKjKRx6Dlm04RaL5Q==</wsc:Nonce>
</wsc:DerivedKeyToken>
<xenc:ReferenceList>
<xenc:DataReference URI="#EncDataId-2" />
</xenc:ReferenceList>
</wsse:Security>
</soapenv:Header>
<soapenv:Body xmlns:wsu="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsd" wsu:Id="Id-15079889">
<xenc:EncryptedData Id="EncDataId-2" Type="http://www.w3.org/2001/04/xmlenc#Content">
<xenc:EncryptionMethod Algorithm="http://www.w3.org/2001/04/xmlenc#aes128-cbc" />
<ds:KeyInfo xmlns:ds="http://www.w3.org/2000/09/xmldsig#">
<wsse:SecurityTokenReference xmlns:wsse="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd">
<wsse:Reference URI="#derivedKeyId-1" />
</wsse:SecurityTokenReference>
</ds:KeyInfo>
<xenc:CipherData>
<xenc:CipherValue>
+Tx9+XL7QqFVZKCr5wEhyOBENlCfHm0y1y5yWwnIk2kHNoO3IFFJj2rSQdt7HiqfcU6XxAVn3eVJKmmuN+rPYISoJstl8EnStaEIqSTuUyTUrgchx5Zxor47TOknXXjo3dYhTKHqvsx8SX70GG3M+bJS/Q1CWDlWzidKWxORo8D02iVcQdu00dnw7SHWYwyzzhduQbsozyzcAER5cYnQuuUPOcBusivq/L0xDOVTFaGr9/vvPGo+yk2bN0nBLeikk0uSJr7Z/IqGL+Dqg5BA0f+8X8sxFQpRQmtSoXtvhs2bGy8v1MPkCYKPmajSR/XwMaQB2zxR6vKsGA7ODH9+ocqO+rbPOYWpRz+czogOUo5s+OYIwX9u+99NmC5zuSjvK5bwJzWWrJ0h31OM0KeTkc7rxTIm8QMR5ytBNnCtU9QXQeAMbBdwGok330rq5ZH9bN4TdBg9Qhzs8CGGpjMYZaQ9ApTt6vkGK0i9gtdXdvY1fVZpsPcU67MYvkXJARQMpwj9Z3ZDVscdiPIxvfHyBkT8Ta21mDlYRidxanr87CrLB6HyiEyhD1XKwpTZ7OpNja6UOzfGNOJx07SbgGF+ozDBaC7zs691L4iawDioXagUZSkQ9UgwaqycSh3YYa5+RYuPka1Z0z2cmdAaFnEtoZAaSftGj8k=
</xenc:CipherValue>
</xenc:CipherData>
</xenc:EncryptedData>
</soapenv:Body>
</soapenv:Envelope>
也许有人可以告诉我如何实现这一目标,或者我可以找到一些教程。
提前谢谢。
这是我在实现Custom Binding和Messsage-Encoder后得到的Resposne:
<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/">
<soapenv:Header>
<wsse:Security xmlns:wsse="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd" soapenv:mustUnderstand="1">
<wsc:DerivedKeyToken xmlns:wsc="http://docs.oasis-open.org/ws-sx/ws-secureconversation/200512" xmlns:wsu="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsd" wsu:Id="derivedKeyId-159">
<wsse:SecurityTokenReference>
<wsse:KeyIdentifier EncodingType="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-soap-message-security-1.0#Base64Binary" ValueType="http://docs.oasis-open.org/wss/oasis-wss-soap-message-security-1.1#EncryptedKeySHA1">Aef7igYIlyWYa9XrbSYSt9Lh5Q4=</wsse:KeyIdentifier>
</wsse:SecurityTokenReference>
<wsc:Offset>0</wsc:Offset>
<wsc:Length>16</wsc:Length>
<wsc:Nonce>Ub30ogcNT6p7ZkH+qXFclw==</wsc:Nonce>
</wsc:DerivedKeyToken>
<wsc:DerivedKeyToken xmlns:wsc="http://docs.oasis-open.org/ws-sx/ws-secureconversation/200512" xmlns:wsu="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsd" wsu:Id="derivedKeyId-159">
<wsse:SecurityTokenReference>
<wsse:KeyIdentifier EncodingType="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-soap-message-security-1.0#Base64Binary" ValueType="http://docs.oasis-open.org/wss/oasis-wss-soap-message-security-1.1#EncryptedKeySHA1">">Aef7igYIlyWYa9XrbSYSt9Lh5Q4=</wsse:KeyIdentifier>
</wsse:SecurityTokenReference>
<wsc:Offset>0</wsc:Offset>
<wsc:Length>16</wsc:Length>
<wsc:Nonce>Ub30ogcNT6p7ZkH+qXFclw==</wsc:Nonce>
</wsc:DerivedKeyToken>
<xenc:ReferenceList xmlns:xenc="http://www.w3.org/2001/04/xmlenc#">
<xenc:DataReference URI="#EncDataId-160"/>
</xenc:ReferenceList>
</wsse:Security>
</soapenv:Header>
<soapenv:Body xmlns:wsu="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsd" wsu:Id="Id-1046510178">
<xenc:EncryptedData xmlns:xenc="http://www.w3.org/2001/04/xmlenc#" Id="EncDataId-160" Type="http://www.w3.org/2001/04/xmlenc#Content">
<xenc:EncryptionMethod Algorithm="http://www.w3.org/2001/04/xmlenc#aes128-cbc"/>
<ds:KeyInfo xmlns:ds="http://www.w3.org/2000/09/xmldsig#">
<wsse:SecurityTokenReference xmlns:wsse="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd">
<wsse:Reference URI="#derivedKeyId-159"/>
</wsse:SecurityTokenReference>
</ds:KeyInfo>
<xenc:CipherData>
<xenc:CipherValue>zQUBHBX2nMTfL5gxXseNqqE5goAFSPQEd2D1RAsUZi+L64gqYfdQQIg//hWhw0Ed9gGFxLX8/ocq
svVX7oVTN4YkCF9LdLmY1y7/SmbDMyjKjzhxvQ5Bz2mu1EzWBtWRjAYGnMtLTJCCWEK0ZeqKGXDi
rqcHMwJYK4vGKeizAl/BMN2dLqp4gANSHB7kryGYiK4C2NncYwpbbws/It6Lm2RPuUenFW+2VCaC
OW8YdCMMfveEvO+18+BaApxS2ShckTbip9nbpDzVvGw4gFw/70xAupMkkUEGJPdBnb6ce9qC/jQm
MeBL4FSenEJbqR1qSU5xh6rD7m6Vqug5mEP7c2Tk/mPSFVlZ88TXV2S31NB+3PDAXxyZss9aftBl
L+q+m8oP/hqse9Oju8MaztP/gBQDSKuTBLWgMPvwluEZmnPnpItZX9CFOVGDaaWlnoN1Lgc6iKk/
8xDC95t87++NesK6Zqa+J15qGm4MozFBe5pS75wARrGA34USnHytNNJGyidx15wQgNrT9gxTlypQ
BU3830rWiWAsrFwzSQBC20TcNb0ofscNJqVhwmRnMHz75Gbn70jyGTM0W27PFYfq/xfJ3MCe/pov
Dqn647j2Ixvj/Rik02HJdUUm/cdmRxawWQVUvmxPbPNNOjCoccwOWxf623zXpD3DdV8U/5+jDite
eQnrpaU4griXc7jq85OIoghf++cShAK+tx5t8BjLaD1rBF3ni5Eqt2xbMoZ6cfzr314PxmffyjHM
rCzSMU4cw0BndzJrV2r0aKTEPxVRPIQur8ztEtIYCRWloceS4N2YKkdRm/W7TWBsIa+HOCpq9Rpr
bu0KLP54tBBTO5hzjIsjYn7JzfohYk5aDN/8ZsQqgsO0LhWu/9qj8j2fY+yC4W9i7m+/bLvuYSbO
Tm7B0vV5s79uG4Xi/ONM7O1NR/C1HSEddQnr0/zdDxJcJsxwAmyryILmLynaZyxeFYz5ueqQuNCZ
MTRvKdEfw2+Tt7l3lUSZ/WqPcAz2UFA7kdASk2esmQjVZjvvdLQfan7xHffU1Ga5nmafuXrCZR81
k+1OYs64oy14qFor0e3DXlyeUOPC67iEP92lBQl7hz4v9I0afSmEhmc3iR/XoYTgliP2QhkeEw11
gSGa9u6oLfQfGZVsDV6meL51kkM+FRKq8Y2QjJjSyVFUzQXmg0lAySjlTjVeYZbRCSleCSqk+tIJ
XIcsdkY9PSVxdWOiqXQcQlrae1Wj34Xf+h6NpNuIt/TSKxd896b0ACzz8ouHUvI/Wyk5Rz/Rmvzi
g/cGK9YnX8VGV2hpUzsVZLByUoWvMH+hv9ep1syQiA5EiIu+paTS92CW1i2x39pnKeMrYhI6Ug==</xenc:CipherValue>
</xenc:CipherData>
</xenc:EncryptedData>
</soapenv:Body>
</soapenv:Envelope>
这是My MessageEncoder的ReadMessage-Function(我知道这不是解析Xml的最佳方法)。它删除了两个派生键中的一个:
public override Message ReadMessage(ArraySegment<byte> buffer, BufferManager bufferManager, string contentType)
{
var msg = innerEncoder.ReadMessage(buffer, bufferManager, contentType);
var xml = msg.ToString();
var msgbuffer = msg.CreateBufferedCopy( int.MaxValue );
msg = msgbuffer.CreateMessage();
MemoryStream stream = new MemoryStream();
XmlDictionaryWriter xmlWriter = XmlDictionaryWriter.CreateBinaryWriter(stream);
msg.WriteMessage(xmlWriter);
xmlWriter.Flush();
stream.Position = 0;
XmlDictionaryReader xmlReader = XmlDictionaryReader.CreateBinaryReader(stream, XmlDictionaryReaderQuotas.Max);
XmlDocument doc = new XmlDocument();
doc.Load(xmlReader);
XmlNode security = null;
XmlNode derivdeKey = null;
foreach (XmlNode xnode in doc.DocumentElement.FirstChild.ChildNodes)
{
if (xnode.LocalName == "Security")
foreach (XmlNode node in xnode.ChildNodes)
{
security = node;
if(node.LocalName == "DerivedKeyToken")
{
}
if(derivdeKey != null)
{
XmlNode pnode = node.ParentNode;
pnode.RemoveChild( node );
}
else
{
derivdeKey = node;
}
}
}
Stream memStream = new MemoryStream();
xmlWriter = XmlDictionaryWriter.CreateBinaryWriter( memStream );
doc.WriteTo(xmlWriter);
xmlWriter.Flush();
memStream.Position = 0;
xmlReader = XmlDictionaryReader.CreateBinaryReader(memStream, XmlDictionaryReaderQuotas.Max);
Message newMessage = Message.CreateMessage(xmlReader, 10240, msg.Version);
xml = newMessage.ToString();
return newMessage;
}
我想知道Message如何显示为字符串(newMessage.ToString()),因为正文是shon是... stream ....
问题是我收到以下错误消息:
System.ServiceModel.Security.MessageSecurityException : The 'Body', 'http://schemas.xmlsoap.org/soap/envelope/' required message part was not signed.
所以我删除了这里描述的安全节点http://webservices20.blogspot.de/2012/04/when-enableunsecuredrespose-requires.html。
这是被剥夺的共鸣:
<?xml version="1.0" encoding="utf-16"?><soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/"><soapenv:Body wsu:Id="Id-1532543044" xmlns:wsu="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsd"><xenc:EncryptedData Id="EncDataId-586" Type="http://www.w3.org/2001/04/xmlenc#Content" xmlns:xenc="http://www.w3.org/2001/04/xmlenc#"><xenc:EncryptionMethod Algorithm="http://www.w3.org/2001/04/xmlenc#aes128-cbc"></xenc:EncryptionMethod><ds:KeyInfo xmlns:ds="http://www.w3.org/2000/09/xmldsig#">
<wsse:SecurityTokenReference xmlns:wsse="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd"><wsse:Reference URI="#derivedKeyId-585"></wsse:Reference></wsse:SecurityTokenReference>
</ds:KeyInfo><xenc:CipherData><xenc:CipherValue>APZ9aATpcMu5qU6PdoKeTLjAblJP/uLZAzX8imgSSfvaZGGeI8prg9JNTEOjZ1SAeuWxod/ZV4pb
3OeY3b1IWxxhG5WWGxu51WAAehGBmiyFYOzJwbpR5cOHUc7aRBm7hkeqr/1RlcYDlAk4Y+G1URgv
0K2nzqfDR3m7ydZSVoa3aSWWzmhjMTnJnPyQ060fDXiU7/k0tI12danfv+tUcBAlvfssTTEB33bH
RXTjobJDuW3lEbbQBN+KD9SUu02GvFF4Vs31pSf1YxHIzMuf3Q2njz58oY0kmDRvR6+n9IIUQVgK
5+iJOx9E5pY7xzmEf5LpbiTt2RSuxmt2+nkin+wxF94hkgW/N6TwmbbjybN2TY3IyZ2PgdzobCj9
sG9UAwAE1peDvIpiXhgXyojU7eRnAfJKE4HrxEjs9GKdgA4SG3rsM7t/JAeiThqe4GZCvrKwnTHS
OZSz8wplTEV7VfALj5TvwK8DqOP4Qsk1F6pml/IQg0YSUJGQmuxZzTiM3ABRzf21/BUj9j3mlo7R
/QFhNnEAhHTLoJIW1fhKYrhT7vk6rMLlZtP7iyE63MEp4cghvSk9OZDauUBoUAkKwv9N2TSOBe3W
N0fVIpLg+gNmu8s1Myzl9MEDpqQFvJbG2+hTjREo9cyvfJdKLjZVpWVoaaghiZrOFwUWJsIGCyuy
aW+eF1wFP6WgXixmvX/mdkEqCyU29+DAlIb5yIABgIxNk4MSJP/9+cSZ7L6EOVJc9khsMgw1aGe9
k3QbIeM7WLXcHNnWFE+PuqORg7OvvG+jqFGyfGlGaE85lbD2+0ONTmxU3MwNhg9ngZLheiIzxxty
3R2KXDMkDEQpWJ7cIi2QSvwu0XZ/Ku5hwW8fXbUgHTClpAQbwu3HqeeHv2BkhrUbPbx3pRpu6B4L
tyGO4vfp/vlnPyT0xS5O99KX6iKpDDS3zqC9j0cheJIqIvixNvrLd/KrpQJ8nc7+B/29h444y/3I
jooRtDmtNuG2T3b4QB2oec7FS+ufXUJIEgPWtE6iPMZxMqiL1z64eL0sg2xO4QXWwoGzMCZHP89y
ibhjhsKDTffz/s4cgRgzRWAQSNlLpuvzDeHjbNUnXIz3C1NnQOBV0LF5KpCuyYeIfQDbJQpyTre1
q5KMTGHq4ksG2zSpgNNouS279WmlGOmuawLW28VxRBlW92K//l16yJglEcKbqlRuxzM0gcw1BG/O
9sp25te+Ad68Vo2dyELZYstIRhSnV2j2J6UyZd1WC1rBWHiu3gDvKgeCNtgUbeHKfm0RVo9ZBVbi
vHQWAL57hOBERoXK5MkhwqlsYZzOHzkoVyxok+UspcmVy1MQccOcB6y5xbuqt6zR+iFuKyZVGQ==</xenc:CipherValue></xenc:CipherData></xenc:EncryptedData></soapenv:Body></soapenv:Envelope>
现在,服务完成且没有错误,但result-object为null。 - &GT;例如:
result = testserviceproxy.testservicefunction(); 结果为空;
答案 0 :(得分:0)
这个绑定是你用ootb wcf最接近的:
<customBinding>
<binding name="NewBinding0">
<textMessageEncoding messageVersion="Soap11" />
<security defaultAlgorithmSuite="Basic128Rsa15" authenticationMode="AnonymousForCertificate"
includeTimestamp="false" messageProtectionOrder="EncryptBeforeSign">
<secureConversationBootstrap />
</security>
<httpTransport />
</binding>
</customBinding>
它产生了一个非常相似的XML,它有一个不同的:它还增加了一个数字签名。无法直接告诉WCF不添加签名。大多数机会都不会成为您发送消息(带签名)的问题。如果这是一个问题,您可以实现一个WCF自定义消息编码器来手动删除签名元素(以及两个专门用于签名的派生密钥中的一个)。