mirror of
https://gitflic.ru/project/openide/openide.git
synced 2026-09-27 10:03:11 +07:00
fixed PY-7975 isTestFrameworkInstalled throws exception for remote interpreter
This commit is contained in:
@@ -120,7 +120,8 @@ public class PyNames {
|
||||
|
||||
public static final String NOSE_TEST = "nose";
|
||||
public static final String PY_TEST = "pytest";
|
||||
public static final String AT_TEST = "attest";
|
||||
public static final String AT_TEST = "Attest";
|
||||
public static final String AT_TEST_IMPORT = "attest";
|
||||
|
||||
public static final String PYCACHE = "__pycache__";
|
||||
|
||||
|
||||
@@ -92,19 +92,19 @@ public class PyIntegratedToolsConfigurable implements SearchableConfigurable, No
|
||||
if (sdk != null) {
|
||||
final Object selectedItem = myTestRunnerComboBox.getSelectedItem();
|
||||
if (PythonTestConfigurationsModel.PY_TEST_NAME.equals(selectedItem)) {
|
||||
if (!VFSTestFrameworkListener.getInstance().isPyTestInstalled(sdk.getHomePath())) {
|
||||
if (!VFSTestFrameworkListener.getInstance().isPyTestInstalled(sdk)) {
|
||||
return new ValidationResult(PyBundle.message("runcfg.testing.no.test.framework", "py.test"),
|
||||
createQuickFix(sdk, facetErrorPanel, PyNames.PY_TEST));
|
||||
}
|
||||
}
|
||||
else if (PythonTestConfigurationsModel.PYTHONS_NOSETEST_NAME.equals(selectedItem)) {
|
||||
if (!VFSTestFrameworkListener.getInstance().isNoseTestInstalled(sdk.getHomePath())) {
|
||||
if (!VFSTestFrameworkListener.getInstance().isNoseTestInstalled(sdk)) {
|
||||
return new ValidationResult(PyBundle.message("runcfg.testing.no.test.framework", "nosetest"),
|
||||
createQuickFix(sdk, facetErrorPanel, PyNames.NOSE_TEST));
|
||||
}
|
||||
}
|
||||
else if (PythonTestConfigurationsModel.PYTHONS_ATTEST_NAME.equals(selectedItem)) {
|
||||
if (!VFSTestFrameworkListener.getInstance().isAtTestInstalled(sdk.getHomePath())) {
|
||||
if (!VFSTestFrameworkListener.getInstance().isAtTestInstalled(sdk)) {
|
||||
return new ValidationResult(PyBundle.message("runcfg.testing.no.test.framework", "attest"),
|
||||
createQuickFix(sdk, facetErrorPanel, PyNames.AT_TEST));
|
||||
}
|
||||
|
||||
@@ -51,6 +51,11 @@ public class PyDocstringLexer extends PythonIndentingLexer {
|
||||
}
|
||||
advanceBase();
|
||||
}
|
||||
if (getBaseTokenType() == PyTokenTypes.LINE_BREAK) {
|
||||
advanceBase();
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (getBaseTokenType() == null) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -92,11 +92,11 @@ public class PyTestRunnerUpdater implements StartupActivity {
|
||||
final Sdk sdk = PythonSdkType.findPythonSdk(module);
|
||||
if (sdk != null && sdk.getSdkType() instanceof PythonSdkType && testRunner.isEmpty()) {
|
||||
String sdkHome = sdk.getHomePath();
|
||||
if (VFSTestFrameworkListener.isTestFrameworkInstalled(sdkHome, VFSTestFrameworkListener.NOSETESTSEARCHER))
|
||||
if (VFSTestFrameworkListener.isTestFrameworkInstalled(sdk, PyNames.NOSE_TEST))
|
||||
testRunner = PythonTestConfigurationsModel.PYTHONS_NOSETEST_NAME;
|
||||
else if (VFSTestFrameworkListener.isTestFrameworkInstalled(sdkHome, VFSTestFrameworkListener.PYTESTSEARCHER))
|
||||
else if (VFSTestFrameworkListener.isTestFrameworkInstalled(sdk, PyNames.PY_TEST))
|
||||
testRunner = PythonTestConfigurationsModel.PY_TEST_NAME;
|
||||
else if (VFSTestFrameworkListener.isTestFrameworkInstalled(sdkHome, VFSTestFrameworkListener.ATTESTSEARCHER))
|
||||
else if (VFSTestFrameworkListener.isTestFrameworkInstalled(sdk, PyNames.AT_TEST))
|
||||
testRunner = PythonTestConfigurationsModel.PYTHONS_ATTEST_NAME;
|
||||
}
|
||||
|
||||
@@ -140,7 +140,7 @@ public class PyTestRunnerUpdater implements StartupActivity {
|
||||
testRunner = PythonTestConfigurationsModel.PY_TEST_NAME;
|
||||
break;
|
||||
}
|
||||
if (stringValue.contains(PyNames.AT_TEST)) {
|
||||
if (stringValue.contains(PyNames.AT_TEST_IMPORT)) {
|
||||
testRunner = PythonTestConfigurationsModel.PYTHONS_ATTEST_NAME;
|
||||
break;
|
||||
}
|
||||
@@ -197,7 +197,7 @@ public class PyTestRunnerUpdater implements StartupActivity {
|
||||
if (PyNames.PY_TEST.equals(importElement.getVisibleName())) {
|
||||
return PythonTestConfigurationsModel.PY_TEST_NAME;
|
||||
}
|
||||
if (PyNames.AT_TEST.equals(importElement.getVisibleName())) {
|
||||
if (PyNames.AT_TEST_IMPORT.equals(importElement.getVisibleName())) {
|
||||
return PythonTestConfigurationsModel.PYTHONS_ATTEST_NAME;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,6 +1,5 @@
|
||||
package com.jetbrains.python.testing;
|
||||
|
||||
import com.intellij.execution.process.ProcessOutput;
|
||||
import com.intellij.openapi.application.ApplicationManager;
|
||||
import com.intellij.openapi.components.*;
|
||||
import com.intellij.openapi.diagnostic.Logger;
|
||||
@@ -17,12 +16,12 @@ import com.intellij.util.ui.update.MergingUpdateQueue;
|
||||
import com.intellij.util.ui.update.Update;
|
||||
import com.intellij.util.xmlb.XmlSerializerUtil;
|
||||
import com.jetbrains.python.PyNames;
|
||||
import com.jetbrains.python.PythonHelpersLocator;
|
||||
import com.jetbrains.python.sdk.PySdkUtil;
|
||||
import com.jetbrains.python.packaging.PyExternalProcessException;
|
||||
import com.jetbrains.python.packaging.PyPackageManager;
|
||||
import com.jetbrains.python.packaging.PyPackageManagerImpl;
|
||||
import com.jetbrains.python.sdk.PythonSdkType;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.io.File;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
@@ -39,9 +38,6 @@ import java.util.Map;
|
||||
public class VFSTestFrameworkListener implements ApplicationComponent, PersistentStateComponent<VFSTestFrameworkListener> {
|
||||
|
||||
private static final Logger LOG = Logger.getInstance("#com.jetbrains.python.testing.VFSTestFrameworkListener");
|
||||
public static final String PYTESTSEARCHER = "pycharm/finders/find_pytest.py";
|
||||
public static final String NOSETESTSEARCHER = "pycharm/finders/find_nosetest.py";
|
||||
public static final String ATTESTSEARCHER = "pycharm/finders/find_attest.py";
|
||||
|
||||
private static final MergingUpdateQueue myQueue = new MergingUpdateQueue("TestFrameworkChecker", 5000, true, null);
|
||||
|
||||
@@ -61,14 +57,14 @@ public class VFSTestFrameworkListener implements ApplicationComponent, Persisten
|
||||
for (String root : sdk.getRootProvider().getUrls(OrderRootType.CLASSES)) {
|
||||
if (path.contains(root)) {
|
||||
if (containsNose) {
|
||||
updateTestFrameworks(sdk.getHomePath(), NOSETESTSEARCHER, PyNames.NOSE_TEST);
|
||||
updateTestFrameworks(sdk, PyNames.NOSE_TEST);
|
||||
break SDKLOOP;
|
||||
}
|
||||
else if (containsPy) {
|
||||
updateTestFrameworks(sdk.getHomePath(), PYTESTSEARCHER, PyNames.PY_TEST);
|
||||
updateTestFrameworks(sdk, PyNames.PY_TEST);
|
||||
break SDKLOOP;
|
||||
} else {
|
||||
updateTestFrameworks(sdk.getHomePath(), ATTESTSEARCHER, PyNames.AT_TEST);
|
||||
updateTestFrameworks(sdk, PyNames.AT_TEST);
|
||||
break SDKLOOP;
|
||||
}
|
||||
}
|
||||
@@ -79,18 +75,18 @@ public class VFSTestFrameworkListener implements ApplicationComponent, Persisten
|
||||
});
|
||||
}
|
||||
|
||||
public void updateAllTestFrameworks(final String sdkHome) {
|
||||
updateTestFrameworks(sdkHome, PYTESTSEARCHER, PyNames.PY_TEST);
|
||||
updateTestFrameworks(sdkHome, NOSETESTSEARCHER, PyNames.NOSE_TEST);
|
||||
updateTestFrameworks(sdkHome, ATTESTSEARCHER, PyNames.AT_TEST);
|
||||
public void updateAllTestFrameworks(final Sdk sdk) {
|
||||
updateTestFrameworks(sdk, PyNames.PY_TEST);
|
||||
updateTestFrameworks(sdk, PyNames.NOSE_TEST);
|
||||
updateTestFrameworks(sdk, PyNames.AT_TEST);
|
||||
myQueue.flush();
|
||||
}
|
||||
|
||||
public void updateTestFrameworks(final String sdkHome, final String searcher, final String sdkType) {
|
||||
myQueue.queue(new Update(Pair.create(sdkHome, searcher)) {
|
||||
public void updateTestFrameworks(final Sdk sdk, final String testPackageName) {
|
||||
myQueue.queue(new Update(Pair.create(sdk, testPackageName)) {
|
||||
@Override
|
||||
public void run() {
|
||||
testInstalled(isTestFrameworkInstalled(sdkHome, searcher), sdkHome, sdkType);
|
||||
testInstalled(isTestFrameworkInstalled(sdk, testPackageName), sdk.getHomePath(), testPackageName);
|
||||
}
|
||||
});
|
||||
}
|
||||
@@ -109,24 +105,17 @@ public class VFSTestFrameworkListener implements ApplicationComponent, Persisten
|
||||
return "VFSTestFrameworkListener";
|
||||
}
|
||||
|
||||
public static boolean isTestFrameworkInstalled(String sdkHome, String searcher) {
|
||||
if (StringUtil.isEmptyOrSpaces(sdkHome)) {
|
||||
LOG.info("Searching test runner in empty sdkHome");
|
||||
public static boolean isTestFrameworkInstalled(Sdk sdk, String testPackageName) {
|
||||
if (sdk == null || StringUtil.isEmptyOrSpaces(sdk.getHomePath())) {
|
||||
LOG.info("Searching test runner in empty sdk");
|
||||
return false;
|
||||
}
|
||||
final String formatter = new File(PythonHelpersLocator.getHelpersRoot(), searcher).getAbsolutePath();
|
||||
ProcessOutput
|
||||
output = PySdkUtil.getProcessOutput(new File(sdkHome).getParent(),
|
||||
new String[]{
|
||||
sdkHome,
|
||||
formatter
|
||||
},
|
||||
null,
|
||||
2000);
|
||||
if (output.getExitCode() != 0 || !output.getStderr().isEmpty()) {
|
||||
LOG.info("Cannot find test runner in " + sdkHome + ". Use searcher " + formatter + ".\nGot exit code: " + output.getExitCode() +
|
||||
".\nError output: " + output.getStderr());
|
||||
return false;
|
||||
final PyPackageManagerImpl packageManager = (PyPackageManagerImpl)PyPackageManager.getInstance(sdk);
|
||||
try {
|
||||
return packageManager.findPackage(testPackageName) != null;
|
||||
}
|
||||
catch (PyExternalProcessException e) {
|
||||
LOG.info("Can't load package list " + e.getMessage());
|
||||
}
|
||||
return true;
|
||||
}
|
||||
@@ -153,10 +142,10 @@ public class VFSTestFrameworkListener implements ApplicationComponent, Persisten
|
||||
SDK_TO_PYTEST.put(sdkHome, installed);
|
||||
}
|
||||
|
||||
public boolean isPyTestInstalled(final String sdkHome) {
|
||||
Boolean isInstalled = SDK_TO_PYTEST.get(sdkHome);
|
||||
public boolean isPyTestInstalled(final Sdk sdk) {
|
||||
Boolean isInstalled = SDK_TO_PYTEST.get(sdk.getHomePath());
|
||||
if (isInstalled == null) {
|
||||
updateTestFrameworks(sdkHome, PYTESTSEARCHER, PyNames.PY_TEST);
|
||||
updateTestFrameworks(sdk, PyNames.PY_TEST);
|
||||
return true;
|
||||
}
|
||||
return isInstalled;
|
||||
@@ -166,10 +155,10 @@ public class VFSTestFrameworkListener implements ApplicationComponent, Persisten
|
||||
SDK_TO_NOSETEST.put(sdkHome, installed);
|
||||
}
|
||||
|
||||
public boolean isNoseTestInstalled(final String sdkHome) {
|
||||
Boolean isInstalled = SDK_TO_NOSETEST.get(sdkHome);
|
||||
public boolean isNoseTestInstalled(final Sdk sdk) {
|
||||
Boolean isInstalled = SDK_TO_NOSETEST.get(sdk.getHomePath());
|
||||
if (isInstalled == null) {
|
||||
updateTestFrameworks(sdkHome, NOSETESTSEARCHER, PyNames.NOSE_TEST);
|
||||
updateTestFrameworks(sdk, PyNames.NOSE_TEST);
|
||||
return true;
|
||||
}
|
||||
return isInstalled;
|
||||
@@ -179,10 +168,10 @@ public class VFSTestFrameworkListener implements ApplicationComponent, Persisten
|
||||
SDK_TO_ATTEST.put(sdkHome, installed);
|
||||
}
|
||||
|
||||
public boolean isAtTestInstalled(final String sdkHome) {
|
||||
Boolean isInstalled = SDK_TO_ATTEST.get(sdkHome);
|
||||
public boolean isAtTestInstalled(final Sdk sdk) {
|
||||
Boolean isInstalled = SDK_TO_ATTEST.get(sdk.getHomePath());
|
||||
if (isInstalled == null) {
|
||||
updateTestFrameworks(sdkHome, ATTESTSEARCHER, PyNames.AT_TEST);
|
||||
updateTestFrameworks(sdk, PyNames.AT_TEST);
|
||||
return true;
|
||||
}
|
||||
return isInstalled;
|
||||
|
||||
@@ -8,6 +8,7 @@ import com.intellij.openapi.options.SettingsEditor;
|
||||
import com.intellij.openapi.util.InvalidDataException;
|
||||
import com.intellij.openapi.util.WriteExternalException;
|
||||
import com.jetbrains.python.PyBundle;
|
||||
import com.jetbrains.python.sdk.PythonSdkType;
|
||||
import com.jetbrains.python.testing.AbstractPythonTestRunConfiguration;
|
||||
import com.jetbrains.python.testing.VFSTestFrameworkListener;
|
||||
import org.jdom.Element;
|
||||
@@ -68,7 +69,7 @@ public class PythonAtTestRunConfiguration extends AbstractPythonTestRunConfigura
|
||||
@Override
|
||||
public void checkConfiguration() throws RuntimeConfigurationException {
|
||||
super.checkConfiguration();
|
||||
if (!VFSTestFrameworkListener.getInstance().isAtTestInstalled(getInterpreterPath()))
|
||||
if (!VFSTestFrameworkListener.getInstance().isAtTestInstalled(PythonSdkType.findSdkByPath(getInterpreterPath())))
|
||||
throw new RuntimeConfigurationWarning(PyBundle.message("runcfg.testing.no.test.framework", "attest"));
|
||||
}
|
||||
}
|
||||
|
||||
+2
-1
@@ -9,6 +9,7 @@ import com.intellij.openapi.util.InvalidDataException;
|
||||
import com.intellij.openapi.util.JDOMExternalizerUtil;
|
||||
import com.intellij.openapi.util.WriteExternalException;
|
||||
import com.jetbrains.python.PyBundle;
|
||||
import com.jetbrains.python.sdk.PythonSdkType;
|
||||
import com.jetbrains.python.testing.AbstractPythonTestRunConfiguration;
|
||||
import com.jetbrains.python.testing.VFSTestFrameworkListener;
|
||||
import org.jdom.Element;
|
||||
@@ -85,7 +86,7 @@ public class PythonNoseTestRunConfiguration extends AbstractPythonTestRunConfigu
|
||||
@Override
|
||||
public void checkConfiguration() throws RuntimeConfigurationException {
|
||||
super.checkConfiguration();
|
||||
if (!VFSTestFrameworkListener.getInstance().isNoseTestInstalled(getInterpreterPath()))
|
||||
if (!VFSTestFrameworkListener.getInstance().isNoseTestInstalled(PythonSdkType.findSdkByPath(getInterpreterPath())))
|
||||
throw new RuntimeConfigurationWarning(PyBundle.message("runcfg.testing.no.test.framework", "nosetest"));
|
||||
}
|
||||
|
||||
|
||||
@@ -10,6 +10,7 @@ import com.intellij.openapi.util.JDOMExternalizerUtil;
|
||||
import com.intellij.openapi.util.WriteExternalException;
|
||||
import com.intellij.openapi.util.text.StringUtil;
|
||||
import com.jetbrains.python.PyBundle;
|
||||
import com.jetbrains.python.sdk.PythonSdkType;
|
||||
import com.jetbrains.python.testing.AbstractPythonTestRunConfiguration;
|
||||
import com.jetbrains.python.testing.VFSTestFrameworkListener;
|
||||
import org.jdom.Element;
|
||||
@@ -119,7 +120,7 @@ public class PyTestRunConfiguration extends AbstractPythonTestRunConfiguration i
|
||||
if (StringUtil.isEmptyOrSpaces(myTestToRun)) {
|
||||
throw new RuntimeConfigurationError("Please specify target folder or script");
|
||||
}
|
||||
if (!VFSTestFrameworkListener.getInstance().isPyTestInstalled(getInterpreterPath()))
|
||||
if (!VFSTestFrameworkListener.getInstance().isPyTestInstalled(PythonSdkType.findSdkByPath(getInterpreterPath())))
|
||||
throw new RuntimeConfigurationWarning(PyBundle.message("runcfg.testing.no.test.framework", "py.test"));
|
||||
}
|
||||
|
||||
|
||||
@@ -28,7 +28,7 @@ public class PyTestRunnableScriptFilter implements RunnableScriptFilter {
|
||||
private static boolean isPyTestInstalled(Module module) {
|
||||
// TODO[yole] add caching to avoid disk I/O in findPyTestRunner()?
|
||||
final Sdk sdk = PythonSdkType.findPythonSdk(module);
|
||||
return sdk != null && VFSTestFrameworkListener.getInstance().isPyTestInstalled(sdk.getHomePath());
|
||||
return sdk != null && VFSTestFrameworkListener.getInstance().isPyTestInstalled(sdk);
|
||||
}
|
||||
|
||||
public static boolean isPyTestScript(PsiFile script) {
|
||||
|
||||
Reference in New Issue
Block a user