2

I understand that to put data into an TPL Dataflow target I can use Post or SendAsync and that will return immediately if the item could be put into the target. I understand that SendAsync will wait longer to try an put it in however I am not certain what is the meaning of SendAsync returning false.

Does SendAsync returning false signal that the target (specifically a BufferBlock) has finished and will never accept more messages?
Is it possible that it could start accepting messages later?

VMAtm
  • 27,943
  • 17
  • 79
  • 125
bsagal
  • 591
  • 1
  • 4
  • 10
  • It is not possible to restart block and `SendAsync` will return `false` when the block cannot accept any messages. Answers are: [SendAsync](https://stackoverflow.com/questions/13599305/tpl-dataflow-whats-the-functional-difference-between-post-and-sendasync) and [Restarting a block](https://stackoverflow.com/questions/15967903/task-dataflow-can-a-data-block-be-changed-from-completion-state) – JSteward Aug 17 '17 at 18:17

1 Answers1

1

I understand that to put data into an TPL Dataflow target I can use Post or SendAsync

Correct

that will return immediately if the item could be put into the target.

Not correct - whose method both return immediately. If you're using the Post, it will return false as well.

I understand that SendAsync will wait longer to try an put it in

Partially correct. SendAsync will setup a state machine, which eventually will return a result.

however I am not certain what is the meaning of SendAsync returning false.

It means that the target block cannot accept the message at the time.

Does SendAsync returning false signal that the target (specifically a BufferBlock) has finished and will never accept more messages?

There are many reasons for that, not only that target is in completed state. For example, it's own buffer may be full of messages, and another doesn't fit in it (if your block is constrained with BoundedCapacity). So you can't say for sure that the reason the method returned false is the completed state. However, if you do not limiting the capacity of buffer, it's probably is.

Is it possible that it could start accepting messages later?

No, blocks are designed in a way that they can be completed only once. You need to re-create a block and plug it into the pipeline to restart it.

VMAtm
  • 27,943
  • 17
  • 79
  • 125
  • 2
    I thought the point of ```SendAsync``` running the Task was that it could wait for the buffer to clear. If the buffer being full can also cause ```SendAsync``` to return ```false``` what is the differance to ```Post```? in what situations with a full buffer cause ```SendAsync``` to return ```false``` in the task and not wait longer till the buffer clears? – bsagal Aug 21 '17 at 06:23
  • `SendAsync` firstly tries to send the message synchronously, so there is no difference from `Post` at that time. If target do not provide any result, then method creates a state machine and returns a `Task`, which may finish later. It still can `false` in it, for example, if target is in faulted state. You may see whole possibilities in the code on Github. – VMAtm Aug 21 '17 at 11:59
  • 2
    from your original answer i understand that the ```SendAsync``` task could return ```false``` but in the future have a task returning ```true```. however the example you give in the comments of a faulted state will never allow sending again. Is there any case where the ```SendAsync``` task could return ```false``` and later allow sending again? – bsagal Aug 21 '17 at 13:08
  • No, I didn't meant that. One task cannot return two different results. `SendAsync` returns a `Task`, not the `boolean`, that what I meant. – VMAtm Aug 21 '17 at 13:39
  • @bsagal this is not documented, so you shoudn't rely on this, in theory. In practice it looks like it cannot return `true`, but still, this isn't documented. – VMAtm Aug 21 '17 at 13:41