Live data from Hacker News

Async Python Is Secretly Deterministic

dbos.dev

11–20 of 38 posts

Re: Async Python Is Secretly Deterministic

#11

No, determinstic scheduling is not a property of async python. Yes, the stdlib asyncio event loop does have deterministic scheduling, but that's an implementation detail and I would not rely on it for anything critical. Other event loops - for instance trio [1] - explicitly randomize startup order so that you won't accidentally write code that relies on it. [1] https://github.com/python-trio/trio/issues/32

It's been a stable (and documented) behavior of the Python standard library for almost a decade now. It's possible it may change--nothing is ever set in stone--but that would be a large change in Python that would come with plenty of warning and time for adjustment.

Re: Async Python Is Secretly Deterministic

#12
post #7

Is this guaranteed by the async specification? Or is this just current behavior which could be changed in a future update. Feels like a brittle dependency if its not part of the spec.

It's documented behavior for the low-level API (e.g. asyncio.call_soon https://docs.python.org/3/library/asyncio-eventloop.html#asy...). More broadly, this has been a stable behavior of the Python standard library for almost a decade now. If it does change, that would be a huge behavioral change that would come with plenty of warning and time for adjustment.

Re: Async Python Is Secretly Deterministic

#13

Earlier quoted context omitted.

That's the cool thing about this behavior--it doesn't matter how complex your program is, your async functions start in the same order they're called (though after that, they may interleave and finish in any order).

Only for tasks that are created in synchronous code. If you start two tasks that each make a web request and then start a new task with the result of that request you will immediately lose ordering.

Yes, this only applies for tasks created from the same (sync or async) function. If tasks are creating other tasks, anything is possible.

Re: Async Python Is Secretly Deterministic

#14
That's deterministic dispatch, as soon as it forks or communicates, it is non deterministic again?

Don't you need something like a network clock to get deterministic replay?

It can't use immediate return on replay, or else the order will change.

This makes me twitchy. The dependencies should be better modelled, and idempotency used instead of logging and caching.

Re: Async Python Is Secretly Deterministic

#15

No, determinstic scheduling is not a property of async python. Yes, the stdlib asyncio event loop does have deterministic scheduling, but that's an implementation detail and I would not rely on it for anything critical. Other event loops - for instance trio [1] - explicitly randomize startup order so that you won't accidentally write code that relies on it. [1] https://github.com/python-trio/trio/issues/32

> but that's an implementation detail

That sounds familiar...

https://stackoverflow.com/questions/39980323/are-dictionarie...

Re: Async Python Is Secretly Deterministic

#16
post #4
post #3

While not production ready, I’ve been happily surprised at this functionality when building with it. I love my interpreters to be deterministic, or when random to be explicitly seeded. It makes debugging much easier when I can rerun the same program multiple times and expect identical results.

Interestingly I think things that should not be deterministic should actually forced not to be. Swift for instance will explicitly make iterating on a dictionary not deterministic (by randomizing the iteration), in order to catch weird bugs early if a client relies (knowingly or not) on the specific order the elements of the dictionary are ordered.

One more reason for randomizing hash table iteration was to prevent Denial of service attacks:

https://lukasmartinelli.ch/web/2014/11/17/php-dos-attack-rev...

Re: Async Python Is Secretly Deterministic

#17
post #7

Is this guaranteed by the async specification? Or is this just current behavior which could be changed in a future update. Feels like a brittle dependency if its not part of the spec.

It's documented behavior for the low-level API (e.g. asyncio.call_soon https://docs.python.org/3/library/asyncio-eventloop.html#asy... ). More broadly, this has been a stable behavior of the Python standard library for almost a decade now. If it does change, that would be a huge behavioral change that would come with plenty of warning and time for adjustment.

In my experience, developers who rely on precise and relatively obscure corner cases, tend to assume that they are more stable than they later prove to be. I've been that developer, and I've been burned because of it.

Even more painfully, I've been the maintenance programmer who was burned because some OTHER programmer trusted such a feature. And then it was my job to figure out the hidden assumption after it broke, long after the original programmer was gone. You know the old saying that you have to be twice as clever to debug code, as you need to be to write it? Debugging another person's clever and poorly commented tricks is no fun!

I'd therefore trust this feature a lot less than you appear to. I'd be tempted to instead wrap the existing loop with a new loop to which I can add instrumentation etc. It's more work. But if it breaks, it will be clear why it broke.

Re: Async Python Is Secretly Deterministic

#18

No, determinstic scheduling is not a property of async python. Yes, the stdlib asyncio event loop does have deterministic scheduling, but that's an implementation detail and I would not rely on it for anything critical. Other event loops - for instance trio [1] - explicitly randomize startup order so that you won't accidentally write code that relies on it. [1] https://github.com/python-trio/trio/issues/32

It's been a stable (and documented) behavior of the Python standard library for almost a decade now. It's possible it may change--nothing is ever set in stone--but that would be a large change in Python that would come with plenty of warning and time for adjustment.

And then one day, Astral creates a new Python implementation in Rust or something that is way faster and all the rage, but does this particular thing different than CPython. Whoops, you can’t use that runtime, because you now have cursed parts in your codebase that produce nondeterministic behaviour you can’t really find a reason for.

Re: Async Python Is Secretly Deterministic

#19
post #18

Earlier quoted context omitted.

It's been a stable (and documented) behavior of the Python standard library for almost a decade now. It's possible it may change--nothing is ever set in stone--but that would be a large change in Python that would come with plenty of warning and time for adjustment.

And then one day, Astral creates a new Python implementation in Rust or something that is way faster and all the rage, but does this particular thing different than CPython. Whoops, you can’t use that runtime, because you now have cursed parts in your codebase that produce nondeterministic behaviour you can’t really find a reason for.

That's a bit what it felt like when I was learning Rust async.

I get it, but "ecosystems" of async runtimes have a pretty big cost.

Re: Async Python Is Secretly Deterministic

#20

No, determinstic scheduling is not a property of async python. Yes, the stdlib asyncio event loop does have deterministic scheduling, but that's an implementation detail and I would not rely on it for anything critical. Other event loops - for instance trio [1] - explicitly randomize startup order so that you won't accidentally write code that relies on it. [1] https://github.com/python-trio/trio/issues/32

It's been a stable (and documented) behavior of the Python standard library for almost a decade now. It's possible it may change--nothing is ever set in stone--but that would be a large change in Python that would come with plenty of warning and time for adjustment.

Well, in my early days programming python I made a lot(!!) of code assuming non-concurrent execution, but some of that code will break in the future with GIL removal. Hopefully the Python devs keep these important changes as opt-ins.
Post reply on HN