Skip to content
Snippets Groups Projects
NewGroupComponent.swift 1.81 KiB
Newer Older
import AppCore
Dariusz Rybicki's avatar
Dariusz Rybicki committed
import ComposableArchitecture
import Foundation
import XXMessengerClient
import XXModels
Dariusz Rybicki's avatar
Dariusz Rybicki committed

public struct NewGroupComponent: ReducerProtocol {
  public struct State: Equatable {
    public init(
      contacts: IdentifiedArrayOf<XXModels.Contact> = [],
      members: IdentifiedArrayOf<XXModels.Contact> = []
    ) {
      self.contacts = contacts
      self.members = members
    }

    public var contacts: IdentifiedArrayOf<XXModels.Contact>
    public var members: IdentifiedArrayOf<XXModels.Contact>
Dariusz Rybicki's avatar
Dariusz Rybicki committed
  }

  public enum Action: Equatable {
    case start
    case didFetchContacts([XXModels.Contact])
    case didSelectContact(XXModels.Contact)
    case didFinish
Dariusz Rybicki's avatar
Dariusz Rybicki committed
  }

  public init() {}

  @Dependency(\.app.messenger) var messenger: Messenger
  @Dependency(\.app.dbManager.getDB) var db: DBManagerGetDB
  @Dependency(\.app.mainQueue) var mainQueue: AnySchedulerOf<DispatchQueue>
  @Dependency(\.app.bgQueue) var bgQueue: AnySchedulerOf<DispatchQueue>

Dariusz Rybicki's avatar
Dariusz Rybicki committed
  public func reduce(into state: inout State, action: Action) -> EffectTask<Action> {
    switch action {
    case .start:
      let myId = try? messenger.e2e.tryGet().getContact().getId()
      return Effect
        .catching { try db() }
        .flatMap { $0.fetchContactsPublisher(.init()) }
        .assertNoFailure()
        .map { $0.filter { $0.id != myId } }
        .map(Action.didFetchContacts)
        .subscribe(on: bgQueue)
        .receive(on: mainQueue)
        .eraseToEffect()

    case .didFetchContacts(let contacts):
      state.contacts = IdentifiedArray(uniqueElements: contacts)
Dariusz Rybicki's avatar
Dariusz Rybicki committed
      return .none
    case .didSelectContact(let contact):
      if state.members.contains(contact) {
        state.members.remove(contact)
      } else {
        state.members.append(contact)
      }
      return .none

    case .didFinish:
      return .none