Fixed refreshing SDK roots and updating current files after installing/uninstalling packages (PY-7250)

This commit is contained in:
Andrey Vlasovskikh
2012-08-22 20:35:49 +04:00
parent b25a6e0deb
commit 6065082ce0
3 changed files with 41 additions and 16 deletions
@@ -14,4 +14,5 @@ public abstract class PyPackageManager {
public abstract boolean hasPip();
public abstract void install(String requirementString) throws PyExternalProcessException;
public abstract void showInstallationError(Project project, String title, String description);
public abstract void refresh();
}
@@ -22,22 +22,22 @@ import com.intellij.openapi.util.Ref;
import com.intellij.openapi.util.SystemInfo;
import com.intellij.openapi.util.io.FileUtil;
import com.intellij.openapi.util.text.StringUtil;
import com.intellij.openapi.vfs.LocalFileSystem;
import com.intellij.openapi.vfs.VfsUtilCore;
import com.intellij.openapi.vfs.VirtualFile;
import com.intellij.openapi.vfs.VirtualFileManager;
import com.intellij.openapi.vfs.newvfs.BulkFileListener;
import com.intellij.openapi.vfs.newvfs.NewVirtualFile;
import com.intellij.openapi.vfs.newvfs.events.VFileEvent;
import com.intellij.util.ArrayUtil;
import com.intellij.util.Function;
import com.intellij.util.SystemProperties;
import com.intellij.util.messages.MessageBusConnection;
import com.intellij.util.net.HttpConfigurable;
import com.jetbrains.python.PyNames;
import com.jetbrains.python.PythonHelpersLocator;
import com.jetbrains.python.psi.PyExpression;
import com.jetbrains.python.psi.PyListLiteralExpression;
import com.jetbrains.python.psi.PyStringLiteralExpression;
import com.jetbrains.python.psi.search.PyProjectScopeBuilder;
import com.jetbrains.python.remote.PyRemoteInterpreterException;
import com.jetbrains.python.remote.PythonRemoteInterpreterManager;
import com.jetbrains.python.remote.PythonRemoteSdkAdditionalData;
@@ -154,6 +154,7 @@ public class PyPackageManagerImpl extends PyPackageManager {
exceptions.add(e);
}
}
manager.refresh();
return exceptions;
}
}, progressTitle, successTitle, "Installed packages: " + PyPackageUtil.requirementsToString(requirements),
@@ -171,13 +172,17 @@ public class PyPackageManagerImpl extends PyPackageManager {
run(new MultiExternalRunnable() {
@Override
public List<PyExternalProcessException> run(@NotNull ProgressIndicator indicator) {
final PyPackageManagerImpl manager = (PyPackageManagerImpl)PyPackageManagers.getInstance().forSdk(mySdk);
try {
((PyPackageManagerImpl)PyPackageManagers.getInstance().forSdk(mySdk)).uninstall(packages);
manager.uninstall(packages);
return list();
}
catch (PyExternalProcessException e) {
return list(e);
}
finally {
manager.refresh();
}
}
}, "Uninstalling packages", "Packages uninstalled successfully", "Uninstalled packages: " + packagesString,
"Uninstall packages failed");
@@ -231,10 +236,6 @@ public class PyPackageManagerImpl extends PyPackageManager {
if (myListener != null) {
myListener.finished(exceptions);
}
VirtualFileManager.getInstance().refreshWithoutFileWatcher(false);
if (exceptions.isEmpty()) {
PythonSdkType.getInstance().setupSdkPaths(mySdk);
}
final Notification notification = notificationRef.get();
if (notification != null) {
notification.notify(myProject);
@@ -257,6 +258,36 @@ public class PyPackageManagerImpl extends PyPackageManager {
}
}
@Override
public void refresh() {
final Application application = ApplicationManager.getApplication();
application.invokeLater(new Runnable() {
@Override
public void run() {
application.runWriteAction(new Runnable() {
@Override
public void run() {
syncFiles(mySdk.getRootProvider().getFiles(OrderRootType.CLASSES));
}
});
PythonSdkType.getInstance().setupSdkPaths(mySdk);
clearCaches();
}
});
}
private void syncFiles(VirtualFile[] files) {
// Similar to LocalFileSystemImpl.syncFiles(), VirtualFile.refresh() doesn't run update index tasks immediately, so we get stale virtual
// files when we want to bind a stub to an AST. Another option is to use VirtualFileManager.refreshWithoutFileWatcher(), but it takes
// more time to refresh the whole local file system
for (VirtualFile root : files) {
if (root instanceof NewVirtualFile && root.getFileSystem() instanceof LocalFileSystem) {
((NewVirtualFile)root).markDirtyRecursively();
}
}
LocalFileSystem.getInstance().refreshFiles(Arrays.asList(files), false, true, null);
}
private void installManagement(String name) throws PyExternalProcessException {
final File helperFile = PythonHelpersLocator.getHelperFile(name + ".tar.gz");
@@ -496,16 +527,9 @@ public class PyPackageManagerImpl extends PyPackageManager {
return null;
}
public void clearCaches() {
private void clearCaches() {
myPackagesCache = null;
myExceptionCache = null;
VirtualFile libDir = PyProjectScopeBuilder.findLibDir(mySdk);
if (libDir != null) {
VirtualFile sitePackages = libDir.findChild(PyNames.SITE_PACKAGES);
if (sitePackages != null) {
sitePackages.refresh(true, true);
}
}
}
private static <T> List<T> list(T... xs) {
@@ -501,7 +501,7 @@ public class PyPackagesPanel extends JPanel {
final String description = PyPackageManagerImpl.UI.createDescription(exceptions, firstLine);
packageManager.showInstallationError(myProject, "Failed to install " + name, description);
}
packageManager.clearCaches();
packageManager.refresh();
updatePackages(sdk);
for (Consumer<Sdk> listener : myPathChangedListeners) {
listener.consume(sdk);