如何将SOAP标头从客户端传递到Web服务

时间:2014-12-18 16:58:50

标签: c# xml web-services wcf soap

我在C#中有一个客户端,Web Service必须收到证书头。我不知道如何将标头添加到Web服务。这是我的代码:

// Define a SOAP header by deriving from the SoapHeader base class.
// The header contains just one string value.
public class MyHeader : SoapHeader
{
    public string MyValue;
}

public partial class Service: System.Web.UI.Page
{
    MyWebService ESClient = new MyWebservice();
    private static String TAG_CERTIFICATE = "MxIFZjFCBFa...";
    protected void Page_Load(object sender, EventArgs e)
    {
        ServicePointManager.ServerCertificateValidationCallback = new RemoteCertificateValidationCallback(ValidateServerCertificate);
        CredentialCache cache = new CredentialCache();

        MyHeader header = new MyHeader();

        // Populate the values of the SOAP header.
        header.MyValue = TAG_CERTIFICATE;

        //HOW CAN I ADD THIS CERTIFICATE TO MY ESCLIENT WEB SERVICE?????

        //remSolSal is the response of the Web Service
        remSolSal response= new remSolSal();
        //remDatSol is the method of the Web Service and getRemSolEnt the parameters that I send in another function
        response = ESClient.remDatSol(getRemSolEnt());
    }

XML模型证书:

<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/" xmlns:sol="url...">
    <soapenv:Header>
        <certificate>
            JgsJSP6Ql8f........
        </certificate>

另外,我有一个Java客户端,它在C#中做了我必须做的事情。它使用这个功能来添加标题,其中paramName是&#34; certificate&#34;和paramContent是值&#34; JgsJSP6Ql8f ........&#34;:

 /**
 * This method adds a custom header to message.
 * 
 * @param paramName
 */
private static void addHeaderParam(String paramName, String paramContent) {
    try {
        List<Header> headers = new ArrayList<Header>();
        Header dummyHeader = new Header(new QName(TARGETNAMESPACE,
                paramName), paramContent, new JAXBDataBinding(String.class));
        headers.add(dummyHeader);

        // client side:
        ((BindingProvider) port).getRequestContext().put(
                Header.HEADER_LIST, headers);
    } catch (JAXBException e) {
        e.printStackTrace();
    }
}

2 个答案:

答案 0 :(得分:2)

有许多方法可以实现您的要求,这取决于您的客户端设置方式以及您希望如何维护。您使用的是服务参考吗?您想在配置或代码中管理吗?只需插入自定义标头的最简单方法是在配置中使用端点配置中的<headers>元素,如下所示: http://msdn.microsoft.com/en-us/library/ms731749(v=vs.110).aspx

我个人建议不要在您的应用中添加证书的定义,而是将其存储在服务器的密钥库中。然后,您可以在应用于客户端的行为中引用证书。您还可以使用代码提取证书,并通过引用ESClient.ClientCredentials对象执行您需要的操作。

答案 1 :(得分:1)

最后,我使用ClientMessageInspector类来修改SOAP消息:

public class ClientMessageInspector : System.ServiceModel.Dispatcher.IClientMessageInspector
{
    #region IClientMessageInspector Members

     public void AfterReceiveReply(ref System.ServiceModel.Channels.Message reply, object correlationState)
     {

     }

     public object BeforeSendRequest(ref System.ServiceModel.Channels.Message request, System.ServiceModel.IClientChannel channel)
     {
         CustomMessageHeader header = new CustomMessageHeader();

         request.Headers.Add(header);

         return null;
     }

     #endregion
 }

/// <summary>
/// Represents a custom message header.
/// </summary>
public class CustomMessageHeader : MessageHeader
{
    private const string HeaderName = "CustomHeader";
    private const string HeaderNamespace = "";

    /// <summary>
    /// Gets the name of the message header.
    /// </summary>
    /// <returns>The name of the message header.</returns>
    public override string Name
    {
        get { return HeaderName; }
    }

    /// <summary>
    /// Gets the namespace of the message header.
    /// </summary>
    /// <returns>The namespace of the message header.</returns>
    public override string Namespace
    {
        get { return HeaderNamespace; }
    }

    /// <summary>
    /// Called when the header content is serialized using the specified XML writer.
    /// </summary>
    /// <param name="writer">
    /// An <see cref="T:System.Xml.XmlDictionaryWriter" /> that is used to serialize the header contents.
    /// </param>
    /// <param name="messageVersion">
    /// The object that contains information related to the version of SOAP associated with a message and its exchange.
    /// </param>
    protected override void OnWriteHeaderContents(XmlDictionaryWriter writer, MessageVersion messageVersion)
    {
        writer.WriteElementString("certificate", "JgsJSP6Ql8f........");
    }
}