]> git.lyx.org Git - features.git/commitdiff
Change python run time detection to privilege python 3 over python 2.
authorJosé Matos <jamatos@lyx.org>
Fri, 7 Jun 2019 14:27:25 +0000 (15:27 +0100)
committerJean-Marc Lasgouttes <lasgouttes@lyx.org>
Thu, 18 Jun 2020 13:48:33 +0000 (15:48 +0200)
This should work as before but now we also control the python version and ignore it if it is not in the supported range.

src/support/os.cpp

index 8eea49370ae7d125bfe033d44cbae497086c89af..936e759b8b7774488cae1585479e42b81117760e 100644 (file)
 
 #include <config.h>
 
+#include "support/convert.h"
 #include "support/debug.h"
 #include "support/filetools.h"
 #include "support/qstring_helpers.h"
+#include "support/regex.h"
 
 #include <QDir>
 
@@ -40,18 +42,25 @@ namespace os {
 
 static string const python23(string const & binary, bool verbose = false)
 {
+       const string version_info = " -c 'from __future__ import print_function;import sys; print(sys.version_info[:2], end=\"\")'";
+       static regex const python_reg("\\((\\d*), (\\d*)\\)");
        if (verbose)
                lyxerr << "Examining " << binary << "\n";
 
        // Check whether this is a python 2 or 3 binary.
-       cmd_ret const out = runCommand(binary + " -V 2>&1");
-       if (out.first < 0 ||
-           (!prefixIs(out.second, "Python 2") &&
-            !prefixIs(out.second, "Python 3")))
+       cmd_ret const out = runCommand(binary + version_info);
+
+       smatch sm;
+       if (out.first < 0 || !regex_match(out.second, sm, python_reg))
+               return string();
+
+       int major = convert<int>(sm.str(1));
+       int minor = convert<int>(sm.str(2));
+       if((major == 2 and minor < 7) or (major == 3 and minor < 4))
                return string();
 
        if (verbose)
-               lyxerr << "Found " << out.second << "\n";
+               lyxerr << "Found Python " << out.second << "\n";
        return binary;
 }
 
@@ -64,26 +73,25 @@ int timeout_min()
 
 string const python(bool reset)
 {
-       // Check whether the first python in PATH is the right one.
-       static string command = python23("python -tt");
+       // Check whether python3 in PATH is the right one.
+       static string command = python23("python3");
        // FIXME THREAD
        if (reset) {
-               command = python23("python -tt");
+               command = python23("python3");
        }
 
+       // python3 does not exists, let us try python3.x
        if (command.empty()) {
                // It was not, so check whether we can find it elsewhere in
                // PATH, maybe with some suffix appended.
                vector<string> const path = getEnvPath("PATH");
-               vector<string>::const_iterator it = path.begin();
-               vector<string>::const_iterator const end = path.end();
-               lyxerr << "Looking for python v2.x or 3.x ...\n";
-               for (; it != end; ++it) {
-                       QString const dir = toqstr(*it);
+               lyxerr << "Looking for python 3.x ...\n";
+               for (auto bin: path) {
+                       QString const dir = toqstr(bin);
                        string const localdir = dir.toLocal8Bit().constData();
                        QDir qdir(dir);
                        qdir.setFilter(QDir::Files | QDir::Executable);
-                       QStringList list = qdir.entryList(QStringList("python*"));
+                       QStringList list = qdir.entryList(QStringList("python3*"));
                        for (int i = 0; i < list.size() && command.empty(); ++i) {
                                string const binary = addName(localdir,
                                        list.at(i).toLocal8Bit().constData());
@@ -91,16 +99,42 @@ string const python(bool reset)
                        }
                }
 
-               // Default to "python" if no usable binary was found.
-               if (command.empty()) {
-                       lyxerr << "Warning: No python v2.x or 3.x binary found.\n";
-                       command = "python";
+       }
+       // python 3 not found let us look for python 2
+       if (command.empty())
+               command = python23("python2");
+
+       // python2 does not exists, let us try python2.x
+       if (command.empty()) {
+               // It was not, so check whether we can find it elsewhere in
+               // PATH, maybe with some suffix appended.
+               vector<string> const path = getEnvPath("PATH");
+               lyxerr << "Looking for python 3.x ...\n";
+               for (auto bin: path) {
+                       QString const dir = toqstr(bin);
+                       string const localdir = dir.toLocal8Bit().constData();
+                       QDir qdir(dir);
+                       qdir.setFilter(QDir::Files | QDir::Executable);
+                       QStringList list = qdir.entryList(QStringList("python2*"));
+                       for (int i = 0; i < list.size() && command.empty(); ++i) {
+                               string const binary = addName(localdir,
+                                       list.at(i).toLocal8Bit().constData());
+                               command = python23(binary, true);
+                       }
                }
 
-               // Add the -tt switch so that mixed tab/whitespace
-               // indentation is an error
-               command += " -tt";
        }
+
+       // Default to "python" if no usable binary was found.
+       // If this happens all hope is lost that there is a sane system
+       if (command.empty()) {
+               lyxerr << "Warning: No python v2.x or 3.x binary found.\n";
+               command = "python";
+       }
+
+       // Add the -tt switch so that mixed tab/whitespace
+       // indentation is an error
+       command += " -tt";
        return command;
 }