> Edmond Dantes <[email protected]> hat am 22.11.2025 13:37 CET geschrieben: > > > > basically in $result = foo(spawn(bar(baz(file_get_contents())))); > > file_get_contents() receives outside context from spawn() to turn into > > async mode. > > Also foo(), bar(), baz() can be in different namespaces, different classes, > > so by looking at the code calling file_get_contents(), it's not clear if > > the result is sync or async. > > Ok, then let’s look in detail at what is happening. > > > foo(spawn(bar(baz(file_get_contents())))) > > i.e. > > ```php > $result = foo(spawn(bar(...), fn () => baz(file_get_contents()))); > ``` > > Did I understand the code correctly? > (Assume there was also some parameter there, like a file name.) > > 1. We call `bar` in a separate coroutine, which > 2. First calls `file_get_contents` > 3. Then passes the result to the function `baz()` > > Is that correct? > > > Also foo(), bar(), baz() can be in different namespaces, different classes, > > so by looking at the code calling file_get_contents(), it's not clear if > > the result is sync or async. > If we are discussing the code above, then it returns a Promise not of > the file-reading result. > This is a completely different logic, and here the programmer clearly > intended to do something else. > What if the function baz replaces every a character with baz? It's ok. > > ```php > $foo = file_get_contents('foo.txt'); // sync > $result = spawn($foo); // error because $foo is string > ``` > > Here I don’t understand why someone would intentionally write incorrect code. > > Code: > ```php > $result = foo(file_get_contents('foo.txt')); > > // equivalent to > // the code below has no practical purpose > > $result = foo(await(spawn(file_get_contents(...), 'foo.txt'))); > ``` > > Is that correct?
So I guess you want to use spawn() in a similar way as call_user_func() works. This changes the behavior of file_get_contents() from the outside, so it gives file_get_contents() async context from the outside to behave differently. Assuming every io operation inside spawn() runs async, I guess it's not possible to mix sync and async io inside of one function. As mentioned before I'm not suggesting to use coroutines for async io. My recommendation would be implementing new functions for async io and a promise object. Having everything that's executed async explicitly named "_async" helps a lot when reading and understanding userland code. Regarding Coroutines in Go from userland perspective: the idea is nice but often fails with deadlocks, hanging processes and having to run a "Data Race Detector" all the time. Sure it's always the developers fault, but it happens too often. Best Regards Thomas
