F#和邮箱处理器不执行

问题描述 投票:0回答:1

我正在使用F#邮箱处理器来同步数据交换,所以有一些操作和标志(发送和最终确定)被设置为真,但有时我需要重置然后,所以我使用api来做到这一点,所以我的api有一个特殊的命令,我叫系统清除这个操作设置一些系统标志回到假,但问题是,它不火。

作为一个api引擎,我使用的是Nancy(但我不认为这是问题的根源),所以重置系统标志的模块styatuis会像。

let purgeHandler = 

    Func<obj, Response> 
        (fun _ -> 
            try
                HandshakeProcessor.Post(HandshakeService.Purge)
                let jsonBytes = System.Text.Encoding.UTF8.GetBytes(""" {} """)
                new Response 
                        (ContentType = "application/json", 
                            StatusCode = HttpStatusCode.OK,
                            Contents = fun s -> s.WriteAsync(jsonBytes, 0, jsonBytes.Length) |> Async.AwaitTask |> Async.RunSynchronously)
            with
                ex -> 
                    let jsonBytes = System.Text.Encoding.UTF8.GetBytes(sprintf """ { "result": "false", "error": "%s" } """ ex.Message)
                    new Response 
                        (ContentType = "application/json", 
                            StatusCode = HttpStatusCode.InternalServerError,
                            Contents = fun s -> s.WriteAsync(jsonBytes, 0, jsonBytes.Length) |> Async.AwaitTask |> Async.RunSynchronously))

this.Put("Purge", purgeHandler)

很简单,只要我收到请求,我就会向邮箱发送清除命令,将标志设置为假。

所以我的邮箱看起来是这样的。

    type HandshakeService =
      | Finalized of (bool * bool)
      | Purge
      | Get of AsyncReplyChannel<HandshakePools>

    let HandshakeProcessor : MailboxProcessor<HandshakeService> = 
    let handshake = HandshakePools()
      MailboxProcessor.Start(fun inbox ->
        let rec registerMessagePoint (responseType : ResponseType, message : DatabaseMessage) =
            async{
                let! msg = inbox.Receive()
                match msg with 
                | Finalized (send, finalized) -> 
                    handshake.Finalized <- finalized
                    handshake.Send <- send
                | Purge ->
                    handshake.Send <- false
                    handshake.Finalized <- false
                    return! registerMessagePoint(responseType, message)
                | Get replyChannel ->
                    handshake |> replyChannel.Reply
                    return! registerMessagePoint (responseType, message)  
            }
        registerMessagePoint(ResponseType.Unknown, DatabaseMessage (0us, 0us, String.Empty)))

另外,当我在FUNC里面使用get flag状态时,比如说:

let pools = HandshakeProcessor.PostAndReply((fun reply -> HandshakeService.Get reply), timeout = 10000)
printfn "\n\n\n\n  FINALIZED %b  \n\n\n\n" pools.Finalized

我收到了超时异常。

另外,如果我在FUNC之前移动Post,它就会启动,但只在模块初始化时启动一次,然后当我再次调用这个方法时,它就不会出现bugde,比如。

let purgeHandler (handshakePool : HandshakePools) = 

    HandshakeProcessor.Post(HandshakeService.Purge) 
    Func<obj, Response> 

所以问题是当我启动API方法时,清除帖子被跳过了。它不进入邮箱的清除方法和标志保持不变,我已经把断点在邮箱的清除部分。有人知道如何解决这个问题吗?

f# nancy
1个回答
1
投票

似乎没有简单的方法可以做到这一点,我所找到的都是SignalR与nancyFx在这种情况下的用法。所以从邮箱处理器辞职,创建了mediator。

调解器。

type HttpCommunicationMediator private () =   

  static member val private _instance = lazy HttpCommunicationMediator()
  static member Instance = HttpCommunicationMediator._instance.Value

  member val private purgeSettings = Event<unit>()
  [<CLIEvent>]
  member this.PurgeSetting = this.purgeSettings.Publish
  member this.InvokePurgeSetting = this.purgeSettings.Trigger

当有API请求时调用

HttpCommunicationMediator.Instance.InvokePurgeSetting()

执行事件(放在可以注册的地方)。

HttpCommunicationMediator.Instance.PurgeSetting.AddHandler (fun _ _-> (* resets flags *))  

虽然不是很完美,但还是能用的。

© www.soinside.com 2019 - 2024. All rights reserved.