Connection
public class Connection<State, Props, Actions> : StoreSubscriber where State : StateType
A ReRxSwift Connection that manages the mapping between ReSwift application state and ReSwift actions on the one hand, and view controller props and actions on the other hand.
In order to use this, you have to make your view controller conform to
Connectable and add a Connection instance. In your view controller
you need to call connect() and disconnect() at the right time.
Examples
The folder Example
contains example of how to use this.
Usage
Create an extension to your view controller to make it
Connectable, defining thePropsandActionsthat your view controller needs:extension MyViewController: Connectable { struct Props { let text: String } struct Actions { let updatedText: (String) -> Void } }Define how your state is mapped to the above
Propstype:private let mapStateToProps = { (appState: AppState) in return MyViewController.Props( text: appState.content ) }Define the actions that are dispatched:
private let mapDispatchToActions = { (dispatch: @escaping DispatchFunction) in return MyViewController.Actions( updatedText: { newText in dispatch(SetContent(newContent: newText)) } ) }Define the connection and hook it up:
class MyViewController: UIViewController { @IBOutlet weak var textField: UITextField! let connection = Connection( store: store, mapStateToProps: mapStateToProps, mapDispatchToActions: mapDispatchToActions ) override func viewWillAppear(_ animated: Bool) { super.viewWillAppear(animated) connection.connect() } override func viewDidDisappear(_ animated: Bool) { super.viewDidDisappear(animated) connection.disconnect() } }Bind the text field’s text, using a Swift 4 key path to refer to the
textproperty ofProps:override func viewDidLoad() { super.viewDidLoad() connection.bind(\Props.text, to: textField.rx.text) }Call the action:
@IBAction func editingChanged(_ sender: UITextField) { actions.updatedText(sender.text ?? "") }
-
The RxSwift
BehaviorRelaythat holds your view controller props. Normally you don’t use this this directly, you use it throughConnectable.propsinstead. This variable is public so that you can use it for unit testing. In cases where you don’t want to use thebind(_:to:)methods in this class and want to create your own RxSwift observing code, you do need to use this variable directly.Declaration
Swift
public let props: BehaviorRelay<Props> -
This holds you view controller’s actions. Don’t use this directly, use
Connectable.actionsinstead. This variable is public so that you can use it for unit testing.Declaration
Swift
public var actions: Actions! -
The ReSwift store used by this connection object. Normally you pass your global app store as a parameter to the constructor. This variable is public so that you can inject a different store during unit testing. It is not intended to be used directly from production code.
Declaration
Swift
public var store: Store<State> { get set } -
RxSwift memory management.
Declaration
Swift
public let disposeBag: DisposeBag -
Constructs a new
Connectionobject. For examples see the class documentation above, or the code examples inSimpleTextFieldViewControllerandSteppingUpViewController.Declaration
Swift
public init(store: Store<State>, mapStateToProps: @escaping (State) -> (Props), mapDispatchToActions: @escaping (@escaping DispatchFunction) -> (Actions) )Parameters
storeYour application’s global store.
mapStateToPropsA mapping function that takes the global application state, and maps it into a view controller specific structure
Connectable.props. Whenever a new state comes in from your ReSwift store, the connection calls this function to map it to theConnectable.propsneeded by your view controller.mapDispatchToActionsA mapping function that specifies which ReSwift action needs to be dispatched when your view controller calls its
Connectable.actions. -
“Activates” the connection in the sense that it subscribes to the store so that store updates are received and can be processed. Failing to call this method will mean that your view controller does not get new
Connectable.propswhen the global state changes. Call this method from your view controller’sviewWillAppear()orviewDidAppear().Declaration
Swift
public func connect() -
“Deactivates” the connection: unsubscribes from the store so that state updates are no longer processed for your view controller. Call this method from your view controller’s
viewWillDisappear()orviewDidDisappear().Declaration
Swift
public func disconnect() -
ReSwift’s callback method. Don’t call this yourself.
Declaration
Swift
public func newState(state: State)
-
Undocumented
Declaration
Swift
public func propsEntry<T>(at keyPath: KeyPath<Props, T>, isEqual: @escaping (T,T) -> Bool) -> Observable<T>
-
Bind a RxSwift observer to one of your
Connectable.propsentries. Convenience method forbind(keyPath, to: observer, mapping: nil).Declaration
Swift
public func bind<T: Equatable, O>(_ keyPath: KeyPath<Props, T>, to observer: O) where O: ObserverType, O.Element == T?Parameters
keyPathSwift 4
KeyPaththat points to the entry in your view controllersConnectable.propsthat you want to bind.observerThe RxSwift observer that you want to bind to.
-
Bind a RxSwift observer to one of your
Connectable.propsentries.All
bind()functions are variants of the following basic implementation:self.props .asObservable() .distinctUntilChanged { $0[keyPath: keyPath] == $1[keyPath: keyPath] } .map { $0[keyPath: keyPath] } .map(mapping) // if not nil .bind(to: binder) .disposed(by: disposeBag)Declaration
Swift
public func bind<T: Equatable, O, M>(_ keyPath: KeyPath<Props, T>, to observer: O, mapping: ((T)->M)? = nil) where O: ObserverType, O.Element == M?Parameters
keyPathSwift 4
KeyPaththat points to the entry in your view controllersConnectable.propsthat you want to bind.observerThe RxSwift observer that you want to bind to.
mappingAn optional function that takes the entry in your
Connectable.propsand converts it to the thing needed by the observable. This is useful if yourConnectable.propsentry is a different type that needs to be converted before it can be put into the observer, for example converting aFloatinto aStringso that it can be put in a text field’stext.
-
Subscribe to one of your
Connectable.propsentries, having a closure called whenever it changes. Variant for non-optional entries.Declaration
Swift
public func subscribe<T: Equatable>(_ keyPath: KeyPath<Props, T>, onNext: @escaping (T)->())Parameters
keyPathSwift 4
KeyPaththat points to the entry in your view controllersConnectable.propsthat you want to subscribe to.onNextThe closure that is called whenever the entry at the given key path changes. The new value is passed into the closure as a parameter.
-
Bind a RxSwift observer to one of your
Connectable.propsentries. Convenience method forbind(keyPath, to: observer, mapping: nil).Declaration
Swift
public func bind<T: Equatable, O>(_ keyPath: KeyPath<Props, T>, to observer: O) where O: ObserverType, O.Element == TParameters
keyPathSwift 4
KeyPaththat points to the entry in your view controllersConnectable.propsthat you want to bind.observerThe RxSwift observer that you want to bind to.
-
Bind a RxSwift observer to one of your
Connectable.propsentries.All
bind()functions are variants of the following basic implementation:self.props .asObservable() .distinctUntilChanged { $0[keyPath: keyPath] == $1[keyPath: keyPath] } .map { $0[keyPath: keyPath] } .map(mapping) // if not nil .bind(to: binder) .disposed(by: disposeBag)Declaration
Swift
public func bind<T: Equatable, O, M>(_ keyPath: KeyPath<Props, T>, to observer: O, mapping: ((T)->M)? = nil) where O: ObserverType, O.Element == MParameters
keyPathSwift 4
KeyPaththat points to the entry in your view controllersConnectable.propsthat you want to bind.observerThe RxSwift observer that you want to bind to.
mappingAn optional function that takes the entry in your
Connectable.propsand converts it to the thing needed by the observable. This is useful if yourConnectable.propsentry is a different type that needs to be converted before it can be put into the observer, for example converting aFloatinto aStringso that it can be put in a text field’stext.
-
Subscribe to one of your
Connectable.propsentries, having a closure called whenever it changes. Variant for non-optional entries.Declaration
Swift
public func subscribe<T: Equatable>(_ keyPath: KeyPath<Props, [T]>, onNext: @escaping ([T])->())Parameters
keyPathSwift 4
KeyPaththat points to the entry in your view controllersConnectable.propsthat you want to subscribe to.onNextThe closure that is called whenever the entry at the given key path changes. The new value is passed into the closure as a parameter.
-
Bind a RxSwift observer to one of your
Connectable.propsentries.Declaration
Swift
public func bind<S: Sequence,M>(_ keyPath: KeyPath<Props, S>, to binder: (Observable<M>) -> Disposable, mapping: ((S)->M)? = nil) where S.Element: EquatableParameters
keyPathSwift 4
KeyPaththat points to the entry in your view controllersConnectable.propsthat you want to bind.binderThe RxSwift binder function such as used by
UICollectionView.rx.itemsandUITableView.rx.items.
View on GitHub
Connection Class Reference