Ian Herbert
Ian Herbert

Reputation: 1019

.NET service responds 500 internal error and "missing parameter" to HttpWebRequest POSTS but test form works fine

I am using a simple .NET service (asmx) that works fine when invoking via the test form (POST). When invoking via a HttpWebRequest object, I get a WebException "System.Net.WebException: The remote server returned an error: (500) Internal Server Error." Digging deeper, reading the WebException.Response.GetResponseStream() I get the message: "Missing parameter: serviceType." but I've clearly included this parameter.

I'm at a loss here, and its worse that I don't have access to debug the service itself.

Here is the code being used to make the request:

string postData = String.Format("serviceType={0}&SaleID={1}&Zip={2}", request.service, request.saleId, request.postalCode);
byte[] data = (new ASCIIEncoding()).GetBytes(postData);

HttpWebRequest httpWebRequest = (HttpWebRequest)WebRequest.Create(url);
httpWebRequest.Timeout = 60000;
httpWebRequest.Method = "POST";
httpWebRequest.ContentType = "application/x-www-form-urlencoded";
httpWebRequest.ContentLength =  data.Length;

using (Stream newStream = httpWebRequest.GetRequestStream())
{
    newStream.Write(data, 0, data.Length);
}

try
{
    using (response = (HttpWebResponse)httpWebRequest.GetResponse())
    {
        if (response.StatusCode != HttpStatusCode.OK)
            throw new Exception("There was an error with the shipping freight service.");

        string responseData;
        using (StreamReader responseStream = new      StreamReader(httpWebRequest.GetResponse().GetResponseStream(),    System.Text.Encoding.GetEncoding("iso-8859-1")))
        {
            responseData = responseStream.ReadToEnd();
            responseStream.Close();
        }

        if (string.IsNullOrEmpty(responseData))
            throw new Exception("There was an error with the shipping freight service.  Request went through but response is empty.");

        XmlDocument providerResponse = new XmlDocument();
        providerResponse.LoadXml(responseData);

        return providerResponse;
    }
}
catch (WebException webExp)
{
    string exMessage = webExp.Message;

    if (webExp.Response != null)
    {
        using (StreamReader responseReader = new StreamReader(webExp.Response.GetResponseStream()))
        {
            exMessage = responseReader.ReadToEnd();
        }
    }

    throw new Exception(exMessage);
}

Anyone have an idea what could be happening?

Thanks.

UPDATE

Stepping through the debugger, I see the parameters are correct. I also see the parameters are correct in fiddler.

Examining fiddler, I get 2 requests each time this code executes. The first request is a post that sends the parameters. It gets a 301 response code with a "Document Moved Object Moved This document may be found here" message. The second request is a GET to the same URL with no body. It gets a 500 server error with "Missing parameter: serviceType." message.

Upvotes: 0

Views: 2132

Answers (1)

Ichabod Clay
Ichabod Clay

Reputation: 2011

It seems like you found your problem when you looked at the requests in Fiddler. Taking an excerpt from http://www.w3.org/Protocols/rfc2616/rfc2616-sec10.html:

10.3.2 301 Moved Permanently

The requested resource has been assigned a new permanent URI and any future references to this resource SHOULD use one of the returned URIs. Clients with link editing capabilities ought to automatically re-link references to the Request-URI to one or more of the new references returned by the server, where possible.

.....

Note: When automatically redirecting a POST request after receiving a 301 status code, some existing HTTP/1.0 user agents will erroneously change it into a GET request.

Here's a couple options that you can take:

  1. Hard-code your program to use the new Url that you see in the 301 response in Fiddler
  2. Adjust your code to retrieve the 301 response, parse out the new Url from the response, and build a new response with the new Url.

The latter option would be ideal if you're dealing with user-based input on the Url (like a web browser), since you don't know where the user is going to want your program to go.

Upvotes: 0

Related Questions