]> git.lyx.org Git - features.git/commitdiff
Fix converters in our scripts directory
authorGeorg Baum <Georg.Baum@post.rwth-aachen.de>
Mon, 11 Sep 2006 16:07:49 +0000 (16:07 +0000)
committerGeorg Baum <Georg.Baum@post.rwth-aachen.de>
Mon, 11 Sep 2006 16:07:49 +0000 (16:07 +0000)
* src/graphics/GraphicsConverter.C
(build_script): quote filenames in the python script properly
(build_script):
(build_script):

* src/support/filetools.[Ch]
(quoteName): Add quote_style argument and quoting of python filenames
(libScriptSearch): Add quote_style argument

* src/support/filetools.C
(quote_style): New enum to specify the quoting style

git-svn-id: svn://svn.lyx.org/lyx/lyx-devel/trunk@14978 a592a061-630c-0410-9148-cb99ea01b6c8

src/graphics/GraphicsConverter.C
src/support/filetools.C
src/support/filetools.h

index 4986fc643c0126136b5de2637a96e21d99d67fbf..2fbad942f41a7b77f4a511bd37b141e003e39e05 100644 (file)
@@ -39,6 +39,7 @@ using support::libScriptSearch;
 using support::onlyPath;
 using support::onlyFilename;
 using support::quoteName;
+using support::quote_python;
 using support::subst;
 using support::tempName;
 using support::unlink;
@@ -327,9 +328,8 @@ void build_script(string const & from_file,
        // in python, but the converters might be shell scripts and have more
        // troubles with it.
        string outfile = changeExtension(to_base, getExtension(from_file));
-       script << "infile = '"
-              << subst(subst(from_file, "\\", "\\\\"), "'", "\\'") << "'\n"
-                 "outfile = " << quoteName(outfile) << "\n"
+       script << "infile = " << quoteName(from_file, quote_python) << "\n"
+                 "outfile = " << quoteName(outfile, quote_python) << "\n"
                  "shutil.copy(infile, outfile)\n";
 
        if (edgepath.empty()) {
@@ -337,13 +337,18 @@ void build_script(string const & from_file,
                // converter path from from_format to to_format, so we use
                // the default converter.
                script << "infile = outfile\n"
-                      << "outfile = " << quoteName(to_file) << '\n';
+                      << "outfile = " << quoteName(to_file, quote_python)
+                      << '\n';
 
                ostringstream os;
-               os << support::os::python() << " \""
-                  << libFileSearch("scripts", "convertDefault.py") << "\" ";
+               os << support::os::python() << ' '
+                  << libScriptSearch("$$s/scripts/convertDefault.py",
+                                     quote_python) << ' ';
                if (!from_format.empty())
                        os << from_format << ':';
+               // The extra " quotes around infile and outfile are needed
+               // because the filename may contain spaces and it is used
+               // as argument of os.system().
                os << "' + '\"' + infile + '\"' + ' "
                   << to_format << ":' + '\"' + outfile + '\"' + '";
                string const command = os.str();
@@ -373,21 +378,23 @@ void build_script(string const & from_file,
                outfile = changeExtension(to_base, conv.To->extension());
 
                // Store these names in the python script
-               script << "infile = "      << quoteName(infile) << '\n'
-                      << "infile_base = " << quoteName(infile_base) << '\n'
-                      << "outfile = "     << quoteName(outfile) << '\n';
+               script << "infile = "      << quoteName(infile, quote_python) << "\n"
+                         "infile_base = " << quoteName(infile_base, quote_python) << "\n"
+                         "outfile = "     << quoteName(outfile, quote_python) << '\n';
 
+               // See comment about extra " quotes above (although that
+               // applies only for the first loop run here).
                string command = conv.command;
                command = subst(command, token_from, "' + '\"' + infile + '\"' + '");
                command = subst(command, token_base, "' + '\"' + infile_base + '\"' + '");
                command = subst(command, token_to,   "' + '\"' + outfile + '\"' + '");
-               command = libScriptSearch(command);
+               command = libScriptSearch(command, quote_python);
 
                build_conversion_command(command, script);
        }
 
        // Move the final outfile to to_file
-       script << move_file("outfile", quoteName(to_file));
+       script << move_file("outfile", quoteName(to_file, quote_python));
        lyxerr[Debug::GRAPHICS] << "ready!" << endl;
 }
 
index ca5584211ef376414d70ad8440663f57f062a7af..5259f4090c047c5a1a2fc5d5d96d3e5e6eefc58f 100644 (file)
@@ -133,11 +133,26 @@ string const makeLatexName(string const & file)
 }
 
 
-string const quoteName(string const & name)
+string const quoteName(string const & name, quote_style style)
 {
-       return (os::shell() == os::UNIX) ?
-               '\'' + name + '\'':
-               '"' + name + '"';
+       switch(style) {
+       case quote_shell:
+               // This does not work for filenames containing " (windows)
+               // or ' (all other OSes). This can't be changed easily, since
+               // we would need to adapt the command line parser in
+               // Forkedcall::generateChild. Therefore we don't pass user
+               // filenames to child processes if possible. We store them in
+               // a python script instead, where we don't have these
+               // limitations.
+               return (os::shell() == os::UNIX) ?
+                       '\'' + name + '\'':
+                       '"' + name + '"';
+       case quote_python:
+               return "\"" + subst(subst(name, "\\", "\\\\"), "\"", "\\\"")
+                    + "\"";
+       }
+       // shut up stupid compiler
+       return string();
 }
 
 
@@ -313,7 +328,7 @@ string const i18nLibFileSearch(string const & dir, string const & name,
 }
 
 
-string const libScriptSearch(string const & command_in)
+string const libScriptSearch(string const & command_in, quote_style style)
 {
        static string const token_scriptpath = "$$s/";
 
@@ -339,7 +354,7 @@ string const libScriptSearch(string const & command_in)
        } else {
                // Replace "$$s/foo/some_script" with "<path to>/some_script".
                string::size_type const size_replace = size_script + 4;
-               command.replace(pos1, size_replace, quoteName(script));
+               command.replace(pos1, size_replace, quoteName(script, style));
        }
 
        return command;
index 96fd707b5a3b4979d6f98d5ed527bd6386831a8d..73b2c8c2a3ee232853cb813b1c2ec65aefda0ef7 100644 (file)
@@ -100,13 +100,28 @@ i18nLibFileSearch(std::string const & dir,
                  std::string const & name,
                  std::string const & ext = std::string());
 
+/// How to quote a filename
+enum quote_style {
+       /** Quote for the (OS dependant) shell. This is needed for command
+           line arguments of subprocesses. */
+       quote_shell,
+       /** Quote for python. Use this if you want to store a filename in a
+           python script. Example: \code
+           os << "infile = " << quoteName(filename) << '\\n';
+           \endcode This uses double quotes, so that you can also use this
+           to quote filenames as part of a string if the string is quoted
+           with single quotes. */
+       quote_python
+};
+
 /** Takes a command such as "python $$s/scripts/convertDefault.py file.in file.out"
  *  and replaces "$$s/" with the path to the LyX support directory containing
  *  this script. If the script is not found, "$$s/" is removed. Executing the
  *  command will still fail, but the error message will make some sort of
  *  sense ;-)
  */
-std::string const libScriptSearch(std::string const & command);
+std::string const libScriptSearch(std::string const & command,
+               quote_style style = quote_shell);
 
 enum latex_path_extension {
        PROTECT_EXTENSION,
@@ -144,8 +159,9 @@ std::string const latex_path(std::string const & path,
 /// Substitutes active latex characters with underscores in filename
 std::string const makeLatexName(std::string const & file);
 
-/// Put the name in quotes suitable for the current shell
-std::string const quoteName(std::string const & file);
+/** Put the name in quotes suitable for the current shell or python,
+    depending on \p style. */
+std::string const quoteName(std::string const & file, quote_style style = quote_shell);
 
 /// Add a filename to a path. Any path from filename is stripped first.
 std::string const addName(std::string const & path, std::string const & fname);