Hi > * Is TrueAsync intended strictly to enable concurrency without parallelism > (e.g. single-threaded cooperative multitasking)? > Is there a future path in mind for parallelism (actual simultaneous > execution)?
In short, it mostly depends on the PHP core. TrueAsync itself could support multithreading. At the moment, achieving a fully multithreaded PHP seems extremely complex and offers very little benefit. In other words, the cost-to-benefit ratio is close to “irrational.” If you’d like, I can elaborate on this idea, though probably not in this thread. > Following on from that question, I note that there is no way to annotate > types as being safely sendable across concurrent execution contexts I actually studied this topic about a year ago. All of this can be done if one really wants to. To put it simply, implementing a SharedObject is already possible now, and it seems that it already exists in the parallel extension. As for data types and deep changes to PHP, that’s not directly related to TrueAsync. And even if it is, it can always be changed in the future. If someone decides to create a parallel version of PHP, they will definitely face backward compatibility issues. I wouldn’t even worry about that :) > That said: the TrueAsync proposal isn't proposing async/await keywords. There is an RFC proposing new syntax, but it was unanimously decided not to use it. For now. Maybe in PHP 9? > Perhaps it's sufficient to say that "TrueAsync" is single-thread only, and > the multithreaded case will be handled with a completely different API later > so BC isn't an issue. But either way, this should > be at least mentioned in > the Future Scope section. Yes, of course, that’s possible. > * Rob Landers brought up the question about multiple-value Awaitables. > I agree with him that it is a potential footgun. If an Awaitable is going to > return multiple values, then it should implement have a different interface > to indicate that contract. It seems to me that this discussion has gotten a bit tangled: 1. Functions like awaitXX are not part of this RFC, yet we’re discussing them. Is that really necessary? 2. Awaitable objects do not return multiple values. 3. The Awaitable interface is basic for others, just like in many other programming languages. And for some reason, it’s not considered a problem there. So far, no real example has been found where this would actually be a problem. > For example: Swift's standard library provides the AsyncSequence Comparing the Swift model directly with TrueAsync would be quite difficult, and such a discussion would require studying Swift’s implementation. It’s not even worth comparing it to Rust, since Rust has its own Future-based model, while Swift relies on code generation. I haven’t looked deeply into this topic, so I can’t really add much more. It would be good to fully figure things out with PHP first :) > The answer in Swift to what happens if multiple readers await a > non-idempotent Awaiter This is the general approach for the Event-Driven pattern, because asynchronous execution under the hood is event-driven. That’s exactly why the Awaitable exists. It acts as an EventProvider, and await() is effectively a subscription to events. Therefore, when await, awaitAll, or awaitAny is called, the code receives the first event, not multiple events. > I don't have a particular view on whether values should be replicated to > multiple readers or not, > but I do find it a bit annoying that Swift's standard library doesn't provide > an easy way to get replicated values. The current RFC does not prohibit this. It does not restrict how objects produce their results or how many subscribers they send them to. This behavior is part of the object’s own contract. > For cancellation, I'm confused on the resulting value. Thank you, that’s a great catch!!! I need to check this case. > For clarity, the case when exit/die is called outside of async code In TrueAsync, there is no longer any non-asynchronous code. Everything is a coroutine. Actually, that’s not entirely accurate, but it’s fine to think of it that way. > I think Async\protect() and forcibly cancelling coroutines beyond calling > $coroutine->cancel() should be removed. If PHP were a language for spacecraft or airplanes, where extremely high reliability is required, this might make sense. However, the current model allows for more concise code and has already proven itself well in other languages. I actually have a stricter explanation for why the cancellable model is more advantageous than any other. This particular model fits well for read operations, which are usually as frequent as, or even more frequent than, write operations. Therefore, this approach simplifies asynchronous code while keeping the overall risk low. > Yes, this means that a coroutine might never complete. > But this is no different than non-async code calling a function that has an > infinite loop and never returns. The cancellation (a cooperative cancellation model) mechanism does not exist to interrupt infinite loops. It is designed to provide a simple yet powerful way to cancel coroutines that are running normally. “Normally” means without an infinite loop. > Also bikeshedding, but I would suggest renaming Coroutine to Task. It could be named that way too. Although I don’t think there’s much difference here. But Task is a shorter word. Thanks, Ed
