MailboxProcessor.PostAndTryAsyncReply<'Msg,'Reply> Method (F#)

Like MailboxProcessor.AsyncPostAndReply, but returns None if no reply within the timeout period.

Namespace/Module Path: Microsoft.FSharp.Control

Assembly: FSharp.Core (in FSharp.Core.dll)

// Signature:
member this.PostAndTryAsyncReply : (AsyncReplyChannel<'Reply> -> 'Msg) * ?int -> Async<'Reply option>

// Usage:
mailboxProcessor.PostAndTryAsyncReply (buildMessage)
mailboxProcessor.PostAndTryAsyncReply (buildMessage, timeout = timeout)

Parameters

  • buildMessage
    Type: AsyncReplyChannel<'Reply> -> 'Msg

    The function to incorporate the AsyncReplyChannel into the message to be sent.

  • timeout
    Type: int

    An optional timeout parameter (in milliseconds) to wait for a reply message. The default is -1 which corresponds to Infinite().

Return Value

An asynchronous computation (Async object) that will return the reply or None if the timeout expires.

Example

The following code shows how to use the PostAndTryAsyncReply method.

open System

type Message = string * AsyncReplyChannel<string>

let formatString = "Message number {0} was received. Message contents: {1}"

let agent = MailboxProcessor<Message>.Start(fun inbox ->
    let rec loop n =
        async {          
            let! (message, replyChannel) = inbox.Receive();
            // The delay gets longer with each message, and eventually triggers a timeout.
            do! Async.Sleep(200 * n );
            if (message = "Stop") then
                replyChannel.Reply("Stop")
            else
                replyChannel.Reply(String.Format(formatString, n, message))
            do! loop (n + 1)
        }
    loop (0))

printfn "Mailbox Processor Test"
printfn "Type some text and press Enter to submit a message."
printfn "Type 'Stop' to close the program."

let mutable isCompleted = false
while (not isCompleted) do
    printf "> "
    let input = Console.ReadLine()
    let messageAsync = agent.PostAndTryAsyncReply((fun replyChannel -> input, replyChannel), 1000)
    // Set up a continuation function (the first argument below) that prints the reply.
    // The second argument is the exception continuation.
    // The third argument is the cancellation continuation (not used).
    Async.StartWithContinuations(messageAsync, 
         (fun reply -> 
             match reply with
             | None -> printfn "Reply timeout exceeded."
             | Some reply -> if (reply = "Stop") then
                                 isCompleted <- true
                             else printfn "%s" reply),
         (fun exn ->
            printfn "Exception occurred: %s" exn.Message),
         (fun _ -> ()))

printfn "Press Enter to continue."
Console.ReadLine() |> ignore

A sample session follows.

Mailbox Processor Test
Type some text and press Enter to submit a message.
Type 'Stop' to close the program.
> test1
> Message number 0 was received. Message contents: test1
test2
> Message number 1 was received. Message contents: test2
test3
> Message number 2 was received. Message contents: test3
test4
> Message number 3 was received. Message contents: test4
test5
> Message number 4 was received. Message contents: test5
test6
> Reply timeout exceeded.

Platforms

Windows 7, Windows Vista SP2, Windows XP SP3, Windows XP x64 SP2, Windows Server 2008 R2, Windows Server 2008 SP2, Windows Server 2003 SP2

Version Information

F# Runtime

Supported in: 2.0, 4.0

Silverlight

Supported in: 3

See Also

Reference

Control.MailboxProcessor<'Msg> Class (F#)

Microsoft.FSharp.Control Namespace (F#)

Change History

Date

History

Reason

January 2011

Added code example.

Information enhancement.