हर WCF कॉल में एक कस्टम HTTP हेडर कैसे जोड़ें?


162

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

यदि यह एक अच्छा विचार है, तो मैं हेडर की जानकारी के लिए पहचानकर्ता को स्वचालित रूप से कैसे जोड़ सकता हूं। दूसरे शब्दों में, जब भी उपयोगकर्ता WCF विधि को कॉल करता है, तो पहचानकर्ता को हेडर में स्वचालित रूप से जोड़ा जाना चाहिए।

अद्यतन: ग्राहक जो WCF सेवा का उपयोग कर रहे हैं, वे दोनों विंडोज़ अनुप्रयोग और विंडोज मोबाइल एप्लिकेशन (कॉम्पैक्ट फ्रेमवर्क का उपयोग करके) हैं।


1
क्या आप अपनी समस्या को हल करने में सक्षम थे?
मार्क गुड

क्या आपने कॉम्पैक्ट फ्रेमवर्क पर काम करने के लिए इसे समाप्त किया है?
वेकैनो

जवाबों:


185

इसका फायदा यह है कि यह हर कॉल पर लागू होता है।

एक वर्ग बनाएं जो IClientMessageInspector को लागू करता है । इससे पहले कि वेन्डर्सप्रिडेस्ट विधि में, अपने कस्टम हेडर को आउटगोइंग मैसेज में जोड़ें। यह कुछ इस तरह लग सकता है:

    public object BeforeSendRequest(ref System.ServiceModel.Channels.Message request,  System.ServiceModel.IClientChannel channel)
{
    HttpRequestMessageProperty httpRequestMessage;
    object httpRequestMessageObject;
    if (request.Properties.TryGetValue(HttpRequestMessageProperty.Name, out httpRequestMessageObject))
    {
        httpRequestMessage = httpRequestMessageObject as HttpRequestMessageProperty;
        if (string.IsNullOrEmpty(httpRequestMessage.Headers[USER_AGENT_HTTP_HEADER]))
        {
            httpRequestMessage.Headers[USER_AGENT_HTTP_HEADER] = this.m_userAgent;
        }
    }
    else
    {
        httpRequestMessage = new HttpRequestMessageProperty();
        httpRequestMessage.Headers.Add(USER_AGENT_HTTP_HEADER, this.m_userAgent);
        request.Properties.Add(HttpRequestMessageProperty.Name, httpRequestMessage);
    }
    return null;
}

फिर एक समापन बिंदु व्यवहार बनाएँ जो क्लाइंट रनटाइम के लिए संदेश निरीक्षक को लागू करता है। आप व्यवहार एक्सटेंशन तत्व का उपयोग करके किसी विशेषता के माध्यम से या कॉन्फ़िगरेशन के माध्यम से व्यवहार को लागू कर सकते हैं।

सभी अनुरोध संदेशों में HTTP उपयोगकर्ता-एजेंट शीर्षलेख को जोड़ने का एक शानदार उदाहरण यहां दिया गया है । मैं अपने कुछ ग्राहकों में इसका उपयोग कर रहा हूं। आप IDispatchMessageInspector को लागू करके सेवा पक्ष पर भी कर सकते हैं ।

क्या यह है जो आप के मन में था?

अद्यतन: मुझे WCF सुविधाओं की यह सूची मिली है जो कॉम्पैक्ट फ्रेमवर्क द्वारा समर्थित हैं। मेरा मानना ​​है कि संदेश निरीक्षकों को 'चैनल एक्स्टेंसिबिलिटी' के रूप में वर्गीकृत किया गया है, जो इस पोस्ट के अनुसार, कॉम्पैक्ट फ्रेमवर्क द्वारा समर्थित हैं


2
@ मर्क, यह एक बहुत अच्छा जवाब है। धन्यवाद। मैंने इसे net.tcp पर आज़माया है, लेकिन सीधे हेडर संग्रह का उपयोग कर रहा हूं (Http हेडर्स ने काम नहीं किया)। मैं ServiceHost AfterReceiveRequest इवेंट में अपने टोकन (नाम) के साथ एक हेडर प्राप्त करता हूं, लेकिन मूल्य नहीं (मूल्य के लिए संपत्ति भी नहीं लगती है?)। क्या मैं कुछ छोड़ रहा हूं? मैंने नाम / मूल्य जोड़ी की अपेक्षा की होगी जब मैं शीर्षलेख बनाता हूं तो यह मुझसे पूछता है: request.Headers.Add (MessageHeader.CreateHeader (नाम, एनएस, मूल्य));
प्रोग्राम। एक्स

13
+1 OutgoingMessagePropertiesवे हैं जो आपको HTTP हेडर एक्सेस करने की आवश्यकता है - न OutgoingMessageHeadersकि SOAP हेडर।
स्लीवरनिंजा

1
बस, बहुत बढ़िया कोड! :)
अभिलाषा

3
यह केवल एक हार्डकोड उपयोगकर्ता एजेंट की अनुमति देता है, जो - दिए गए उदाहरण के अनुसार - web.config में हार्डकोड है!
क्रिस्टियन बी

1
यह एक उत्कृष्ट उत्तर है। जब HttpRequestMessageProperty.Name संदेश गुणों में अभी तक उपलब्ध नहीं है, तो यह मामला भी संभालता है। किसी कारण से, अपने कोड को डीबग करना, मुझे एहसास हुआ कि कुछ समय के मुद्दों के आधार पर यह मूल्य हमेशा नहीं था। धन्यवाद मार्क!
carlos357

80

आप इसे कॉल का उपयोग करके जोड़ते हैं:

using (OperationContextScope scope = new OperationContextScope((IContextChannel)channel))
{
    MessageHeader<string> header = new MessageHeader<string>("secret message");
    var untyped = header.GetUntypedHeader("Identity", "http://www.my-website.com");
    OperationContext.Current.OutgoingMessageHeaders.Add(untyped);

    // now make the WCF call within this using block
}

और फिर, सर्वर-साइड जिसे आप इसका उपयोग कर लेते हैं:

MessageHeaders headers = OperationContext.Current.IncomingMessageHeaders;
string identity = headers.GetHeader<string>("Identity", "http://www.my-website.com");

5
कोड-स्निपेट के लिए धन्यवाद। लेकिन इसके साथ मुझे हर बार हेडर को जोड़ना होगा जो मैं एक विधि को कॉल करना चाहता हूं। मैं इस प्रक्रिया को पारदर्शी बनाना चाहता था। मेरा मतलब है कि एक बार लागू करने के बाद, हर बार उपयोगकर्ता एक सेवा क्लाइंट बनाता है और एक विधि का उपयोग करता है, ग्राहक हेडर स्वचालित रूप से संदेश में जुड़ जाता है।
मृत्कांडी जू

यह इस जवाब में दिए गए सुझाव पर विस्तार करने के लिए एक उदाहरण के साथ एक अच्छा MSDN लिंक है: msdn.microsoft.com/en-us/library/…
atconway

1
धन्यवाद, यदि आप कस्टम क्लाइंट लाइब्रेरी का उपयोग कर रहे हैं तो यह एक बेहतरीन कोड है। इस तरह से आपको मैसेजइंसपेक्टर को लागू करने की आवश्यकता नहीं है। बस एक सामान्य आवरण विधि बनाएं जो trhe OperationContextScope में प्रत्येक क्लाइंट कॉल को लपेटती है।
जस्टअमार्टिन

3
एक नोट के रूप में, यह समस्याग्रस्त है यदि आप अपने कॉल के साथ किसी भी प्रकार का एसिंक्स सामान कर रहे हैं, क्योंकि OperationContextScope(और OperationContext) हैं ThreadStatic- मार्क गुड का जवाब ThreadStaticआइटमों पर भरोसा किए बिना काम करेगा ।
zimdanen

2
यह एक HTTP हेडर नहीं जोड़ता है! यह SOAP लिफाफे में हेडर जोड़ता है।
br3nt

32

यदि आप सेवा में सभी अनुरोधों के लिए एक ही हेडर जोड़ना चाहते हैं, तो आप इसे किसी भी कोडिंग के साथ कर सकते हैं!
बस अपने क्लाइंट कॉन्फ़िगरेशन फ़ाइल में समापन बिंदु नोड के तहत आवश्यक हेडर के साथ हेडर नोड जोड़ें

<client>  
  <endpoint address="http://localhost/..." >  
    <headers>  
      <HeaderName>Value</HeaderName>  
    </headers>   
 </endpoint>  

18
ये SOAP हेडर ( alaMessageHeader ) हैं - HTTP हेडर नहीं।
स्लीवरनिंजा

18

यहाँ अपने क्लाइंट WCF अनुरोध पर ChannelFactoryप्रॉक्सी HTTP के रूप में कस्टम HTTP हेडर को मैन्युअल रूप से जोड़ने के लिए एक और उपयोगी समाधान है । यह प्रत्येक अनुरोध के लिए किया जाना चाहिए, लेकिन एक साधारण डेमो के रूप में पर्याप्त है, यदि आपको गैर-नेट प्लेटफार्मों के लिए तैयारी में अपने प्रॉक्सी का परीक्षण करने की आवश्यकता है।

// create channel factory / proxy ...
using (OperationContextScope scope = new OperationContextScope(proxy))
{
    OperationContext.Current.OutgoingMessageProperties[HttpRequestMessageProperty.Name] = new HttpRequestMessageProperty()
    {
        Headers = 
        { 
            { "MyCustomHeader", Environment.UserName },
            { HttpRequestHeader.UserAgent, "My Custom Agent"}
        }
    };    
    // perform proxy operations... 
}

1
मैंने 4 अन्य समान दिखने वाले सुझावों की कोशिश की और यह एकमात्र ऐसा है जिसने मेरे लिए काम किया।
जॉनऑपिनर

यह वास्तव में HTTP हेडर जोड़ता है, धन्यवाद! :) लेकिन jeez यह बदसूरत दिखने वाला कोड है।
br3nt

11

यह NimsDotNet उत्तर के समान है लेकिन दिखाता है कि इसे प्रोग्रामेटिक रूप से कैसे करना है।

बस हेडर को बाइंडिंग में जोड़ें

var cl = new MyServiceClient();

var eab = new EndpointAddressBuilder(cl.Endpoint.Address);

eab.Headers.Add( 
      AddressHeader.CreateAddressHeader("ClientIdentification",  // Header Name
                                         string.Empty,           // Namespace
                                         "JabberwockyClient"));  // Header Value

cl.Endpoint.Address = eab.ToEndpointAddress();

मुझे यह कोड मेरे वर्तमान कॉल (क्लाइंट साइड) में मिला दिया गया है .. मुझे यह कैसे प्राप्त होता है सिर में System.ServiceModel.OperationContext? (सर्वर साइड) (मैं अपनी उंगलियों को पार कर रहा हूं कि यह मेरी मदद करेगा)
ग्रेनाडोडर

1
समझ गया ! System.ServiceModel.Channels.MessageHeaders हेडर = ऑपरेशनContext.RequestContext.RequestMessage.Headers; int हैडरइन्डेक्स = हेडर.फाइन्डर ("क्लाइंटइंटिफिकेशन", स्ट्रिंग.इम्प्टी); var requestName = (शीर्ष लेख <0)? "UNKNOWN": हेडर.गेटहेडर <string> (हैडरइन्डेक्स);
ग्रेनडाकोडर

1
@granadaCoder मुझे वह साइट बहुत पसंद है! ;-)
megaMan

यह एक हेडर को SOAP लिफाफे में जोड़ता है, न कि HTTP हेडर
br3nt

5
var endpoint = new EndpointAddress(new Uri(RemoteAddress),
               new[] { AddressHeader.CreateAddressHeader(
                       "APIKey", 
                       "",
                       "bda11d91-7ade-4da1-855d-24adfe39d174") 
                     });

12
यह एक SOAP संदेश हैडर है, न कि HTTP हैडर।
रेने

3

यह मेरे लिए काम किया है, HTTP हेडर जोड़ने से WCF कॉल के लिए अनुकूलित

// Message inspector used to add the User-Agent HTTP Header to the WCF calls for Server
public class AddUserAgentClientMessageInspector : IClientMessageInspector
{
    public object BeforeSendRequest(ref System.ServiceModel.Channels.Message request, IClientChannel channel)
    {
        HttpRequestMessageProperty property = new HttpRequestMessageProperty();

        var userAgent = "MyUserAgent/1.0.0.0";

        if (request.Properties.Count == 0 || request.Properties[HttpRequestMessageProperty.Name] == null)
        {
            var property = new HttpRequestMessageProperty();
            property.Headers["User-Agent"] = userAgent;
            request.Properties.Add(HttpRequestMessageProperty.Name, property);
        }
        else
        {
            ((HttpRequestMessageProperty)request.Properties[HttpRequestMessageProperty.Name]).Headers["User-Agent"] = userAgent;
        }
        return null;
    }

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

// Endpoint behavior used to add the User-Agent HTTP Header to WCF calls for Server
public class AddUserAgentEndpointBehavior : IEndpointBehavior
{
    public void ApplyClientBehavior(ServiceEndpoint endpoint, ClientRuntime clientRuntime)
    {
        clientRuntime.MessageInspectors.Add(new AddUserAgentClientMessageInspector());
    }

    public void AddBindingParameters(ServiceEndpoint endpoint, BindingParameterCollection bindingParameters)
    {
    }

    public void ApplyDispatchBehavior(ServiceEndpoint endpoint, EndpointDispatcher endpointDispatcher)
    {
    }

    public void Validate(ServiceEndpoint endpoint)
    {
    }
}

इन वर्गों को घोषित करने के बाद आप अपने WCF क्लाइंट में इस तरह से नया व्यवहार जोड़ सकते हैं:

client.Endpoint.Behaviors.Add(new AddUserAgentEndpointBehavior());

यह संकलित नहीं करेगा: त्रुटि CS0136 एक स्थानीय या 'संपत्ति' नाम का पैरामीटर इस दायरे में घोषित नहीं किया जा सकता है, क्योंकि उस नाम का उपयोग स्थानीय या पैरामीटर को परिभाषित करने के लिए एक स्थानीय स्कोप में किया जाता है।
लेस्ज़ेक पी

बस इस्तेमाल नहीं किए जाने वाले को हटा दें
kosnkov

3

यह मेरे लिए काम करता है

TestService.ReconstitutionClient _serv = new TestService.TestClient();

using (OperationContextScope contextScope = new OperationContextScope(_serv.InnerChannel))
{
   HttpRequestMessageProperty requestMessage = new HttpRequestMessageProperty();

   requestMessage.Headers["apiKey"] = ConfigurationManager.AppSettings["apikey"]; 
   OperationContext.Current.OutgoingMessageProperties[HttpRequestMessageProperty.Name] = 
      requestMessage;
   _serv.Method(Testarg);
}

2

.NET 3.5 में संदर्भ बाइंडिंग वही हो सकती है जो आप खोज रहे हैं। बॉक्स में से तीन हैं: BasicHttpContextBinding, NetTcpContextBinding, और WSHttpContextBinding। संदर्भ प्रोटोकॉल मूल रूप से संदेश हेडर में कुंजी-मूल्य जोड़े को पास करता है। MSDN पत्रिका पर टिकाऊ सेवा लेख के साथ प्रबंध राज्य की जाँच करें ।


यह भी ध्यान दें कि आप सर्वर के साथ एक सत्र स्थापित करने से पहले केवल एक बार संदर्भ सेट करते हैं। तब संदर्भ आसानी से पढ़ जाता है। यदि आप चाहते हैं कि संदर्भ सेटअप क्लाइंट की तरफ से पारदर्शी हो, तो आप क्लाइंट प्रोक्स्ट क्लास से प्राप्त कर सकते हैं और इसके विपरीत में आप अपने संदर्भ को बनाने वाली जानकारी जोड़ सकते हैं। फिर हर बार क्लाइंट क्लाइंट के एक उदाहरण का निर्माण करता है, संदर्भ स्वचालित रूप से बनाया जाएगा और क्लाइंट प्रॉक्सी उदाहरण में जोड़ा जाएगा।
मेहमत अरस

2

अगर मैं आपकी आवश्यकता को सही ढंग से समझता हूं, तो सरल उत्तर है: आप नहीं कर सकते।

ऐसा इसलिए है क्योंकि WCF सेवा का क्लाइंट आपकी सेवा का उपयोग करने वाले किसी भी तीसरे पक्ष द्वारा उत्पन्न किया जा सकता है।

यदि आपके पास आपकी सेवा के ग्राहकों का नियंत्रण है, तो आप एक आधार ग्राहक वर्ग बना सकते हैं जो वांछित हेडर जोड़ते हैं और वर्कर वर्ग के व्यवहार को विरासत में प्राप्त करते हैं।


1
सहमत होने पर, यदि आप वास्तव में SOA का निर्माण कर रहे हैं, तो आप यह नहीं मान सकते कि सभी ग्राहक .NET-आधारित हैं। तब तक प्रतीक्षा करें जब तक आपका व्यवसाय हासिल नहीं हो जाता।
स्लीवरनिंजा

2
क्या यह वास्तव में सच है? जावा वेब सेवा क्लाइंट में SOAP हेडर में नाम / मान जोड़ने की क्षमता नहीं है? मेरे लिए इस पर भरोसा करना मुश्किल है। यकीन है कि यह एक अलग कार्यान्वयन होगा, लेकिन यह एक अंतर-समाधान है
एडम

2

आप MessageContract में कस्टम हेडर निर्दिष्ट कर सकते हैं ।

आप <एंडपॉइंट> हेडर का भी उपयोग कर सकते हैं जो कॉन्फ़िगरेशन फ़ाइल में संग्रहीत हैं और क्लाइंट / सेवा द्वारा भेजे गए सभी संदेशों के हेडर में ऑलॉन्ग को कॉपी करेंगे। यह कुछ स्थिर हेडर को आसानी से जोड़ने के लिए उपयोगी है।


3
ये SOAP हेडर ( alaMessageHeader ) हैं - HTTP हेडर नहीं।
स्लीवरनिंजा

0

यदि आप हर WCF कॉल में कस्टम HTTP हेडर को ऑब्जेक्ट ओरिएंटेड तरीके से जोड़ना चाहते हैं, तो आगे न देखें।

जिस तरह मार्क गुड्स और पॉलविट के उत्तर में, हमें डब्ल्यूटीएफ IClientMessageInspectorअनुरोध में कस्टम HTTP हेडर को इंजेक्ट करने के लिए उप-वर्ग की आवश्यकता है । हालाँकि, हम एक शब्दकोश को जोड़ने वाले मुखिया को स्वीकार करके निरीक्षक को अधिक सामान्य बनाने की सुविधा देते हैं:

public class HttpHeaderMessageInspector : IClientMessageInspector
{
    private Dictionary<string, string> Headers;

    public HttpHeaderMessageInspector(Dictionary<string, string> headers)
    {
        Headers = headers;
    }

    public object BeforeSendRequest(ref Message request, IClientChannel channel)
    {
        // ensure the request header collection exists
        if (request.Properties.Count == 0 || request.Properties[HttpRequestMessageProperty.Name] == null)
        {
            request.Properties.Add(HttpRequestMessageProperty.Name, new HttpRequestMessageProperty());
        }

        // get the request header collection from the request
        var HeadersCollection = ((HttpRequestMessageProperty)request.Properties[HttpRequestMessageProperty.Name]).Headers;

        // add our headers
        foreach (var header in Headers) HeadersCollection[header.Key] = header.Value;

        return null;
    }

    // ... other unused interface methods removed for brevity ...
}

जिस तरह मार्क गुड्स और पॉलविट के जवाब में, हमें अपने डब्ल्यूसीएफ क्लाइंट में IEndpointBehaviorइंजेक्ट करने के लिए उपवर्ग की आवश्यकता है HttpHeaderMessageInspector

public class AddHttpHeaderMessageEndpointBehavior : IEndpointBehavior
{
    private IClientMessageInspector HttpHeaderMessageInspector;

    public AddHttpHeaderMessageEndpointBehavior(Dictionary<string, string> headers)
    {
        HttpHeaderMessageInspector = new HttpHeaderMessageInspector(headers);
    }

    public void ApplyClientBehavior(ServiceEndpoint endpoint, ClientRuntime clientRuntime)
    {
        clientRuntime.ClientMessageInspectors.Add(HttpHeaderMessageInspector);
    }

    // ... other unused interface methods removed for brevity ...
}

हमारे ऑब्जेक्ट ओरिएंटेड दृष्टिकोण को समाप्त करने के लिए आवश्यक अंतिम भाग, हमारे WCF ऑटो-जेनरेट किए गए क्लाइंट का उप-वर्ग बनाना है (मैंने WCF क्लाइंट उत्पन्न करने के लिए Microsoft के WCF वेब सेवा संदर्भ गाइड का उपयोग किया है)।

मेरे मामले में, मुझे x-api-keyHTML हेडर के लिए एक एपीआई कुंजी संलग्न करने की आवश्यकता है ।

उपवर्ग निम्नलिखित करता है:

  • आवश्यक मानकों के साथ बेस क्लास के निर्माता को कॉल करता है (मेरे मामले में ए EndpointConfiguration में कंस्ट्रक्टर में पारित होने के लिए एनुम उत्पन्न किया गया था - शायद आपके कार्यान्वयन में यह नहीं होगा)
  • हेडर को परिभाषित करता है जो हर अनुरोधों से जुड़ा होना चाहिए
  • देता AddHttpHeaderMessageEndpointBehaviorग्राहक के लिए Endpointव्यवहार
public class Client : MySoapClient
{
    public Client(string apiKey) : base(EndpointConfiguration.SomeConfiguration)
    {
        var headers = new Dictionary<string, string>
        {
            ["x-api-key"] = apiKey
        };

        var behaviour = new AddHttpHeaderMessageEndpointBehavior(headers);
        Endpoint.EndpointBehaviors.Add(behaviour);
    }
}

अंत में, अपने ग्राहक का उपयोग करें!

var apiKey = 'XXXXXXXXXXXXXXXXXXXXXXXXX';
var client = new Client (apiKey);
var result = client.SomeRequest()

परिणामस्वरूप HTTP अनुरोध में आपका HTTP हेडर होना चाहिए और कुछ इस तरह दिखना चाहिए:

POST http://localhost:8888/api/soap HTTP/1.1
Cache-Control: no-cache, max-age=0
Connection: Keep-Alive
Content-Type: text/xml; charset=utf-8
Accept-Encoding: gzip, deflate
x-api-key: XXXXXXXXXXXXXXXXXXXXXXXXX
SOAPAction: "http://localhost:8888/api/ISoapService/SomeRequest"
Content-Length: 144
Host: localhost:8888

<s:Envelope xmlns:s="http://schemas.xmlsoap.org/soap/envelope/">
  <s:Body>
    <SomeRequestxmlns="http://localhost:8888/api/"/>
  </s:Body>
</s:Envelope>

-1

पार्टी के लिए थोड़ा देर से लेकिन जुवेल लोवी ने अपनी किताब और संबंधित ServiceModelEx में इस सटीक परिदृश्य को संबोधित किया पुस्तकालय ।

मूल रूप से वह ClientBase और ChannelFactory विशिष्टताओं को परिभाषित करता है जो टाइप-सुरक्षित हेडर मान निर्दिष्ट करने की अनुमति देता है। मैं स्रोत डाउनलोड करने और HeaderClientBase और HeaderChannelFactory कक्षाओं को देखने की सुविधा देता हूं।

जॉन


1
यह किसी के काम को बढ़ावा देने के अलावा बहुत कुछ नहीं है। क्या आप एक प्रासंगिक अंश / एल्गोरिथ्म जोड़ सकते हैं - अर्थात प्रश्न का उत्तर दें - या आपके पास किसी भी संबद्धता का खुलासा करें? अन्यथा यह सिर्फ फैन-अप स्पैम है।
निधि मोनिका का मुकदमा 12

मैं कहूंगा कि यह किसी को एक पॉइंटर के माध्यम से एक दृष्टिकोण के लिए एक उत्तर दे रहा है, जिसके बारे में वे नहीं जानते होंगे। मैंने प्रासंगिक लिंक दिया है मुझे और जोड़ने की आवश्यकता क्यों होनी चाहिए? यह सभी संदर्भों में है। और मुझे यकीन है कि जुवेले लोवी इससे बेहतर वर्णन कर सकती है जितना मैं कभी कर सकता था :-) मेरे संबद्धता के लिए - मैंने किताब खरीदी! बस। मैं मिस्टर लोवी से कभी नहीं मिला, लेकिन मुझे यकीन है कि वह एक बेहतरीन चैप है। WCF के बारे में स्पष्ट रूप से बहुत कुछ जानता है ;-)
BrizzleOwl

आपको अधिक जोड़ना चाहिए क्योंकि संभवतः आप उत्तर देने से पहले उत्तर को पढ़ते हैं , और आपने उस अनुभाग को नोट किया है जो कहता है "हमेशा एक महत्वपूर्ण लिंक का सबसे प्रासंगिक हिस्सा उद्धृत करें, यदि लक्ष्य साइट अप्राप्य है या स्थायी रूप से ऑफ़लाइन है।" आपका जुड़ाव महत्वपूर्ण नहीं है। केवल उत्तर की गुणवत्ता है।
निधि मोनिका के मुकदमे

ठीक। मैं इसमें अंकों के लिए नहीं हूँ - जैसा कि आप शायद मेरे स्कोर से बता सकते हैं! बस सोचा कि यह एक उपयोगी सूचक हो सकता है।
BrizzleOwl

1
मैं यह नहीं कह रहा कि यह एक बुरा सूचक है। मैं कह रहा हूँ कि, अपने दम पर, यह एक अच्छा जवाब नहीं है। यह लोगों को बहुत अच्छी तरह से मदद कर सकता है, और यह एक अच्छी बात है, लेकिन इसका उत्तर बेहतर होगा यदि आप इसमें शामिल की गई कक्षाओं का बहुत संक्षिप्त विवरण देने के बजाय, उनके द्वारा उपयोग की जाने वाली विधि का वर्णन कर सकते हैं। इस तरह, इस अवसर पर कि साइट तक पहुँचा नहीं जा सकता है - जो भी कारण से - आपका जवाब अभी भी मदद करता है।
निधि मोनिका का मुकदमा
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.