0

我一直在看MSDN和codeproject,但我还是有点困惑。

同步服务与异步服务。

我有一个 WCF 服务端点。该服务将 2way SSL 应用于其 web.config 文件。客户端是一个基于 Oracle 的 java Weblogic Suite。这有自己的私钥和公钥。客户端需要与我们的服务进行异步和同步通信。

我只能在服务器端进行更改

http://www.codeproject.com/Articles/91528/How-to-Call-WCF-Services-Synchronously-and-Asynchr

http://msdn.microsoft.com/en-us/library/ms731177.aspx

以下代码是SVC、cs文件的同步部分:-

public getQuoteSyncResponse1 getQuoteSync(getQuoteSyncRequest request)
     {
        // Create new response
        getQuoteSyncResponse1 res = new getQuoteSyncResponse1();

        res.GetQuoteSyncResponse = new GetQuoteSyncResponse();
        res.GetQuoteSyncResponse.Header = new GetQuoteResponseHeaderType();
        res.GetQuoteSyncResponse.Response = new GetQuoteSyncResponseType();

        // Create and populate header
        res.GetQuoteSyncResponse.Header.MessageId = request.GetQuoteRequestSync.Header.MessageId;
        res.GetQuoteSyncResponse.Header.Timestamp = request.GetQuoteRequestSync.Header.Timestamp;
        res.GetQuoteSyncResponse.Header.QuoteId = request.GetQuoteRequestSync.Header.QuoteId;
        res.GetQuoteSyncResponse.Header.CarrierId = request.GetQuoteRequestSync.Header.CarrierId;


        List<RejectionType> rj = new List<RejectionType>();


        string _sTotalEmployees = request.GetQuoteRequestSync.Request.Employer.TotalEmployees;
        int _TotalEmployees = 0;
        if (int.TryParse(_sTotalEmployees, out _TotalEmployees) == false)
        {


            RejectionType rt;
            rt = new RejectionType();
            rt.ReasonCode = "R01";
            rt.ReasonDescription = "Invalid Number of Employees";

            rj.Add(rt);

            res.GetQuoteSyncResponse.Response.Rejections = rj.ToArray();

            res.GetQuoteSyncResponse.Response.ReceiptStatus = AcceptanceContentType.Reject;

            return res;
        }

        res.GetQuoteSyncResponse.Response.ReceiptStatus = AcceptanceContentType.Success;

        List<QuoteType> q = new List<QuoteType>();

        QuoteType qt;

        qt = new QuoteType();
        qt.PlanId = "P345678";
        qt.EEPremium = 1220;
        qt.EESPPremium = 2222;
        qt.EEDepPremium = 3333;
        qt.EEFamilyPremium = 4444;
        qt.TotalMonthlyPremium = 3456;
        qt.CoverageEffectiveDate = DateTime.Now;

        q.Add(qt);

        res.GetQuoteSyncResponse.Response.Quotes = q.ToArray();

        return res;}

所以服务的这个同步部分正在工作。现在,我如何使用它来将其转换为异步等效项?

我应该在 cs 文件中启动异步方法吗?还是在 svc 文件中?我很困惑...

 public getQuoteAsyncResponse getQuoteAsync(getQuoteAsyncRequest request, AsyncCallback callback, Object state)
    {
        // Create new response
        getQuoteAsyncResponse res = new getQuoteAsyncResponse();

        return new getQuoteAsyncResponse();
    }

我对回调 deli-gator、对象状态等有所了解,但是有人可以为我进一步说明这一点吗?如何格式化服务的异步部分?网络上有很多例子……但都非常混乱。我一定对这个概念有一些内在的误解。

编辑:-我在答案中被告知,服务器端不需要操作异步通信方式。但是我发现了这个:-

在 WCF 中实现异步操作 正如 WCF 管道使客户端能够异步调用服务器操作,而服务器不需要知道任何有关它的信息,WCF 也允许异步定义服务操作。所以像这样的操作:

[OperationContract]
string DoWork(int value);

……可能在服务合同中表示为:

[OperationContract(AsyncPattern = true)]
IAsyncResult BeginDoWork(int value, AsyncCallback callback, object state);

string EndDoWork(IAsyncResult result);

请注意,这两种形式是等效的,并且在 WCF 元数据中无法区分:它们都公开了一个名为 DoWork[1] 的操作:

4

1 回答 1

1

异步部分需要在客户端完成。这意味着您可能正在做类似的事情: var response = ServiceReference.GetSomething();

相反,制作一个代理来获取回调。每当回调收到响应时,创建和触发(或调用)事件(或委托)。在上面的语句中,您显然在等待响应被分配到变量中,然后再移动到下一行。

相反,你可以

  1. 在 Service 契约上,一定要用 [OperationContract(IsOneWay = true)] 来装饰
  2. 如果您使用 ServiceReference 或 serviceutil,它将自动创建“传入事件”并为您完成所有客户端异步工作。
  3. 如果你使用 TCP,也创建一个回调合约,然后在客户端你可以做类似 ServiceReference1.IncomingSomething += new eventHandler 的事情。现在您可以执行 ServiceReferecnce1.GetSomething(),响应将转到 eventhandler 函数。
  4. 如果这是 RESTFUL:

      public void MakeAsyncRequest(string url, string contentType)
                {
                    try
                    {
                        HttpWebRequest request = (HttpWebRequest)WebRequest.Create(url);
                        request.ContentType = contentType;
                        request.Method = WebRequestMethods.Http.Get;
                        request.Timeout = 10000;
                        request.Proxy = null;
    
                        request.BeginGetResponse(new AsyncCallback(ReadCallback), request);
                    }
                    catch (Exception ex)
                    {
                        LogManager.LogException(ex);
                    }
                }
    
                private void ReadCallback(IAsyncResult asyncResult)
                {
                    HttpWebRequest request = (HttpWebRequest)asyncResult.AsyncState;
                    string strContent = string.Empty;
                    string s;
    
                    try
                    {
                        using (HttpWebResponse response = (HttpWebResponse)request.EndGetResponse(asyncResult))
                        {
                            Stream responseStream = response.GetResponseStream();
                            using (StreamReader sr = new StreamReader(responseStream))
                            {
                                //Need to return this response 
                                strContent = sr.ReadToEnd();
                            }
                        }
                    }
                    catch (Exception ex)
                    {
                        throw;
                    }
                }
    
于 2013-04-18T20:05:06.443 回答