This post is of interest only to Lightroom plugin developers.
Round about Lightroom 3.2, Adobe added support for intercepting “lightroom://” URLs, but have not documented it yet, so I'll do so here. It's particularly useful as part of an OAuth-authentication procedure.
What
You can have your plugin automatically respond to certain “lightroom://” URLs if they are formatted correctly, and if you add appropriate support to your plugin.
URL Form
After registering the appropriate handler in you plugin, as described below, the handler will be invoked when your system browser receives a URL of the form:
The “your.plugin.id” is the LrToolkitIdentifier in Info.lua. For example, the id for my Flickr plugin is “info.regex.lightroom.export.flickr2”, so it can be set to handle URLs such as:
lightroom://info.regex.lightroom.export.flickr2?this=blah&that=blah
lightroom://info.regex.lightroom.export.flickr2#foobar
etc.
How
Create a .lua file that returns a table along the lines:
return {
URLHandler = function(url)
-- The url string sometimes actually have a double quote as
-- the first and last byte, so strip just in case.
url = url:gsub('^"(.*)"$', "%1")
-- Work with url here....
.
.
.
end }
Wrapping the function in a one-element table seems like an odd level of indirection, but that's how it works.
You then add a reference to that file in your Info.lua, as “URLHandler”. If the file is named “MyUrlHandler.lua”, for example, the reference in Info.lua would look like:
return {
LrToolkitIdentifier = "info.regex.lightroom.export.flickr2",
LrPluginName = "jf Flickr",
LrPluginInfoUrl = "http://regex.info/blog/lightroom-goodies/flickr",
LrSdkVersion = 3.4,
LrSdkMinimumVersion = 3.4,
.
.
.
.
URLHandler = "MyUrlHandler.lua",
}
Within the URLHandler function, you can access parts of the URL (e.g. in an OAuth situation, the token) and stuff into global variables, and perhaps shut down a dialog that had been open by calling LrDialogs.stopModalWithResult(...).
That last bit seems to be unfortunately necessary... I've found that the handler is not properly invoked in some rare OS/browser combinations, so I feel that to cover all my bases, the plugin must open a dialog to tell the user to paste in their token; if the handler ends up working, the plugin can immediately shut down that dialog so the user is not bothered with it. Usually, that's exactly what happens, and it happens so quickly that the user never even sees the dialog.
I don't think Adobe's plugins do this, so maybe the problem has been on my end, but I thought I'd mention it because this is what my plugins do.
Hot tip – many possibilities…
For those trying this out, you will need to check whether the URL supplied to your handler is surrounded in double quotes. I don’t think it always is so its worth explicitly checking before you try to process the URL received.
Good point, Matt, thanks, I should have mentioned that. I’ll go back and update the post to include it. —Jeffrey
I take it this is for one-way communication only, right? i.e. no way for plugin to respond and have it be heard(?)
I’m not quite sure what you mean… a plugin can open dialogs, launch applications, and cause web pages to load, so that’s one way to be heard… —Jeffrey
Well, if you issue an http “get”, then you can read a response. So, if a web-app issued a lightroom://… url, would it possible to know if the plugin is disabled, and hence the url fell on deaf ears? Would it be possible for a web-app to issue a lightroom url that requests a bunch of info from a plugin for use in the web-app?
From SF, CA, USA
Ah, I see, sorry, I was looking at it from the wrong point of view. No, I don’t see any way for the issuer of the lightroom:// url to get any follow-on information (including even whether Lightroom is installed) without going through all kinds of hoops of passing something like a session ID one way, then waiting for a response on some other avenue agreed upon in advance by the issuer and the plugin. —Jeffrey
This is the kind of thing that I wish Adobe would touch on/include in their SDK. Hopefully it’s included in Lr4 SDK.
It’s a small thing, but makes things a lot easier for end users.
Thanks, Jeffrey!