Creating a plugin to share item with Spillo is very simple. The SDK is just a single header declaring a LLSpilloSharingService
protocol that your plugin’s principal class needs to conform to.
You can find more about Spillo by visiting the official page.
Following are the steps that one need to go through in order to develop a plugin:
- In Xcode, create a new project and select the
Bundle
template. SelectCocoa
as the Framework to link to. - In your newly created bundle target, navigate to the Build Settings. In there, change the Wrapper Extension setting (under the Packaging section) from
bundle
tospillosharing
. - In your project, create a new class. A subclass of
NSObject
will do. - Going back to the target info, add a new entry to the Info plist
NSPrincipalClass
. Specify the name of the class you’ve just created. - Drag the two files
LLSpilloSharingServicePlugin.h
andLLSpilloSharingServicePlugin.m
to your project making sure that they are copied into your project. - In your newly created class,
#import LLSpilloSharingServicePlugin.h
. - Make your class conform to the
LLSpilloSharingService
protocol. - Implement the required methods in the protocol.
identifier
needs to be a unique identifier for your plugin, the bundle identifier will do. Display name is the name of your plugin as displayed in the share menu and the display image is the 16x16 icon. - Implement the
createSharingOperationForItems:
method. This is the core of the plugin. You will be passed an array ofNSURL
instances (most likely containing a single item) and you will have to return anNSOperation
that actually perform the sharing work. The returnedNSOperation
needs to conform to theLLSpilloSharingServiceOperation
protocol which means it just needs to have a valid completion provider when goingisFinished
. See the comments in the header for more documentation. - If your plugin requires authentication, makes sure to return an appropriate value for the
authenticated
property so that Spillo can correcly kick in authentication for your plugin when needed. - Again, if you need to authenticate your plugin, you can return a view controller from the
createLoginViewControllerWithCompletion:
method. In this controller you should ask for credentials input from the user, persist them to the keychain and invoke the completion block when done authenticating. If you need to cancel simply invoke the completion block with aNSUserCancelledError
error code fromNSCocoaErrorDomain
. - If you implement the login method you should also implement the
logout
one and clean up any credentials from the keychain.
- If your sharing operation fails because of an authentication issue, make sure that you return an error with the
LLSpilloSharingServiceErrorDomain
error domain andLLSpilloSharingServiceAuthenticationError
error code so that Spillo can recover from it and present the login view again. - You shouldn’t invoke the completion block in
createLoginViewControllerWithCompletion:
until the authentication process as a whole completes. - The view controller’s view returned by
createLoginViewControllerWithCompletion:
will be added to the content view of a window itself presented as a sheet. Layout constraints will be added to the view to make sure that the window is correctly sized. You should have non-ambiguous constrained set up in your view. - You should codesign your plugin with a Developer ID certificate.
Plugins need to be installed in the application sandbox (there is a PlugIns
directory under ~/Library/Application Support
in the sandbox). Since it can be tricky to navigate down there a menu item is available in Spillo’s help menu to quickly opening the PlugIns
directory.
After pasting the plugin in the PlugIns directory, you will have to relaunch Spillo for it to load the plugin.
A very simple project is included as an example. It builds a sharing plugin to open an item in the default browser. It is exactly the same that ships in Spillo. This plugin doesn’t require authentication but it gives you a good idea of what a plugin looks like nonetheless.
While working on the plugin, it might be helpful setting a special user default that will report errors while loading the plugin.
defaults write com.ddeville.spillo developerShowPluginLoadingErrors true
With this on, any error happening while loading your plugin will be shown as an alert.