Added system library to handle running external commands on different operating systems in a transparent manner. Added file and path quoting that is cross platform compatible. Changed gimp.lua to use the new utilities.

This commit is contained in:
Bill Ferguson
2018-07-11 11:32:48 -04:00
parent d96d8fb4fc
commit 1a22bfbcef
4 changed files with 167 additions and 4 deletions

View File

@@ -65,6 +65,7 @@
local dt = require "darktable"
local df = require "lib/dtutils.file"
local dtsys = require "lib/dtutils.system"
require "official/yield"
local gettext = dt.gettext
local gimp_widget = nil
@@ -94,7 +95,7 @@ local function group_if_not_member(img, new_img)
dt.print_log("Added to group")
end
end
--[[
local function sanitize_filename(filepath)
local path = df.get_path(filepath)
local basename = df.get_basename(filepath)
@@ -104,7 +105,7 @@ local function sanitize_filename(filepath)
return path .. sanitized .. "." .. filetype
end
]]
local function show_status(storage, image, format, filename,
number, total, high_quality, extra_data)
dt.print(string.format(_("Export Image %i/%i"), number, total))
@@ -130,7 +131,7 @@ local function gimp_edit(storage, image_table, extra_data) --finalize
img_list = ""
for _,exp_img in pairs(image_table) do
exp_img = sanitize_filename(exp_img)
exp_img = df.sanitize_filename(exp_img)
img_list = img_list ..exp_img.. " "
end
@@ -141,7 +142,7 @@ local function gimp_edit(storage, image_table, extra_data) --finalize
dt.print_log(gimpStartCommand)
dt.control.execute( gimpStartCommand)
dtsys.external_command(gimpStartCommand)
-- for each of the image, exported image pairs
-- move the exported image into the directory with the original

View File

@@ -1,5 +1,6 @@
local dtutils_file = {}
local dt = require "darktable"
local ds = require "lib/dtutils.string"
local log = require "lib/dtutils.log"
@@ -529,4 +530,28 @@ function dtutils_file.executable_path_widget(executables)
return box
end
dtutils_file.libdoc.functions["sanitize_filename"] = {
Name = [[sanitize_filename]],
Synopsis = [[make a filename safe to pass as an argument]],
Usage = [[local df = require "lib/dtutils.file"
local sanitized_filename = df.sanitize_filename(filename)
filename - string - a filepath and filename]],
Description = [[sanitize_file places quotes around the filename in an
operating system specific manner. The result is safe to pass as
an argument to the operating system.]],
Return_Value = [[sanitized_filename - string - quoted filename]],
Limitations = [[]],
Example = [[]],
See_Also = [[]],
Reference = [[]],
License = [[]],
Copyright = [[]],
}
function dtutils_file.sanitize_filename(filename)
return ds.sanitize(filename)
end
return dtutils_file

View File

@@ -1,4 +1,7 @@
local dtutils_string = {}
local dt = require "darktable"
dtutils_string.libdoc = {
Name = [[dtutils.string]],
Synopsis = [[a library of string utilities for use in darktable lua scripts]],
@@ -170,4 +173,35 @@ function dtutils_string.urlencode(str)
return str
end
dtutils_string.libdoc.functions["sanitize"] = {
Name = [[sanitize]],
Synopsis = [[surround a string in quotes making it safe to pass as an argument]],
Usage = [[local ds = require "lib/dtutils.string"
local result = ds.sanitize(str)
str - string - the string that needs to be made safe]],
Description = [[sanitize converts a string into a version suitable for
use passing as an argument in a system command.]],
Return_Value = [[result - string - a websafe string]],
Limitations = [[]],
Example = [[]],
See_Also = [[]],
Reference = [[]],
License = [[]],
Copyright = [[]],
}
function dtutils_string.sanitize(str)
local result = ""
if dt.configuration.running_os == "windows" then
result = '"' .. str .. '"'
else
result = "'" .. str .. "'"
end
return result
end
return dtutils_string

103
lib/dtutils/system.lua Normal file
View File

@@ -0,0 +1,103 @@
local dtutils_system = {}
local dt = require "darktable"
dtutils_system.libdoc = {
Name = [[dtutils.system]],
Synopsis = [[a library of system utilities for use in darktable lua scripts]],
Usage = [[local ds = require "lib/dtutils.system"]],
Description = [[This library contains routines for interfacing to the operating system from
darktable lua scripts.]],
Return_Value = [[du - library - the darktable lua system library]],
Limitations = [[]],
Example = [[]],
See_Also = [[]],
Reference = [[]],
License = [[This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>.]],
Copyright = [[Copyright (c) 2018 Bill Ferguson <wpferguson@gmail.com>]],
functions = {}
}
dtutils_system.libdoc.functions["external_command"] = {
Name = [[external_command]],
Synopsis = [[pass a command to the operating system for execution and return the result]],
Usage = [[local dsys = require "lib/dtutils.system"
local result = dsys.external_command(command)
command - string - a string containing the command and arguments to be passed to the operating system for execution.]],
Description = [[external_command passes a command to the operating system for execution and returns the results.]],
Return_Value = [[result - the return value signalling success or failure.]],
Limitations = [[]],
Example = [[]],
See_Also = [[]],
Reference = [[]],
License = [[]],
Copyright = [[]],
}
function dtutils_system.external_command(command)
local result = nil
if dt.configuration.running_os == "windows" then
result = dtutils_system.windows_command(command)
else
result = dt.control.execute(command)
end
return result
end
dtutils_system.libdoc.functions["windows_command"] = {
Name = [[windows_command]],
Synopsis = [[pass a command to the windows operating system for execution and return the result]],
Usage = [[local dsys = require "lib/dtutils.system"
local result = dsys.windows_command(command)
command - string - a string containing the command and arguments to be passed to the operating system for execution.]],
Description = [[The normal method of executing an operating system command is using dt.control.execute(), but that doesn't
work with Windows when more than one item in the command is quoted. In order to ensure command execution on Windows we
create a batch file in the temporary directory, put the command in it, execute the batch file, then return the result.]],
Return_Value = [[result - the return value signalling success or failure.]],
Limitations = [[]],
Example = [[]],
See_Also = [[]],
Reference = [[]],
License = [[]],
Copyright = [[]],
}
function dtutils_system.windows_command(command)
local result = 1
local fname = dt.configuration.tmp_dir .. "/run_command.bat"
local file = io.open(fname, "w")
if file then
dt.print_log("opened file")
command = string.gsub(command, "%%", "%%%%") -- escape % from windows shell
file:write(command)
file:close()
result = dt.control.execute(fname)
dt.print_log("result from windows command was " .. result)
os.remove(fname)
else
dt.print_error("Windows command failed: unable to create batch file")
end
return result
end
return dtutils_system