2016-04-02 14 views
5

Tôi đang gửi một tin nhắn json đơn giản tới một ứng dụng máy chủ WCF.Tại sao tôi nhận được yêu cầu xấu (mã 400) bằng HttpWebReponse?

Json nhắn:

{"Name":"Julian", "Id":123} 

Khách hàng mã phía:

public string MakeRequest(string parameters) 
{ 
     Console.WriteLine("parameters:" + parameters); 

     var request = (HttpWebRequest)WebRequest.Create(EndPoint); 
     request.Method = Method.ToString(); 
     request.ContentLength = 0; 
     request.ContentType = ContentType; 

     Console.WriteLine("request: " + request.Headers.ToString()); 

     if (PostData != null && Method == HttpVerb.POST) 
     { 
      var encoding = new UTF8Encoding(); 
      var bytes = ObjectToByteArray(PostData); 
      request.ContentLength = bytes.Length; 
      Console.WriteLine("Content length: " + request.ContentLength); 

      using (var writeStream = request.GetRequestStream()) 
      { 
       writeStream.Write(bytes, 0, bytes.Length); 
      } 
     } 

     try 
     { 
      using (var response = (HttpWebResponse)request.GetResponse()) 
      { 
       var responseValue = string.Empty; 

       if (response.StatusCode != HttpStatusCode.OK) 
       { 
        var message = String.Format("Request failed. Received HTTP {0}", response.StatusCode); 
        throw new ApplicationException(message); 
       } 

       // grab the response 
       using (var responseStream = response.GetResponseStream()) 
       { 
        if (responseStream != null) 
         using (var reader = new StreamReader(responseStream)) 
         { 
          responseValue = reader.ReadToEnd(); 
         } 
       } 

       return responseValue; 
      } 
     } 
     catch (WebException exception) 
     { 
      string responseText; 

      using (var reader = new StreamReader(exception.Response.GetResponseStream())) 
      { 
       responseText = reader.ReadToEnd(); 
       return responseText; 
      } 
     } 

private byte[] ObjectToByteArray(object obj) 
{ 
     if (obj == null) 
      return null; 
     BinaryFormatter bf = new BinaryFormatter(); 
     using (MemoryStream ms = new MemoryStream()) 
     { 
      bf.Serialize(ms, obj); 
      return ms.ToArray(); 
     } 
} 

server side code:

[WebInvoke(Method = "POST", 
       ResponseFormat = WebMessageFormat.Json, 
       RequestFormat =WebMessageFormat.Json, 
       UriTemplate = "/postdata")] 
    public Person PostData(Person data) 
    { 
     //Return new person with data inputted from json message 
     return new Person() 
     { 
      Id = data.Id, 
      Name = data.Name 
     }; 
    } 

Config tập tin Server

<?xml version="1.0"?> 
<configuration> 
    <system.serviceModel> 

    <services> 
     <service name="WcfJsonRestService.Service1" behaviorConfiguration="Metadata"> 
     <host> 
     <baseAddresses> 
      <add baseAddress="http://localhost:8732/service1"/> 
     </baseAddresses> 
     </host> 
      <endpoint address="http://localhost:8732/service1" 
        binding="webHttpBinding" 
        contract="WcfJsonRestService.IService1"/> 
     </service> 
    </services> 

    <behaviors> 
    <serviceBehaviors> 
     <behavior name="Metadata"> 
     <serviceMetadata httpGetEnabled="true" policyVersion="Policy15"/> 
     <serviceDebug includeExceptionDetailInFaults="true"/> 
     </behavior> 
    </serviceBehaviors> 

    <endpointBehaviors> 
      <behavior> 
      <webHttp /> 
      </behavior> 
     </endpointBehaviors> 
    </behaviors> 

    </system.serviceModel> 
    <startup> 
    <supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.0"/> 
    </startup> 
</configuration> 

Về mã:

  • (Khách hàng bên) Các đầu vào cho phương thức makeRequest chỉ là dữ liệu json trình bày ở trên.
  • (phía máy khách) Uri được đăng lên chỉ là "localhost: 8732/service1/postdata" (có bao gồm http: // không thể bao gồm nó ở đây vì nó được tính là liên kết và tôi chỉ có thể có hai)
  • (Server side) các mã máy chủ là một thực hiện giải pháp này tôi tìm thấy ở mã số dự án:

http://www.codeproject.com/Articles/167159/How-to-create-a-JSON-WCF-RESTful-Service-in-sec?fid=1614381&fr=1&df=90&mpp=25&prof=False&sort=Position&view=Normal&spc=Relaxed#xx0xx

Những gì tôi đã cố gắng:

  • Tôi đã sử dụng Postman để POST một tin nhắn json tới uri ở trên và đã nhận được phản hồi (hiện tại nó chỉ trả về một gói có cùng dữ liệu) nên tôi gặp khó khăn khi tìm bất kỳ vấn đề nào trong uri.
  • Tôi đã xác thực gói json bằng JSONLint.
  • Tôi đã thêm các khối try/catch khác nhau để có thêm thông tin lỗi nhưng tất cả đều bị lỗi giao thức/mã lỗi yêu cầu không hợp lệ 400.
  • Tôi cũng đã đập tan mọi thứ trong tâm trí của tôi (rẻ hơn và ít báo động hơn cho người bạn cùng phòng của mình))

Output hiện tại:

tôi nhận được một câu trả lời yêu cầu xấu từ máy chủ không có dữ liệu.

Cập nhật 1:

Tôi phải đã nhận được lệnh chuyển đổi dữ liệu sai.Trước khi tôi:

  • đối tượng Person tạo
  • đối tượng Person chuyển đổi sang json
  • qua json phương pháp makeRequest
  • (trong makeRequest) tạo WebRequest json chuyển sang mảng byte

Đầu tiên if-statement của phương thức MakeRequest() (Client side) đã được cập nhật với một đoạn mã tạo yêu cầu với json . bây giờ tôi nhận được một lỗi vi phạm giao thức khi write.Flush() thực hiện: Lỗi

Giao thức vi phạm từ:

Cập nhật mã phía máy khách (makeRequest phương pháp)

if (PostData != null && Method == HttpVerb.POST) 
    { 
     //var encoding = new UTF8Encoding(); 
     //var bytes = ObjectToByteArray(PostData); 
     //request.ContentLength = bytes.Length; 
     //Console.WriteLine("Content length: " + request.ContentLength); 

     //using (var writeStream = request.GetRequestStream()) 
     //{ 
     // writeStream.Write(bytes, 0, bytes.Length); 
     //} 


     using (var streamWriter = new StreamWriter(request.GetRequestStream())) 
     { 
      streamWriter.Write(json); 
      streamWriter.Flush(); 
      streamWriter.Close(); 
     } 

     var httpResponse = (HttpWebResponse)request.GetResponse(); 
     using (var streamReader = new StreamReader(httpResponse.GetResponseStream())) 
     { 
      var result = streamReader.ReadToEnd(); 
     } 

    } 

Cập nhật 2 cuộc gọi streamWriter.Flush() là vì tôi đã không đặt request.ContentLenth. Bây giờ tôi đã thiết lập các Content.Length để json.Length và bây giờ tôi nhận được lỗi này:

System.ArgumentException: Stream was not readable

Hình ảnh là một chút nhỏ nhưng được thông báo lỗi đọc:

"System.ArgumentException: Stream was not readable." 

Trả lời

0

Tôi nghĩ vấn đề là trong dòng đầu tiên của khối try. Tôi cố đọc phản hồi từ đối tượng yêu cầu ... ehem ... Mặc dù tôi đã cố đọc phản hồi từ đối tượng phản hồi tiếp tục giảm sát thương đã được thực hiện. Tôi đã bao gồm mã hoạt động bên dưới cùng với mã nhận xét đã gây ra sự cố. Tôi đã đánh dấu request.GetResponse() với **** cũng như phản hồi chính xác.GetResponseStream() mà bạn sẽ rất vui khi được nghe, bây giờ là miễn phí để thực hiện công việc của mình.

Hy vọng điều này sẽ giúp bạn tiết kiệm rất nhiều thời gian!

Tất cả các bộ phận liên quan của phương pháp makeRequest:

var request = (HttpWebRequest)WebRequest.Create(EndPoint); 
     request.Method = Method.ToString(); 
     request.ContentLength = 0; 
     request.ContentType = ContentType; 


     Console.WriteLine("request: " + request.Headers.ToString()); 

     if (PostData != null && Method == HttpVerb.POST) 
     { 
      Console.WriteLine("json length: " + json.Length); 
      Console.WriteLine(json); 
      request.ContentLength = json.Length; 
      var encoding = new UTF8Encoding();    

      using (var streamWriter = new StreamWriter(request.GetRequestStream())) 
      { 
       streamWriter.Write(json); 
       streamWriter.Flush(); 
       streamWriter.Close(); 
      } 
     } 

     try 
     { 
      // **** FIRST READ USING request.GetResponse() **** 
      //var httpResponse = (HttpWebResponse)request.GetResponse(); 
      //using (var streamReader = new StreamReader(httpResponse.GetResponseStream())) 
      //{ 
      // streamReader.ReadToEnd(); 
      //} 

      using (var response = (HttpWebResponse)request.GetResponse()) 
      { 
       var responseValue = string.Empty; 

       if (response.StatusCode != HttpStatusCode.OK) 
       { 
        var message = String.Format("Request failed. Received HTTP {0}", response.StatusCode); 
        throw new ApplicationException(message); 
       } 

       // grabs the response 
       using (var responseStream = response.GetResponseStream()) 
       { 
        if (responseStream != null) 
         using (var reader = new StreamReader(responseStream)) 
         { 
          // **** SECOND READ USING response.GetResponseStream() **** 
          responseValue = reader.ReadToEnd(); 
         } 
       } 
       return responseValue; 
      } 
     } 
0

Khi bạn đọc một dòng để kết thúc, bạn phải tìm kiếm nó trở lại đầu.

Bạn có thể thử này:

StreamReader sr = new StreamReader(stream); 
sr.ReadToEnd(); 
stream.Seek(0, SeekOrigin.Begin); 
sr.ReadToEnd(); // This should work now 
+0

Không khắc phục vấn đề - có một cái gì đó ngoại lệ về hoạt động tìm kiếm không được hỗ trợ bởi dòng? Tôi có một giải pháp ngay bây giờ! –

Các vấn đề liên quan