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

カッコ悪くリアクティブじゃダメですか?

0d04162c7a3c2907c059a06dbcd23cf4?s=47 tokorom
April 13, 2016

 カッコ悪くリアクティブじゃダメですか?

レガシーな既存プロジェクトへのRxSwift導入事例

0d04162c7a3c2907c059a06dbcd23cf4?s=128

tokorom

April 13, 2016
Tweet

Transcript

  1. Χοίѱ͘ ϦΞΫςΟϒ ͡ΌμϝͰ͔͢ʁ ॴ ༑ଠ @tokorom iOS App Programer Reactive

    Swift Meetup
  2. ॴ༑ଠ @tokorom ɾϑϦʔλʔ ɾΧοίѱ͍ϦΞΫςΟϒ෩ϓϩάϥϚ ɾpotatotipsӡӦ૭ޱʢओ࠵ऀ͞Μ͍ͭ΋ืूதʣ

  3. ΧοίΠΠ ϦΞΫςΟϒϓϩάϥϛϯά FRP RxSwift ReSwift Redux Flux

  4. ʢ࣭໰ʣ •͓࢓ࣄͰ͸ɺطଘϓϩδΣΫτͷόʔδϣϯΞο ϓ͕ϝΠϯʁ •൒೥ʹҰճ͘Β͍৽نϓϩδΣΫτʹθϩ͔Β ܞΘΕΔ޾ͤऀʁ

  5. ΅͘ͷϦΞΫςΟϒϓϩάϥϛϯάʁ •ϓϩδΣΫτ։࢝࣌͸͘͝ී௨ͷMVCߏ੒ •όʔδϣϯΞοϓ࣌ʹϦΞΫςΟϒϓϩάϥϛ ϯά༻ϥΠϒϥϦಋೖ •ϦϦʔεؒࡍʹύϑΥʔϚϯε໰୊ൃ֮ •RxSwiftʹࠩ͠ସ͑ •ݱঢ়ɺ҆ఆಈ࡞ •ؾʹೖͬͯΔ

  6. ී௨ͷMVCߏ੒ •ModelManager UserManager TopicManager XXXManager XXXViewController XXXViewController

  7. ී௨ͷMVCߏ੒ •ModelManager UserManager TopicManager XXXManager XXXViewController XXXViewController XXXManager໋໊ͬͯͲ͏ͳͷ !?

  8. ී௨ͷMVCߏ੒ •ModelManager UserManager TopicManager XXXManager XXXViewController XXXViewController Topic Topic Topic

  9. ී௨ͷMVCߏ੒ •ModelManager UserManager TopicManager XXXManager XXXViewController XXXViewController Topic Topic Topic

  10. class Topic { let identifier: String var title: String? var

    isHearted: Bool } Modelͷߋ৽Λ؂ࢹ •೰Μͩ݁Ռ -> ModelΛ௚઀ KVO class Topic: NSObject { let identifier: String dynamic var title: String? dynamic var isHearted: Bool } ग़ͨʔʂ Swift࣌୅ʹ NSObjectʂ
  11. topic.rx_observe(Bool.self, "isHearted") .subscribeNext { [weak self] in self?.heartButton?.selected = $0

    ?? false } //.addDisposableTo(disposeBag) Modelͷߋ৽Λ؂ࢹ •؂ࢹଆαϯϓϧʢViewʣ ͑ͬ!? ViewModel ͸?
  12. Θ͍Θ͍ ϦΞΫςΟϒ ϓϩάϥϛϯά ͩͬʂʂʂ ͜Ε͸ ϦΞΫςΟϒ ϓϩάϥϛϯά ͳͷʂʁ

  13. KVO + αʁ •΍͍ͬͯΔ͜ͱݟฦͨ͠ΒɺͨͩKVOͰViewͱ ModelΛόΠϯσΟϯάͯ͠Δ͚ͩ •debounce ͱ͔ distinctUntilChanged ͱ͔ Rxతศརػೳ΋͋ΔͷͰRxSwift࢖͏ํָ͕͸ָ

    •Ͱ΋໾ʹཱͭͳΒͦΕͰྑ͍ʁ ͳΜ͔Χοίѱ͍͚ͲͶ
  14. ໾ʹཱͭʢ۩ମతʹ͸ʁʣ •όά͕ݮΔ? ɹ=> ݮͬͨʂ •࣮૷ָ͕ʹͳΔ? => ָʹͳͬͨʂ

  15. ࣮ࡍʹྑ͍ޮՌ͕͋ͬͨͱ͜Ζ •ࢄΒ͹ΔὑͪΌΜ໰୊ͷղܾ •௨৴઀ଓ෮׆͞Μ໰୊ͷղܾ

  16. ࢄΒ͹ΔὑͪΌΜ໰୊ •ৄࡉը໘Ͱὑͯ͠Ϧετը໘ʹ໭ͬͨΒʁ

  17. ࢄΒ͹ΔὑͪΌΜ໰୊ •ϕλͳ࣮૷ •viewWillAppear + visibleCellsͰὑ͞Ε͍ͯΔ͔ νΣοΫ •cellForRowAtIndexPathͰὑ͞Ε͍ͯΔ͔νΣοΫ •willDisplayCellͰὑ͞Ε͍ͯΔ͔νΣοΫ

  18. ࢄΒ͹ΔὑͪΌΜ໰୊ •ὑ͢Δ௨৴தʹը໘ભҠͪ͠ΌͬͨΒʁ

  19. ࢄΒ͹ΔὑͪΌΜ໰୊ •ϕλͳ࣮૷ •௨৴੒ޭ࣌ʹNSNotificationͰ௨஌͢Δʁ

  20. ࢄΒ͹ΔὑͪΌΜ໰୊ •RxSwiftͳΒͳʹ΋ߟ͑ͳ͍͍ͯ͘ topic.rx_observe(Bool.self, "isHearted") .subscribeNext { [weak self] in self?.heartButton?.selected

    = $0 ?? false } //.addDisposableTo(disposeBag) ܁Γฦ͚͢ͲɺͨͩͷKVO͔ͩΒͶ
  21. ௨৴઀ଓ෮׆͞Μ໰୊ •௨৴ΤϥʔͰίϯςϯπະऔಘͷ͚࣌ͩɺ௨৴ ઀ଓ෮׆ޙʹίϯςϯπ࠶औಘ͍ͨ͠

  22. ௨৴઀ଓ෮׆͞Μ໰୊ •ϕλͳ࣮૷ •௨৴઀ଓ෮׆ΛNSNotificationͳͲͰϋϯυϦϯά •ͦͷͱ͖ίϯςϯπऔಘࣦഊޙͰɺ͔ͭɺطʹ௨৴ தͰͳ͚Ε͹௨৴Λ࠶౓૸ΒͤΔ •։ൃ͍ͯ͠Δͱ͞Βʹ৚͕݅ՃΘͬͯ͘Δ •௨৴։࢝ͷτϦΨʔͱ৚͕݅͹Β͚ͯ൥ࡶʹͳΓ͕ ͪ

  23. ௨৴઀ଓ෮׆͞Μ໰୊ •RxSwiftͳΒҰݩ؅ཧͰ͖Δ let a = Reachability.rx_reachable.asObservable() let b = rx_contentState.asObservable()

    Observable.combineLatest(a, b) { ($0, $1) } .filter { reachable, contentState in reachable && contentState == .Unload } .subscribeNext { [weak self] _ in self?.reloadDataIfNeeded() }
  24. ϦΞΫςΟϒ෩ϓϩάϥϛϯά Ͱ΋ޮՌ͋Γͦ͏ :) Ͱ΋Χοίѱ͍͚ͲͶ

  25. Χοίѱࣦ͘ഊͨ͠ͱ͜Ζ •উखʹߋ৽ͪΌΜ໰୊ •εΫϩʔϧ͔͔ͬ͘͘Μ໰୊

  26. উखʹߋ৽ͪΌΜ໰୊ •ͱ͋Δը໘Λ։͍ͨޙʹҙਤͤͣ಺༰͕มΘΔ

  27. উखʹߋ৽ͪΌΜ໰୊ •͜ͷྫ͸୯ʹόΠϯσΟϯά͕ෆద੾ͳ͚ͩ •ϓϩΞΫςΟϒ →ϦΞΫςΟϒͳΒͰ͸ͷෆ۩ ߹͕͋Δ͜ͱ͸͋Δ •ͨͩ͠ϓϩΞΫςΟϒΦϯϦʔͷ࣌ͷෆ۩߹ͷ ΄͏͕ଟ͍

  28. εΫϩʔϧ͔͔ͬ͘͘Μ໰୊ •͍͟ಈ͔ͯ͠ΈͨΒύϑΥʔϚϯεѱ͍ •UICollectionViewCellʹରͯ͠εΫϩʔϧͷ౓ʹ όΠϯσΟϯάͷॲཧ͕૸ΔͨΊ •͜Ε͕ղܾͰ͖ͳͯ͘RxSwiftΛಋೖͨ͠ΒͳΜ ͱ͔ͳͬͨ

  29. εΫϩʔϧ͔͔ͬ͘͘Μ໰୊ •ར༻͢ΔϥΠϒϥϦ΍࣮૷ͷ͔ͨ͠ʹΑͬͯม Θͬͯ͘ΔͷͰࣄલʹςετ •ྫ͑͹ࠜݩ͸ࣗ෼ͷ޷͖ͳ࣮૷ʹͯ͠ɺόΠϯ σΟϯάͷͱ͜Ζ͚ͩSwiftBondΛར༻͢Δͱ ͍ͬͨղܾͷํ๏΋ߟ͑ΒΕΔ

  30. ࣮ࡍʹϓϩδΣΫτͰ࢖ͬͯΈͯͷॴײ •࣮૷͕γϯϓϧʹͳͬͨ •ಛʹෳ਺ͷλΠϛϯά΍৚݅ʹΑΓ࣮ߦ͢΂͖ॲཧ •ෆ۩߹͕50%Ҏ্ݮ͍ͬͯΔͷͰ͸ʢମײʣ •ࠓޙɺϦΞΫςΟϒͳ࣮૷Λ࢖Θͳ͍͜ͱ͸ߟ ͑ͮΒ͍

  31. Χοίѱ͘ ϦΞΫςΟϒ ͡ΌμϝͰ͔͢ʁ

  32. มΘ͍ͬͯ͘͜ͱ •ઈࢍਐԽத •ReactKit / SwiftBond / RxSwift •The Evolution of

    Flux Framework (2015೥5݄ʣ •SwiftFlux / Swift Flow / ReduxKit / ReSwift •̍೥ޙʹ͸·ͩݟ͵ϥΠϒϥϦ࢖ͬͯΔʁ •RxSwift͸ྑ͍ײ͡ʹރΕ͖ͯͯΔ͔΋
  33. ΩʔϫʔυͷτϨϯυ •MVVM •React / Flux / Redux •ϨΨγʔͳModelManager + KVO

    ʹࣅͯΔʁ
  34. มΘΒͳ͍͜ͱ •ϦΞΫςΟϒͷ༗༻ੑ •ϓϩΞΫςΟϒͷ༗༻ੑ

  35. ऄ଍ •KVOͱ͔ݹ͍࢓૊Έʁ࢖͏ͷͬͯͲ͏ͳͷʁ •ΠϯλʔϑΣʔεͳͲ͸͔֬ʹݹ͍͕ར༻͢Δ ͷ͸ѱ͘ͳ͍ͷͰ͸ •ͨͩɺiOS͕ඪ४Ͱඋ͑Δ΋ͷͰ།Ұແೋͳϝ Ϧοτ͕͋ͬͨΓ͢Δ •ϥοϐϯάͳͲͯ͠ར༻͢Δ͜ͱͰΠϯλʔ ϑΣʔεͷ໰୊͸؇࿨Ͱ͖Δ෦෼΋͋Δ

  36. KVO •ίϯύΠϧ࣌ʹ͸keyPathޡΓΛൃݟͰ͖ͳ͍ •ղܾํ๏͸͋ΔͩΖ͏͚Ͳ… •࣮ߦ࣌ʹ͸Exception͕ൃੜ͢Δ: addObserver:<RxCocoa.KVOObserver 0x7f8133b500b0> forKeyPath:@"hoge" options: 5 context:0x0]

    … •ύϑΥʔϚϯε͸ྑ͘লϝϞϦ
  37. sendAction (Responder Chain) •RxSwiftʹ૊Έࠐ·Εͯ͸͍ͳ͍͕ϥοϐϯά͠ ͯར༻͢Ε͹ϝϦοτ͕ग़ͯ͘Δ͔΋͠Εͳ͍ʁ

  38. UIApplication - sendAction NEW! iOS 9 Ͱ ྲྀ੕ ͷ͝ͱ͘ݱΕͨ ࠷ڧ

    ͷ function !?
  39. UIApplication - sendAction iPhone OS 2 ͔Β ͘͝ ී௨ ʹଘࡏ͢Δ

    ͋·Γ ࢖ΘΕͳ͍ ΍ͭ
  40. Responder Chain (in UIKit) •Ԟ·ͬͨ֊૚ͰൃՐ •֊૚ͷͲ͜Ͱ΋ड͚ΒΕΔ •DelegateͷΑ͏ʹreceiverΛड͚ ౉͢ඞཁ͕ͳ͍ •ଞखஈͰಉ͡ߏ଄Λ࣮ݱ͢Δͷ͸ ೉͍͠

  41. Responder Chain (in UIKit) UITabBarController UIViewController UITabBarController UIViewController UIViewController UIViewController

    UITableView UITableViewCell UIView UIButton
  42. sendActionͷμϝͳͱ͜Ζ •ΠϯλʔϑΣʔε͕ݹ͍ •Selector(จࣈྻ)ࢦఆ •ܾ·ͬͨҾ਺ͷϝιουͰ͔͠௨஌Λड͚ΒΕ ͳ͍ •ಛఆͷObjectΛ౉ͮ͠Β͍

  43. sendAction + Rx // HogeΛ؂ࢹ self.rx_action(Int.self, .Hoge) .subscribeNext { NSLog("context:

    \($0 ?? 0)") //< 100 } //.addDisposableTo(disposeBag) // HogeΛൃՐ self.sendActionForKey(.Hoge, context: 100)
  44. ·ͱΊ •ϨΨγʔͳϓϩδΣΫτʹϦΞΫςΟϒͳཁૉ ΛऔΓೖΕΔͷ΋ҙ֎ͱ؆୯ˍҰఆҎ্ͷޮՌ ͕ݟࠐΊΔ •KVOͳͲݹ͖ྑ͖࢓૊Έ΋৔߹ʹΑͬͯ͸༗༻ ͳબ୒ࢶ

  45. Χοίѱ͘ ϦΞΫςΟϒ ͡ΌμϝͰ͔͢ʁ μϝ͡Όͳ͍ͬ!!

  46. More Information Yuta ToKoRo iOS App Programer Twitter @tokorom http://www.tokoro.me/