diff --git a/python/openapi/src/com/jetbrains/python/packaging/PyPackage.java b/python/openapi/src/com/jetbrains/python/packaging/PyPackage.java index 9c51750d0431..d73f1cb61172 100644 --- a/python/openapi/src/com/jetbrains/python/packaging/PyPackage.java +++ b/python/openapi/src/com/jetbrains/python/packaging/PyPackage.java @@ -19,11 +19,6 @@ public class PyPackage extends InstalledPackage { myRequirements = requirements; } - @Override - public String toString() { - return getName(); - } - @NotNull public List getRequirements() { return myRequirements; @@ -37,4 +32,10 @@ public class PyPackage extends InstalledPackage { public boolean isInstalled() { return myLocation != null; } + + @Nullable + @Override + public String getTooltipText() { + return myLocation; + } } diff --git a/python/src/com/jetbrains/python/packaging/PyPIPackageUtil.java b/python/src/com/jetbrains/python/packaging/PyPIPackageUtil.java index b590a8a2f0e5..42fed5b535cc 100644 --- a/python/src/com/jetbrains/python/packaging/PyPIPackageUtil.java +++ b/python/src/com/jetbrains/python/packaging/PyPIPackageUtil.java @@ -243,14 +243,19 @@ public class PyPIPackageUtil { } public Collection getPackageNames() throws IOException { + Map pyPIPackages = loadAndGetPackages(); + ArrayList list = Lists.newArrayList(pyPIPackages.keySet()); + Collections.sort(list); + return list; + } + + public Map loadAndGetPackages() throws IOException { Map pyPIPackages = getPyPIPackages(); if (pyPIPackages.isEmpty()) { updatePyPICache(PyPackageService.getInstance()); pyPIPackages = getPyPIPackages(); } - ArrayList list = Lists.newArrayList(pyPIPackages.keySet()); - Collections.sort(list); - return list; + return pyPIPackages; } public static Map getPyPIPackages() { diff --git a/python/src/com/jetbrains/python/packaging/ui/InstalledPackagesPanel.java b/python/src/com/jetbrains/python/packaging/ui/InstalledPackagesPanel.java index 04c0f5a4d935..a4aa10d30b02 100644 --- a/python/src/com/jetbrains/python/packaging/ui/InstalledPackagesPanel.java +++ b/python/src/com/jetbrains/python/packaging/ui/InstalledPackagesPanel.java @@ -150,7 +150,7 @@ public class InstalledPackagesPanel extends JPanel { @Nullable String errorDescription) { myNotificationArea.showResult(packageName, errorDescription); myPackagesTable.clearSelection(); - doUpdatePackages(mySelectedSdk); + doUpdatePackages(myPackageManagementService); } }); } @@ -337,39 +337,40 @@ public class InstalledPackagesPanel extends JPanel { myPackageManagementService = packageManagementService; myPackagesTable.clearSelection(); myPackagesTableModel.getDataVector().clear(); - doUpdatePackages(selectedSdk); + doUpdatePackages(packageManagementService); } - public void doUpdatePackages(final Sdk selectedSdk) { + public void doUpdatePackages(final PackageManagementService packageManagementService) { myPackagesTable.setPaintBusy(true); final Application application = ApplicationManager.getApplication(); application.executeOnPooledThread(new Runnable() { @Override public void run() { - List packages = Lists.newArrayList(); - if (selectedSdk != null) { + Collection packages = Lists.newArrayList(); + if (packageManagementService != null) { try { - packages = ((PyPackageManagerImpl)PyPackageManager.getInstance(selectedSdk)).getPackages(); + packages = packageManagementService.getInstalledPackages(); } - catch (PyExternalProcessException e) { + catch (IOException e) { // do nothing, we already have an empty list } finally { - final List finalPackages = packages; - final Map cache = PyPIPackageUtil.getPyPIPackages(); + final Collection finalPackages = packages; + + final Map cache = buildNameToPackageMap(packageManagementService.getAllPackagesCached()); if (cache.isEmpty()) { - updateCache(application); + refreshLatestVersions(); } application.invokeLater(new Runnable() { @Override public void run() { - - if (selectedSdk == mySelectedSdk) { + if (packageManagementService == myPackageManagementService) { myPackagesTableModel.getDataVector().clear(); - for (PyPackage pyPackage : finalPackages) { - final String version = cache.get(pyPackage.getName()); + for (InstalledPackage pkg : finalPackages) { + RepoPackage repoPackage = cache.get(pkg.getName()); + final String version = repoPackage != null ? repoPackage.getLatestVersion() : null; myPackagesTableModel - .addRow(new Object[]{pyPackage, pyPackage.getVersion(), version == null ? "" : version}); + .addRow(new Object[]{pkg, pkg.getVersion(), version == null ? "" : version}); } if (!cache.isEmpty()) { myPackagesTable.setPaintBusy(false); @@ -383,20 +384,21 @@ public class InstalledPackagesPanel extends JPanel { }); } - private void updateCache(final Application application) { + private void refreshLatestVersions() { + final Application application = ApplicationManager.getApplication(); application.executeOnPooledThread(new Runnable() { @Override public void run() { try { - PyPIPackageUtil.INSTANCE.updatePyPICache(PyPackageService.getInstance()); + List packages = myPackageManagementService.reloadAllPackages(); + final Map packageMap = buildNameToPackageMap(packages); application.invokeLater(new Runnable() { @Override public void run() { - final Map cache = PyPIPackageUtil.getPyPIPackages(); for (int i = 0; i != myPackagesTableModel.getRowCount(); ++i) { - final PyPackage pyPackage = (PyPackage)myPackagesTableModel.getValueAt(i, 0); - final String version = cache.get(pyPackage.getName()); - myPackagesTableModel.setValueAt(version, i, 2); + final InstalledPackage pyPackage = (PyPackage)myPackagesTableModel.getValueAt(i, 0); + final RepoPackage repoPackage = packageMap.get(pyPackage.getName()); + myPackagesTableModel.setValueAt(repoPackage == null ? null : repoPackage.getLatestVersion(), i, 2); } myPackagesTable.setPaintBusy(false); } @@ -409,6 +411,14 @@ public class InstalledPackagesPanel extends JPanel { }); } + private static Map buildNameToPackageMap(List packages) { + final Map packageMap = new HashMap(); + for (RepoPackage aPackage : packages) { + packageMap.put(aPackage.getName(), aPackage); + } + return packageMap; + } + private static class MyTableCellRenderer extends DefaultTableCellRenderer { @Override public Component getTableCellRendererComponent(final JTable table, final Object value, final boolean isSelected, diff --git a/python/src/com/jetbrains/python/packaging/ui/PyPackageManagementService.java b/python/src/com/jetbrains/python/packaging/ui/PyPackageManagementService.java index 1174a936e50d..e741dd809480 100644 --- a/python/src/com/jetbrains/python/packaging/ui/PyPackageManagementService.java +++ b/python/src/com/jetbrains/python/packaging/ui/PyPackageManagementService.java @@ -54,23 +54,41 @@ public class PyPackageManagementService extends PackageManagementService { @Override public List getAllPackages() throws IOException { - List packages = new ArrayList(); - final Collection packageNames; + final Map packageToVersionMap; try { - packageNames = PyPIPackageUtil.INSTANCE.getPackageNames(); + packageToVersionMap = PyPIPackageUtil.INSTANCE.loadAndGetPackages(); } catch (IOException e) { throw new IOException("Could not reach URL " + e.getMessage() + ". Please, check your internet connection."); } - final boolean customRepoConfigured = !PyPackageService.getInstance().additionalRepositories.isEmpty(); - String url = customRepoConfigured? PyPIPackageUtil.PYPI_URL : ""; - for (String name : packageNames) { - packages.add(new RepoPackage(name, url)); - } + List packages = versionMapToPackageList(packageToVersionMap); packages.addAll(PyPIPackageUtil.INSTANCE.getAdditionalPackageNames()); return packages; } + private static List versionMapToPackageList(Map packageToVersionMap) { + final boolean customRepoConfigured = !PyPackageService.getInstance().additionalRepositories.isEmpty(); + String url = customRepoConfigured? PyPIPackageUtil.PYPI_URL : ""; + List packages = new ArrayList(); + for (Map.Entry entry : packageToVersionMap.entrySet()) { + packages.add(new RepoPackage(entry.getKey(), url, entry.getValue())); + } + return packages; + } + + @Override + public List reloadAllPackages() throws IOException { + final PyPackageService service = PyPackageService.getInstance(); + PyPIPackageUtil.INSTANCE.updatePyPICache(service); + service.LAST_TIME_CHECKED = System.currentTimeMillis(); + return getAllPackages(); + } + + @Override + public List getAllPackagesCached() { + return versionMapToPackageList(PyPIPackageUtil.getPyPIPackages()); + } + @Override public boolean canInstallToUser() { return !PythonSdkType.isVirtualEnv(mySdk); @@ -94,14 +112,6 @@ public class PyPackageManagementService extends PackageManagementService { PyPackageService.getInstance().addSdkToUserSite(mySdk.getHomePath(), newValue); } - @Override - public List reloadAllPackages() throws IOException { - final PyPackageService service = PyPackageService.getInstance(); - PyPIPackageUtil.INSTANCE.updatePyPICache(service); - service.LAST_TIME_CHECKED = System.currentTimeMillis(); - return getAllPackages(); - } - @Override public Collection getInstalledPackages() throws IOException { List packages;