Update README.md

This commit is contained in:
Oliver Foggin
2023-12-15 12:01:12 +00:00
committed by GitHub
parent 7a491bbe05
commit 837050e42f

View File

@@ -2,13 +2,64 @@
A higher order reducer for subscribing to `AsyncStream` from your app.
A common pattern in our app for shared data is to create a dependency that exposes an `AsyncStream` of the data that is shared.
Then in the `Reducer` on a `task` action we can do soemthing like...
```
Reduce { state, action in
switch action {
case .task:
return { send in
for await value in await dependency.stream() {
await send(.responseAction(value))
}
}
}
}
```
When you have a lot of publishers/subscribers this gets very repetetive.
This gives a new way to subscribe to an async stream using a higher order reducer.
Any dependency that returns an `AsyncStream` can be subscribed to in the following way.
# If the action takes the same type as the stream
If the `AsyncStream` `Element` type is the same as the input type of the response action you can just do:
```
Reduce {
// your usual reducer here
}
.subscribe(to: myDependency.stream, on: \.some.trigger.action, with: \.some.response.action)
.subscribe(to: myDependency.stream, on: \.some.trigger.action, with: \.some.response.actionThatTakesStreamElement)
```
There is a requirement that the AsyncStream returns the same type as the response action takes.
# If the type doesn't match
If the stream `Element` type needs to be transformed you can do:
```
Reduce {
// your usual reducer here
}
.subscribe(to: myDependency.stream, on: \.some.trigger.action, with: \.response.actionThatTakesAString) { streamElement in
// return some type created from the streamElement
"\(streamElement)"
}
```
# If you have a more complex scenarios and want to run some logic
If you don't necessarily need a response action but you want to do something else like running another dependency or something. You can do:
```
Reduce {
// your usual reducer here
}
.subscribe(to: myDependency.stream, on: \.some.trigger.action) { send, streamElement in
await send(.responseAction)
await otherDependency.doSomethingElse()
}
```