-
The documentation at Effection Collections mentions that Stream corresponds to AsyncIterable, but in practice, const delay = (x: number) => new Promise(r => setTimeout(r, x));
(async () => {
const stream: AsyncIterable<number> = (async function* () {
await delay(100)
yield 1
await delay(100)
yield 2
await delay(100)
yield 3
})();
const subcription1 = stream[Symbol.asyncIterator]() // No `await` on the stream itself
// const subcription2 = ...
console.log(await subcription1.next())
// ....
})() The example in the Effection documentation is also confusing: let subscription1 = yield* channel;
let subscription2 = yield* channel; There are two different subscriptions created here, and it feels like merely using Nowadays, for the same functionality, I think the following expression in Effection is better: import { main, createChannel } from 'effection';
await main(function*() {
let channel = createChannel();
// the channel has no subscribers yet!
yield* channel.send('too early');
let subscription1 = channel.subscribe();
let subscription2 = channel.subscribe();
yield* channel.send('hello');
yield* channel.send('world');
console.log(yield* subscription1.next());
//=> { done: false, value: "hello" }
console.log(yield* subscription1.next());
//=> { done: false, value: "world" }
console.log(yield* subscription2.next());
//=> { done: false, value: "hello" }
console.log(yield* subscription2.next());
//=> { done: false, value: "world" }
}); Hmm, what about Stream? Maybe the signature of Stream should be |
Beta Was this translation helpful? Give feedback.
Replies: 1 comment 2 replies
-
@iplaylf2 I think I see where you're coming from. There definitely are some differences between the Async/Await primitives and their Effection analogues, and that they can seem confusing and/or unnecessary when you are new to Effection. However, it is precisely in these differences that you will find the key to the guarantees that Effection provides you that Async/Await does not. Specifically: It is impossible in Effection to create any effect whatsoever that is not bound to a scope. This may seem restrictive at first, but it is actually a superpower. Take for example the const delay = (x: number) => new Promise(r => setTimeout(r, x)); This eagerly creates the timeout effect every time it is called, and it can be called anywhere at any time: const delay = (x: number) => new Promise(r => setTimeout(r, x));
delay(500);
(() => { delay(1000}; delay(400); })();
for (let i = 0; i < 1000; i++) {
delay(i);
} This will create over 1000 calls to const delay = (x: number) => action(r => {
let timeoutId = setTimout(r,x};
return () => clearTimeout(timeoutId);
});
delay(500);
(() => { delay(1000}; delay(400); })();
for (let i =0; i < 1000; i++) {
delay(i);
} Which causes The same principle applies to subscriptions. Usually, whether it is a file handle, a web socket, a bucket storage download, or whatever, there is some "hot" state associated with a subscription. const subcription1 = stream[Symbol.asyncIterator]() // No `await` on the stream itself In that code, it is unknown what state I hope that helps explain why the differences are necessary. While there are analogues for Async/Await constructs in Effection, they are only that: analogues. They must be different it very distinct ways so that we can experience the guarantees that structured concurrency provides which Async/Await doesn't. I'll leave one final difference which I think is important to grasp. In Effection, |
Beta Was this translation helpful? Give feedback.
@iplaylf2 I think I see where you're coming from. There definitely are some differences between the Async/Await primitives and their Effection analogues, and that they can seem confusing and/or unnecessary when you are new to Effection. However, it is precisely in these differences that you will find the key to the guarantees that Effection provides you that Async/Await does not. Specifically:
It is impossible in Effection to create any effect whatsoever that is not bound to a scope.
This may seem restrictive at first, but it is actually a superpower.
Take for example the
delay
function you defined:This eagerly creates the …