2012-08-15 12 views
21

में प्रतिक्रिया के लिए प्रतिनिधिमंडल हैंडलर वर्तमान में हस्ताक्षर आदि को मान्य करने जैसी चीजों के लिए भेजे जाने से पहले अनुरोध पर काम करने के लिए कई प्रतिनिधिमंडल हैंडलर (DelegatingHandler से प्राप्त कक्षाएं) का उपयोग कर रहा हूं। यह सब बहुत अच्छा है, क्योंकि मैं नहीं करता सभी कॉलों पर हस्ताक्षर सत्यापन को डुप्लिकेट करना होगा (उदाहरण के लिए)।वेबएपी

मैं उसी वेब अनुरोध से प्रतिक्रिया पर एक ही सिद्धांत का उपयोग करना चाहता हूं। प्रतिक्रिया के लिए DelegatingHandler के समान कुछ है? विधि से वापस लौटने से पहले प्रतिक्रिया को पकड़ने का एक तरीका, एक तरह से?

अतिरिक्त जानकारी: मैं HttpClient.PutAsync(...)

उत्तर

37

का उपयोग कर एक वेब एपीआई बोल रहा हूँ हाँ। आप इसे निरंतर कार्य में कर सकते हैं।

मैं इसे here समझाता हूं।

उदाहरण के लिए, यह कोड (उपरोक्त ब्लॉग से) निशान यूआरआई का अनुरोध करता है और प्रतिक्रिया के लिए एक डमी हेडर जोड़ता है।

public class DummyHandler : DelegatingHandler 
{ 
    protected override Task<HttpResponseMessage> SendAsync(HttpRequestMessage request, CancellationToken cancellationToken) 
    { 
     // work on the request 
     Trace.WriteLine(request.RequestUri.ToString()); 

     return base.SendAsync(request, cancellationToken) 
      .ContinueWith(task => 
      { 
       // work on the response 
       var response = task.Result; 
       response.Headers.Add("X-Dummy-Header", Guid.NewGuid().ToString()); 
       return response; 
      }); 
    } 
} 
+0

आह दिखा रहा है, अब मैं ContinueWith के उपयोग के उदाहरण से समझते हैं। यह बहुत अच्छा काम करता है। धन्यवाद (और धीमी उत्तर के लिए खेद है) – Halvard

+0

आप यहां प्रतिक्रिया सामग्री को पढ़ने के बारे में कैसे जाएंगे? मैं इसे पढ़ने की कोशिश करता हूं हालांकि यह एक ऑब्जेक्ट डिस्पोजेड अपवाद फेंकता है। –

+0

@RossJones यह विचित्र है ... क्या आप एक रेपो भेज सकते हैं? – Aliostad

13

अनुरोध और प्रतिक्रिया को रोकने के लिए यहां एक उदाहरण दिया गया है। ओवरराइड विधि SendAsync का मूल अनुरोध कैप्चर करने के लिए उपयोग किया जाता है, जबकि प्रतिक्रिया को पकड़ने के लिए ResponseHandler नामक विधि का उपयोग किया जाता है।

उदाहरण मूल अनुरोध और प्रतिक्रिया

using System.Net.Http; 
using System.Threading.Tasks; 
namespace webAPI_Test 
{ 
    public class MessageInterceptor : DelegatingHandler 
    { 
     protected override System.Threading.Tasks.Task<HttpResponseMessage> SendAsync(HttpRequestMessage request, System.Threading.CancellationToken cancellationToken) 
     { 
      // CATCH THE REQUEST BEFORE SENDING TO THE ROUTING HANDLER 
      var headers = request.ToString(); 
      var body = request.Content.ReadAsStringAsync().Result; 
      var fullRequest = headers + "\n" + body; 

      // SETUP A CALLBACK FOR CATCHING THE RESPONSE - AFTER ROUTING HANDLER, AND AFTER CONTROLLER ACTIVITY 
      return base.SendAsync(request, cancellationToken).ContinueWith(
         task => 
         { 
          // GET THE COPY OF THE TASK, AND PASS TO A CUSTOM ROUTINE 
          ResponseHandler(task); 

          // RETURN THE ORIGINAL RESULT 
          var response = task.Result; 
          return response; 
         } 
      ); 
     } 

     public void ResponseHandler(Task<HttpResponseMessage> task) 
     { 
      var headers = task.Result.ToString(); 
      var body = task.Result.Content.ReadAsStringAsync().Result; 

      var fullResponse = headers + "\n" + body; 
     } 
    } 
} 

इस विधि का उपयोग करने के लिए कब्जा करने के लिए, वर्ग की पहचान की है और एक MessageHandler के रूप में पंजीकृत किया जाना चाहिए। मैं अपने Global.asax फ़ाइल में निम्नलिखित पंक्ति ...

उदाहरण जोड़ा कैसे नए MessageInterceptor वर्ग

GlobalConfiguration.Configuration.MessageHandlers.Add(new MessageInterceptor()); 

यहाँ मेरा पूरा Global.asax फ़ाइल है रजिस्टर करने के लिए। गौर करें कि MessageInterceptor संदर्भित है ...

Global.asax के पूर्ण संस्करण MessageInterceptor एकीकरण

using System.Web.Http; 
using System.Web.Mvc; 
using System.Web.Optimization; 
using System.Web.Routing; 
namespace webAPI_Test 
{ 
    // Note: For instructions on enabling IIS6 or IIS7 classic mode, 
    // visit http://go.microsoft.com/?LinkId=9394801 

    public class WebApiApplication : System.Web.HttpApplication 
    { 
     protected void Application_Start() 
     { 
      AreaRegistration.RegisterAllAreas(); 

      WebApiConfig.Register(GlobalConfiguration.Configuration); 
      FilterConfig.RegisterGlobalFilters(GlobalFilters.Filters); 
      RouteConfig.RegisterRoutes(RouteTable.Routes); 
      BundleConfig.RegisterBundles(BundleTable.Bundles); 

      GlobalConfiguration.Configuration.MessageHandlers.Add(new MessageInterceptor()); 
     } 
    } 
} 
संबंधित मुद्दे