Upgrade to Pro — share decks privately, control downloads, hide ads and more …

ReactorKit at Wantedly

ReactorKit at Wantedly

28.Jun.2018 ReactorKit Meetup Japan
https://wantedly.connpass.com/event/90261/

03c0e11ea6f2a3e08b3c46db5877c8e1?s=128

Jiro Nagashima

June 28, 2018
Tweet

Transcript

  1. ©2018 Wantedly, Inc. ReactorKit at Wantedly ReactorKit Meetup Japan 28.Jun.2018

    - Jiro Nagashima
  2. ©2018 Wantedly, Inc. ReactorKit is simple and powerful Page Title

    Page Subtitle
  3. ϖʔδλΠτϧ ϖʔδαϒλΠτϧ ©2018 Wantedly, Inc. Jiro Nagashima @hedjirog Software Engineer

    Wantedly Visit App
  4. ©2018 Wantedly, Inc. https://wantedlyinc.com/ja/products

  5. ©2018 Wantedly, Inc. An app which requires a lot of

    state management search, profile, chat, etc… Page Title Page Subtitle
  6. ©2018 Wantedly, Inc. ReactorKit took care of it all ❤

    Page Title Page Subtitle
  7. ©2018 Wantedly, Inc. 2017 Page Title Page Subtitle 2018 Used

    in one screen Used everywhere
  8. ©2018 Wantedly, Inc. ReactorKit is simple Page Title Page Subtitle

  9. ϖʔδλΠτϧ ϖʔδαϒλΠτϧ ©2018 Wantedly, Inc. https://github.com/ReactorKit/ReactorKit#basic-concept

  10. ©2018 Wantedly, Inc. Less typing Easy to understand Easy to

    code review ReactorKit is simple, therefore
  11. ©2018 Wantedly, Inc. ReactorKit is powerful Page Title Page Subtitle

  12. ©2018 Wantedly, Inc. Example 1 Showing bookmarked status Page Title

    Page Subtitle
  13. ϖʔδλΠτϧ ϖʔδαϒλΠτϧ ©2018 Wantedly, Inc.

  14. ϖʔδλΠτϧ ϖʔδαϒλΠτϧ ©2018 Wantedly, Inc. Reactor View Action State

  15. ϖʔδλΠτϧ ϖʔδαϒλΠτϧ ©2018 Wantedly, Inc. Reactor View Action State

  16. ϖʔδλΠτϧ ϖʔδαϒλΠτϧ ©2018 Wantedly, Inc. // ProjectViewController func bind(reactor: ProjectReactor)

    { // Action rx.methodInvoked(#selector(viewDidLoad)) .map { _ in Reactor.Action.load } .bind(to: reactor.action) .disposed(by: disposeBag) // State reactor.state.map { $0.isBookmarking } .bind(to: bookmarkButton.rx.isSelected) .disposed(by: disposeBag) }
  17. ϖʔδλΠτϧ ϖʔδαϒλΠτϧ ©2018 Wantedly, Inc. Reactor View Action State

  18. ϖʔδλΠτϧ ϖʔδαϒλΠτϧ ©2018 Wantedly, Inc. // ProjectReactor enum Action {

    case load } enum Mutation { case setProject(Project) } struct State { let projectId: Int var isBookmarking: Bool }
  19. ϖʔδλΠτϧ ϖʔδαϒλΠτϧ ©2018 Wantedly, Inc. // ProjectReactor func mutate(action: Action)

    -> Observable<Mutation> { switch action { case .load: return projectRepository.project(id: currentState.projectId) .asObservable() .map(Mutation.setProject) } } func reduce(state: State, mutation: Mutation) -> State { var state = state switch mutation { case let .setProject(project): state.isBookmarking = project.bookmarked } return state }
  20. ©2018 Wantedly, Inc. Example 2 Bookmark event propagation Page Title

    Page Subtitle
  21. ϖʔδλΠτϧ ϖʔδαϒλΠτϧ ©2018 Wantedly, Inc.

  22. ϖʔδλΠτϧ ϖʔδαϒλΠτϧ ©2018 Wantedly, Inc. Reactor View Action State Reactor

    View Action State Event Stream
  23. ϖʔδλΠτϧ ϖʔδαϒλΠτϧ ©2018 Wantedly, Inc. Reactor View Action State Reactor

    View Action State Event Stream
  24. ϖʔδλΠτϧ ϖʔδαϒλΠτϧ ©2018 Wantedly, Inc. // ProjectRepository func bookmark(projectId: Int)

    -> Single<Void> { return provider.rx.request(.bookmark(projectId: projectId)) .filterSuccessfulStatusCodes() .map { _ in } .do(onSubscribe: { _ in ProjectEvent.stream.onNext( .updateBookmarking(projectId: projectId, isBookmarking: true) ) }) .do(onError: { _ in ProjectEvent.stream.onNext( .updateBookmarking(projectId: projectId, isBookmarking: false) ) }) }
  25. ϖʔδλΠτϧ ϖʔδαϒλΠτϧ ©2018 Wantedly, Inc. // ProjectReactor enum Action {

    case toggleBookmarking } func mutate(action: Action) -> Observable<Mutation> { switch action { case .toggleBookmarking: if currentState.isBookmarking { _ = projectRepository.unbookmark(projectId: currentState.projectId).subscribe() } else { _ = projectRepository.bookmark(projectId: currentState.projectId).subscribe() } return .empty() } }
  26. ϖʔδλΠτϧ ϖʔδαϒλΠτϧ ©2018 Wantedly, Inc. Reactor View Action State Reactor

    View Action State Event Stream
  27. ϖʔδλΠτϧ ϖʔδαϒλΠτϧ ©2018 Wantedly, Inc. // ProjectCellReactor func transform(mutation: Observable<Mutation>)

    -> Observable<Mutation> { let projectId = currentState.projectId let fromProjectEvent = ProjectEvent.stream .flatMap { event -> Observable<Mutation> in switch event { case let .updateBookmarking(id, isBookmarking): return id == projectId ? .just(.setBookmarking(isBookmarking)) : .empty() } } return Observable.merge(mutation, fromProjectEvent) } func reduce(state: State, mutation: Mutation) -> State { var state = state switch mutation { case let .setBookmarking(isBookmarking): state.isBookmarking = isBookmarking } return state }
  28. ©2018 Wantedly, Inc. Example 3 Company page Page Title Page

    Subtitle
  29. ϖʔδλΠτϧ ϖʔδαϒλΠτϧ ©2018 Wantedly, Inc.

  30. ϖʔδλΠτϧ ϖʔδαϒλΠτϧ ©2018 Wantedly, Inc. Company Home Posts Info Projects

    Employees
  31. ϖʔδλΠτϧ ϖʔδαϒλΠτϧ ©2018 Wantedly, Inc. Company Home Posts Info Projects

    Employees
  32. ϖʔδλΠτϧ ϖʔδαϒλΠτϧ ©2018 Wantedly, Inc. Company Home Posts Info Projects

    Employees Event Stream Reactor View Action State Reactor View Action State
  33. ©2018 Wantedly, Inc. Complicated state management is possible Covers most

    use cases ReactorKit is powerful, therefore
  34. ©2018 Wantedly, Inc. ReactorKit is simple and powerful Page Title

    Page Subtitle
  35. ©2018 Wantedly, Inc. I can wholeheartedly recommend it! Page Title

    Page Subtitle
  36. None