WCF:方法 return 一个响应,在生成一个线程以进行后台处理之后

WCF: Method return a response, after spawning a thread to do background processing

所以我有以下场景。我的 WCF 中有一个方法,客户端将在其中发送请求,然后 WCF 服务将执行一些后台处理并调用外部 web 服务方法,该方法将立即以确认响应(在后台处理完成之前) ).

我想做的方法是让我的 WCF 方法 return 在生成线程进行后台处理并调用外部 Web 服务后做出响应。流程是这样的:

参见下面的示例代码:

[ServiceBehavior(InstanceContextMode = InstanceContextMode.PerCall)]
public class Service : IService


public bool INITIAL_CALL()
{

     new Thread(()=>
                {
                    PROCESS();
                }).Start();
    return true;
}


private void PROCESS()
{
    //Do some background processing and create request for call below
    var processRequest = "Request goes here";
    using (var client = new EXTERNALWS.ResponseTypeClient())
    {
       var postResponse = client.POST(processRequest);

       //Log postResponse to database

    }

}

考虑到 PROCESS() 可能 运行 很长一段时间,我只是想看看是否有更好的方法使用 WCF 和 IIS 执行此操作?或者如果有任何我必须考虑的陷阱,即 IIS 应用程序池回收破坏线程。

我已经找到了解决办法。我最终使用 Hangfire 进行所需的后台处理 (https://www.hangfire.io/). Hangfire seems to be specifically made for this. I have implemented it following the documentation found at their homepage, in a separate ASP MVC application. I have also configured it as always running on IIS. All instructions and sample codes to setup Hangfire to do this are found here https://docs.hangfire.io/en/latest/index.html. I had to change the flow (since I am not spawning any new threads manually as previously), and also create a new table in the database so that the INITIAL_CALL in the WCF Application would queue all the long running jobs (later to be picked up and executed by Hangfire). Have in mind this is seperate from Hangfire's queue, this table will be checked by Hangfire in a predefined interval, and will check this database table that stores which function to call, its parameters, and an indicator if the job has already been picked up by Hangfire or not (to avoid the re-entrant scenario described here https://docs.hangfire.io/en/latest/best-practices.html)。有点额外的工作,但效果很好。

现在流程的工作方式如下:

  • 调用方发送请求到INITIAL_CALL

  • 在INITIAL_CALL中,在新数据库table中创建了一个条目(这是作业 Hangfire 将在预定义的时间间隔内检查的队列)。

  • INITIAL_CALL returns 真

  • Hangfire 使用 PROCESS_JOBS 在预定义的时间间隔内检查此数据库 table(此时间间隔可以在 Hangfire 本身中定义)。

  • 如果有排队的项目,PROCESS_JOBS 继续并调用 EXTERNALWS 并在 postResponse 中获得响应。如果没有,它就退出,什么也不做。

  • postReponse 被记录到数据库中。

请参阅下面更新的示例代码:

WCF 应用程序

[ServiceBehavior(InstanceContextMode = InstanceContextMode.PerCall)]
public class Service : IService


public bool INITIAL_CALL()
{
   //Add job queue entry in database table to be picked up by Hangfire 
    return true;
}

Hangfire 应用程序

public void PROCESS_JOBS()
{
    //Check in a predefined interval if there is a pending job in the queue. 
    //If there is continue with below, otherwise exit function.

    //Do some background processing and create request for call below
    var processRequest = "Request goes here";
    using (var client = new EXTERNALWS.ResponseTypeClient())
    {
       var postResponse = client.POST(processRequest);

       //Log postResponse to database

    }

}