Making a plugin that plays nice with the major package managers can be tricky. Here's how to do it safely:
Note: Xcode project files are very fragile and buggy, and tend to break when you make changes to them. Usually you'll end up with phantom targets, or crashes after which the project file won't load anymore. You may have to quit Xcode, wipe out all changes and start over a few times:
git restore --staged .
git checkout .
git clean -df
Once your project is properly set up, quit Xcode and then reopen the workspace to make sure the project file is okay.
- Open
Bugsnag.xcworkspace - From the menu, select
File->New->Project - Use the
Frameworktemplate (ios) - Give it a name like
BugsnagXYZ - Make sure it is part of workspace
Bugsnag - Select the
BugsnagXYZtarget - Under
General->Frameworks and Libraries, click+and add theBugsnag.frameworkfor your architecture (ios). Set itsEmbedtype toDo not embed. - Under
General->Deployment Info, make sureDeployment Targetmatches the targets in the mainBugsnagproject (you may need to manually edit the.pbxprojfile in a text editor to change the variousxyz_DEPLOYMENT_TARGETfields).
In the targets pane (BugsnagXYZ project in the left pane, Targets list in the middle pane):
- Rename the
BugsnagXYZtarget toBugsnagXYZ-iOS - Rename the
BugsnagXYZTeststarget toBugsnagXYZ-iOSTests
In the target's build settings (Bugsnag project in the left pane, Targets list in the middle pane, BugsnagXYZ-iOS, Build Settings):
- Change
Product NamefromBugsnagXYZ-iOStoBugsnagXYZ
In the schemes manager (Click the schemes selector in the middle pane -> Manage Schemes):
- Rename the
BugsnagXYZscheme toBugsnagXYZ-iOS - Untick and re-tick the new scheme's
Sharedcheckbox (this generates the needed .xcscheme file) - Edit the scheme and make sure under the
Testssection it has the targetBugsnagXYZ-iOSTests(use+to add it if it's missing) - Use the
+button to add theBugsnagXYZ-iOSTestsscheme (Cocoapods generates a broken project if there's no test scheme)
- New targets:
BugsnagXYZ-iOSandBugsnagXYZ-iOSTests - New schemes:
BugsnagXYZ-iOSandBugsnagXYZ-iOSTests - New top-level directories:
BugsnagXYZandBugsnagXYZTests
You must add support for the following platforms: macOS, tvOS. Your additional targets will share the same base directories BugsnagXYZ and BugsnagXYZTests.
- Select the
BugsnagXYZproject, then in the center pane in theTargetslist, click+ - Select a platform (macOS, tvOS, etc) and choose the
Frameworktemplate - Call it
BugsnagXYZlike you did for the main target - Delete the extra
BugsnagXYZandBugsnagXYZTestsgroups that were added to theBugsnatXYZproject (remove references only). - Apply fixups and workarounds like you did for the iOS target
- Place all new code inside the
BugsnagXYZdirectory. - Make sure your new files have appropriate
BugsnagXYZ-nnnmembership in the right-side pane. - Create the directory
BugsnagXYZ/BugsnagXYZ/include/BugsnagXYZand place all public headers in there. - Add the
includedirectory as a group in your project. - Make sure all public headers are marked as public in the right-side pane (they're
Projectby default). - When importing from the main Bugsnag library, use angle bracket style (
#import <Bugsnag/whatever.h>)
Carthage looks in your project for shared schemas, so everything should already be set up, and users should be able to reference the new plugin once you've pushed.
Use a file:// reference in your tester app's Cartfile:
git "file:///path/to/bugsnag-cocoa" "my-exploratory-branch"
Then update Carthage: carthage update --use-xcframeworks
Now add Bugsnag.framework and BugsnagXYZ.framework from Carthage/Build/ to your project.
Note: Carthage will only see changes that have been committed to your bugsnag-cocoa git repo!
Modify Package.swift.
Add a new entry to products:
.library(name: "BugsnagXYZ", targets: ["BugsnagXYZ"]),
Add a new entry to targets (note BugsnagXYZ/BugsnagXYZ because of how Xcode structures the project):
.target(
name: "BugsnagXYZ",
dependencies: ["Bugsnag"],
path: "BugsnagXYZ/BugsnagXYZ",
publicHeadersPath: "include",
cSettings: [
.headerSearchPath("."),
.headerSearchPath("include/Bugsnag"),
]
),
Once your changes are pushed, users can reference the new plugin.
- Drag the
bugsnag-cocoafolder (containingPackage.swift) into the Navigator tab (left side) of your tester app project in xcode. - In your app project's general settings, go to
Frameworks, Libraries, and Embedded Content, click+and add the appropriateBugsnagandBugsnagXYZproducts.
Create a BugsnagXYZ.podspec.json file similar to the existing Bugsnag.podspec.json file:
{
"name": "BugsnagXYZ",
"version": "6.11.0",
"summary": "A Bugsnag plugin that does XYZ.",
"homepage": "https://bugsnag.com",
"license": "MIT",
"authors": {
"Bugsnag": "notifiers@bugsnag.com"
},
"source": {
"git": "https://github.com/bugsnag/bugsnag-cocoa.git",
"tag": "v6.11.0"
},
"dependencies": {
"Bugsnag": "6.11.0"
},
"platforms": {
"ios": "9.0",
"osx": "10.11",
"tvos": "9.2"
},
"source_files": [
"BugsnagXYZ/BugsnagXYZ/{**/,}*.{m,h,mm,c}"
],
"requires_arc": true,
"prefix_header_file": false,
"public_header_files": [
"BugsnagXYZ/BugsnagXYZ/include/Bugsnag/*.h"
]
}
Notes:
- The plugin podspec version must remain lockstep with the main
Bugsnag.podspec.jsonversion. - The source files will have the directory structure
BugsnagXYZ/BugsnagXYZbecause of how Xcode structures the project.
Make sure your testing app's Podfile has the following entries:
pod 'Bugsnag', :path => "/path/to/bugsnag-cocoa"
pod 'BugsnagXYZ', :path => "/path/to/bugsnag-cocoa"
Then run pod install and open the generated .xcworkspace file