ReducerProtocol in TCA — Composing Reducers using Result Builders

ReducerProtocol in TCA — Composing Reducers using Result Builders

Let’s consider our app has three features —?Shop,?Inventory?&?Search. We create three new types for these features and each of them conform to?ReducerProtocol.

import ComposableArchitecture

struct Shop: ReducerProtocol {
    struct State: Equatable {
        // property declarations
    }
    
    enum Action: Equatable {
        // action cases goes here...
    }
    
    func reduce(into state: inout State, action: Action) -> EffectTask<Action> {
        // reducer implementation
    }
}

struct Inventory: ReducerProtocol {
    struct State: Equatable {
        // property declarations
    }
    
    enum Action: Equatable {
        // action cases goes here...
    }
    
    func reduce(into state: inout State, action: Action) -> EffectTask<Action> {
        // reducer implementation
    }
}

struct Search: ReducerProtocol {
    struct State: Equatable {
        // property declarations
    }
    
    enum Action: Equatable {
        // action cases goes here...
    }
    
    func reduce(into state: inout State, action: Action) -> EffectTask<Action> {
        // reducer implementation
    }
}        

Our app level reducer will compose these three features together. By conforming our features to?ReducerProtocol, we can leverage Swift’s result builders along with constrainted opaque types to compose three reducers as follows -

struct App: ReducerProtocol {
    struct State: Equatable {
        var shop: Shop.State
        var inventory: Inventory.State
        var search: Search.State
    }
    
    enum Action: Equatable {
        case shop(Shop.Action)
        case inventory(Inventory.Action)
        case search(Search.Action)
    }
    
    var body: some ReducerProtocol<State, Action> {
        Scope(state: \.shop, action: /Action.shop) {
            Shop()
        }
        Scope(state: \.inventory, action: /Action.inventory) {
            Inventory()
        }
        Scope(state: \.search, action: /Action.search) {
            Search()
        }
    }
}        

This syntax is more cleaner than what we had to do prior to?ReducerProtocol. Also this syntax looks more similar to SwiftUI syntax.

Evangelist Apps: Embracing TCA with SwiftUI for Powerful, Scalable, and Testable Applications.

Thanks for reading!

Co-authored by Atikur Rahman , Lead iOS Developer at Evangelist Apps.

Romain Brunie ????

Sharing my TCA expertise to empower your development ?? | ?????? with TCA in apps with 100,000+ monthly active users | iOS Software Engineer @ AVIV

1 年

It Is a great way to export navigation from a reducer using this technique ?? Since TCA 1.0 got released: ?? ReducerProtocol has been renamed Reducer ?? EffectTask has been renamed Effect

要查看或添加评论,请登录

Evangelist Apps的更多文章

社区洞察

其他会员也浏览了