Hello

> Without well-defined suspension points, literally all code is unpredictable. 
> This is what people have been trying to tell you for the last several weeks. 
> How can I know when the code will yield to the scheduler?
> How do I reason about it? The foundation is there in the RFC and the code, 
> but it needs more definition and guarantees.

What guarantee does suspend() give? You can still break the code with
it. I understand what you’re talking about, but I don’t see a big
difference between situations like these:

```php
// ---------------------------
// 1. File get contents suspend inside PHP CORE
// ---------------------------

$data = ['value' => 1];
$content = file_get_contents('http://example.com');
$data['value'] = 2;

// ---------------------------
// 2. Asynchronous version special API
// ---------------------------

$data = ['value' => 1];
// Yes we know about this here.
$content = file_get_contents_async('http://example.com');
$data['value'] = 2; // write happens after resume, timing is different
```

I understand that you are trying to say that if `file_get_contents` is
blocking, then there is *slightly more chance* that the code won’t
break.
And if `file_get_contents_async` is explicitly non-blocking, then the
programmer will have to rewrite the code.

But which is cheaper:

1. Rewrite **all** the code?
2. Or rewrite **only the code that uses shared memory**?

And at the same time, using `file_get_contents_async` does **not**
save the programmer from mistakes.
I can already imagine a situation where a programmer, trying to adapt
the code for async, simply renames the functions hoping it will “just
work” :)
No. It's not!

This approach:

* Increases the amount of refactoring
* Does not protect you from errors

> The foundation is there in the RFC and the code, but it needs more definition 
> and guarantees.
There is another approach.
You can use a special `async` attribute for functions that support it.
This would allow not only highlighting the code in the editor, but
also validating it with static analysis.

In transparent asynchrony there is a rule when writing code.
Only code that makes no function calls at all is considered guaranteed safe.
Any call is potentially treated as a hypothetical yield point. I use
the same mindset when writing highly reliable code.
I imagine that it can crash literally at any line. The principle here
is similar.

Asynchronous code in this sense is always divided into two major parts:

1. code that accesses shared memory
2. code that does **not** access shared memory

You only need to be careful in the first case. Everything else
requires no special attention.

This leads to other principles:

1. Shared state should only be passed when it is truly necessary.
2. If an object can be made immutable, it *should* be immutable.
3. If an object must be mutable, then it deserves double attention.

Above these principles there is one more, the most important:

* if you can avoid writing asynchronous code, you should avoid it

> Global state is a core part of PHP, like it or not.

I love the global state. I’m not one of those people who shout that
some approach is “bad.”
Global state is great. The only question is how and when to use it.

So... summary:
Coroutines require:

1. A framework that can work correctly in an asynchronous environment.
2. A different mindset for framework and library developers.
3. More knowledge from regular developers — a bit of a minus… and a
plus at the same time.
4. Strict memory discipline for everyone. Hooray! This is the future
of programming. You can’t run away from it.

I’m confident that PHP can be adapted for more convenient memory
handling. There are possibilities for that.... at the syntax level and
at the helper-object level. This still needs discussion.

P.S.
If someone ever writes documentation, these would be excellent phrases for it :)

Reply via email to