Copy link to clipboard
Copied
Hello,
when i normally use lua, it is possible to create a custom *.dll/*.so file and load/use the extension via e.g. require().
After the require call i can use the functions from the shared library.
As i read in the lightroom sdk documentation this is prohibited, but why?
The only possible solutions which i found is to use LrTasks and communicate with an executable file or to communicate via LrSockets.
But this solutions are not more better as the direct solution over shared libraries
Has anybody a solution to use my own lua extensions (*.dll/*.so files)
Thanks in advance
Regards
1 Correct answer
I see a number of issues:
- LrTasks.execute() must be called from an async task. The API documentation is a little ambiguous about that. If you call it from the main task, as you're doing, you get the error "We can only wait from within a task", which is the mysterious error thrown whenever you try to invoke any of the numerous API functions that can only be called from a separate tsk.
- Any task that throws an error will usually just halt silently with no indication from LR. You need to catch err
...Copy link to clipboard
Copied
Unfortunately, no one has reported here how to load and access dynamic libraries from a plugin.
Copy link to clipboard
Copied
I tried a second attempt. I tried to start an external server app on plugin init and stop it when the lightroom shuts down.
to commuicate with the server i want to use sockets and to start/stop the server on plugin start/end it tried LrTasks but this is blocking. how can i use async LrTasks?
Copy link to clipboard
Copied
The Lightroom SDK contains "lightroom-controller-sdk-guide_2019.pdf", which walks through an example of using sockets to communicate with an external program.
Copy link to clipboard
Copied
Thanks I will have a look at it, it seems that i have overseen this pdf
Copy link to clipboard
Copied
Hello again john,
the problem with this pdf is that it creates a sender and a receiver socket in the plugin.
I interpreted it like i must start the custom server by hand but my idea was to start the server like "myserver --start" in the startup lua script and call "myserver --stop" when the plugin shutdown is called
The problem is that i can't get this simple task working
Copy link to clipboard
Copied
Post the startup script and maybe I can see what's going wrong. (I've never used LrSocket myself.)
Copy link to clipboard
Copied
Hello john,
the startup looks something like
local LrDialogs = import 'LrDialogs'
local LrTasks = import 'LrTasks'
local commandLine = '"MyServer'
if WIN_ENV then
commandLine = 'START ' .. commandLine .. '.exe'
end
commandLine = commandLine .. '" --start'
LrDialogs.message(commandLine)
local exitStatus = LrTasks.execute (commandLine)
LrDialogs.message(' 2 ')
the shutdown looks like:
local LrDialogs = import 'LrDialogs'
local LrTasks = import 'LrTasks'
local commandLine = '"MyServer'
if WIN_ENV then
commandLine = commandLine .. '.exe'
end
commandLine = commandLine .. '" --shutdown'
LrDialogs.message(' 3 ')
local exitStatus = LrTasks.execute (commandLine)
LrDialogs.message(' 4 ')
and bewtween these two the socket connection from the pdf should work
the server only listen to some port and should exchange data with the lightroom plugin
thanks in advance
regards
Copy link to clipboard
Copied
I see a number of issues:
- LrTasks.execute() must be called from an async task. The API documentation is a little ambiguous about that. If you call it from the main task, as you're doing, you get the error "We can only wait from within a task", which is the mysterious error thrown whenever you try to invoke any of the numerous API functions that can only be called from a separate tsk.
- Any task that throws an error will usually just halt silently with no indication from LR. You need to catch errors explicitly LrTasks.pcall() and LrDialogs.attachErrorDialogToFunctionContext(). Or use my Debugging Toolkit, which makes that easier to do (and provides a simple debugger as well). It will take an hour or two to learn and set up your code to use the toolkit, but you'll get that back in saved time almost immediately -- trying to debug plugins with print statements is a huge waste of time. You could also use the Zero Brane IDE (search this forum), but its debugger doesn't know the specifics of LR tasks and unless you're careful, it won't trap all errors.
- LrTasks.execute() runs the child process with a current working directory of the LR application folder (I think). So you'll need to provide absolute paths to program names (like "MyServer").
- Check the returned status code from LrTasks.execute() to make sure it ran correctly.
- When passing command lines to LrTasks.execute() on Windows, they should be wrapped with an extra set of quotes:
LrTasks.execute ('"' .. commandLine ..'"')
It's a long-known workaround for a bug in how the SDK invokes Windows cmd.exe that never got documented.
Copy link to clipboard
Copied
Thank you very much for your explanation.
This means that for LrTasks it should be enough to wrap startAsyncTask around like
LrTasks.startAsyncTask( function()
LrTasks.execute ('"' .. commandLine ..'"')
end )
Right?
Best Regards
Copy link to clipboard
Copied
Right. As an aside, there are so many APi calls that must be run in a separate task that a number of plugins simply run the main body of their plugin in a separate task.
Copy link to clipboard
Copied
Copy link to clipboard
Copied
"get the absolute path of my plugin?"
_PLUGIN.path gives the full path of the plugin folder. See the LrPlugin documentation in the SDK for details.

