Git Product home page Git Product logo

reactiveobjcbridge's Introduction

ReactiveObjCBridge

After the announcement of Swift, ReactiveCocoa was rewritten in Swift. This framework creates a bridge between those Swift and Objective-C APIs (now known as ReactiveSwift and ReactiveObjC respectively).

Because the APIs are based on fundamentally different designs, the conversion is not always one-to-one; however, every attempt has been made to faithfully translate the concepts between the two APIs (and languages).

The bridged types include:

  1. RACSignal and SignalProducer or Signal
  2. RACCommand and Action
  3. RACScheduler and SchedulerType
  4. RACDisposable and Disposable

For the complete bridging API, including documentation, see ObjectiveCBridging.swift.

RACSignal and SignalProducer or Signal

In ReactiveSwift, “cold” signals are represented by the SignalProducer type, and “hot” signals are represented by the Signal type.

“Cold” RACSignals can be converted into SignalProducers using the SignalProducer initializer:

extension SignalProducer where Error == Swift.Error {
	public init<SignalValue>(_ signal: RACSignal<SignalValue>) where Value == SignalValue?
}

“Hot” RACSignals cannot be directly converted into Signals, because any RACSignal subscription could potentially involve side effects. To obtain a Signal, use RACSignal.toSignalProducer followed by SignalProducer.start, which will make those potential side effects explicit.

For the other direction, use the bridged property.

When invoked on a SignalProducer, these functions will create a RACSignal to start() the producer once for each subscription:

extension SignalProducerProtocol where Value: AnyObject {
	public var bridged: RACSignal<Value>
}

extension SignalProducerProtocol where Value: OptionalProtocol, Value.Wrapped: AnyObject {
	public var bridged: RACSignal<Value.Wrapped>
}

When invoked on a Signal, these methods will create a RACSignal that simply observes it:

extension SignalProtocol where Value: AnyObject {
    public var bridged: RACSignal<Value.Wrapped> {
}

extension SignalProtocol where Value: OptionalProtocol, Value.Wrapped: AnyObject {
    public var bridged: RACSignal<Value.Wrapped> {
}

RACSignals of numbered tuples can be bridged to SignalProducers of Swift tuples with a special initializer, init(bridging:):

extension SignalProducer where Error == Swift.Error {
	public init<First>(bridging tupleSignal: RACSignal<RACOneTuple<First>>) where Value == First?
  public init<First, Second>(bridging tupleSignal: RACSignal<RACTwoTuple<First, Second>>) where Value == (First?, Second?)?
  public init<First, Second, Third>(bridging tupleSignal: RACSignal<RACThreeTuple<First, Second, Third>>) where Value == (First?, Second?, Third?)?
  public init<First, Second, Third, Fourth>(bridging tupleSignal: RACSignal<RACFourTuple<First, Second, Third, Fourth>>) where Value == (First?, Second?, Third?, Fourth?)?
  public init<First, Second, Third, Fourth, Fifth>(bridging tupleSignal: RACSignal<RACFiveTuple<First, Second, Third, Fourth, Fifth>>) where Value == (First?, Second?, Third?, Fourth?, Fifth?)?
}

RACCommand and Action

To convert RACCommands into the new Action type, use the Action initializer:

extension Action where Error == Swift.Error {
	public convenience init<CommandInput, CommandOutput>(
		_ command: RACCommand<CommandInput, CommandOutput>
	) where Input == CommandInput?, Output == CommandOutput?
}

To convert Actions into RACCommands, use the bridged instance method:

extension Action where Input: AnyObject, Output: AnyObject {
	public var bridged: RACCommand<Input, Output>
}

extension Action where Input: OptionalProtocol, Input.Wrapped: AnyObject, Output: AnyObject {
	public var bridged: RACCommand<Input.Wrapped, Output>
}

extension Action where Input: AnyObject, Output: OptionalProtocol, Output.Wrapped: AnyObject {
	public var bridged: RACCommand<Input, Output.Wrapped>
}

extension Action where Input: OptionalProtocol, Input.Wrapped: AnyObject, Output: OptionalProtocol, Output.Wrapped: AnyObject {
	public var bridged: RACCommand<Input.Wrapped, Output.Wrapped>
}

NOTE: The executing properties of actions and commands are not synchronized across the API bridge. To ensure consistency, only observe the executing property from the base object (the one passed into the bridge, not retrieved from it), so updates occur no matter which object is used for execution.

RACScheduler and SchedulerType

Any RACScheduler instance is automatically a DateSchedulerType (and therefore a SchedulerType), and can be passed directly into any function or method that expects one.

All Schedulers and DateSchedulers can be wrapped as a RACScheduler using the RACScheduler initializer:

extension RACScheduler {
	public convenience init(_ scheduler: Scheduler)
	public convenience init(_ scheduler: DateScheduler)
}

Note that wrapped Schedulers would behave like RACImmediateScheduler when deferred scheduling methods are used.

RACDisposable and Disposable

Any RACDisposable instance is automatically a Disposable, and can be used directly anywhere a type conforming to Disposable is expected.

Use the RACDisposable initializer to wrap an instance of Disposable:

extension RACDisposable {
	public convenience init(_ disposable: Disposable?)
}

Numbered RACTuples

Numbered (and typed) RACTuple subtypes, such as RACOneTuple, RACTwoTuple etc., can be bridged to native Swift tuples with a series of global functions:

public func bridgedTuple<First>(from tuple: RACOneTuple<First>) -> (First?)
public func bridgedTuple<First, Second>(from tuple: RACTwoTuple<First, Second>) -> (First?, Second?)
public func bridgedTuple<First, Second, Third>(from tuple: RACThreeTuple<First, Second, Third>) -> (First?, Second?, Third?)
public func bridgedTuple<First, Second, Third, Fourth>(from tuple: RACFourTuple<First, Second, Third, Fourth>) -> (First?, Second?, Third?, Fourth?)
public func bridgedTuple<First, Second, Third, Fourth, Fifth>(from tuple: RACFiveTuple<First, Second, Third, Fourth, Fifth>) -> (First?, Second?, Third?, Fourth?, Fifth?)

reactiveobjcbridge's People

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

reactiveobjcbridge's Issues

how to "value" parameter in ResultExtensions.swift of ReactiveSwift folder

I use the "ReactiveObjCBridge" master branch to pod install. But Recently, I just pod install without modify any version (still use master), found that the "value" parameter is changed to internal, so that I can not use it anymore. Could you please help to share what can I do then ?

Here is the old code sample:
guard let value = event.value else { return }

Any idea for this ? Thanks a lot.

`RACsignal.toSignalProducer()` unavailable

The README.md reads:

“Hot” RACSignals cannot be directly converted into Signals, because any RACSignal subscription could potentially involve side effects. To obtain a Signal, use RACSignal.toSignalProducer followed by SignalProducer.start, which will make those potential side effects explicit.

I have an instance of RACSignal due to a mixed-language project. Looking through XCode's auto-completion suggestions, I'm not seeing anything like toSignalProducer.

Could I get a code example of how to turn a RACSignal back to Signal?

Thanks!

ReactiveObjCBridge errors on Swift master; possibly add this repo to Swift source compat suite?

Hi there! A recent regression makes this repo fails to type check on Swift master: https://bugs.swift.org/browse/SR-7341. It's still not fixed, and it's unclear whether or not this will be fixed. I suppose this is more of a PSA, but there are some possible next steps:

  1. Change the name of one of the isEnabled properties in question (not ideal).
  2. If you feel so inclined, contribute a patch to Swift that fixes the regression or help find someone who can do so.
  3. Figure out how to add this repo to https://github.com/apple/swift-source-compat-suite

This last step would help both prevent issues and the future and raise more awareness about the current issue. Given the dependencies in this repo, I think a separate repo would need to be opened by the maintainers (part of the "Have maintainers who will commit to resolve issues in a timely manner" requirement of that suite) that includes all of the dependencies in a single project.

Thanks for your time and consideration!

Add support for bridging tuples to/from generic RACTuples

I'm not sure how useful this would end up being nor how much can actually be done given the constraints involved (such as the impossibility to know at runtime how many elements a Swift tuple holds, etc.).

However, I thought I'd have a look to see what could be done. If I finish anything that looks reasonable, I'll create a pull request.

Being able to bridge a RACTwoTuple<NSString, NSNumber> into (NSString, NSNumber) would be quite useful. For instance when we have bridged our RACSignal<RACTwoTuple<NSString, NSNumber>> (do we actually retain nested types like this? I'm not sure) to a SignalProducer<RACTwoTuple<NSString, NSNumber>, NSError>, it'd make it easy to map that to get a SignalProducer<(NSString, NSNumber), NSError>.

Being able to turn a (String, Bool) into a RACTwoTuple<NSString, NSNumber> would also be useful when bridging to RACSignal.

Cocoa pods spec has not been updated

Hello. The released version contains outdated podspec files, as far as CocoaPods do not know anything about version 5.0.0: the master repo still refers to 4.0.0 version. It would be great to have both up-to-date

Xcode 10 broken

extension Action { fileprivate var isEnabled: RACSignal<NSNumber> { return self.isEnabled.producer.map { $0 as NSNumber }.bridged } }

Gives error: Value of type 'RACSignal<NSNumber>' has no member 'producer'

carthage update fails

carthage update fails on Xcode10.2.

ReactiveSwift/Sources/Scheduler.swift:187:18: error: 'Hashable.hashValue' is deprecated as a protocol requirement; conform type 'DispatchSourceTimerWrapper' to 'Hashable' by implementing 'hash(into:)' instead
        fileprivate var hashValue: Int {
                        ^

** ARCHIVE FAILED **

Probably need ReactiveSwift 5.0 dependency.

Ready for a release yet?

I'm going through some of my Cartfiles and noticed that this repo still doesn't have a release tag set yet. Is there anything that we're waiting on before throwing a 1.0.0 on this?

Can't use as static library

With cocoapods 1.5.2 I am getting the error:


The Swift pod `ReactiveObjCBridge` depends upon `ReactiveObjC`, which do not define modules. To opt into those targets generating module maps (which is necessary to import them from Swift when building as static libraries), you may set `use_modular_headers!` globally in your Podfile, or specify `:modular_headers => true` for particular dependencies.```

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.