简体   繁体   English

使用XML将HTTP POST请求发送到Web服务并在Windows 8手机的C#中读取响应数据

[英]Sending HTTP POST Request with XML to a web service and reading response data in C# for windows 8 phone

I a newbie at windows 8 phone development. 我是Windows 8手机开发的新手。 I want to send an aync HTTP POST Request to a PHP web service with some headers and XML in the request body. 我想将aync HTTP POST请求发送到在请求正文中带有一些标头和XML的PHP​​ Web服务。

Also, I want to read the response sent back by the PHP web service. 另外,我想阅读PHP Web服务发送回的响应。

Please guide me, how can I achieve the above two stated things. 请指导我,如何实现上述两个目标。


what I have tried until now i am giving below 到目前为止,我一直在尝试以下

// Main begins program execution.
    public static void SendRequest()
    {

        HttpWebRequest webRequest = (HttpWebRequest)HttpWebRequest.CreateHttp("http://mytestserver.com/Test.php");
        webRequest.Method = "POST";
        webRequest.ContentType = "text/xml";
        webRequest.Headers["SOURCE"] = "WinApp";

        var response = await httpRequest(webRequest);           

    }

    public static async Task<string> httpRequest(HttpWebRequest request)
    {
        string received;

        using (var response = (HttpWebResponse)(await Task<WebResponse>.Factory.FromAsync(request.BeginGetResponse, request.EndGetResponse, null)))
        {
            using (var responseStream = response.GetResponseStream())
            {
                using (var sr = new StreamReader(responseStream))
                {

                    received = await sr.ReadToEndAsync();

                    MessageBox.Show(received.ToString());
                }
            }
        }
        return received;
    }

I am able to send the request using the above code. 我可以使用上面的代码发送请求。 I just need to know that how I can send the XML in the request body to my web service. 我只需要知道如何将请求正文中的XML发送到Web服务即可。

For Set a file, and receive a server Response, I use that for sending .csv files: 对于“设置文件,并接收服务器响应”,我将其用于发送.csv文件:

First I initialize a POST Request: 首先,我初始化一个POST请求:

/// <summary>
///     Initialize the POST HTTP request.
/// </summary>
public void SentPostReport()
{
    string url = "http://MyUrlPerso.com/";
    Uri uri = new Uri(url);
    // Create a boundary for HTTP request.
    Boundary = "----------------------------" + DateTime.Now.Ticks.ToString("x");

    HttpWebRequest request = (HttpWebRequest)WebRequest.Create(uri);
    request.ContentType = "multipart/form-data; boundary=" + Boundary;
    request.Method = "POST";
    request.BeginGetRequestStream(new AsyncCallback(GetRequestStreamCallback), est);
        allDone.WaitOne();
}

After initialized Request, I send the differents parts of my files (headers + content + footer). 初始化请求后,我发送文件的不同部分(标题+内容+页脚)。

/// <summary>
///     Send a File with initialized request.
/// </summary>
private void GetRequestStreamCallback(IAsyncResult asynchronousResult)
{
    string contentType = "binary";
    string myFileContent = "one;two;three;four;five;"; // CSV content.
    HttpWebRequest request = (HttpWebRequest)asynchronousResult.AsyncState;
    Stream memStream = request.EndGetRequestStream(asynchronousResult);
    byte[] boundarybytes = System.Text.Encoding.UTF8.GetBytes("\r\n--" + Boundary + "\r\n");

    memStream.Write(boundarybytes, 0, boundarybytes.Length);

    // Send headers.
    string headerTemplate = "Content-Disposition: form-data; ";
    headerTemplate += "name=\"{0}\"; filename=\"{1}\"\r\nContent-Type: " + contentType + "\r\n\r\n";
    string fileName = "MyFileName.csv";
    string header = string.Format(headerTemplate, "file", fileName);
    byte[] headerbytes = System.Text.Encoding.UTF8.GetBytes(header);
    memStream.Write(headerbytes, 0, headerbytes.Length);

    byte[] contentbytes = System.Text.Encoding.UTF8.GetBytes(myFileContent);

    // send the content of the file.
    memStream.Write(contentbytes, 0, contentbytes.Length);

    // Send last boudary of the file ( the footer) for specify post request is finish.
    byte[] boundarybytesend = System.Text.Encoding.UTF8.GetBytes("\r\n--" + Boundary + "--\r\n");
    memStream.Write(boundarybytesend, 0, boundarybytesend.Length);
    memStream.Flush();
    memStream.Close();

    allDone.Set();
    // Start the asynchronous operation to get the response
    request.BeginGetResponse(new AsyncCallback(GetResponseCallback), request);
}

And, Finnaly, I get The response server response, indicate the file is transmetted. 而且,Finnaly,我得到了响应服务器响应,指示文件已转换。

/// <summary>
///     Get the Response server.
/// </summary>
private static void GetResponseCallback(IAsyncResult asynchronousResult)
{
    HttpWebRequest request = (HttpWebRequest)asynchronousResult.AsyncState;

    try
    {
        HttpWebResponse response = (HttpWebResponse)request.EndGetResponse(asynchronousResult);
        Stream streamResponse = response.GetResponseStream();
        StreamReader streamRead = new StreamReader(streamResponse);

        string responseString = streamRead.ReadToEnd(); // this is a response server.

        // Close the stream object
        streamResponse.Close();
        streamRead.Close();

        // Release the HttpWebResponse
        response.Close();
    }
        catch (Exception ex)
        {
            // error.
        }
    }

This sample works on Windows Phone 7 and Windows Phone 8. This is for send a .csv content. 此示例在Windows Phone 7和Windows Phone 8上运行。这是用于发送.csv内容的。 You can adapt this code for send Xml content. 您可以修改此代码以发送Xml内容。 Replace just 仅替换

string myFileContent = "one;two;three;four;five;"; // CSV content.
string fileName = "MyFileName.csv";

by your XML 通过您的XML

string myFileContent = "<xml><xmlnode></xmlnode></xml>"; // XML content.
string fileName = "MyFileName.xml";

If all you're looking to do is take XML you've already generated and add it to your existing request as content, you'll need to be able to write to the request stream. 如果您要做的只是获取已经生成的XML并将其作为内容添加到现有请求中,那么您将需要能够写入请求流。 I don't particularly care for the stock model of getting the request stream, so I'd recommend the following extension to make your life a little easier: 我并不特别在意获取请求流的股票模型,因此,我建议使用以下扩展名,使您的生活更轻松一些:

public static class Extensions
{
    public static System.Threading.Tasks.Task<System.IO.Stream> GetRequestStreamAsync(this System.Net.HttpWebRequest wr)
    {
        if (wr.ContentLength < 0)
        {
            throw new InvalidOperationException("The ContentLength property of the HttpWebRequest must first be set to the length of the content to be written to the stream.");
        }

        var tcs = new System.Threading.Tasks.TaskCompletionSource<System.IO.Stream>();

        wr.BeginGetRequestStream((result) =>
        {
            var source = (System.Net.HttpWebRequest)result.AsyncState;

            tcs.TrySetResult(source.EndGetRequestStream(result));

        }, wr);

        return tcs.Task;
    }
}

From here, augment your SendRequest method: 在这里,增加您的SendRequest方法:

public static void SendRequest(string myXml)
{
    HttpWebRequest webRequest = (HttpWebRequest)HttpWebRequest.CreateHttp("http://mytestserver.com/Test.php");
    webRequest.Method = "POST";
    webRequest.Headers["SOURCE"] = "WinApp";

    // Might not hurt to specify encoding here
    webRequest.ContentType = "text/xml; charset=utf-8";

    // ContentLength must be set before a stream may be acquired
    byte[] content = System.Text.Encoding.UTF8.GetBytes(myXml);
    webRequest.ContentLength = content.Length;

    var reqStream = await webRequest.GetRequestStreamAsync();
    reqStream.Write(content, 0, content.Length);

    var response = await httpRequest(webRequest);
}

If the service you're trying to reach is a SOAP service, you could simplify this a bit more by having the IDE generate a client class for you. 如果您要访问的服务是SOAP服务,则可以通过让IDE为您生成客户端类来进一步简化此服务。 For more information on how to do that, check out this MSDN article . 有关如何执行操作的更多信息,请参见MSDN文章 However, if the service does not have a Web Service Definition Language (WSDL) document, this approach will not be able to assist you. 但是,如果该服务没有Web服务定义语言(WSDL)文档,则该方法将无法为您提供帮助。

You can use the HTTP Client libraries in Windows Phone 8 and use the client in the same way that Windows 8. 您可以使用Windows Phone 8中的HTTP客户端库,并以与Windows 8相同的方式使用客户端。

First, get the HTTP Client Libraries from Nuget. 首先,从Nuget获取HTTP客户端库 And now, to perform a POST call 现在,执行POST呼叫

HttpClient client = new HttpClient();
HttpContent httpContent = new StringContent("my content: xml, json or whatever");
httpContent.Headers.Add("name", "value");

HttpResponseMessage response = await client.PostAsync("uri", httpContent);
if (response.IsSuccessStatusCode)
{
    // DO SOMETHING
}

i hope this helps you :) 我希望这可以帮助你 :)

I have solved the problem in some other way.. 我已经以其他方式解决了这个问题。

    class HTTPReqRes
    {
    private static HttpWebRequest webRequest;

    public static void SendRequest()
    {
        webRequest = (HttpWebRequest)HttpWebRequest.CreateHttp("https://www.mydomain.com");
        webRequest.Method = "PUT";
        webRequest.ContentType = "text/xml; charset=utf-8";
        webRequest.Headers["Header1"] = "Header1Value";



        String myXml = "<Roottag><info>test</info></Roottag>";

        // Convert the string into a byte array. 
        byte[] byteArray = Encoding.UTF8.GetBytes(myXml);

        webRequest.ContentLength = byteArray.Length;

        // start the asynchronous operation
        webRequest.BeginGetRequestStream(new AsyncCallback(GetRequestStreamCallback), webRequest);                  
        //webRequest.BeginGetResponse(new AsyncCallback(GetResponseCallback), webRequest);
    }

    private static void GetRequestStreamCallback(IAsyncResult asynchronousResult)
    {
        HttpWebRequest request = (HttpWebRequest)asynchronousResult.AsyncState;

        // End the operation
        Stream postStream = request.EndGetRequestStream(asynchronousResult);

        String myXml = <Roottag><info>test</info></Roottag>";

        // Convert the string into a byte array. 
        byte[] byteArray = Encoding.UTF8.GetBytes(myXml);

        // Write to the request stream.
        postStream.Write(byteArray, 0, byteArray.Length);
        postStream.Close();

        // Start the asynchronous operation to get the response
        request.BeginGetResponse(new AsyncCallback(GetResponseCallback), request);
    }

    private static void GetResponseCallback(IAsyncResult asynchronousResult)
    {
        HttpWebRequest request = (HttpWebRequest)asynchronousResult.AsyncState;

        // End the operation
        HttpWebResponse response = (HttpWebResponse)request.EndGetResponse(asynchronousResult);
        Stream streamResponse = response.GetResponseStream();
        StreamReader streamRead = new StreamReader(streamResponse);
        string responseString = streamRead.ReadToEnd();
        System.Diagnostics.Debug.WriteLine(responseString);
        // Close the stream object
        streamResponse.Close();
        streamRead.Close();

        // Release the HttpWebResponse
        response.Close();
    }
}

This perfectly solves my problem, send an XML within the HTTP Request and in Response receive the XML from the web service. 这可以完美解决我的问题,在HTTP请求中发送XML,并在响应中从Web服务接收XML。

I recommend using the RestSharp library. 我建议使用RestSharp库。 You can find a sample request here . 您可以在此处找到示例请求。

This is what I used. 这就是我用的。 It's really simple, add WindowsPhonePostClient.dll to your References (if you can't, try unblock the file first by properties->unblock), then use this code: 确实很简单,将WindowsPhonePostClient.dll添加到您的引用中(如果不能,请首先尝试通过properties-> unblock取消阻止文件),然后使用以下代码:

private void Post(string YourUsername, string Password)
{
        Dictionary<string, object> parameters = new Dictionary<string, object>();
        parameters.Add("User", YourUsername);
        parameters.Add("Password", Password);
        PostClient proxy = new PostClient(parameters);
        proxy.DownloadStringCompleted += proxy_UploadDownloadStringCompleted;

        proxy.DownloadStringAsync(new Uri("http://mytestserver.com/Test.php",UriKind.Absolute));

} 


private void proxy_UploadDownloadStringCompleted(object sender,WindowsPhonePostClient.DownloadStringCompletedEventArgs e)
{
    if (e.Error == null)
        MessageBox.Show(e.Result.ToString());
}     

您需要创建对Web服务wsdl的引用,也可以尝试按此处详细说明手动进行操作: https : //stackoverflow.com/a/1609427/2638872

//The below code worked for me. I receive xml response back. 
private void SendDataUsingHttps()
{                   
     WebRequest req = null;       
     WebResponse rsp = null;
     string fileName = @"C:\Test\WPC\InvoiceXMLs\123File.xml";                  string uri = "https://service.XYZ.com/service/transaction/cxml.asp";
            try
            {
                if ((!string.IsNullOrEmpty(uri)) && (!string.IsNullOrEmpty(fileName)))
                {
                    req = WebRequest.Create(uri);
                    //req.Proxy = WebProxy.GetDefaultProxy(); // Enable if using proxy
                    req.Method = "POST";        // Post method
                    req.ContentType = "text/xml";     // content type
                    // Wrap the request stream with a text-based writer                  
                    StreamWriter writer = new StreamWriter(req.GetRequestStream());
                    // Write the XML text into the stream
                    StreamReader reader = new StreamReader(file);
                    string ret = reader.ReadToEnd();
                    reader.Close();
                    writer.WriteLine(ret);
                    writer.Close();
                    // Send the data to the webserver
                    rsp = req.GetResponse();
                    HttpWebResponse hwrsp = (HttpWebResponse)rsp;
                    Stream streamResponse = hwrsp.GetResponseStream();
                    StreamReader streamRead = new StreamReader(streamResponse);
                    string responseString = streamRead.ReadToEnd();                    
                    rsp.Close();
                }
            }
            catch (WebException webEx) { }
            catch (Exception ex) { }
            finally
            {
                if (req != null) req.GetRequestStream().Close();
                if (rsp != null) rsp.GetResponseStream().Close();
            }

}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM