Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[0.40] Warning: Swift Projects Fail #11572

Closed
sjmueller opened this issue Dec 20, 2016 · 12 comments
Closed

[0.40] Warning: Swift Projects Fail #11572

sjmueller opened this issue Dec 20, 2016 · 12 comments
Labels
Resolution: Locked This issue was locked by the bot.

Comments

@sjmueller
Copy link
Contributor

With the new changes in e1577df and 59407f3, header references have been changed from quotes to angle brackets. While this may work in an Obj-C project, it causes several compilation errors for swift projects.

Previously to 0.40, you could create a new swift project and perform the following steps to compile successfully:

  • add the -all_load and -lc++ linker flags
  • add react native dir (recursively) to Header Search Paths
  • setup your bridging header

Full steps for swift setup details can be seen here.

Now according to the summary in update 59407f3:

$(BUILT_PRODUCTS_DIR)/include, which is added to the include path by Xcode by default

The above statement implies that customizing Header Search Paths is no longer necessary, but is this true for Swift? In fact it seems there's no longer any straightforward way for Swift projects to find these angle bracket headers when libraries are included directly in the project (not using cocoapods), similar to what has been detailed on stack overflow. In addition to Header Search Paths, I've tried User Header Search Paths and setting Always Search User Paths to Yes. No combination thus far yields successful compilation, instead throwing these errors:

image

Why is this change being made? I've been using swift with RN successfully since the very beginning, and now there is risk of not being able to upgrade without jumping through hoops (i.e. npm post install scripts to rewrite headers). Please don't introduce such a breaking change unless there's a verified way of supporting swift!

@robhogan
Copy link
Contributor

robhogan commented Dec 22, 2016

As far as I can tell master is effectively broken at the moment, even for simple Obj-C projects created with react-native init. Certainly it seems to break compatibility with nearly all third-party native code.

react-native init foo --version=react-native@facebook/react-native#59276468f289adfec418768366086882453878ea
cd foo
yarn add react-native-vector-icons
react-native link
react-native run-ios

Fails due to redefinitions, because react-native-vector-icons (and pretty much any other native extension) uses the quote style to include RCT headers, so anything they include (eg "RCTLog.h") get included twice -> redefinition errors.

0.40.0-rc.2 (which has e1577df but not 59407f3) fails because headers can't be found - I think that's because third-party libraries pick up RCT headers as user headers, which in turn try to include more RCT headers as library headers, but then they're not found (because the third-party lib doesn't have the proper dependency on React? Not sure).

Edit: I've just noticed the discussion on e1577df . Looks like this one's going to be painful.

@robhogan
Copy link
Contributor

@sjmueller I'd be interested to know if #11614 helps you.

@robhogan
Copy link
Contributor

@sjmueller I've just given Swift a try, and I had success with the latest master if I use #import <React/RCTRootView.h> etc in all of my bridging header imports (rather than a quote style), and have [js root]node_modules/react-native/React recursive in my header search paths.

@sjmueller
Copy link
Contributor Author

@rh389 I tried latest, but still getting errors. Can you outline how to reproduce your success? Keep in mind I'm trying to start from a fresh swift project, rather than using swift files inside the Obj-C project that's create with react-native-init.

@sjmueller
Copy link
Contributor Author

Did you mean latest master with your #11614 PR applied?

@robhogan
Copy link
Contributor

robhogan commented Dec 25, 2016

Sure. And nope, I didn't mean with the PR applied, although if you do have the PR applied it's possible to continue to use a quote style in your bridging header's imports. Below works without my PR:

  1. Create a new single page Swift app with the Xcode wizard.
  2. In the project root: yarn cache clean && yarn add react-native@facebook/react-native#master
  3. Add node_modules/react-native/React/React.xcodeproj to 'Linked frameworks and libraries'
  4. Add libReact.a (iOS target, not TV) to 'Linked frameworks and libraries'
  5. Add a dummy objective C file to get Xcode to prompt about a bridging header. Create the bridging header and delete the dummy file. (Or create a bridging header manually)
  6. Add #import <React/RCTRootView.h> (and whatever other headers you need - but use that format) to your bridging header.
  7. Add -lc++ to Other linker flags in your project's build settings. It should build fine at this point.
  8. Modify your AppDelegate.swift in the usual way. You should be able to use RCTRootView() without errors and without #importing anything except in your bridging header.

I haven't gone through step 8 myself, but I've pushed the rest up here: https://github.com/rh389/react-native-swift-template.

I haven't needed to touch header search paths here because node_modules is underneath the Xcode project's root directory. If it's outside (e.g. you've got your Xcode project under an ios subdirectory) you'll need to add a recursive header search path to node_modules/react-native/React. Edit: Actually, it doesn't seem to matter where react-native is installed as you're only using angle bracket includes and React is linked as a framework.

HTH🎄

@sjmueller
Copy link
Contributor Author

sjmueller commented Dec 25, 2016

@rh389 just came to say I had success starting from scratch and using the similar steps you outlined above. I'll also mention some extra info for anyone else trying to get get swift 3 running end to end:

6a. In addition, include #import <React/RCTBundleURLProvider.h> to get the minimum needed to get the app launched successfully.

7a. Add -all_load in addition to -lc++ to avoid runtime error [error][tid:com.facebook.react.JavaScript] Native module cannot be null. and 'NSInvalidArgumentException', reason: '-[RCTRootView reactTag]: unrecognized selector sent to instance

8a. Example Swift 3 code as a drop-in to AppDelegate.swift:

    func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool {
        let jsCodeLocation: URL
        
        jsCodeLocation = RCTBundleURLProvider.sharedSettings().jsBundleURL(forBundleRoot: "index.ios", fallbackResource:nil)
        let rootView = RCTRootView(bundleURL: jsCodeLocation, moduleName: "YOUR_PROJECT_NAME", initialProperties: nil, launchOptions: launchOptions)
        let rootViewController = UIViewController()
        rootViewController.view = rootView
        
        self.window = UIWindow(frame: UIScreen.main.bounds)
        self.window?.rootViewController = rootViewController
        self.window?.makeKeyAndVisible()
        
        return true
    }
  1. Add the following to Info.plist to ensure RN can load your bundle from package server:
    <key>NSAppTransportSecurity</key>
    <dict>
        <key>NSAllowsArbitraryLoads</key>
        <true/>
    </dict>

@robhogan
Copy link
Contributor

Cheers for fleshing that out, glad you got it working.

I think you'll still have problems with any third-party libs that import anything you've already imported, unfortunately, until either they're updated or something like #11614 is merged.

@sjmueller
Copy link
Contributor Author

I just found out that we still have problems, in both 0.40 rc0 and latest master. While the steps above do get you a build that works, unfortunately once someone else clones from source control, thefile not found problems resurface.

The only solution I know of is to remove all of the core react libs from Linked Frameworks and Libraries except for libReact.a. Then build the project successfully, and finally add back all the libraries you just removed:

image

What a pain! It seems that xcode is getting confused because of not building the react project first, which results in all the other dependent projects failing left and right.

@robhogan
Copy link
Contributor

You'll probably want to make React the first target and disable build parallelisation to ensure that it's built first, See @SandroMachado's comment at #11721 (comment).

@vongohren
Copy link

vongohren commented Feb 2, 2017

Have any RN core developer made any comments about that they want to focus on swift support? So this doesnt keep happening? Or if there is any updates in the near future that fixes this?

We are currently looking at RN to be our platform, but we are very interested in using swift with cocoapods. And this issue here has made us stop at version 0.38 so far. But we would really see that we were at the newest version.

vongohren referenced this issue Feb 2, 2017
Summary:
To make React Native play nicely with our internal build infrastructure we need to properly namespace all of our header includes.

Where previously you could do `#import "RCTBridge.h"`, you must now write this as `#import <React/RCTBridge.h>`. If your xcode project still has a custom header include path, both variants will likely continue to work, but for new projects, we're defaulting the header include path to `$(BUILT_PRODUCTS_DIR)/usr/local/include`, where the React and CSSLayout targets will copy a subset of headers too. To make Xcode copy headers phase work properly, you may need to add React as an explicit dependency to your app's scheme and disable "parallelize build".

Reviewed By: mmmulani

Differential Revision: D4213120

fbshipit-source-id: 84a32a4b250c27699e6795f43584f13d594a9a82
@robhogan
Copy link
Contributor

robhogan commented Feb 2, 2017

Speaking as an observer, Swift doesn't appear to have first-class support from the RN team because AFAIK they don't use it internally (and I think it's healthy, at least for now, to regard RN as part of facebook's stack they've chosen to share rather than as something they build primarily for the community's needs).

There are plans to add some more tests to prevent big regressions though, and as you can see from this thread, it's very possible to use Swift currently. #12089 should make it smoother - using CocoaPods to build RN as a framework avoids the need for bridging headers.

nicktate pushed a commit to nicktate/react-native that referenced this issue Feb 7, 2017
Summary:
Fixes facebook#11272
Fixes facebook#11572
Fixes facebook#11781

The main changes here are:

* This depends on the latest CocoaPods (1.2.0). It’s currently in RC, but if I’m not mistaken a proper release is expected soon. /cc dantoml
* Adds required header search paths for the jschelpers and cxxreact subspecs.
* Makes the jschelpers and cxxreact headers private to building React Native, not visible to the user’s project.
* It uses the canonical upstream Yoga v1.0.0 podspec: https://github.com/facebook/yoga/blob/master/Yoga.podspec
* Consistent styling.

I have been able to get our app to build again using this artsy/emission#437. The spec has some warnings, but otherwise fully passes lint.

rh389 sjmueller Could you please test with your projects?
Closes facebook#12089

Differential Revision: D4518605

fbshipit-source-id: ecf86232d8b1af52d139eadd1acc10f5c1d42c29
normanjoyner pushed a commit to nicktate/react-native that referenced this issue Feb 9, 2017
Summary:
Fixes facebook#11272
Fixes facebook#11572
Fixes facebook#11781

The main changes here are:

* This depends on the latest CocoaPods (1.2.0). It’s currently in RC, but if I’m not mistaken a proper release is expected soon. /cc dantoml
* Adds required header search paths for the jschelpers and cxxreact subspecs.
* Makes the jschelpers and cxxreact headers private to building React Native, not visible to the user’s project.
* It uses the canonical upstream Yoga v1.0.0 podspec: https://github.com/facebook/yoga/blob/master/Yoga.podspec
* Consistent styling.

I have been able to get our app to build again using this artsy/emission#437. The spec has some warnings, but otherwise fully passes lint.

rh389 sjmueller Could you please test with your projects?
Closes facebook#12089

Differential Revision: D4518605

fbshipit-source-id: ecf86232d8b1af52d139eadd1acc10f5c1d42c29
nicktate pushed a commit to nicktate/react-native that referenced this issue Feb 9, 2017
Summary:
Fixes facebook#11272
Fixes facebook#11572
Fixes facebook#11781

The main changes here are:

* This depends on the latest CocoaPods (1.2.0). It’s currently in RC, but if I’m not mistaken a proper release is expected soon. /cc dantoml
* Adds required header search paths for the jschelpers and cxxreact subspecs.
* Makes the jschelpers and cxxreact headers private to building React Native, not visible to the user’s project.
* It uses the canonical upstream Yoga v1.0.0 podspec: https://github.com/facebook/yoga/blob/master/Yoga.podspec
* Consistent styling.

I have been able to get our app to build again using this artsy/emission#437. The spec has some warnings, but otherwise fully passes lint.

rh389 sjmueller Could you please test with your projects?
Closes facebook#12089

Differential Revision: D4518605

fbshipit-source-id: ecf86232d8b1af52d139eadd1acc10f5c1d42c29
nicktate pushed a commit to nicktate/react-native that referenced this issue Feb 9, 2017
Summary:
Fixes facebook#11272
Fixes facebook#11572
Fixes facebook#11781

The main changes here are:

* This depends on the latest CocoaPods (1.2.0). It’s currently in RC, but if I’m not mistaken a proper release is expected soon. /cc dantoml
* Adds required header search paths for the jschelpers and cxxreact subspecs.
* Makes the jschelpers and cxxreact headers private to building React Native, not visible to the user’s project.
* It uses the canonical upstream Yoga v1.0.0 podspec: https://github.com/facebook/yoga/blob/master/Yoga.podspec
* Consistent styling.

I have been able to get our app to build again using this artsy/emission#437. The spec has some warnings, but otherwise fully passes lint.

rh389 sjmueller Could you please test with your projects?
Closes facebook#12089

Differential Revision: D4518605

fbshipit-source-id: ecf86232d8b1af52d139eadd1acc10f5c1d42c29
alloy added a commit to alloy/react-native that referenced this issue Feb 9, 2017
Summary:
Fixes facebook#11272
Fixes facebook#11572
Fixes facebook#11781

The main changes here are:

* This depends on the latest CocoaPods (1.2.0). It’s currently in RC, but if I’m not mistaken a proper release is expected soon. /cc dantoml
* Adds required header search paths for the jschelpers and cxxreact subspecs.
* Makes the jschelpers and cxxreact headers private to building React Native, not visible to the user’s project.
* It uses the canonical upstream Yoga v1.0.0 podspec: https://github.com/facebook/yoga/blob/master/Yoga.podspec
* Consistent styling.

I have been able to get our app to build again using this artsy/emission#437. The spec has some warnings, but otherwise fully passes lint.

rh389 sjmueller Could you please test with your projects?
Closes facebook#12089

Differential Revision: D4518605

fbshipit-source-id: ecf86232d8b1af52d139eadd1acc10f5c1d42c29
nicktate pushed a commit to nicktate/react-native that referenced this issue Feb 9, 2017
Summary:
Fixes facebook#11272
Fixes facebook#11572
Fixes facebook#11781

The main changes here are:

* This depends on the latest CocoaPods (1.2.0). It’s currently in RC, but if I’m not mistaken a proper release is expected soon. /cc dantoml
* Adds required header search paths for the jschelpers and cxxreact subspecs.
* Makes the jschelpers and cxxreact headers private to building React Native, not visible to the user’s project.
* It uses the canonical upstream Yoga v1.0.0 podspec: https://github.com/facebook/yoga/blob/master/Yoga.podspec
* Consistent styling.

I have been able to get our app to build again using this artsy/emission#437. The spec has some warnings, but otherwise fully passes lint.

rh389 sjmueller Could you please test with your projects?
Closes facebook#12089

Differential Revision: D4518605

fbshipit-source-id: ecf86232d8b1af52d139eadd1acc10f5c1d42c29
grabbou pushed a commit that referenced this issue Feb 14, 2017
Summary:
Fixes #11272
Fixes #11572
Fixes #11781

The main changes here are:

* This depends on the latest CocoaPods (1.2.0). It’s currently in RC, but if I’m not mistaken a proper release is expected soon. /cc dantoml
* Adds required header search paths for the jschelpers and cxxreact subspecs.
* Makes the jschelpers and cxxreact headers private to building React Native, not visible to the user’s project.
* It uses the canonical upstream Yoga v1.0.0 podspec: https://github.com/facebook/yoga/blob/master/Yoga.podspec
* Consistent styling.

I have been able to get our app to build again using this artsy/emission#437. The spec has some warnings, but otherwise fully passes lint.

rh389 sjmueller Could you please test with your projects?
Closes #12089

Differential Revision: D4518605

fbshipit-source-id: ecf86232d8b1af52d139eadd1acc10f5c1d42c29
GaborWnuk pushed a commit to GaborWnuk/react-native that referenced this issue Feb 28, 2017
Summary:
Fixes facebook#11272
Fixes facebook#11572
Fixes facebook#11781

The main changes here are:

* This depends on the latest CocoaPods (1.2.0). It’s currently in RC, but if I’m not mistaken a proper release is expected soon. /cc dantoml
* Adds required header search paths for the jschelpers and cxxreact subspecs.
* Makes the jschelpers and cxxreact headers private to building React Native, not visible to the user’s project.
* It uses the canonical upstream Yoga v1.0.0 podspec: https://github.com/facebook/yoga/blob/master/Yoga.podspec
* Consistent styling.

I have been able to get our app to build again using this artsy/emission#437. The spec has some warnings, but otherwise fully passes lint.

rh389 sjmueller Could you please test with your projects?
Closes facebook#12089

Differential Revision: D4518605

fbshipit-source-id: ecf86232d8b1af52d139eadd1acc10f5c1d42c29
maarf pushed a commit to fullcontact/react-native that referenced this issue Apr 26, 2017
Summary:
Fixes facebook#11272
Fixes facebook#11572
Fixes facebook#11781

The main changes here are:

* This depends on the latest CocoaPods (1.2.0). It’s currently in RC, but if I’m not mistaken a proper release is expected soon. /cc dantoml
* Adds required header search paths for the jschelpers and cxxreact subspecs.
* Makes the jschelpers and cxxreact headers private to building React Native, not visible to the user’s project.
* It uses the canonical upstream Yoga v1.0.0 podspec: https://github.com/facebook/yoga/blob/master/Yoga.podspec
* Consistent styling.

I have been able to get our app to build again using this artsy/emission#437. The spec has some warnings, but otherwise fully passes lint.

rh389 sjmueller Could you please test with your projects?
Closes facebook#12089

Differential Revision: D4518605

fbshipit-source-id: ecf86232d8b1af52d139eadd1acc10f5c1d42c29
@facebook facebook locked as resolved and limited conversation to collaborators May 24, 2018
@react-native-bot react-native-bot added the Resolution: Locked This issue was locked by the bot. label Jul 19, 2018
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
Resolution: Locked This issue was locked by the bot.
Projects
None yet
Development

Successfully merging a pull request may close this issue.

4 participants