Sat, 23 Feb 2019 15:46:15 +0100
Merged with the pypi branch.
--- a/Documentation/Source/eric6.Plugins.UiExtensionPlugins.PipInterface.ConfigurationPage.PipPage.html Sat Feb 23 13:05:18 2019 +0100 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,89 +0,0 @@ -<!DOCTYPE html> -<html><head> -<title>eric6.Plugins.UiExtensionPlugins.PipInterface.ConfigurationPage.PipPage</title> -<meta charset="UTF-8"> -<style> -body { - background: #EDECE6; - margin: 0em 1em 10em 1em; - color: black; -} - -h1 { color: white; background: #85774A; } -h2 { color: white; background: #85774A; } -h3 { color: white; background: #9D936E; } -h4 { color: white; background: #9D936E; } - -a { color: #BA6D36; } - -</style> -</head> -<body><a NAME="top" ID="top"></a> -<h1>eric6.Plugins.UiExtensionPlugins.PipInterface.ConfigurationPage.PipPage</h1> -<p> -Package implementing the pip configuration page. -</p> -<h3>Global Attributes</h3> -<table> -<tr><td>None</td></tr> -</table> -<h3>Classes</h3> -<table> -<tr> -<td><a href="#PipPage">PipPage</a></td> -<td>Class implementing the pip configuration page.</td> -</tr> -</table> -<h3>Functions</h3> -<table> -<tr><td>None</td></tr> -</table> -<hr /><hr /> -<a NAME="PipPage" ID="PipPage"></a> -<h2>PipPage</h2> -<p> - Class implementing the pip configuration page. -</p> -<h3>Derived from</h3> -ConfigurationPageBase, Ui_PipPage -<h3>Class Attributes</h3> -<table> -<tr><td>None</td></tr> -</table> -<h3>Class Methods</h3> -<table> -<tr><td>None</td></tr> -</table> -<h3>Methods</h3> -<table> -<tr> -<td><a href="#PipPage.__init__">PipPage</a></td> -<td>Constructor</td> -</tr><tr> -<td><a href="#PipPage.save">save</a></td> -<td>Public slot to save the pip configuration.</td> -</tr> -</table> -<h3>Static Methods</h3> -<table> -<tr><td>None</td></tr> -</table> -<a NAME="PipPage.__init__" ID="PipPage.__init__"></a> -<h4>PipPage (Constructor)</h4> -<b>PipPage</b>(<i>plugin</i>) -<p> - Constructor -</p><dl> -<dt><i>plugin</i> (PipInterfacePlugin)</dt> -<dd> -reference to the plugin object -</dd> -</dl><a NAME="PipPage.save" ID="PipPage.save"></a> -<h4>PipPage.save</h4> -<b>save</b>(<i></i>) -<p> - Public slot to save the pip configuration. -</p> -<div align="right"><a href="#top">Up</a></div> -<hr /> -</body></html> \ No newline at end of file
--- a/Documentation/Source/eric6.Plugins.UiExtensionPlugins.PipInterface.Pip.html Sat Feb 23 13:05:18 2019 +0100 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,608 +0,0 @@ -<!DOCTYPE html> -<html><head> -<title>eric6.Plugins.UiExtensionPlugins.PipInterface.Pip</title> -<meta charset="UTF-8"> -<style> -body { - background: #EDECE6; - margin: 0em 1em 10em 1em; - color: black; -} - -h1 { color: white; background: #85774A; } -h2 { color: white; background: #85774A; } -h3 { color: white; background: #9D936E; } -h4 { color: white; background: #9D936E; } - -a { color: #BA6D36; } - -</style> -</head> -<body><a NAME="top" ID="top"></a> -<h1>eric6.Plugins.UiExtensionPlugins.PipInterface.Pip</h1> -<p> -Package implementing the pip GUI logic. -</p> -<h3>Global Attributes</h3> -<table> -<tr><td>None</td></tr> -</table> -<h3>Classes</h3> -<table> -<tr> -<td><a href="#Pip">Pip</a></td> -<td>Class implementing the pip GUI logic.</td> -</tr> -</table> -<h3>Functions</h3> -<table> -<tr><td>None</td></tr> -</table> -<hr /><hr /> -<a NAME="Pip" ID="Pip"></a> -<h2>Pip</h2> -<p> - Class implementing the pip GUI logic. -</p> -<h3>Derived from</h3> -QObject -<h3>Class Attributes</h3> -<table> -<tr><td>None</td></tr> -</table> -<h3>Class Methods</h3> -<table> -<tr><td>None</td></tr> -</table> -<h3>Methods</h3> -<table> -<tr> -<td><a href="#Pip.__init__">Pip</a></td> -<td>Constructor</td> -</tr><tr> -<td><a href="#Pip.__aboutToShowMenu">__aboutToShowMenu</a></td> -<td>Private slot to set the action enabled status.</td> -</tr><tr> -<td><a href="#Pip.__checkUpgradePyQt">__checkUpgradePyQt</a></td> -<td>Private method to check, if an upgrade of PyQt packages is attempted.</td> -</tr><tr> -<td><a href="#Pip.__editConfiguration">__editConfiguration</a></td> -<td>Private method to edit a configuration.</td> -</tr><tr> -<td><a href="#Pip.__editUserConfiguration">__editUserConfiguration</a></td> -<td>Private slot to edit the user configuration.</td> -</tr><tr> -<td><a href="#Pip.__editVirtualenvConfiguration">__editVirtualenvConfiguration</a></td> -<td>Private slot to edit the current virtualenv configuration.</td> -</tr><tr> -<td><a href="#Pip.__generateRequirements">__generateRequirements</a></td> -<td>Private slot to generate the contents for a requirements file.</td> -</tr><tr> -<td><a href="#Pip.__getUserConfig">__getUserConfig</a></td> -<td>Private method to get the name of the user configuration file.</td> -</tr><tr> -<td><a href="#Pip.__getVirtualenvConfig">__getVirtualenvConfig</a></td> -<td>Private method to get the name of the virtualenv configuration file.</td> -</tr><tr> -<td><a href="#Pip.__handleTearOffMenu">__handleTearOffMenu</a></td> -<td>Private slot to handle a change of the selected virtual environment.</td> -</tr><tr> -<td><a href="#Pip.__installLocalPackage">__installLocalPackage</a></td> -<td>Private slot to install a package available on local storage.</td> -</tr><tr> -<td><a href="#Pip.__installPackages">__installPackages</a></td> -<td>Private slot to install packages to be given by the user.</td> -</tr><tr> -<td><a href="#Pip.__installPip">__installPip</a></td> -<td>Private slot to install pip.</td> -</tr><tr> -<td><a href="#Pip.__installRequirements">__installRequirements</a></td> -<td>Private slot to install packages as given in a requirements file.</td> -</tr><tr> -<td><a href="#Pip.__listOutdatedPackages">__listOutdatedPackages</a></td> -<td>Private slot to list all installed, up-to-date packages.</td> -</tr><tr> -<td><a href="#Pip.__listPackages">__listPackages</a></td> -<td>Private slot to list all installed packages.</td> -</tr><tr> -<td><a href="#Pip.__listUptodatePackages">__listUptodatePackages</a></td> -<td>Private slot to list all installed, up-to-date packages.</td> -</tr><tr> -<td><a href="#Pip.__pipConfigure">__pipConfigure</a></td> -<td>Private slot to open the configuration page.</td> -</tr><tr> -<td><a href="#Pip.__repairPip">__repairPip</a></td> -<td>Private method to repair the pip installation.</td> -</tr><tr> -<td><a href="#Pip.__searchPyPI">__searchPyPI</a></td> -<td>Private slot to search the Python Package Index.</td> -</tr><tr> -<td><a href="#Pip.__selectPipVirtualenv">__selectPipVirtualenv</a></td> -<td>Private method to select the virtual environment to be used.</td> -</tr><tr> -<td><a href="#Pip.__uninstallPackages">__uninstallPackages</a></td> -<td>Private slot to uninstall packages to be given by the user.</td> -</tr><tr> -<td><a href="#Pip.__uninstallRequirements">__uninstallRequirements</a></td> -<td>Private slot to uninstall packages as given in a requirements file.</td> -</tr><tr> -<td><a href="#Pip.__upgradePackages">__upgradePackages</a></td> -<td>Private slot to upgrade packages to be given by the user.</td> -</tr><tr> -<td><a href="#Pip.getDefaultEnvironmentString">getDefaultEnvironmentString</a></td> -<td>Public method to get the string for the default environment.</td> -</tr><tr> -<td><a href="#Pip.getMenu">getMenu</a></td> -<td>Public method to get a reference to the requested menu.</td> -</tr><tr> -<td><a href="#Pip.getMenuNames">getMenuNames</a></td> -<td>Public method to get the names of all menus.</td> -</tr><tr> -<td><a href="#Pip.getProjectEnvironmentString">getProjectEnvironmentString</a></td> -<td>Public method to get the string for the project environment.</td> -</tr><tr> -<td><a href="#Pip.getVirtualenvInterpreter">getVirtualenvInterpreter</a></td> -<td>Public method to get the interpreter for a virtual environment.</td> -</tr><tr> -<td><a href="#Pip.getVirtualenvNames">getVirtualenvNames</a></td> -<td>Public method to get a sorted list of virtual environment names.</td> -</tr><tr> -<td><a href="#Pip.initActions">initActions</a></td> -<td>Public method to define the actions.</td> -</tr><tr> -<td><a href="#Pip.initMenu">initMenu</a></td> -<td>Public slot to initialize the menu.</td> -</tr><tr> -<td><a href="#Pip.installPackages">installPackages</a></td> -<td>Public method to install the given list of packages.</td> -</tr><tr> -<td><a href="#Pip.runProcess">runProcess</a></td> -<td>Public method to execute the current pip with the given arguments.</td> -</tr><tr> -<td><a href="#Pip.uninstallPackages">uninstallPackages</a></td> -<td>Public method to uninstall the given list of packages.</td> -</tr><tr> -<td><a href="#Pip.upgradePackages">upgradePackages</a></td> -<td>Public method to upgrade the given list of packages.</td> -</tr><tr> -<td><a href="#Pip.upgradePip">upgradePip</a></td> -<td>Public method to upgrade pip itself.</td> -</tr> -</table> -<h3>Static Methods</h3> -<table> -<tr><td>None</td></tr> -</table> -<a NAME="Pip.__init__" ID="Pip.__init__"></a> -<h4>Pip (Constructor)</h4> -<b>Pip</b>(<i>plugin, parent=None</i>) -<p> - Constructor -</p><dl> -<dt><i>plugin</i> (PipInterfacePlugin)</dt> -<dd> -reference to the plugin object -</dd><dt><i>parent</i> (QObject)</dt> -<dd> -parent -</dd> -</dl><a NAME="Pip.__aboutToShowMenu" ID="Pip.__aboutToShowMenu"></a> -<h4>Pip.__aboutToShowMenu</h4> -<b>__aboutToShowMenu</b>(<i></i>) -<p> - Private slot to set the action enabled status. -</p><a NAME="Pip.__checkUpgradePyQt" ID="Pip.__checkUpgradePyQt"></a> -<h4>Pip.__checkUpgradePyQt</h4> -<b>__checkUpgradePyQt</b>(<i>packages</i>) -<p> - Private method to check, if an upgrade of PyQt packages is attempted. -</p><dl> -<dt><i>packages</i> (list of str)</dt> -<dd> -list of packages to upgrade -</dd> -</dl><dl> -<dt>Returns:</dt> -<dd> -flag indicating to abort the upgrade attempt -</dd> -</dl><dl> -<dt>Return Type:</dt> -<dd> -bool -</dd> -</dl><a NAME="Pip.__editConfiguration" ID="Pip.__editConfiguration"></a> -<h4>Pip.__editConfiguration</h4> -<b>__editConfiguration</b>(<i>virtualenv=False</i>) -<p> - Private method to edit a configuration. -</p><dl> -<dt><i>virtualenv</i> (bool)</dt> -<dd> -flag indicating to edit the current virtualenv - configuration file -</dd> -</dl><a NAME="Pip.__editUserConfiguration" ID="Pip.__editUserConfiguration"></a> -<h4>Pip.__editUserConfiguration</h4> -<b>__editUserConfiguration</b>(<i></i>) -<p> - Private slot to edit the user configuration. -</p><a NAME="Pip.__editVirtualenvConfiguration" ID="Pip.__editVirtualenvConfiguration"></a> -<h4>Pip.__editVirtualenvConfiguration</h4> -<b>__editVirtualenvConfiguration</b>(<i></i>) -<p> - Private slot to edit the current virtualenv configuration. -</p><a NAME="Pip.__generateRequirements" ID="Pip.__generateRequirements"></a> -<h4>Pip.__generateRequirements</h4> -<b>__generateRequirements</b>(<i></i>) -<p> - Private slot to generate the contents for a requirements file. -</p><a NAME="Pip.__getUserConfig" ID="Pip.__getUserConfig"></a> -<h4>Pip.__getUserConfig</h4> -<b>__getUserConfig</b>(<i></i>) -<p> - Private method to get the name of the user configuration file. -</p><dl> -<dt>Returns:</dt> -<dd> -path of the user configuration file -</dd> -</dl><dl> -<dt>Return Type:</dt> -<dd> -str -</dd> -</dl><a NAME="Pip.__getVirtualenvConfig" ID="Pip.__getVirtualenvConfig"></a> -<h4>Pip.__getVirtualenvConfig</h4> -<b>__getVirtualenvConfig</b>(<i></i>) -<p> - Private method to get the name of the virtualenv configuration file. -</p><dl> -<dt>Returns:</dt> -<dd> -path of the virtualenv configuration file -</dd> -</dl><dl> -<dt>Return Type:</dt> -<dd> -str -</dd> -</dl><a NAME="Pip.__handleTearOffMenu" ID="Pip.__handleTearOffMenu"></a> -<h4>Pip.__handleTearOffMenu</h4> -<b>__handleTearOffMenu</b>(<i>venvName</i>) -<p> - Private slot to handle a change of the selected virtual environment. -</p><dl> -<dt><i>venvName</i> (str)</dt> -<dd> -logical name of the virtual environment -</dd> -</dl><a NAME="Pip.__installLocalPackage" ID="Pip.__installLocalPackage"></a> -<h4>Pip.__installLocalPackage</h4> -<b>__installLocalPackage</b>(<i></i>) -<p> - Private slot to install a package available on local storage. -</p><a NAME="Pip.__installPackages" ID="Pip.__installPackages"></a> -<h4>Pip.__installPackages</h4> -<b>__installPackages</b>(<i></i>) -<p> - Private slot to install packages to be given by the user. -</p><a NAME="Pip.__installPip" ID="Pip.__installPip"></a> -<h4>Pip.__installPip</h4> -<b>__installPip</b>(<i>userSite=False</i>) -<p> - Private slot to install pip. -</p><dl> -<dt><i>userSite</i> (bool)</dt> -<dd> -flag indicating an install to the user install - directory -</dd> -</dl><a NAME="Pip.__installRequirements" ID="Pip.__installRequirements"></a> -<h4>Pip.__installRequirements</h4> -<b>__installRequirements</b>(<i></i>) -<p> - Private slot to install packages as given in a requirements file. -</p><a NAME="Pip.__listOutdatedPackages" ID="Pip.__listOutdatedPackages"></a> -<h4>Pip.__listOutdatedPackages</h4> -<b>__listOutdatedPackages</b>(<i></i>) -<p> - Private slot to list all installed, up-to-date packages. -</p><a NAME="Pip.__listPackages" ID="Pip.__listPackages"></a> -<h4>Pip.__listPackages</h4> -<b>__listPackages</b>(<i></i>) -<p> - Private slot to list all installed packages. -</p><a NAME="Pip.__listUptodatePackages" ID="Pip.__listUptodatePackages"></a> -<h4>Pip.__listUptodatePackages</h4> -<b>__listUptodatePackages</b>(<i></i>) -<p> - Private slot to list all installed, up-to-date packages. -</p><a NAME="Pip.__pipConfigure" ID="Pip.__pipConfigure"></a> -<h4>Pip.__pipConfigure</h4> -<b>__pipConfigure</b>(<i></i>) -<p> - Private slot to open the configuration page. -</p><a NAME="Pip.__repairPip" ID="Pip.__repairPip"></a> -<h4>Pip.__repairPip</h4> -<b>__repairPip</b>(<i></i>) -<p> - Private method to repair the pip installation. -</p><dl> -<dt>Returns:</dt> -<dd> -flag indicating a successful execution -</dd> -</dl><dl> -<dt>Return Type:</dt> -<dd> -bool -</dd> -</dl><a NAME="Pip.__searchPyPI" ID="Pip.__searchPyPI"></a> -<h4>Pip.__searchPyPI</h4> -<b>__searchPyPI</b>(<i></i>) -<p> - Private slot to search the Python Package Index. -</p><a NAME="Pip.__selectPipVirtualenv" ID="Pip.__selectPipVirtualenv"></a> -<h4>Pip.__selectPipVirtualenv</h4> -<b>__selectPipVirtualenv</b>(<i></i>) -<p> - Private method to select the virtual environment to be used. -</p><a NAME="Pip.__uninstallPackages" ID="Pip.__uninstallPackages"></a> -<h4>Pip.__uninstallPackages</h4> -<b>__uninstallPackages</b>(<i></i>) -<p> - Private slot to uninstall packages to be given by the user. -</p><a NAME="Pip.__uninstallRequirements" ID="Pip.__uninstallRequirements"></a> -<h4>Pip.__uninstallRequirements</h4> -<b>__uninstallRequirements</b>(<i></i>) -<p> - Private slot to uninstall packages as given in a requirements file. -</p><a NAME="Pip.__upgradePackages" ID="Pip.__upgradePackages"></a> -<h4>Pip.__upgradePackages</h4> -<b>__upgradePackages</b>(<i></i>) -<p> - Private slot to upgrade packages to be given by the user. -</p><a NAME="Pip.getDefaultEnvironmentString" ID="Pip.getDefaultEnvironmentString"></a> -<h4>Pip.getDefaultEnvironmentString</h4> -<b>getDefaultEnvironmentString</b>(<i></i>) -<p> - Public method to get the string for the default environment. -</p><dl> -<dt>Returns:</dt> -<dd> -string for the default environment -</dd> -</dl><dl> -<dt>Return Type:</dt> -<dd> -str -</dd> -</dl><a NAME="Pip.getMenu" ID="Pip.getMenu"></a> -<h4>Pip.getMenu</h4> -<b>getMenu</b>(<i>name</i>) -<p> - Public method to get a reference to the requested menu. -</p><dl> -<dt><i>name</i> (str)</dt> -<dd> -name of the menu -</dd> -</dl><dl> -<dt>Returns:</dt> -<dd> -reference to the menu or None, if no - menu with the given name exists -</dd> -</dl><dl> -<dt>Return Type:</dt> -<dd> -QMenu or None -</dd> -</dl><a NAME="Pip.getMenuNames" ID="Pip.getMenuNames"></a> -<h4>Pip.getMenuNames</h4> -<b>getMenuNames</b>(<i></i>) -<p> - Public method to get the names of all menus. -</p><dl> -<dt>Returns:</dt> -<dd> -menu names -</dd> -</dl><dl> -<dt>Return Type:</dt> -<dd> -list of str -</dd> -</dl><a NAME="Pip.getProjectEnvironmentString" ID="Pip.getProjectEnvironmentString"></a> -<h4>Pip.getProjectEnvironmentString</h4> -<b>getProjectEnvironmentString</b>(<i></i>) -<p> - Public method to get the string for the project environment. -</p><dl> -<dt>Returns:</dt> -<dd> -string for the project environment -</dd> -</dl><dl> -<dt>Return Type:</dt> -<dd> -str -</dd> -</dl><a NAME="Pip.getVirtualenvInterpreter" ID="Pip.getVirtualenvInterpreter"></a> -<h4>Pip.getVirtualenvInterpreter</h4> -<b>getVirtualenvInterpreter</b>(<i>venvName</i>) -<p> - Public method to get the interpreter for a virtual environment. -</p><dl> -<dt><i>venvName</i> (str)</dt> -<dd> -logical name for the virtual environment -</dd> -</dl><dl> -<dt>Returns:</dt> -<dd> -interpreter path -</dd> -</dl><dl> -<dt>Return Type:</dt> -<dd> -str -</dd> -</dl><a NAME="Pip.getVirtualenvNames" ID="Pip.getVirtualenvNames"></a> -<h4>Pip.getVirtualenvNames</h4> -<b>getVirtualenvNames</b>(<i></i>) -<p> - Public method to get a sorted list of virtual environment names. -</p><dl> -<dt>Returns:</dt> -<dd> -sorted list of virtual environment names -</dd> -</dl><dl> -<dt>Return Type:</dt> -<dd> -list of str -</dd> -</dl><a NAME="Pip.initActions" ID="Pip.initActions"></a> -<h4>Pip.initActions</h4> -<b>initActions</b>(<i></i>) -<p> - Public method to define the actions. -</p><a NAME="Pip.initMenu" ID="Pip.initMenu"></a> -<h4>Pip.initMenu</h4> -<b>initMenu</b>(<i></i>) -<p> - Public slot to initialize the menu. -</p><dl> -<dt>Returns:</dt> -<dd> -the menu generated -</dd> -</dl><dl> -<dt>Return Type:</dt> -<dd> -QMenu -</dd> -</dl><a NAME="Pip.installPackages" ID="Pip.installPackages"></a> -<h4>Pip.installPackages</h4> -<b>installPackages</b>(<i>packages, venvName="", userSite=False</i>) -<p> - Public method to install the given list of packages. -</p><dl> -<dt><i>packages</i> (list of str)</dt> -<dd> -list of packages to install -</dd><dt><i>venvName</i> (str)</dt> -<dd> -name of the virtual environment to be used -</dd><dt><i>userSite</i> (bool)</dt> -<dd> -flag indicating an install to the user install - directory -</dd> -</dl><a NAME="Pip.runProcess" ID="Pip.runProcess"></a> -<h4>Pip.runProcess</h4> -<b>runProcess</b>(<i>args, interpreter</i>) -<p> - Public method to execute the current pip with the given arguments. -</p><p> - The selected pip executable is called with the given arguments and - waited for its end. -</p><dl> -<dt><i>args</i> (list of str)</dt> -<dd> -list of command line arguments -</dd><dt><i>interpreter</i> (str)</dt> -<dd> -path of the Python interpreter to be used -</dd> -</dl><dl> -<dt>Returns:</dt> -<dd> -tuple containing a flag indicating success and the output - of the process -</dd> -</dl><dl> -<dt>Return Type:</dt> -<dd> -tuple of (bool, str) -</dd> -</dl><a NAME="Pip.uninstallPackages" ID="Pip.uninstallPackages"></a> -<h4>Pip.uninstallPackages</h4> -<b>uninstallPackages</b>(<i>packages, venvName=""</i>) -<p> - Public method to uninstall the given list of packages. -</p><dl> -<dt><i>packages</i> (list of str)</dt> -<dd> -list of packages to uninstall -</dd><dt><i>venvName</i> (str)</dt> -<dd> -name of the virtual environment to be used -</dd> -</dl><dl> -<dt>Returns:</dt> -<dd> -flag indicating a successful execution -</dd> -</dl><dl> -<dt>Return Type:</dt> -<dd> -bool -</dd> -</dl><a NAME="Pip.upgradePackages" ID="Pip.upgradePackages"></a> -<h4>Pip.upgradePackages</h4> -<b>upgradePackages</b>(<i>packages, venvName="", userSite=False</i>) -<p> - Public method to upgrade the given list of packages. -</p><dl> -<dt><i>packages</i> (list of str)</dt> -<dd> -list of packages to upgrade -</dd><dt><i>venvName</i> (str)</dt> -<dd> -name of the virtual environment to be used -</dd><dt><i>userSite</i> (bool)</dt> -<dd> -flag indicating an install to the user install - directory -</dd> -</dl><dl> -<dt>Returns:</dt> -<dd> -flag indicating a successful execution -</dd> -</dl><dl> -<dt>Return Type:</dt> -<dd> -bool -</dd> -</dl><a NAME="Pip.upgradePip" ID="Pip.upgradePip"></a> -<h4>Pip.upgradePip</h4> -<b>upgradePip</b>(<i>venvName="", userSite=False</i>) -<p> - Public method to upgrade pip itself. -</p><dl> -<dt><i>venvName</i> (str)</dt> -<dd> -name of the virtual environment to be used -</dd><dt><i>userSite</i> (bool)</dt> -<dd> -flag indicating an install to the user install - directory -</dd> -</dl><dl> -<dt>Returns:</dt> -<dd> -flag indicating a successful execution -</dd> -</dl><dl> -<dt>Return Type:</dt> -<dd> -bool -</dd> -</dl> -<div align="right"><a href="#top">Up</a></div> -<hr /> -</body></html> \ No newline at end of file
--- a/Documentation/Source/eric6.Plugins.UiExtensionPlugins.PipInterface.PipDialog.html Sat Feb 23 13:05:18 2019 +0100 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,224 +0,0 @@ -<!DOCTYPE html> -<html><head> -<title>eric6.Plugins.UiExtensionPlugins.PipInterface.PipDialog</title> -<meta charset="UTF-8"> -<style> -body { - background: #EDECE6; - margin: 0em 1em 10em 1em; - color: black; -} - -h1 { color: white; background: #85774A; } -h2 { color: white; background: #85774A; } -h3 { color: white; background: #9D936E; } -h4 { color: white; background: #9D936E; } - -a { color: #BA6D36; } - -</style> -</head> -<body><a NAME="top" ID="top"></a> -<h1>eric6.Plugins.UiExtensionPlugins.PipInterface.PipDialog</h1> -<p> -Module implementing a dialog showing the output of a pip command. -</p> -<h3>Global Attributes</h3> -<table> -<tr><td>None</td></tr> -</table> -<h3>Classes</h3> -<table> -<tr> -<td><a href="#PipDialog">PipDialog</a></td> -<td>Class implementing a dialog showing the output of a 'python -m pip' command.</td> -</tr> -</table> -<h3>Functions</h3> -<table> -<tr><td>None</td></tr> -</table> -<hr /><hr /> -<a NAME="PipDialog" ID="PipDialog"></a> -<h2>PipDialog</h2> -<p> - Class implementing a dialog showing the output of a 'python -m pip' - command. -</p> -<h3>Derived from</h3> -QDialog, Ui_PipDialog -<h3>Class Attributes</h3> -<table> -<tr><td>None</td></tr> -</table> -<h3>Class Methods</h3> -<table> -<tr><td>None</td></tr> -</table> -<h3>Methods</h3> -<table> -<tr> -<td><a href="#PipDialog.__init__">PipDialog</a></td> -<td>Constructor</td> -</tr><tr> -<td><a href="#PipDialog.__addOutput">__addOutput</a></td> -<td>Private method to add some text to the output pane.</td> -</tr><tr> -<td><a href="#PipDialog.__finish">__finish</a></td> -<td>Private slot called when the process finished or the user pressed the button.</td> -</tr><tr> -<td><a href="#PipDialog.__procFinished">__procFinished</a></td> -<td>Private slot connected to the finished signal.</td> -</tr><tr> -<td><a href="#PipDialog.__readStderr">__readStderr</a></td> -<td>Private slot to handle the readyReadStandardError signal.</td> -</tr><tr> -<td><a href="#PipDialog.__readStdout">__readStdout</a></td> -<td>Private slot to handle the readyReadStandardOutput signal.</td> -</tr><tr> -<td><a href="#PipDialog.closeEvent">closeEvent</a></td> -<td>Protected slot implementing a close event handler.</td> -</tr><tr> -<td><a href="#PipDialog.on_buttonBox_clicked">on_buttonBox_clicked</a></td> -<td>Private slot called by a button of the button box clicked.</td> -</tr><tr> -<td><a href="#PipDialog.startProcess">startProcess</a></td> -<td>Public slot used to start the process.</td> -</tr><tr> -<td><a href="#PipDialog.startProcesses">startProcesses</a></td> -<td>Public method to issue a list of commands to be executed.</td> -</tr> -</table> -<h3>Static Methods</h3> -<table> -<tr><td>None</td></tr> -</table> -<a NAME="PipDialog.__init__" ID="PipDialog.__init__"></a> -<h4>PipDialog (Constructor)</h4> -<b>PipDialog</b>(<i>text, parent=None</i>) -<p> - Constructor -</p><dl> -<dt><i>text</i> (str)</dt> -<dd> -text to be shown by the label -</dd><dt><i>parent</i> (QWidget)</dt> -<dd> -reference to the parent widget -</dd> -</dl><a NAME="PipDialog.__addOutput" ID="PipDialog.__addOutput"></a> -<h4>PipDialog.__addOutput</h4> -<b>__addOutput</b>(<i>txt</i>) -<p> - Private method to add some text to the output pane. -</p><dl> -<dt><i>txt</i> (str)</dt> -<dd> -text to be added -</dd> -</dl><a NAME="PipDialog.__finish" ID="PipDialog.__finish"></a> -<h4>PipDialog.__finish</h4> -<b>__finish</b>(<i></i>) -<p> - Private slot called when the process finished or the user pressed - the button. -</p><a NAME="PipDialog.__procFinished" ID="PipDialog.__procFinished"></a> -<h4>PipDialog.__procFinished</h4> -<b>__procFinished</b>(<i>exitCode, exitStatus</i>) -<p> - Private slot connected to the finished signal. -</p><dl> -<dt><i>exitCode</i> (int)</dt> -<dd> -exit code of the process -</dd><dt><i>exitStatus</i> (QProcess.ExitStatus)</dt> -<dd> -exit status of the process -</dd> -</dl><a NAME="PipDialog.__readStderr" ID="PipDialog.__readStderr"></a> -<h4>PipDialog.__readStderr</h4> -<b>__readStderr</b>(<i></i>) -<p> - Private slot to handle the readyReadStandardError signal. -</p><p> - It reads the error output of the process and inserts it into the - error pane. -</p><a NAME="PipDialog.__readStdout" ID="PipDialog.__readStdout"></a> -<h4>PipDialog.__readStdout</h4> -<b>__readStdout</b>(<i></i>) -<p> - Private slot to handle the readyReadStandardOutput signal. -</p><p> - It reads the output of the process, formats it and inserts it into - the contents pane. -</p><a NAME="PipDialog.closeEvent" ID="PipDialog.closeEvent"></a> -<h4>PipDialog.closeEvent</h4> -<b>closeEvent</b>(<i>e</i>) -<p> - Protected slot implementing a close event handler. -</p><dl> -<dt><i>e</i> (QCloseEvent)</dt> -<dd> -close event -</dd> -</dl><a NAME="PipDialog.on_buttonBox_clicked" ID="PipDialog.on_buttonBox_clicked"></a> -<h4>PipDialog.on_buttonBox_clicked</h4> -<b>on_buttonBox_clicked</b>(<i>button</i>) -<p> - Private slot called by a button of the button box clicked. -</p><dl> -<dt><i>button</i> (QAbstractButton)</dt> -<dd> -button that was clicked -</dd> -</dl><a NAME="PipDialog.startProcess" ID="PipDialog.startProcess"></a> -<h4>PipDialog.startProcess</h4> -<b>startProcess</b>(<i>cmd, args, showArgs=True</i>) -<p> - Public slot used to start the process. -</p><dl> -<dt><i>cmd</i> (str)</dt> -<dd> -name of the pip executable to be used -</dd><dt><i>args</i> (list of str)</dt> -<dd> -list of arguments for the process -</dd><dt><i>showArgs=</i> (bool)</dt> -<dd> -flag indicating to show the arguments -</dd> -</dl><dl> -<dt>Returns:</dt> -<dd> -flag indicating a successful start of the process -</dd> -</dl><dl> -<dt>Return Type:</dt> -<dd> -bool -</dd> -</dl><a NAME="PipDialog.startProcesses" ID="PipDialog.startProcesses"></a> -<h4>PipDialog.startProcesses</h4> -<b>startProcesses</b>(<i>processParams</i>) -<p> - Public method to issue a list of commands to be executed. -</p><dl> -<dt><i>processParams</i> (list of tuples of (str, list of str))</dt> -<dd> -list of tuples containing the command - and arguments -</dd> -</dl><dl> -<dt>Returns:</dt> -<dd> -flag indicating a successful start of the first process -</dd> -</dl><dl> -<dt>Return Type:</dt> -<dd> -bool -</dd> -</dl> -<div align="right"><a href="#top">Up</a></div> -<hr /> -</body></html> \ No newline at end of file
--- a/Documentation/Source/eric6.Plugins.UiExtensionPlugins.PipInterface.PipFileSelectionDialog.html Sat Feb 23 13:05:18 2019 +0100 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,123 +0,0 @@ -<!DOCTYPE html> -<html><head> -<title>eric6.Plugins.UiExtensionPlugins.PipInterface.PipFileSelectionDialog</title> -<meta charset="UTF-8"> -<style> -body { - background: #EDECE6; - margin: 0em 1em 10em 1em; - color: black; -} - -h1 { color: white; background: #85774A; } -h2 { color: white; background: #85774A; } -h3 { color: white; background: #9D936E; } -h4 { color: white; background: #9D936E; } - -a { color: #BA6D36; } - -</style> -</head> -<body><a NAME="top" ID="top"></a> -<h1>eric6.Plugins.UiExtensionPlugins.PipInterface.PipFileSelectionDialog</h1> -<p> -Module implementing a dialog to enter a file to be processed. -</p> -<h3>Global Attributes</h3> -<table> -<tr><td>None</td></tr> -</table> -<h3>Classes</h3> -<table> -<tr> -<td><a href="#PipFileSelectionDialog">PipFileSelectionDialog</a></td> -<td>Class implementing a dialog to enter a file to be processed.</td> -</tr> -</table> -<h3>Functions</h3> -<table> -<tr><td>None</td></tr> -</table> -<hr /><hr /> -<a NAME="PipFileSelectionDialog" ID="PipFileSelectionDialog"></a> -<h2>PipFileSelectionDialog</h2> -<p> - Class implementing a dialog to enter a file to be processed. -</p> -<h3>Derived from</h3> -QDialog, Ui_PipFileSelectionDialog -<h3>Class Attributes</h3> -<table> -<tr><td>None</td></tr> -</table> -<h3>Class Methods</h3> -<table> -<tr><td>None</td></tr> -</table> -<h3>Methods</h3> -<table> -<tr> -<td><a href="#PipFileSelectionDialog.__init__">PipFileSelectionDialog</a></td> -<td>Constructor</td> -</tr><tr> -<td><a href="#PipFileSelectionDialog.getData">getData</a></td> -<td>Public method to get the entered data.</td> -</tr><tr> -<td><a href="#PipFileSelectionDialog.on_filePicker_textChanged">on_filePicker_textChanged</a></td> -<td>Private slot to handle entering the name of a file.</td> -</tr> -</table> -<h3>Static Methods</h3> -<table> -<tr><td>None</td></tr> -</table> -<a NAME="PipFileSelectionDialog.__init__" ID="PipFileSelectionDialog.__init__"></a> -<h4>PipFileSelectionDialog (Constructor)</h4> -<b>PipFileSelectionDialog</b>(<i>pip, mode, install=True, parent=None</i>) -<p> - Constructor -</p><dl> -<dt><i>pip</i> (Pip)</dt> -<dd> -reference to the pip object -</dd><dt><i>mode</i> (str)</dt> -<dd> -mode of the dialog -</dd><dt><i>install</i> (bool)</dt> -<dd> -flag indicating an install action -</dd><dt><i>parent</i> (QWidget)</dt> -<dd> -reference to the parent widget -</dd> -</dl><a NAME="PipFileSelectionDialog.getData" ID="PipFileSelectionDialog.getData"></a> -<h4>PipFileSelectionDialog.getData</h4> -<b>getData</b>(<i></i>) -<p> - Public method to get the entered data. -</p><dl> -<dt>Returns:</dt> -<dd> -tuple with the environment name, the name of the - selected file and a flag indicating to install to the - user install directory -</dd> -</dl><dl> -<dt>Return Type:</dt> -<dd> -tuple of (str, str, bool) -</dd> -</dl><a NAME="PipFileSelectionDialog.on_filePicker_textChanged" ID="PipFileSelectionDialog.on_filePicker_textChanged"></a> -<h4>PipFileSelectionDialog.on_filePicker_textChanged</h4> -<b>on_filePicker_textChanged</b>(<i>txt</i>) -<p> - Private slot to handle entering the name of a file. -</p><dl> -<dt><i>txt</i> (str)</dt> -<dd> -name of the file -</dd> -</dl> -<div align="right"><a href="#top">Up</a></div> -<hr /> -</body></html> \ No newline at end of file
--- a/Documentation/Source/eric6.Plugins.UiExtensionPlugins.PipInterface.PipFreezeDialog.html Sat Feb 23 13:05:18 2019 +0100 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,245 +0,0 @@ -<!DOCTYPE html> -<html><head> -<title>eric6.Plugins.UiExtensionPlugins.PipInterface.PipFreezeDialog</title> -<meta charset="UTF-8"> -<style> -body { - background: #EDECE6; - margin: 0em 1em 10em 1em; - color: black; -} - -h1 { color: white; background: #85774A; } -h2 { color: white; background: #85774A; } -h3 { color: white; background: #9D936E; } -h4 { color: white; background: #9D936E; } - -a { color: #BA6D36; } - -</style> -</head> -<body><a NAME="top" ID="top"></a> -<h1>eric6.Plugins.UiExtensionPlugins.PipInterface.PipFreezeDialog</h1> -<p> -Module implementing a dialog to generate a requirements file. -</p> -<h3>Global Attributes</h3> -<table> -<tr><td>None</td></tr> -</table> -<h3>Classes</h3> -<table> -<tr> -<td><a href="#PipFreezeDialog">PipFreezeDialog</a></td> -<td>Class implementing a dialog to generate a requirements file.</td> -</tr> -</table> -<h3>Functions</h3> -<table> -<tr><td>None</td></tr> -</table> -<hr /><hr /> -<a NAME="PipFreezeDialog" ID="PipFreezeDialog"></a> -<h2>PipFreezeDialog</h2> -<p> - Class implementing a dialog to generate a requirements file. -</p> -<h3>Derived from</h3> -QDialog, Ui_PipFreezeDialog -<h3>Class Attributes</h3> -<table> -<tr><td>None</td></tr> -</table> -<h3>Class Methods</h3> -<table> -<tr><td>None</td></tr> -</table> -<h3>Methods</h3> -<table> -<tr> -<td><a href="#PipFreezeDialog.__init__">PipFreezeDialog</a></td> -<td>Constructor</td> -</tr><tr> -<td><a href="#PipFreezeDialog.__refresh">__refresh</a></td> -<td>Private slot to refresh the displayed list.</td> -</tr><tr> -<td><a href="#PipFreezeDialog.__updateButtons">__updateButtons</a></td> -<td>Private method to set the state of the various buttons.</td> -</tr><tr> -<td><a href="#PipFreezeDialog.__writeToFile">__writeToFile</a></td> -<td>Private method to write the requirements text to a file.</td> -</tr><tr> -<td><a href="#PipFreezeDialog.closeEvent">closeEvent</a></td> -<td>Protected slot implementing a close event handler.</td> -</tr><tr> -<td><a href="#PipFreezeDialog.on_buttonBox_clicked">on_buttonBox_clicked</a></td> -<td>Private slot called by a button of the button box clicked.</td> -</tr><tr> -<td><a href="#PipFreezeDialog.on_copyButton_clicked">on_copyButton_clicked</a></td> -<td>Private slot to copy the requirements text to the clipboard.</td> -</tr><tr> -<td><a href="#PipFreezeDialog.on_insertButton_clicked">on_insertButton_clicked</a></td> -<td>Private slot to insert the requirements text at the cursor position of the current editor.</td> -</tr><tr> -<td><a href="#PipFreezeDialog.on_localCheckBox_clicked">on_localCheckBox_clicked</a></td> -<td>Private slot handling the switching of the local mode.</td> -</tr><tr> -<td><a href="#PipFreezeDialog.on_replaceAllButton_clicked">on_replaceAllButton_clicked</a></td> -<td>Private slot to replace the text of the current editor with the requirements text.</td> -</tr><tr> -<td><a href="#PipFreezeDialog.on_replaceSelectionButton_clicked">on_replaceSelectionButton_clicked</a></td> -<td>Private slot to replace the selected text of the current editor with the requirements text.</td> -</tr><tr> -<td><a href="#PipFreezeDialog.on_requirementsEdit_textChanged">on_requirementsEdit_textChanged</a></td> -<td>Private slot handling changes of the requirements text.</td> -</tr><tr> -<td><a href="#PipFreezeDialog.on_requirementsFilePicker_textChanged">on_requirementsFilePicker_textChanged</a></td> -<td>Private slot handling a change of the requirements file name.</td> -</tr><tr> -<td><a href="#PipFreezeDialog.on_saveButton_clicked">on_saveButton_clicked</a></td> -<td>Private slot to save the requirements text to the requirements file.</td> -</tr><tr> -<td><a href="#PipFreezeDialog.on_saveToButton_clicked">on_saveToButton_clicked</a></td> -<td>Private slot to write the requirements text to a new file.</td> -</tr><tr> -<td><a href="#PipFreezeDialog.on_venvComboBox_activated">on_venvComboBox_activated</a></td> -<td>Private slot handling the selection of a virtual environment.</td> -</tr><tr> -<td><a href="#PipFreezeDialog.start">start</a></td> -<td>Public method to start the command.</td> -</tr> -</table> -<h3>Static Methods</h3> -<table> -<tr><td>None</td></tr> -</table> -<a NAME="PipFreezeDialog.__init__" ID="PipFreezeDialog.__init__"></a> -<h4>PipFreezeDialog (Constructor)</h4> -<b>PipFreezeDialog</b>(<i>pip, parent=None</i>) -<p> - Constructor -</p><dl> -<dt><i>pip</i> (Pip)</dt> -<dd> -reference to the master object -</dd><dt><i>parent</i> (QWidget)</dt> -<dd> -reference to the parent widget -</dd> -</dl><a NAME="PipFreezeDialog.__refresh" ID="PipFreezeDialog.__refresh"></a> -<h4>PipFreezeDialog.__refresh</h4> -<b>__refresh</b>(<i></i>) -<p> - Private slot to refresh the displayed list. -</p><a NAME="PipFreezeDialog.__updateButtons" ID="PipFreezeDialog.__updateButtons"></a> -<h4>PipFreezeDialog.__updateButtons</h4> -<b>__updateButtons</b>(<i></i>) -<p> - Private method to set the state of the various buttons. -</p><a NAME="PipFreezeDialog.__writeToFile" ID="PipFreezeDialog.__writeToFile"></a> -<h4>PipFreezeDialog.__writeToFile</h4> -<b>__writeToFile</b>(<i>fileName</i>) -<p> - Private method to write the requirements text to a file. -</p><dl> -<dt><i>fileName</i> (str)</dt> -<dd> -name of the file to write to -</dd> -</dl><a NAME="PipFreezeDialog.closeEvent" ID="PipFreezeDialog.closeEvent"></a> -<h4>PipFreezeDialog.closeEvent</h4> -<b>closeEvent</b>(<i>e</i>) -<p> - Protected slot implementing a close event handler. -</p><dl> -<dt><i>e</i> (QCloseEvent)</dt> -<dd> -close event -</dd> -</dl><a NAME="PipFreezeDialog.on_buttonBox_clicked" ID="PipFreezeDialog.on_buttonBox_clicked"></a> -<h4>PipFreezeDialog.on_buttonBox_clicked</h4> -<b>on_buttonBox_clicked</b>(<i>button</i>) -<p> - Private slot called by a button of the button box clicked. -</p><dl> -<dt><i>button</i> (QAbstractButton)</dt> -<dd> -button that was clicked -</dd> -</dl><a NAME="PipFreezeDialog.on_copyButton_clicked" ID="PipFreezeDialog.on_copyButton_clicked"></a> -<h4>PipFreezeDialog.on_copyButton_clicked</h4> -<b>on_copyButton_clicked</b>(<i></i>) -<p> - Private slot to copy the requirements text to the clipboard. -</p><a NAME="PipFreezeDialog.on_insertButton_clicked" ID="PipFreezeDialog.on_insertButton_clicked"></a> -<h4>PipFreezeDialog.on_insertButton_clicked</h4> -<b>on_insertButton_clicked</b>(<i></i>) -<p> - Private slot to insert the requirements text at the cursor position - of the current editor. -</p><a NAME="PipFreezeDialog.on_localCheckBox_clicked" ID="PipFreezeDialog.on_localCheckBox_clicked"></a> -<h4>PipFreezeDialog.on_localCheckBox_clicked</h4> -<b>on_localCheckBox_clicked</b>(<i>checked</i>) -<p> - Private slot handling the switching of the local mode. -</p><dl> -<dt><i>checked</i> (bool)</dt> -<dd> -state of the local check box -</dd> -</dl><a NAME="PipFreezeDialog.on_replaceAllButton_clicked" ID="PipFreezeDialog.on_replaceAllButton_clicked"></a> -<h4>PipFreezeDialog.on_replaceAllButton_clicked</h4> -<b>on_replaceAllButton_clicked</b>(<i></i>) -<p> - Private slot to replace the text of the current editor with the - requirements text. -</p><a NAME="PipFreezeDialog.on_replaceSelectionButton_clicked" ID="PipFreezeDialog.on_replaceSelectionButton_clicked"></a> -<h4>PipFreezeDialog.on_replaceSelectionButton_clicked</h4> -<b>on_replaceSelectionButton_clicked</b>(<i></i>) -<p> - Private slot to replace the selected text of the current editor - with the requirements text. -</p><a NAME="PipFreezeDialog.on_requirementsEdit_textChanged" ID="PipFreezeDialog.on_requirementsEdit_textChanged"></a> -<h4>PipFreezeDialog.on_requirementsEdit_textChanged</h4> -<b>on_requirementsEdit_textChanged</b>(<i></i>) -<p> - Private slot handling changes of the requirements text. -</p><a NAME="PipFreezeDialog.on_requirementsFilePicker_textChanged" ID="PipFreezeDialog.on_requirementsFilePicker_textChanged"></a> -<h4>PipFreezeDialog.on_requirementsFilePicker_textChanged</h4> -<b>on_requirementsFilePicker_textChanged</b>(<i>txt</i>) -<p> - Private slot handling a change of the requirements file name. -</p><dl> -<dt><i>txt</i> (str)</dt> -<dd> -name of the requirements file -</dd> -</dl><a NAME="PipFreezeDialog.on_saveButton_clicked" ID="PipFreezeDialog.on_saveButton_clicked"></a> -<h4>PipFreezeDialog.on_saveButton_clicked</h4> -<b>on_saveButton_clicked</b>(<i></i>) -<p> - Private slot to save the requirements text to the requirements file. -</p><a NAME="PipFreezeDialog.on_saveToButton_clicked" ID="PipFreezeDialog.on_saveToButton_clicked"></a> -<h4>PipFreezeDialog.on_saveToButton_clicked</h4> -<b>on_saveToButton_clicked</b>(<i></i>) -<p> - Private slot to write the requirements text to a new file. -</p><a NAME="PipFreezeDialog.on_venvComboBox_activated" ID="PipFreezeDialog.on_venvComboBox_activated"></a> -<h4>PipFreezeDialog.on_venvComboBox_activated</h4> -<b>on_venvComboBox_activated</b>(<i>txt</i>) -<p> - Private slot handling the selection of a virtual environment. -</p><dl> -<dt><i>txt</i> (str)</dt> -<dd> -virtual environment -</dd> -</dl><a NAME="PipFreezeDialog.start" ID="PipFreezeDialog.start"></a> -<h4>PipFreezeDialog.start</h4> -<b>start</b>(<i></i>) -<p> - Public method to start the command. -</p> -<div align="right"><a href="#top">Up</a></div> -<hr /> -</body></html> \ No newline at end of file
--- a/Documentation/Source/eric6.Plugins.UiExtensionPlugins.PipInterface.PipListDialog.html Sat Feb 23 13:05:18 2019 +0100 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,331 +0,0 @@ -<!DOCTYPE html> -<html><head> -<title>eric6.Plugins.UiExtensionPlugins.PipInterface.PipListDialog</title> -<meta charset="UTF-8"> -<style> -body { - background: #EDECE6; - margin: 0em 1em 10em 1em; - color: black; -} - -h1 { color: white; background: #85774A; } -h2 { color: white; background: #85774A; } -h3 { color: white; background: #9D936E; } -h4 { color: white; background: #9D936E; } - -a { color: #BA6D36; } - -</style> -</head> -<body><a NAME="top" ID="top"></a> -<h1>eric6.Plugins.UiExtensionPlugins.PipInterface.PipListDialog</h1> -<p> -Module implementing a dialog to list installed packages. -</p> -<h3>Global Attributes</h3> -<table> -<tr><td>None</td></tr> -</table> -<h3>Classes</h3> -<table> -<tr> -<td><a href="#PipListDialog">PipListDialog</a></td> -<td>Class implementing a dialog to list installed packages.</td> -</tr> -</table> -<h3>Functions</h3> -<table> -<tr><td>None</td></tr> -</table> -<hr /><hr /> -<a NAME="PipListDialog" ID="PipListDialog"></a> -<h2>PipListDialog</h2> -<p> - Class implementing a dialog to list installed packages. -</p> -<h3>Derived from</h3> -QDialog, Ui_PipListDialog -<h3>Class Attributes</h3> -<table> -<tr><td>CommandArguments</td></tr><tr><td>ShowProcessClassifiersMode</td></tr><tr><td>ShowProcessEntryPointsMode</td></tr><tr><td>ShowProcessFilesListMode</td></tr><tr><td>ShowProcessGeneralMode</td></tr> -</table> -<h3>Class Methods</h3> -<table> -<tr><td>None</td></tr> -</table> -<h3>Methods</h3> -<table> -<tr> -<td><a href="#PipListDialog.__init__">PipListDialog</a></td> -<td>Constructor</td> -</tr><tr> -<td><a href="#PipListDialog.__executeUpgradePackages">__executeUpgradePackages</a></td> -<td>Private method to execute the pip upgrade command.</td> -</tr><tr> -<td><a href="#PipListDialog.__finish">__finish</a></td> -<td>Private slot called when the process finished or the user pressed the cancel button.</td> -</tr><tr> -<td><a href="#PipListDialog.__procFinished">__procFinished</a></td> -<td>Private slot connected to the finished signal.</td> -</tr><tr> -<td><a href="#PipListDialog.__processOutput">__processOutput</a></td> -<td>Private method to process the captured output.</td> -</tr><tr> -<td><a href="#PipListDialog.__readStderr">__readStderr</a></td> -<td>Private slot to handle the readyReadStandardError signal.</td> -</tr><tr> -<td><a href="#PipListDialog.__readStdout">__readStdout</a></td> -<td>Private slot to handle the readyReadStandardOutput signal.</td> -</tr><tr> -<td><a href="#PipListDialog.__refresh">__refresh</a></td> -<td>Private slot to refresh the displayed list.</td> -</tr><tr> -<td><a href="#PipListDialog.__stopProcess">__stopProcess</a></td> -<td>Private slot to stop the running process.</td> -</tr><tr> -<td><a href="#PipListDialog.__uninstallPackages">__uninstallPackages</a></td> -<td>Private slot to uninstall the selected packages.</td> -</tr><tr> -<td><a href="#PipListDialog.__upgradeAllPackages">__upgradeAllPackages</a></td> -<td>Private slot to upgrade all listed packages.</td> -</tr><tr> -<td><a href="#PipListDialog.__upgradePackages">__upgradePackages</a></td> -<td>Private slot to upgrade the selected packages.</td> -</tr><tr> -<td><a href="#PipListDialog.__upgradePip">__upgradePip</a></td> -<td>Private slot to upgrade pip itself.</td> -</tr><tr> -<td><a href="#PipListDialog.closeEvent">closeEvent</a></td> -<td>Protected slot implementing a close event handler.</td> -</tr><tr> -<td><a href="#PipListDialog.on_buttonBox_clicked">on_buttonBox_clicked</a></td> -<td>Private slot called by a button of the button box clicked.</td> -</tr><tr> -<td><a href="#PipListDialog.on_installedFilesCheckBox_clicked">on_installedFilesCheckBox_clicked</a></td> -<td>Private slot to handle a change of the installed files information checkbox.</td> -</tr><tr> -<td><a href="#PipListDialog.on_localCheckBox_clicked">on_localCheckBox_clicked</a></td> -<td>Private slot handling the switching of the local mode.</td> -</tr><tr> -<td><a href="#PipListDialog.on_notRequiredCheckBox_clicked">on_notRequiredCheckBox_clicked</a></td> -<td>Private slot handling the switching of the 'not required' mode.</td> -</tr><tr> -<td><a href="#PipListDialog.on_packageList_itemSelectionChanged">on_packageList_itemSelectionChanged</a></td> -<td>Private slot handling the selection of a package.</td> -</tr><tr> -<td><a href="#PipListDialog.on_userCheckBox_clicked">on_userCheckBox_clicked</a></td> -<td>Private slot handling the switching of the 'user-site' mode.</td> -</tr><tr> -<td><a href="#PipListDialog.on_venvComboBox_activated">on_venvComboBox_activated</a></td> -<td>Private slot handling the selection of a virtual environment.</td> -</tr><tr> -<td><a href="#PipListDialog.on_verboseCheckBox_clicked">on_verboseCheckBox_clicked</a></td> -<td>Private slot to handle a change of the verbose package information checkbox.</td> -</tr><tr> -<td><a href="#PipListDialog.start">start</a></td> -<td>Public method to start the command.</td> -</tr> -</table> -<h3>Static Methods</h3> -<table> -<tr><td>None</td></tr> -</table> -<a NAME="PipListDialog.__init__" ID="PipListDialog.__init__"></a> -<h4>PipListDialog (Constructor)</h4> -<b>PipListDialog</b>(<i>pip, mode, indexUrl, title, parent=None</i>) -<p> - Constructor -</p><dl> -<dt><i>pip</i> (Pip)</dt> -<dd> -reference to the master object -</dd><dt><i>mode</i> (str)</dt> -<dd> -list command mode (one of 'list', 'uptodate', 'outdated') -</dd><dt><i>indexUrl</i> (str)</dt> -<dd> -URL of the pypi index -</dd><dt><i>title</i> (str)</dt> -<dd> -title of the dialog -</dd><dt><i>parent</i> (QWidget)</dt> -<dd> -reference to the parent widget -</dd> -</dl><a NAME="PipListDialog.__executeUpgradePackages" ID="PipListDialog.__executeUpgradePackages"></a> -<h4>PipListDialog.__executeUpgradePackages</h4> -<b>__executeUpgradePackages</b>(<i>packages</i>) -<p> - Private method to execute the pip upgrade command. -</p><dl> -<dt><i>packages</i> (list of str)</dt> -<dd> -list of package names to be upgraded -</dd> -</dl><a NAME="PipListDialog.__finish" ID="PipListDialog.__finish"></a> -<h4>PipListDialog.__finish</h4> -<b>__finish</b>(<i></i>) -<p> - Private slot called when the process finished or the user pressed - the cancel button. -</p><a NAME="PipListDialog.__procFinished" ID="PipListDialog.__procFinished"></a> -<h4>PipListDialog.__procFinished</h4> -<b>__procFinished</b>(<i>exitCode, exitStatus</i>) -<p> - Private slot connected to the finished signal. -</p><dl> -<dt><i>exitCode</i> (int)</dt> -<dd> -exit code of the process -</dd><dt><i>exitStatus</i> (QProcess.ExitStatus)</dt> -<dd> -exit status of the process -</dd> -</dl><a NAME="PipListDialog.__processOutput" ID="PipListDialog.__processOutput"></a> -<h4>PipListDialog.__processOutput</h4> -<b>__processOutput</b>(<i></i>) -<p> - Private method to process the captured output. -</p><a NAME="PipListDialog.__readStderr" ID="PipListDialog.__readStderr"></a> -<h4>PipListDialog.__readStderr</h4> -<b>__readStderr</b>(<i></i>) -<p> - Private slot to handle the readyReadStandardError signal. -</p><p> - It reads the error output of the process and inserts it into the - error pane. -</p><a NAME="PipListDialog.__readStdout" ID="PipListDialog.__readStdout"></a> -<h4>PipListDialog.__readStdout</h4> -<b>__readStdout</b>(<i></i>) -<p> - Private slot to handle the readyReadStandardOutput signal. -</p><p> - It reads the output of the process, formats it and inserts it into - the contents pane. -</p><a NAME="PipListDialog.__refresh" ID="PipListDialog.__refresh"></a> -<h4>PipListDialog.__refresh</h4> -<b>__refresh</b>(<i></i>) -<p> - Private slot to refresh the displayed list. -</p><a NAME="PipListDialog.__stopProcess" ID="PipListDialog.__stopProcess"></a> -<h4>PipListDialog.__stopProcess</h4> -<b>__stopProcess</b>(<i></i>) -<p> - Private slot to stop the running process. -</p><a NAME="PipListDialog.__uninstallPackages" ID="PipListDialog.__uninstallPackages"></a> -<h4>PipListDialog.__uninstallPackages</h4> -<b>__uninstallPackages</b>(<i></i>) -<p> - Private slot to uninstall the selected packages. -</p><a NAME="PipListDialog.__upgradeAllPackages" ID="PipListDialog.__upgradeAllPackages"></a> -<h4>PipListDialog.__upgradeAllPackages</h4> -<b>__upgradeAllPackages</b>(<i></i>) -<p> - Private slot to upgrade all listed packages. -</p><a NAME="PipListDialog.__upgradePackages" ID="PipListDialog.__upgradePackages"></a> -<h4>PipListDialog.__upgradePackages</h4> -<b>__upgradePackages</b>(<i></i>) -<p> - Private slot to upgrade the selected packages. -</p><a NAME="PipListDialog.__upgradePip" ID="PipListDialog.__upgradePip"></a> -<h4>PipListDialog.__upgradePip</h4> -<b>__upgradePip</b>(<i></i>) -<p> - Private slot to upgrade pip itself. -</p><a NAME="PipListDialog.closeEvent" ID="PipListDialog.closeEvent"></a> -<h4>PipListDialog.closeEvent</h4> -<b>closeEvent</b>(<i>e</i>) -<p> - Protected slot implementing a close event handler. -</p><dl> -<dt><i>e</i> (QCloseEvent)</dt> -<dd> -close event -</dd> -</dl><a NAME="PipListDialog.on_buttonBox_clicked" ID="PipListDialog.on_buttonBox_clicked"></a> -<h4>PipListDialog.on_buttonBox_clicked</h4> -<b>on_buttonBox_clicked</b>(<i>button</i>) -<p> - Private slot called by a button of the button box clicked. -</p><dl> -<dt><i>button</i> (QAbstractButton)</dt> -<dd> -button that was clicked -</dd> -</dl><a NAME="PipListDialog.on_installedFilesCheckBox_clicked" ID="PipListDialog.on_installedFilesCheckBox_clicked"></a> -<h4>PipListDialog.on_installedFilesCheckBox_clicked</h4> -<b>on_installedFilesCheckBox_clicked</b>(<i>checked</i>) -<p> - Private slot to handle a change of the installed files information - checkbox. -</p><dl> -<dt><i>checked</i> (bool)</dt> -<dd> -state of the checkbox -</dd> -</dl><a NAME="PipListDialog.on_localCheckBox_clicked" ID="PipListDialog.on_localCheckBox_clicked"></a> -<h4>PipListDialog.on_localCheckBox_clicked</h4> -<b>on_localCheckBox_clicked</b>(<i>checked</i>) -<p> - Private slot handling the switching of the local mode. -</p><dl> -<dt><i>checked</i> (bool)</dt> -<dd> -state of the local check box -</dd> -</dl><a NAME="PipListDialog.on_notRequiredCheckBox_clicked" ID="PipListDialog.on_notRequiredCheckBox_clicked"></a> -<h4>PipListDialog.on_notRequiredCheckBox_clicked</h4> -<b>on_notRequiredCheckBox_clicked</b>(<i>checked</i>) -<p> - Private slot handling the switching of the 'not required' mode. -</p><dl> -<dt><i>checked</i> (bool)</dt> -<dd> -state of the 'not required' check box -</dd> -</dl><a NAME="PipListDialog.on_packageList_itemSelectionChanged" ID="PipListDialog.on_packageList_itemSelectionChanged"></a> -<h4>PipListDialog.on_packageList_itemSelectionChanged</h4> -<b>on_packageList_itemSelectionChanged</b>(<i></i>) -<p> - Private slot handling the selection of a package. -</p><a NAME="PipListDialog.on_userCheckBox_clicked" ID="PipListDialog.on_userCheckBox_clicked"></a> -<h4>PipListDialog.on_userCheckBox_clicked</h4> -<b>on_userCheckBox_clicked</b>(<i>checked</i>) -<p> - Private slot handling the switching of the 'user-site' mode. -</p><dl> -<dt><i>checked</i> (bool)</dt> -<dd> -state of the 'user-site' check box -</dd> -</dl><a NAME="PipListDialog.on_venvComboBox_activated" ID="PipListDialog.on_venvComboBox_activated"></a> -<h4>PipListDialog.on_venvComboBox_activated</h4> -<b>on_venvComboBox_activated</b>(<i>txt</i>) -<p> - Private slot handling the selection of a virtual environment. -</p><dl> -<dt><i>txt</i> (str)</dt> -<dd> -virtual environment -</dd> -</dl><a NAME="PipListDialog.on_verboseCheckBox_clicked" ID="PipListDialog.on_verboseCheckBox_clicked"></a> -<h4>PipListDialog.on_verboseCheckBox_clicked</h4> -<b>on_verboseCheckBox_clicked</b>(<i>checked</i>) -<p> - Private slot to handle a change of the verbose package information - checkbox. -</p><dl> -<dt><i>checked</i> (bool)</dt> -<dd> -state of the checkbox -</dd> -</dl><a NAME="PipListDialog.start" ID="PipListDialog.start"></a> -<h4>PipListDialog.start</h4> -<b>start</b>(<i></i>) -<p> - Public method to start the command. -</p> -<div align="right"><a href="#top">Up</a></div> -<hr /> -</body></html> \ No newline at end of file
--- a/Documentation/Source/eric6.Plugins.UiExtensionPlugins.PipInterface.PipPackageDetailsDialog.html Sat Feb 23 13:05:18 2019 +0100 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,198 +0,0 @@ -<!DOCTYPE html> -<html><head> -<title>eric6.Plugins.UiExtensionPlugins.PipInterface.PipPackageDetailsDialog</title> -<meta charset="UTF-8"> -<style> -body { - background: #EDECE6; - margin: 0em 1em 10em 1em; - color: black; -} - -h1 { color: white; background: #85774A; } -h2 { color: white; background: #85774A; } -h3 { color: white; background: #9D936E; } -h4 { color: white; background: #9D936E; } - -a { color: #BA6D36; } - -</style> -</head> -<body><a NAME="top" ID="top"></a> -<h1>eric6.Plugins.UiExtensionPlugins.PipInterface.PipPackageDetailsDialog</h1> -<p> -Module implementing a dialog to show details about a package. -</p> -<h3>Global Attributes</h3> -<table> -<tr><td>None</td></tr> -</table> -<h3>Classes</h3> -<table> -<tr> -<td><a href="#PipPackageDetailsDialog">PipPackageDetailsDialog</a></td> -<td>Class implementing a dialog to show details about a package.</td> -</tr> -</table> -<h3>Functions</h3> -<table> -<tr><td>None</td></tr> -</table> -<hr /><hr /> -<a NAME="PipPackageDetailsDialog" ID="PipPackageDetailsDialog"></a> -<h2>PipPackageDetailsDialog</h2> -<p> - Class implementing a dialog to show details about a package. -</p> -<h3>Derived from</h3> -QDialog, Ui_PipPackageDetailsDialog -<h3>Class Attributes</h3> -<table> -<tr><td>None</td></tr> -</table> -<h3>Class Methods</h3> -<table> -<tr><td>None</td></tr> -</table> -<h3>Methods</h3> -<table> -<tr> -<td><a href="#PipPackageDetailsDialog.__init__">PipPackageDetailsDialog</a></td> -<td>Constructor</td> -</tr><tr> -<td><a href="#PipPackageDetailsDialog.__formatSize">__formatSize</a></td> -<td>Private slot to format the size.</td> -</tr><tr> -<td><a href="#PipPackageDetailsDialog.__formatUploadDate">__formatUploadDate</a></td> -<td>Private method to format the upload date.</td> -</tr><tr> -<td><a href="#PipPackageDetailsDialog.__populateDetails">__populateDetails</a></td> -<td>Private method to populate the details tab.</td> -</tr><tr> -<td><a href="#PipPackageDetailsDialog.__populateDownloadUrls">__populateDownloadUrls</a></td> -<td>Private method to populate the download URLs tab.</td> -</tr><tr> -<td><a href="#PipPackageDetailsDialog.__populateRequiresProvides">__populateRequiresProvides</a></td> -<td>Private method to populate the requires/provides tab.</td> -</tr><tr> -<td><a href="#PipPackageDetailsDialog.__sanitize">__sanitize</a></td> -<td>Private method to clean-up the given text.</td> -</tr> -</table> -<h3>Static Methods</h3> -<table> -<tr><td>None</td></tr> -</table> -<a NAME="PipPackageDetailsDialog.__init__" ID="PipPackageDetailsDialog.__init__"></a> -<h4>PipPackageDetailsDialog (Constructor)</h4> -<b>PipPackageDetailsDialog</b>(<i>detailsData, downloadsData, parent=None</i>) -<p> - Constructor -</p><dl> -<dt><i>detailsData</i> (dict)</dt> -<dd> -package details -</dd><dt><i>downloadsData</i> (dict)</dt> -<dd> -downloads information -</dd><dt><i>parent</i> (QWidget)</dt> -<dd> -reference to the parent widget -</dd> -</dl><a NAME="PipPackageDetailsDialog.__formatSize" ID="PipPackageDetailsDialog.__formatSize"></a> -<h4>PipPackageDetailsDialog.__formatSize</h4> -<b>__formatSize</b>(<i>size</i>) -<p> - Private slot to format the size. -</p><dl> -<dt><i>size</i> (int)</dt> -<dd> -size to be formatted -</dd> -</dl><dl> -<dt>Returns:</dt> -<dd> -formatted size -</dd> -</dl><dl> -<dt>Return Type:</dt> -<dd> -str -</dd> -</dl><a NAME="PipPackageDetailsDialog.__formatUploadDate" ID="PipPackageDetailsDialog.__formatUploadDate"></a> -<h4>PipPackageDetailsDialog.__formatUploadDate</h4> -<b>__formatUploadDate</b>(<i>datetime</i>) -<p> - Private method to format the upload date. -</p><dl> -<dt><i>datetime</i> (xmlrpc.DateTime or str)</dt> -<dd> -upload date and time -</dd> -</dl><dl> -<dt>Returns:</dt> -<dd> -formatted date string -</dd> -</dl><dl> -<dt>Return Type:</dt> -<dd> -str -</dd> -</dl><a NAME="PipPackageDetailsDialog.__populateDetails" ID="PipPackageDetailsDialog.__populateDetails"></a> -<h4>PipPackageDetailsDialog.__populateDetails</h4> -<b>__populateDetails</b>(<i>detailsData</i>) -<p> - Private method to populate the details tab. -</p><dl> -<dt><i>detailsData</i> (dict)</dt> -<dd> -package details -</dd> -</dl><a NAME="PipPackageDetailsDialog.__populateDownloadUrls" ID="PipPackageDetailsDialog.__populateDownloadUrls"></a> -<h4>PipPackageDetailsDialog.__populateDownloadUrls</h4> -<b>__populateDownloadUrls</b>(<i>downloadsData</i>) -<p> - Private method to populate the download URLs tab. -</p><dl> -<dt><i>downloadsData</i> (dict)</dt> -<dd> -downloads information -</dd> -</dl><a NAME="PipPackageDetailsDialog.__populateRequiresProvides" ID="PipPackageDetailsDialog.__populateRequiresProvides"></a> -<h4>PipPackageDetailsDialog.__populateRequiresProvides</h4> -<b>__populateRequiresProvides</b>(<i>detailsData</i>) -<p> - Private method to populate the requires/provides tab. -</p><dl> -<dt><i>detailsData</i> (dict)</dt> -<dd> -package details -</dd> -</dl><a NAME="PipPackageDetailsDialog.__sanitize" ID="PipPackageDetailsDialog.__sanitize"></a> -<h4>PipPackageDetailsDialog.__sanitize</h4> -<b>__sanitize</b>(<i>text, forUrl=False</i>) -<p> - Private method to clean-up the given text. -</p><dl> -<dt><i>text</i> (str)</dt> -<dd> -raw text -</dd><dt><i>forUrl</i> (bool)</dt> -<dd> -flag indicating to sanitize an URL text -</dd> -</dl><dl> -<dt>Returns:</dt> -<dd> -processed text -</dd> -</dl><dl> -<dt>Return Type:</dt> -<dd> -str -</dd> -</dl> -<div align="right"><a href="#top">Up</a></div> -<hr /> -</body></html> \ No newline at end of file
--- a/Documentation/Source/eric6.Plugins.UiExtensionPlugins.PipInterface.PipPackagesInputDialog.html Sat Feb 23 13:05:18 2019 +0100 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,123 +0,0 @@ -<!DOCTYPE html> -<html><head> -<title>eric6.Plugins.UiExtensionPlugins.PipInterface.PipPackagesInputDialog</title> -<meta charset="UTF-8"> -<style> -body { - background: #EDECE6; - margin: 0em 1em 10em 1em; - color: black; -} - -h1 { color: white; background: #85774A; } -h2 { color: white; background: #85774A; } -h3 { color: white; background: #9D936E; } -h4 { color: white; background: #9D936E; } - -a { color: #BA6D36; } - -</style> -</head> -<body><a NAME="top" ID="top"></a> -<h1>eric6.Plugins.UiExtensionPlugins.PipInterface.PipPackagesInputDialog</h1> -<p> -Module implementing a dialog to enter package specifications. -</p> -<h3>Global Attributes</h3> -<table> -<tr><td>None</td></tr> -</table> -<h3>Classes</h3> -<table> -<tr> -<td><a href="#PipPackagesInputDialog">PipPackagesInputDialog</a></td> -<td>Class implementing a dialog to enter package specifications.</td> -</tr> -</table> -<h3>Functions</h3> -<table> -<tr><td>None</td></tr> -</table> -<hr /><hr /> -<a NAME="PipPackagesInputDialog" ID="PipPackagesInputDialog"></a> -<h2>PipPackagesInputDialog</h2> -<p> - Class implementing a dialog to enter package specifications. -</p> -<h3>Derived from</h3> -QDialog, Ui_PipPackagesInputDialog -<h3>Class Attributes</h3> -<table> -<tr><td>None</td></tr> -</table> -<h3>Class Methods</h3> -<table> -<tr><td>None</td></tr> -</table> -<h3>Methods</h3> -<table> -<tr> -<td><a href="#PipPackagesInputDialog.__init__">PipPackagesInputDialog</a></td> -<td>Constructor</td> -</tr><tr> -<td><a href="#PipPackagesInputDialog.getData">getData</a></td> -<td>Public method to get the entered data.</td> -</tr><tr> -<td><a href="#PipPackagesInputDialog.on_packagesEdit_textChanged">on_packagesEdit_textChanged</a></td> -<td>Private slot handling entering package names.</td> -</tr> -</table> -<h3>Static Methods</h3> -<table> -<tr><td>None</td></tr> -</table> -<a NAME="PipPackagesInputDialog.__init__" ID="PipPackagesInputDialog.__init__"></a> -<h4>PipPackagesInputDialog (Constructor)</h4> -<b>PipPackagesInputDialog</b>(<i>pip, title, install=True, parent=None</i>) -<p> - Constructor -</p><dl> -<dt><i>pip</i> (Pip)</dt> -<dd> -reference to the pip object -</dd><dt><i>title</i> (str)</dt> -<dd> -dialog title -</dd><dt><i>install</i> (bool)</dt> -<dd> -flag indicating an install action -</dd><dt><i>parent</i> (QWidget)</dt> -<dd> -reference to the parent widget -</dd> -</dl><a NAME="PipPackagesInputDialog.getData" ID="PipPackagesInputDialog.getData"></a> -<h4>PipPackagesInputDialog.getData</h4> -<b>getData</b>(<i></i>) -<p> - Public method to get the entered data. -</p><dl> -<dt>Returns:</dt> -<dd> -tuple with the environment name, the list of package - specifications and a flag indicating to install to the user - install directory -</dd> -</dl><dl> -<dt>Return Type:</dt> -<dd> -tuple of (str, list of str, bool) -</dd> -</dl><a NAME="PipPackagesInputDialog.on_packagesEdit_textChanged" ID="PipPackagesInputDialog.on_packagesEdit_textChanged"></a> -<h4>PipPackagesInputDialog.on_packagesEdit_textChanged</h4> -<b>on_packagesEdit_textChanged</b>(<i>txt</i>) -<p> - Private slot handling entering package names. -</p><dl> -<dt><i>txt</i> (str)</dt> -<dd> -name of the requirements file -</dd> -</dl> -<div align="right"><a href="#top">Up</a></div> -<hr /> -</body></html> \ No newline at end of file
--- a/Documentation/Source/eric6.Plugins.UiExtensionPlugins.PipInterface.PipSearchDialog.html Sat Feb 23 13:05:18 2019 +0100 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,321 +0,0 @@ -<!DOCTYPE html> -<html><head> -<title>eric6.Plugins.UiExtensionPlugins.PipInterface.PipSearchDialog</title> -<meta charset="UTF-8"> -<style> -body { - background: #EDECE6; - margin: 0em 1em 10em 1em; - color: black; -} - -h1 { color: white; background: #85774A; } -h2 { color: white; background: #85774A; } -h3 { color: white; background: #9D936E; } -h4 { color: white; background: #9D936E; } - -a { color: #BA6D36; } - -</style> -</head> -<body><a NAME="top" ID="top"></a> -<h1>eric6.Plugins.UiExtensionPlugins.PipInterface.PipSearchDialog</h1> -<p> -Module implementing a dialog to search PyPI. -</p> -<h3>Global Attributes</h3> -<table> -<tr><td>None</td></tr> -</table> -<h3>Classes</h3> -<table> -<tr> -<td><a href="#PipSearchDialog">PipSearchDialog</a></td> -<td>Class implementing a dialog to search PyPI.</td> -</tr> -</table> -<h3>Functions</h3> -<table> -<tr><td>None</td></tr> -</table> -<hr /><hr /> -<a NAME="PipSearchDialog" ID="PipSearchDialog"></a> -<h2>PipSearchDialog</h2> -<p> - Class implementing a dialog to search PyPI. -</p> -<h3>Derived from</h3> -QDialog, Ui_PipSearchDialog -<h3>Class Attributes</h3> -<table> -<tr><td>Stopwords</td></tr><tr><td>VersionRole</td></tr> -</table> -<h3>Class Methods</h3> -<table> -<tr><td>None</td></tr> -</table> -<h3>Methods</h3> -<table> -<tr> -<td><a href="#PipSearchDialog.__init__">PipSearchDialog</a></td> -<td>Constructor</td> -</tr><tr> -<td><a href="#PipSearchDialog.__detailsError">__detailsError</a></td> -<td>Private method handling a details error.</td> -</tr><tr> -<td><a href="#PipSearchDialog.__displayPackageDetails">__displayPackageDetails</a></td> -<td>Private method to display the returned package details.</td> -</tr><tr> -<td><a href="#PipSearchDialog.__finish">__finish</a></td> -<td>Private slot performing the finishing actions.</td> -</tr><tr> -<td><a href="#PipSearchDialog.__getPackageDownloadsData">__getPackageDownloadsData</a></td> -<td>Private method to store the details data and get downloads information.</td> -</tr><tr> -<td><a href="#PipSearchDialog.__install">__install</a></td> -<td>Private slot to install the selected packages.</td> -</tr><tr> -<td><a href="#PipSearchDialog.__processSearchResult">__processSearchResult</a></td> -<td>Private method to process the search result data from PyPI.</td> -</tr><tr> -<td><a href="#PipSearchDialog.__score">__score</a></td> -<td>Private method to calculate some score for a search result.</td> -</tr><tr> -<td><a href="#PipSearchDialog.__search">__search</a></td> -<td>Private method to perform the search.</td> -</tr><tr> -<td><a href="#PipSearchDialog.__searchError">__searchError</a></td> -<td>Private method handling a search error.</td> -</tr><tr> -<td><a href="#PipSearchDialog.__showDetails">__showDetails</a></td> -<td>Private slot to show details about the selected package.</td> -</tr><tr> -<td><a href="#PipSearchDialog.__transformHits">__transformHits</a></td> -<td>Private method to convert the list returned from pypi into a packages list.</td> -</tr><tr> -<td><a href="#PipSearchDialog.closeEvent">closeEvent</a></td> -<td>Protected slot implementing a close event handler.</td> -</tr><tr> -<td><a href="#PipSearchDialog.on_buttonBox_clicked">on_buttonBox_clicked</a></td> -<td>Private slot called by a button of the button box clicked.</td> -</tr><tr> -<td><a href="#PipSearchDialog.on_resultList_itemActivated">on_resultList_itemActivated</a></td> -<td>Private slot reacting on an item activation.</td> -</tr><tr> -<td><a href="#PipSearchDialog.on_resultList_itemSelectionChanged">on_resultList_itemSelectionChanged</a></td> -<td>Private slot handling changes of the selection.</td> -</tr><tr> -<td><a href="#PipSearchDialog.on_searchButton_clicked">on_searchButton_clicked</a></td> -<td>Private slot handling a press of the search button.</td> -</tr><tr> -<td><a href="#PipSearchDialog.on_searchEdit_textChanged">on_searchEdit_textChanged</a></td> -<td>Private slot handling a change of the search term.</td> -</tr> -</table> -<h3>Static Methods</h3> -<table> -<tr><td>None</td></tr> -</table> -<a NAME="PipSearchDialog.__init__" ID="PipSearchDialog.__init__"></a> -<h4>PipSearchDialog (Constructor)</h4> -<b>PipSearchDialog</b>(<i>pip, indexUrl, parent=None</i>) -<p> - Constructor -</p><dl> -<dt><i>pip</i> (Pip)</dt> -<dd> -reference to the master object -</dd><dt><i>indexUrl</i> (str)</dt> -<dd> -URL of XML RPC interface to the pypi index -</dd><dt><i>parent</i> (QWidget)</dt> -<dd> -reference to the parent widget -</dd> -</dl><a NAME="PipSearchDialog.__detailsError" ID="PipSearchDialog.__detailsError"></a> -<h4>PipSearchDialog.__detailsError</h4> -<b>__detailsError</b>(<i>errorCode, errorString</i>) -<p> - Private method handling a details error. -</p><dl> -<dt><i>errorCode</i> (int)</dt> -<dd> -code of the error -</dd><dt><i>errorString</i> (str)</dt> -<dd> -error message -</dd> -</dl><a NAME="PipSearchDialog.__displayPackageDetails" ID="PipSearchDialog.__displayPackageDetails"></a> -<h4>PipSearchDialog.__displayPackageDetails</h4> -<b>__displayPackageDetails</b>(<i>data</i>) -<p> - Private method to display the returned package details. -</p><dl> -<dt><i>data</i> (tuple)</dt> -<dd> -result data with downloads information in the first element -</dd> -</dl><a NAME="PipSearchDialog.__finish" ID="PipSearchDialog.__finish"></a> -<h4>PipSearchDialog.__finish</h4> -<b>__finish</b>(<i></i>) -<p> - Private slot performing the finishing actions. -</p><a NAME="PipSearchDialog.__getPackageDownloadsData" ID="PipSearchDialog.__getPackageDownloadsData"></a> -<h4>PipSearchDialog.__getPackageDownloadsData</h4> -<b>__getPackageDownloadsData</b>(<i>packageVersion, data</i>) -<p> - Private method to store the details data and get downloads - information. -</p><dl> -<dt><i>packageVersion</i> (str)</dt> -<dd> -version info -</dd><dt><i>data</i> (tuple)</dt> -<dd> -result data with package details in the first - element -</dd> -</dl><a NAME="PipSearchDialog.__install" ID="PipSearchDialog.__install"></a> -<h4>PipSearchDialog.__install</h4> -<b>__install</b>(<i>userSite=False</i>) -<p> - Private slot to install the selected packages. -</p><dl> -<dt><i>userSite</i> (bool)</dt> -<dd> -flag indicating to install to the user directory -</dd> -</dl><a NAME="PipSearchDialog.__processSearchResult" ID="PipSearchDialog.__processSearchResult"></a> -<h4>PipSearchDialog.__processSearchResult</h4> -<b>__processSearchResult</b>(<i>data</i>) -<p> - Private method to process the search result data from PyPI. -</p><dl> -<dt><i>data</i> (tuple)</dt> -<dd> -result data with hits in the first element -</dd> -</dl><a NAME="PipSearchDialog.__score" ID="PipSearchDialog.__score"></a> -<h4>PipSearchDialog.__score</h4> -<b>__score</b>(<i>name, summary</i>) -<p> - Private method to calculate some score for a search result. -</p><dl> -<dt><i>name</i> (str)</dt> -<dd> -name of the returned package -</dd><dt><i>summary</i> (str)</dt> -<dd> -summary text for the package -</dd> -</dl><dl> -<dt>Returns:</dt> -<dd> -score value -</dd> -</dl><dl> -<dt>Return Type:</dt> -<dd> -int -</dd> -</dl><a NAME="PipSearchDialog.__search" ID="PipSearchDialog.__search"></a> -<h4>PipSearchDialog.__search</h4> -<b>__search</b>(<i></i>) -<p> - Private method to perform the search. -</p><a NAME="PipSearchDialog.__searchError" ID="PipSearchDialog.__searchError"></a> -<h4>PipSearchDialog.__searchError</h4> -<b>__searchError</b>(<i>errorCode, errorString</i>) -<p> - Private method handling a search error. -</p><dl> -<dt><i>errorCode</i> (int)</dt> -<dd> -code of the error -</dd><dt><i>errorString</i> (str)</dt> -<dd> -error message -</dd> -</dl><a NAME="PipSearchDialog.__showDetails" ID="PipSearchDialog.__showDetails"></a> -<h4>PipSearchDialog.__showDetails</h4> -<b>__showDetails</b>(<i></i>) -<p> - Private slot to show details about the selected package. -</p><a NAME="PipSearchDialog.__transformHits" ID="PipSearchDialog.__transformHits"></a> -<h4>PipSearchDialog.__transformHits</h4> -<b>__transformHits</b>(<i>hits</i>) -<p> - Private method to convert the list returned from pypi into a - packages list. -</p><dl> -<dt><i>hits</i> (list of dict)</dt> -<dd> -list returned from pypi -</dd> -</dl><dl> -<dt>Returns:</dt> -<dd> -list of packages -</dd> -</dl><dl> -<dt>Return Type:</dt> -<dd> -list of dict -</dd> -</dl><a NAME="PipSearchDialog.closeEvent" ID="PipSearchDialog.closeEvent"></a> -<h4>PipSearchDialog.closeEvent</h4> -<b>closeEvent</b>(<i>e</i>) -<p> - Protected slot implementing a close event handler. -</p><dl> -<dt><i>e</i> (QCloseEvent)</dt> -<dd> -close event -</dd> -</dl><a NAME="PipSearchDialog.on_buttonBox_clicked" ID="PipSearchDialog.on_buttonBox_clicked"></a> -<h4>PipSearchDialog.on_buttonBox_clicked</h4> -<b>on_buttonBox_clicked</b>(<i>button</i>) -<p> - Private slot called by a button of the button box clicked. -</p><dl> -<dt><i>button</i> (QAbstractButton)</dt> -<dd> -button that was clicked -</dd> -</dl><a NAME="PipSearchDialog.on_resultList_itemActivated" ID="PipSearchDialog.on_resultList_itemActivated"></a> -<h4>PipSearchDialog.on_resultList_itemActivated</h4> -<b>on_resultList_itemActivated</b>(<i>item, column</i>) -<p> - Private slot reacting on an item activation. -</p><dl> -<dt><i>item</i> (QTreeWidgetItem)</dt> -<dd> -reference to the activated item -</dd><dt><i>column</i> (int)</dt> -<dd> -activated column -</dd> -</dl><a NAME="PipSearchDialog.on_resultList_itemSelectionChanged" ID="PipSearchDialog.on_resultList_itemSelectionChanged"></a> -<h4>PipSearchDialog.on_resultList_itemSelectionChanged</h4> -<b>on_resultList_itemSelectionChanged</b>(<i></i>) -<p> - Private slot handling changes of the selection. -</p><a NAME="PipSearchDialog.on_searchButton_clicked" ID="PipSearchDialog.on_searchButton_clicked"></a> -<h4>PipSearchDialog.on_searchButton_clicked</h4> -<b>on_searchButton_clicked</b>(<i></i>) -<p> - Private slot handling a press of the search button. -</p><a NAME="PipSearchDialog.on_searchEdit_textChanged" ID="PipSearchDialog.on_searchEdit_textChanged"></a> -<h4>PipSearchDialog.on_searchEdit_textChanged</h4> -<b>on_searchEdit_textChanged</b>(<i>txt</i>) -<p> - Private slot handling a change of the search term. -</p><dl> -<dt><i>txt</i> (str)</dt> -<dd> -search term -</dd> -</dl> -<div align="right"><a href="#top">Up</a></div> -<hr /> -</body></html> \ No newline at end of file
--- a/Documentation/Source/eric6.Plugins.UiExtensionPlugins.PipInterface.PipSelectionDialog.html Sat Feb 23 13:05:18 2019 +0100 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,103 +0,0 @@ -<!DOCTYPE html> -<html><head> -<title>eric6.Plugins.UiExtensionPlugins.PipInterface.PipSelectionDialog</title> -<meta charset="UTF-8"> -<style> -body { - background: #EDECE6; - margin: 0em 1em 10em 1em; - color: black; -} - -h1 { color: white; background: #85774A; } -h2 { color: white; background: #85774A; } -h3 { color: white; background: #9D936E; } -h4 { color: white; background: #9D936E; } - -a { color: #BA6D36; } - -</style> -</head> -<body><a NAME="top" ID="top"></a> -<h1>eric6.Plugins.UiExtensionPlugins.PipInterface.PipSelectionDialog</h1> -<p> -Module implementing a dialog to select the pip executable to be used. -</p> -<h3>Global Attributes</h3> -<table> -<tr><td>None</td></tr> -</table> -<h3>Classes</h3> -<table> -<tr> -<td><a href="#PipSelectionDialog">PipSelectionDialog</a></td> -<td>Class implementing a dialog to select the pip executable to be used.</td> -</tr> -</table> -<h3>Functions</h3> -<table> -<tr><td>None</td></tr> -</table> -<hr /><hr /> -<a NAME="PipSelectionDialog" ID="PipSelectionDialog"></a> -<h2>PipSelectionDialog</h2> -<p> - Class implementing a dialog to select the pip executable to be used. -</p> -<h3>Derived from</h3> -QDialog, Ui_PipSelectionDialog -<h3>Class Attributes</h3> -<table> -<tr><td>None</td></tr> -</table> -<h3>Class Methods</h3> -<table> -<tr><td>None</td></tr> -</table> -<h3>Methods</h3> -<table> -<tr> -<td><a href="#PipSelectionDialog.__init__">PipSelectionDialog</a></td> -<td>Constructor</td> -</tr><tr> -<td><a href="#PipSelectionDialog.getData">getData</a></td> -<td>Public method to get the entered data.</td> -</tr> -</table> -<h3>Static Methods</h3> -<table> -<tr><td>None</td></tr> -</table> -<a NAME="PipSelectionDialog.__init__" ID="PipSelectionDialog.__init__"></a> -<h4>PipSelectionDialog (Constructor)</h4> -<b>PipSelectionDialog</b>(<i>pip, parent=None</i>) -<p> - Constructor -</p><dl> -<dt><i>pip</i> (Pip)</dt> -<dd> -reference to the pip object -</dd><dt><i>parent</i> (QWidget)</dt> -<dd> -reference to the parent widget -</dd> -</dl><a NAME="PipSelectionDialog.getData" ID="PipSelectionDialog.getData"></a> -<h4>PipSelectionDialog.getData</h4> -<b>getData</b>(<i></i>) -<p> - Public method to get the entered data. -</p><dl> -<dt>Returns:</dt> -<dd> -tuple with the environment name and a flag indicating to - install to the user install directory -</dd> -</dl><dl> -<dt>Return Type:</dt> -<dd> -tuple of (str, bool) -</dd> -</dl> -<div align="right"><a href="#top">Up</a></div> -<hr /> -</body></html> \ No newline at end of file
--- a/Documentation/Source/index-eric6.Plugins.UiExtensionPlugins.PipInterface.ConfigurationPage.html Sat Feb 23 13:05:18 2019 +0100 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,35 +0,0 @@ -<!DOCTYPE html> -<html><head> -<title>eric6.Plugins.UiExtensionPlugins.PipInterface.ConfigurationPage</title> -<meta charset="UTF-8"> -<style> -body { - background: #EDECE6; - margin: 0em 1em 10em 1em; - color: black; -} - -h1 { color: white; background: #85774A; } -h2 { color: white; background: #85774A; } -h3 { color: white; background: #9D936E; } -h4 { color: white; background: #9D936E; } - -a { color: #BA6D36; } - -</style> -</head> -<body> -<h1>eric6.Plugins.UiExtensionPlugins.PipInterface.ConfigurationPage</h1> -<p> -Package implementing the configuration page. -</p> - - -<h3>Modules</h3> -<table> -<tr> -<td><a href="eric6.Plugins.UiExtensionPlugins.PipInterface.ConfigurationPage.PipPage.html">PipPage</a></td> -<td>Package implementing the pip configuration page.</td> -</tr> -</table> -</body></html> \ No newline at end of file
--- a/Documentation/Source/index-eric6.Plugins.UiExtensionPlugins.PipInterface.html Sat Feb 23 13:05:18 2019 +0100 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,66 +0,0 @@ -<!DOCTYPE html> -<html><head> -<title>eric6.Plugins.UiExtensionPlugins.PipInterface</title> -<meta charset="UTF-8"> -<style> -body { - background: #EDECE6; - margin: 0em 1em 10em 1em; - color: black; -} - -h1 { color: white; background: #85774A; } -h2 { color: white; background: #85774A; } -h3 { color: white; background: #9D936E; } -h4 { color: white; background: #9D936E; } - -a { color: #BA6D36; } - -</style> -</head> -<body> -<h1>eric6.Plugins.UiExtensionPlugins.PipInterface</h1> -<p> -Package implementing the various pip dialogs and data. -</p> - -<h3>Packages</h3> -<table> -<tr> -<td><a href="index-eric6.Plugins.UiExtensionPlugins.PipInterface.ConfigurationPage.html">ConfigurationPage</a></td> -<td>Package implementing the configuration page.</td> -</tr> -</table> - -<h3>Modules</h3> -<table> -<tr> -<td><a href="eric6.Plugins.UiExtensionPlugins.PipInterface.Pip.html">Pip</a></td> -<td>Package implementing the pip GUI logic.</td> -</tr><tr> -<td><a href="eric6.Plugins.UiExtensionPlugins.PipInterface.PipDialog.html">PipDialog</a></td> -<td>Module implementing a dialog showing the output of a pip command.</td> -</tr><tr> -<td><a href="eric6.Plugins.UiExtensionPlugins.PipInterface.PipFileSelectionDialog.html">PipFileSelectionDialog</a></td> -<td>Module implementing a dialog to enter a file to be processed.</td> -</tr><tr> -<td><a href="eric6.Plugins.UiExtensionPlugins.PipInterface.PipFreezeDialog.html">PipFreezeDialog</a></td> -<td>Module implementing a dialog to generate a requirements file.</td> -</tr><tr> -<td><a href="eric6.Plugins.UiExtensionPlugins.PipInterface.PipListDialog.html">PipListDialog</a></td> -<td>Module implementing a dialog to list installed packages.</td> -</tr><tr> -<td><a href="eric6.Plugins.UiExtensionPlugins.PipInterface.PipPackageDetailsDialog.html">PipPackageDetailsDialog</a></td> -<td>Module implementing a dialog to show details about a package.</td> -</tr><tr> -<td><a href="eric6.Plugins.UiExtensionPlugins.PipInterface.PipPackagesInputDialog.html">PipPackagesInputDialog</a></td> -<td>Module implementing a dialog to enter package specifications.</td> -</tr><tr> -<td><a href="eric6.Plugins.UiExtensionPlugins.PipInterface.PipSearchDialog.html">PipSearchDialog</a></td> -<td>Module implementing a dialog to search PyPI.</td> -</tr><tr> -<td><a href="eric6.Plugins.UiExtensionPlugins.PipInterface.PipSelectionDialog.html">PipSelectionDialog</a></td> -<td>Module implementing a dialog to select the pip executable to be used.</td> -</tr> -</table> -</body></html> \ No newline at end of file
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/PipInterface/Pip.py Sat Feb 23 15:46:15 2019 +0100 @@ -0,0 +1,654 @@ +# -*- coding: utf-8 -*- + +# Copyright (c) 2015 - 2019 Detlev Offenbach <detlev@die-offenbachs.de> +# + +""" +Package implementing the pip GUI logic. +""" + +from __future__ import unicode_literals +try: + str = unicode # __IGNORE_EXCEPTION__ +except NameError: + pass + +import os +import sys +import json + +from PyQt5.QtCore import pyqtSlot, QObject, QProcess, QUrl, QCoreApplication +from PyQt5.QtWidgets import QDialog +from PyQt5.QtNetwork import QNetworkAccessManager, QNetworkRequest, \ + QNetworkReply + +from E5Gui import E5MessageBox +from E5Gui.E5Application import e5App + +from E5Network.E5NetworkProxyFactory import proxyAuthenticationRequired +try: + from E5Network.E5SslErrorHandler import E5SslErrorHandler + SSL_AVAILABLE = True +except ImportError: + SSL_AVAILABLE = False + +from .PipDialog import PipDialog + +import Preferences +import Globals + + +class Pip(QObject): + """ + Class implementing the pip GUI logic. + """ + DefaultPyPiUrl = "https://pypi.org" + DefaultIndexUrlXml = DefaultPyPiUrl + "/pypi" + DefaultIndexUrlPip = DefaultPyPiUrl + "/simple" + + def __init__(self, parent=None): + """ + Constructor + + @param parent parent + @type QObject + """ + super(Pip, self).__init__(parent) + + # attributes for the network objects + self.__networkManager = QNetworkAccessManager(self) + self.__networkManager.proxyAuthenticationRequired.connect( + proxyAuthenticationRequired) + if SSL_AVAILABLE: + self.__sslErrorHandler = E5SslErrorHandler(self) + self.__networkManager.sslErrors.connect( + self.__sslErrorHandler.sslErrorsReply) + self.__replies = [] + + ########################################################################## + ## Methods below implement some utility functions + ########################################################################## + + def runProcess(self, args, interpreter): + """ + Public method to execute the current pip with the given arguments. + + The selected pip executable is called with the given arguments and + waited for its end. + + @param args list of command line arguments + @type list of str + @param interpreter path of the Python interpreter to be used + @type str + @return tuple containing a flag indicating success and the output + of the process + @rtype tuple of (bool, str) + """ + ioEncoding = Preferences.getSystem("IOEncoding") + + process = QProcess() + process.start(interpreter, args) + procStarted = process.waitForStarted() + if procStarted: + finished = process.waitForFinished(30000) + if finished: + if process.exitCode() == 0: + output = str(process.readAllStandardOutput(), ioEncoding, + 'replace') + return True, output + else: + return (False, + self.tr("python exited with an error ({0}).") + .format(process.exitCode())) + else: + process.terminate() + process.waitForFinished(2000) + process.kill() + process.waitForFinished(3000) + return False, self.tr("python did not finish within" + " 30 seconds.") + + return False, self.tr("python could not be started.") + + def getUserConfig(self): + """ + Public method to get the name of the user configuration file. + + @return path of the user configuration file + @rtype str + """ + # Unix: ~/.config/pip/pip.conf + # OS X: ~/Library/Application Support/pip/pip.conf + # Windows: %APPDATA%\pip\pip.ini + # Environment: $PIP_CONFIG_FILE + + try: + return os.environ["PIP_CONFIG_FILE"] + except KeyError: + pass + + if Globals.isWindowsPlatform(): + config = os.path.join(os.environ["APPDATA"], "pip", "pip.ini") + elif Globals.isMacPlatform(): + config = os.path.expanduser( + "~/Library/Application Support/pip/pip.conf") + else: + config = os.path.expanduser("~/.config/pip/pip.conf") + + return config + + def getVirtualenvConfig(self, venvName): + """ + Public method to get the name of the virtualenv configuration file. + + @param venvName name of the environment to get config file path for + @type str + @return path of the virtualenv configuration file + @rtype str + """ + # Unix, OS X: $VIRTUAL_ENV/pip.conf + # Windows: %VIRTUAL_ENV%\pip.ini + + if Globals.isWindowsPlatform(): + pip = "pip.ini" + else: + pip = "pip.conf" + + venvManager = e5App().getObject("VirtualEnvManager") + if venvManager.isGlobalEnvironment(venvName): + venvDirectory = self.__getUserConfig() + else: + venvDirectory = venvManager.getVirtualenvDirectory(venvName) + + if venvDirectory: + config = os.path.join(venvDirectory, pip) + else: + config = "" + + return config + + def getProjectEnvironmentString(self): + """ + Public method to get the string for the project environment. + + @return string for the project environment + @rtype str + """ + if e5App().getObject("Project").isOpen(): + return self.tr("<project>") + else: + return "" + + def getVirtualenvInterpreter(self, venvName): + """ + Public method to get the interpreter for a virtual environment. + + @param venvName logical name for the virtual environment + @type str + @return interpreter path + @rtype str + """ + if venvName == self.getProjectEnvironmentString(): + venvName = \ + e5App().getObject("Project").getDebugProperty("VIRTUALENV") + if not venvName: + # fall back to interpreter used to run eric6 + return sys.executable + + interpreter = \ + e5App().getObject("VirtualEnvManager").getVirtualenvInterpreter( + venvName) + if not interpreter: + E5MessageBox.critical( + None, + self.tr("Interpreter for Virtual Environment"), + self.tr("""No interpreter configured for the selected""" + """ virtual environment.""")) + + return interpreter + + def getVirtualenvNames(self): + """ + Public method to get a sorted list of virtual environment names. + + @return sorted list of virtual environment names + @rtype list of str + """ + return sorted( + e5App().getObject("VirtualEnvManager").getVirtualenvNames()) + + def installPip(self, venvName, userSite=False): + """ + Public method to install pip. + + @param venvName name of the environment to install pip into + @type str + @param userSite flag indicating an install to the user install + directory + @type bool + """ + interpreter = self.getVirtualenvInterpreter(venvName) + if not interpreter: + return + + dia = PipDialog(self.tr('Install PIP')) + if userSite: + commands = [(interpreter, ["-m", "ensurepip", "--user"])] + else: + commands = [(interpreter, ["-m", "ensurepip"])] + if Preferences.getPip("PipSearchIndex"): + indexUrl = Preferences.getPip("PipSearchIndex") + "/simple" + args = ["-m", "pip", "install", "--index-url", indexUrl, + "--upgrade"] + else: + args = ["-m", "pip", "install", "--upgrade"] + if userSite: + args.append("--user") + args.append("pip") + commands.append((interpreter, args[:])) + + res = dia.startProcesses(commands) + if res: + dia.exec_() + + @pyqtSlot() + def repairPip(self, venvName): + """ + Public method to repair the pip installation. + + @param venvName name of the environment to install pip into + @type str + """ + interpreter = self.getVirtualenvInterpreter(venvName) + if not interpreter: + return + + # python -m pip install --ignore-installed pip + if Preferences.getPip("PipSearchIndex"): + indexUrl = Preferences.getPip("PipSearchIndex") + "/simple" + args = ["-m", "pip", "install", "--index-url", indexUrl, + "--ignore-installed"] + else: + args = ["-m", "pip", "install", "--ignore-installed"] + args.append("pip") + + dia = PipDialog(self.tr('Repair PIP')) + res = dia.startProcess(interpreter, args) + if res: + dia.exec_() + + def __checkUpgradePyQt(self, packages): + """ + Private method to check, if an upgrade of PyQt packages is attempted. + + @param packages list of packages to upgrade + @type list of str + @return flag indicating to abort the upgrade attempt + @rtype bool + """ + pyqtPackages = [p for p in packages + if p.lower() in ["pyqt5", "pyqt5-sip", "pyqtwebengine", + "qscintilla", "sip"]] + + if bool(pyqtPackages): + abort = not E5MessageBox.yesNo( + None, + self.tr("Upgrade Packages"), + self.tr( + """You are trying to upgrade PyQt packages. This might""" + """ not work for the current instance of Python ({0}).""" + """ Do you want to continue?""").format(sys.executable), + icon=E5MessageBox.Critical) + else: + abort = False + + return abort + + def upgradePackages(self, packages, venvName, userSite=False): + """ + Public method to upgrade the given list of packages. + + @param packages list of packages to upgrade + @type list of str + @param venvName name of the virtual environment to be used + @type str + @param userSite flag indicating an install to the user install + directory + @type bool + @return flag indicating a successful execution + @rtype bool + """ + if self.__checkUpgradePyQt(packages): + return False + + if not venvName: + return False + + interpreter = self.getVirtualenvInterpreter(venvName) + if not interpreter: + return False + + if Preferences.getPip("PipSearchIndex"): + indexUrl = Preferences.getPip("PipSearchIndex") + "/simple" + args = ["-m", "pip", "install", "--index-url", indexUrl, + "--upgrade"] + else: + args = ["-m", "pip", "install", "--upgrade"] + if userSite: + args.append("--user") + args += packages + dia = PipDialog(self.tr('Upgrade Packages')) + res = dia.startProcess(interpreter, args) + if res: + dia.exec_() + return res + + def installPackages(self, packages, venvName, userSite=False): + """ + Public method to install the given list of packages. + + @param packages list of packages to install + @type list of str + @param venvName name of the virtual environment to be used + @type str + @param userSite flag indicating an install to the user install + directory + @type bool + """ + if venvName: + interpreter = self.getVirtualenvInterpreter(venvName) + if not interpreter: + return + + if Preferences.getPip("PipSearchIndex"): + indexUrl = Preferences.getPip("PipSearchIndex") + "/simple" + args = ["-m", "pip", "install", "--index-url", indexUrl] + else: + args = ["-m", "pip", "install"] + if userSite: + args.append("--user") + args += packages + dia = PipDialog(self.tr('Install Packages')) + res = dia.startProcess(interpreter, args) + if res: + dia.exec_() + + def installRequirements(self, venvName): + """ + Public method to install packages as given in a requirements file. + + @param venvName name of the virtual environment to be used + @type str + """ + from .PipFileSelectionDialog import PipFileSelectionDialog + dlg = PipFileSelectionDialog(self, "requirements") + if dlg.exec_() == QDialog.Accepted: + requirements, user = dlg.getData() + if requirements and os.path.exists(requirements): + interpreter = self.getVirtualenvInterpreter(venvName) + if not interpreter: + return + + if Preferences.getPip("PipSearchIndex"): + indexUrl = Preferences.getPip("PipSearchIndex") + \ + "/simple" + args = ["-m", "pip", "install", "--index-url", indexUrl] + else: + args = ["-m", "pip", "install"] + if user: + args.append("--user") + args += ["--requirement", requirements] + dia = PipDialog(self.tr('Install Packages from Requirements')) + res = dia.startProcess(interpreter, args) + if res: + dia.exec_() + + def uninstallPackages(self, packages, venvName): + """ + Public method to uninstall the given list of packages. + + @param packages list of packages to uninstall + @type list of str + @param venvName name of the virtual environment to be used + @type str + @return flag indicating a successful execution + @rtype bool + """ + res = False + if packages and venvName: + from UI.DeleteFilesConfirmationDialog import \ + DeleteFilesConfirmationDialog + dlg = DeleteFilesConfirmationDialog( + self.parent(), + self.tr("Uninstall Packages"), + self.tr( + "Do you really want to uninstall these packages?"), + packages) + if dlg.exec_() == QDialog.Accepted: + interpreter = self.getVirtualenvInterpreter(venvName) + if not interpreter: + return + args = ["-m", "pip", "uninstall", "--yes"] + packages + dia = PipDialog(self.tr('Uninstall Packages')) + res = dia.startProcess(interpreter, args) + if res: + dia.exec_() + return res + + def uninstallRequirements(self, venvName): + """ + Public method to uninstall packages as given in a requirements file. + + @param venvName name of the virtual environment to be used + @type str + """ + if venvName: + from .PipFileSelectionDialog import PipFileSelectionDialog + dlg = PipFileSelectionDialog(self, "requirements", + install=False) + if dlg.exec_() == QDialog.Accepted: + requirements, _user = dlg.getData() + if requirements and os.path.exists(requirements): + try: + f = open(requirements, "r") + reqs = f.read().splitlines() + f.close() + except (OSError, IOError): + return + + from UI.DeleteFilesConfirmationDialog import \ + DeleteFilesConfirmationDialog + dlg = DeleteFilesConfirmationDialog( + self.parent(), + self.tr("Uninstall Packages"), + self.tr( + "Do you really want to uninstall these packages?"), + reqs) + if dlg.exec_() == QDialog.Accepted: + interpreter = self.getVirtualenvInterpreter(venvName) + if not interpreter: + return + + args = ["-m", "pip", "uninstall", "--requirement", + requirements] + dia = PipDialog( + self.tr('Uninstall Packages from Requirements')) + res = dia.startProcess(interpreter, args) + if res: + dia.exec_() + + def getIndexUrl(self): + """ + Public method to get the index URL for PyPI. + + @return index URL for PyPI + @rtype str + """ + if Preferences.getPip("PipSearchIndex"): + indexUrl = Preferences.getPip("PipSearchIndex") + "/simple" + else: + indexUrl = Pip.DefaultIndexUrlPip + + return indexUrl + + def getIndexUrlXml(self): + """ + Public method to get the index URL for XML RPC calls. + + @return index URL for XML RPC calls + @rtype str + """ + if Preferences.getPip("PipSearchIndex"): + indexUrl = Preferences.getPip("PipSearchIndex") + "/pypi" + else: + indexUrl = Pip.DefaultIndexUrlXml + + return indexUrl + + def getInstalledPackages(self, envName, localPackages=True, + notRequired=False, usersite=False): + """ + Public method to get the list of installed packages. + + @param envName name of the environment to get the packages for + @type str + @param localPackages flag indicating to get local packages only + @type bool + @param notRequired flag indicating to list packages that are not + dependencies of installed packages as well + @type bool + @param usersite flag indicating to only list packages installed + in user-site + @type bool + @return list of tuples containing the package name and version + @rtype list of tuple of (str, str) + """ + packages = [] + + if envName: + interpreter = self.getVirtualenvInterpreter(envName) + if interpreter: + args = [ + "-m", "pip", + "list", + "--format=json", + ] + if localPackages: + args.append("--local") + if notRequired: + args.append("--not-required") + if usersite: + args.append("--user") + + proc = QProcess() + proc.start(interpreter, args) + if proc.waitForStarted(15000): + if proc.waitForFinished(30000): + output = str(proc.readAllStandardOutput(), + Preferences.getSystem("IOEncoding"), + 'replace').strip() + try: + jsonList = json.loads(output) + except Exception: + jsonList = [] + + for package in jsonList: + if isinstance(package, dict): + packages.append(( + package["name"], + package["version"], + )) + + return packages + + def getOutdatedPackages(self, envName, localPackages=True, + notRequired=False, usersite=False): + """ + Public method to get the list of outdated packages. + + @param envName name of the environment to get the packages for + @type str + @param localPackages flag indicating to get local packages only + @type bool + @param notRequired flag indicating to list packages that are not + dependencies of installed packages as well + @type bool + @param usersite flag indicating to only list packages installed + in user-site + @type bool + @return list of tuples containing the package name, installed version + and available version + @rtype list of tuple of (str, str, str) + """ + packages = [] + + if envName: + interpreter = self.getVirtualenvInterpreter(envName) + if interpreter: + args = [ + "-m", "pip", + "list", + "--outdated", + "--format=json", + ] + if localPackages: + args.append("--local") + if notRequired: + args.append("--not-required") + if usersite: + args.append("--user") + + proc = QProcess() + proc.start(interpreter, args) + if proc.waitForStarted(15000): + if proc.waitForFinished(30000): + output = str(proc.readAllStandardOutput(), + Preferences.getSystem("IOEncoding"), + 'replace').strip() + try: + jsonList = json.loads(output) + except Exception: + jsonList = [] + + for package in jsonList: + if isinstance(package, dict): + packages.append(( + package["name"], + package["version"], + package["latest_version"], + )) + + return packages + + def getPackageDetails(self, name, version): + """ + Public method to get package details using the PyPI JSON interface. + + @param name package name + @type str + @param version package version + @type str + @return dictionary containing PyPI package data + @rtype dict + """ + result = {} + + if name and version: + url = "https://pypi.org/pypi/{0}/{1}/json".format(name, version) + request = QNetworkRequest(QUrl(url)) + reply = self.__networkManager.get(request) + while not reply.isFinished(): + QCoreApplication.processEvents() + + reply.deleteLater() + if reply.error() == QNetworkReply.NoError: + data = str(reply.readAll(), + Preferences.getSystem("IOEncoding"), + 'replace') + try: + result = json.loads(data) + except Exception: + # ignore JSON exceptions + pass + + return result
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/PipInterface/PipDialog.py Sat Feb 23 15:46:15 2019 +0100 @@ -0,0 +1,205 @@ +# -*- coding: utf-8 -*- + +# Copyright (c) 2015 - 2019 Detlev Offenbach <detlev@die-offenbachs.de> +# + +""" +Module implementing a dialog showing the output of a pip command. +""" + +from __future__ import unicode_literals +try: + str = unicode # __IGNORE_EXCEPTION__ +except NameError: + pass + +from PyQt5.QtCore import pyqtSlot, Qt, QCoreApplication, QTimer, \ + QProcess +from PyQt5.QtWidgets import QDialog, QDialogButtonBox, QAbstractButton + +from E5Gui import E5MessageBox + +from .Ui_PipDialog import Ui_PipDialog + +import Preferences + + +class PipDialog(QDialog, Ui_PipDialog): + """ + Class implementing a dialog showing the output of a 'python -m pip' + command. + """ + def __init__(self, text, parent=None): + """ + Constructor + + @param text text to be shown by the label + @type str + @param parent reference to the parent widget + @type QWidget + """ + super(PipDialog, self).__init__(parent) + self.setupUi(self) + + self.proc = None + self.__processQueue = [] + self.__ioEncoding = Preferences.getSystem("IOEncoding") + + self.outputGroup.setTitle(text) + + self.show() + QCoreApplication.processEvents() + + def closeEvent(self, e): + """ + Protected slot implementing a close event handler. + + @param e close event + @type QCloseEvent + """ + self.__processQueue = [] + + if self.proc is not None and \ + self.proc.state() != QProcess.NotRunning: + self.proc.terminate() + QTimer.singleShot(2000, self.proc.kill) + self.proc.waitForFinished(3000) + + self.proc = None + + e.accept() + + def __finish(self): + """ + Private slot called when the process finished or the user pressed + the button. + """ + if self.proc is not None and \ + self.proc.state() != QProcess.NotRunning: + self.proc.terminate() + QTimer.singleShot(2000, self.proc.kill) + self.proc.waitForFinished(3000) + + self.proc = None + + self.buttonBox.button(QDialogButtonBox.Close).setEnabled(True) + self.buttonBox.button(QDialogButtonBox.Close).setFocus( + Qt.OtherFocusReason) + + if self.__processQueue: + cmd, args = self.__processQueue.pop(0) + self.__addOutput("\n\n") + self.startProcess(cmd, args) + + @pyqtSlot(QAbstractButton) + def on_buttonBox_clicked(self, button): + """ + Private slot called by a button of the button box clicked. + + @param button button that was clicked + @type QAbstractButton + """ + if button == self.buttonBox.button(QDialogButtonBox.Close): + self.close() + + def __procFinished(self, exitCode, exitStatus): + """ + Private slot connected to the finished signal. + + @param exitCode exit code of the process + @type int + @param exitStatus exit status of the process + @type QProcess.ExitStatus + """ + self.__finish() + + def startProcess(self, cmd, args, showArgs=True): + """ + Public slot used to start the process. + + @param cmd name of the pip executable to be used + @type str + @param args list of arguments for the process + @type list of str + @keyparam showArgs flag indicating to show the arguments + @type bool + @return flag indicating a successful start of the process + @rtype bool + """ + if len(self.errors.toPlainText()) == 0: + self.errorGroup.hide() + + if showArgs: + self.resultbox.append(cmd + ' ' + ' '.join(args)) + self.resultbox.append('') + + self.proc = QProcess() + self.proc.finished.connect(self.__procFinished) + self.proc.readyReadStandardOutput.connect(self.__readStdout) + self.proc.readyReadStandardError.connect(self.__readStderr) + self.proc.start(cmd, args) + procStarted = self.proc.waitForStarted(5000) + if not procStarted: + self.buttonBox.setFocus() + E5MessageBox.critical( + self, + self.tr('Process Generation Error'), + self.tr( + 'The process {0} could not be started.' + ).format(cmd)) + return procStarted + + def startProcesses(self, processParams): + """ + Public method to issue a list of commands to be executed. + + @param processParams list of tuples containing the command + and arguments + @type list of tuples of (str, list of str) + @return flag indicating a successful start of the first process + @rtype bool + """ + if len(processParams) > 1: + for cmd, args in processParams[1:]: + self.__processQueue.append((cmd, args[:])) + cmd, args = processParams[0] + return self.startProcess(cmd, args) + + def __readStdout(self): + """ + Private slot to handle the readyReadStandardOutput signal. + + It reads the output of the process, formats it and inserts it into + the contents pane. + """ + if self.proc is not None: + txt = str(self.proc.readAllStandardOutput(), + self.__ioEncoding, 'replace') + self.__addOutput(txt) + + def __addOutput(self, txt): + """ + Private method to add some text to the output pane. + + @param txt text to be added + @type str + """ + self.resultbox.insertPlainText(txt) + self.resultbox.ensureCursorVisible() + QCoreApplication.processEvents() + + def __readStderr(self): + """ + Private slot to handle the readyReadStandardError signal. + + It reads the error output of the process and inserts it into the + error pane. + """ + if self.proc is not None: + s = str(self.proc.readAllStandardError(), + self.__ioEncoding, 'replace') + self.errorGroup.show() + self.errors.insertPlainText(s) + self.errors.ensureCursorVisible() + + QCoreApplication.processEvents()
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/PipInterface/PipDialog.ui Sat Feb 23 15:46:15 2019 +0100 @@ -0,0 +1,91 @@ +<?xml version="1.0" encoding="UTF-8"?> +<ui version="4.0"> + <class>PipDialog</class> + <widget class="QDialog" name="PipDialog"> + <property name="geometry"> + <rect> + <x>0</x> + <y>0</y> + <width>600</width> + <height>500</height> + </rect> + </property> + <property name="windowTitle"> + <string>pip</string> + </property> + <property name="sizeGripEnabled"> + <bool>true</bool> + </property> + <layout class="QVBoxLayout"> + <item> + <widget class="QGroupBox" name="outputGroup"> + <property name="sizePolicy"> + <sizepolicy hsizetype="Preferred" vsizetype="Expanding"> + <horstretch>0</horstretch> + <verstretch>2</verstretch> + </sizepolicy> + </property> + <property name="title"> + <string>Output</string> + </property> + <layout class="QVBoxLayout"> + <item> + <widget class="QTextEdit" name="resultbox"> + <property name="readOnly"> + <bool>true</bool> + </property> + <property name="acceptRichText"> + <bool>false</bool> + </property> + </widget> + </item> + </layout> + </widget> + </item> + <item> + <widget class="QGroupBox" name="errorGroup"> + <property name="sizePolicy"> + <sizepolicy hsizetype="Preferred" vsizetype="Expanding"> + <horstretch>0</horstretch> + <verstretch>1</verstretch> + </sizepolicy> + </property> + <property name="title"> + <string>Errors</string> + </property> + <layout class="QVBoxLayout"> + <item> + <widget class="QTextEdit" name="errors"> + <property name="readOnly"> + <bool>true</bool> + </property> + <property name="acceptRichText"> + <bool>false</bool> + </property> + </widget> + </item> + </layout> + </widget> + </item> + <item> + <widget class="QDialogButtonBox" name="buttonBox"> + <property name="orientation"> + <enum>Qt::Horizontal</enum> + </property> + <property name="standardButtons"> + <set>QDialogButtonBox::Close</set> + </property> + </widget> + </item> + </layout> + </widget> + <layoutdefault spacing="6" margin="11"/> + <pixmapfunction>qPixmapFromMimeSource</pixmapfunction> + <tabstops> + <tabstop>resultbox</tabstop> + <tabstop>errors</tabstop> + <tabstop>buttonBox</tabstop> + </tabstops> + <resources/> + <connections/> +</ui>
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/PipInterface/PipFileSelectionDialog.py Sat Feb 23 15:46:15 2019 +0100 @@ -0,0 +1,102 @@ +# -*- coding: utf-8 -*- + +# Copyright (c) 2015 - 2019 Detlev Offenbach <detlev@die-offenbachs.de> +# + + +""" +Module implementing a dialog to enter a file to be processed. +""" + +from __future__ import unicode_literals + +import os + +from PyQt5.QtCore import pyqtSlot +from PyQt5.QtWidgets import QDialog, QDialogButtonBox + +from E5Gui.E5PathPicker import E5PathPickerModes + +from .Ui_PipFileSelectionDialog import Ui_PipFileSelectionDialog + +import Utilities + + +class PipFileSelectionDialog(QDialog, Ui_PipFileSelectionDialog): + """ + Class implementing a dialog to enter a file to be processed. + """ + def __init__(self, pip, mode, install=True, parent=None): + """ + Constructor + + @param pip reference to the pip object + @type Pip + @param mode mode of the dialog + @type str + @param install flag indicating an install action + @type bool + @param parent reference to the parent widget + @type QWidget + """ + super(PipFileSelectionDialog, self).__init__(parent) + self.setupUi(self) + + if mode == "requirements": + self.fileLabel.setText(self.tr("Enter requirements file:")) + self.filePicker.setMode(E5PathPickerModes.OpenFileMode) + self.filePicker.setToolTip(self.tr( + "Press to select the requirements file through a file" + " selection dialog.")) + self.filePicker.setFilters( + self.tr("Text Files (*.txt);;All Files (*)")) + elif mode == "package": + self.fileLabel.setText(self.tr("Enter package file:")) + self.filePicker.setMode(E5PathPickerModes.OpenFileMode) + self.filePicker.setToolTip(self.tr( + "Press to select the package file through a file" + " selection dialog.")) + self.filePicker.setFilters( + self.tr("Python Wheel (*.whl);;" + "Archive Files (*.tar.gz *.zip);;" + "All Files (*)")) + else: + self.fileLabel.setText(self.tr("Enter file name:")) + self.filePicker.setMode(E5PathPickerModes.OpenFileMode) + self.filePicker.setToolTip(self.tr( + "Press to select a file through a file selection dialog.")) + self.filePicker.setFilters(self.tr("All Files (*)")) + self.filePicker.setDefaultDirectory(os.path.expanduser("~")) + + self.buttonBox.button(QDialogButtonBox.Ok).setEnabled(False) + + self.userCheckBox.setVisible(install) + + msh = self.minimumSizeHint() + self.resize(max(self.width(), msh.width()), msh.height()) + + @pyqtSlot(str) + def on_filePicker_textChanged(self, txt): + """ + Private slot to handle entering the name of a file. + + @param txt name of the file + @type str + """ + self.buttonBox.button(QDialogButtonBox.Ok).setEnabled( + bool(txt) and + os.path.exists(Utilities.toNativeSeparators(txt)) + ) + + def getData(self): + """ + Public method to get the entered data. + + @return tuple with the name of the selected file and a flag indicating + to install to the user install directory + @rtype tuple of (str, bool) + """ + return ( + self.filePicker.text(), + self.userCheckBox.isChecked() + )
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/PipInterface/PipFileSelectionDialog.ui Sat Feb 23 15:46:15 2019 +0100 @@ -0,0 +1,99 @@ +<?xml version="1.0" encoding="UTF-8"?> +<ui version="4.0"> + <class>PipFileSelectionDialog</class> + <widget class="QDialog" name="PipFileSelectionDialog"> + <property name="geometry"> + <rect> + <x>0</x> + <y>0</y> + <width>600</width> + <height>114</height> + </rect> + </property> + <property name="windowTitle"> + <string>Select File</string> + </property> + <property name="sizeGripEnabled"> + <bool>true</bool> + </property> + <layout class="QVBoxLayout" name="verticalLayout"> + <item> + <widget class="QLabel" name="fileLabel"> + <property name="text"> + <string>File Name:</string> + </property> + </widget> + </item> + <item> + <widget class="E5PathPicker" name="filePicker" native="true"> + <property name="focusPolicy"> + <enum>Qt::StrongFocus</enum> + </property> + </widget> + </item> + <item> + <widget class="QCheckBox" name="userCheckBox"> + <property name="toolTip"> + <string>Select to install to the Python user install directory</string> + </property> + <property name="text"> + <string>Install into User Directory</string> + </property> + </widget> + </item> + <item> + <widget class="QDialogButtonBox" name="buttonBox"> + <property name="orientation"> + <enum>Qt::Horizontal</enum> + </property> + <property name="standardButtons"> + <set>QDialogButtonBox::Cancel|QDialogButtonBox::Ok</set> + </property> + </widget> + </item> + </layout> + </widget> + <customwidgets> + <customwidget> + <class>E5PathPicker</class> + <extends>QWidget</extends> + <header>E5Gui/E5PathPicker.h</header> + <container>1</container> + </customwidget> + </customwidgets> + <resources/> + <connections> + <connection> + <sender>buttonBox</sender> + <signal>accepted()</signal> + <receiver>PipFileSelectionDialog</receiver> + <slot>accept()</slot> + <hints> + <hint type="sourcelabel"> + <x>248</x> + <y>254</y> + </hint> + <hint type="destinationlabel"> + <x>157</x> + <y>274</y> + </hint> + </hints> + </connection> + <connection> + <sender>buttonBox</sender> + <signal>rejected()</signal> + <receiver>PipFileSelectionDialog</receiver> + <slot>reject()</slot> + <hints> + <hint type="sourcelabel"> + <x>316</x> + <y>260</y> + </hint> + <hint type="destinationlabel"> + <x>286</x> + <y>274</y> + </hint> + </hints> + </connection> + </connections> +</ui>
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/PipInterface/PipFreezeDialog.py Sat Feb 23 15:46:15 2019 +0100 @@ -0,0 +1,286 @@ +# -*- coding: utf-8 -*- + +# Copyright (c) 2015 - 2019 Detlev Offenbach <detlev@die-offenbachs.de> +# + +""" +Module implementing a dialog to generate a requirements file. +""" + +from __future__ import unicode_literals +try: + str = unicode # __IGNORE_EXCEPTION__ +except NameError: + pass + +import os + +from PyQt5.QtCore import pyqtSlot, Qt +from PyQt5.QtWidgets import QDialog, QDialogButtonBox, QAbstractButton, \ + QApplication + +from E5Gui import E5MessageBox, E5FileDialog +from E5Gui.E5PathPicker import E5PathPickerModes +from E5Gui.E5Application import e5App + +from .Ui_PipFreezeDialog import Ui_PipFreezeDialog + +import Utilities + + +class PipFreezeDialog(QDialog, Ui_PipFreezeDialog): + """ + Class implementing a dialog to generate a requirements file. + """ + def __init__(self, pip, parent=None): + """ + Constructor + + @param pip reference to the master object + @type Pip + @param parent reference to the parent widget + @type QWidget + """ + super(PipFreezeDialog, self).__init__(parent) + self.setupUi(self) + self.setWindowFlags(Qt.Window) + + self.__refreshButton = self.buttonBox.addButton( + self.tr("&Refresh"), QDialogButtonBox.ActionRole) + + self.requirementsFilePicker.setMode(E5PathPickerModes.SaveFileMode) + self.requirementsFilePicker.setFilters( + self.tr("Text Files (*.txt);;All Files (*)")) + + self.__pip = pip + + self.__requirementsEdited = False + self.__requirementsAvailable = False + + self.__updateButtons() + + def closeEvent(self, e): + """ + Protected slot implementing a close event handler. + + @param e close event + @type QCloseEvent + """ + QApplication.restoreOverrideCursor() + e.accept() + + @pyqtSlot(bool) + def on_localCheckBox_clicked(self, checked): + """ + Private slot handling the switching of the local mode. + + @param checked state of the local check box + @type bool + """ + self.__refresh() + + @pyqtSlot(str) + def on_requirementsFilePicker_textChanged(self, txt): + """ + Private slot handling a change of the requirements file name. + + @param txt name of the requirements file + @type str + """ + self.__updateButtons() + + @pyqtSlot() + def on_requirementsEdit_textChanged(self): + """ + Private slot handling changes of the requirements text. + """ + self.__requirementsEdited = True + + @pyqtSlot(QAbstractButton) + def on_buttonBox_clicked(self, button): + """ + Private slot called by a button of the button box clicked. + + @param button button that was clicked + @type QAbstractButton + """ + if button == self.buttonBox.button(QDialogButtonBox.Close): + self.close() + elif button == self.__refreshButton: + self.__refresh() + + def __refresh(self): + """ + Private slot to refresh the displayed list. + """ + if self.__requirementsEdited: + ok = E5MessageBox.yesNo( + self, + self.tr("Generate Requirements"), + self.tr("""The requirements were changed. Do you want""" + """ to overwrite these changes?""")) + else: + ok = True + if ok: + self.start() + + def start(self, venvName): + """ + Public method to start the command. + + @param venvName name of the environment to act upon + @type str + """ + self.requirementsEdit.clear() + self.__requirementsAvailable = False + + interpreter = self.__pip.getVirtualenvInterpreter(venvName) + if not interpreter: + return + + args = ["-m", "pip", "freeze"] + if self.localCheckBox.isChecked(): + args.append("--local") + if self.requirementsFilePicker.text(): + fileName = Utilities.toNativeSeparators( + self.requirementsFilePicker.text()) + if os.path.exists(fileName): + args.append("--requirement") + args.append(fileName) + + QApplication.setOverrideCursor(Qt.WaitCursor) + success, output = self.__pip.runProcess(args, interpreter) + + if success: + self.requirementsEdit.setPlainText(output) + self.__requirementsAvailable = True + else: + self.requirementsEdit.setPlainText( + self.tr("No output generated by 'pip freeze'.")) + + QApplication.restoreOverrideCursor() + self.__updateButtons() + + self.__requirementsEdited = False + + def __updateButtons(self): + """ + Private method to set the state of the various buttons. + """ + self.saveButton.setEnabled( + self.__requirementsAvailable and + bool(self.requirementsFilePicker.text()) + ) + self.saveToButton.setEnabled(self.__requirementsAvailable) + self.copyButton.setEnabled(self.__requirementsAvailable) + + aw = e5App().getObject("ViewManager").activeWindow() + if aw and self.__requirementsAvailable: + self.insertButton.setEnabled(True) + self.replaceAllButton.setEnabled(True) + self.replaceSelectionButton.setEnabled( + aw.hasSelectedText()) + else: + self.insertButton.setEnabled(False) + self.replaceAllButton.setEnabled(False) + self.replaceSelectionButton.setEnabled(False) + + def __writeToFile(self, fileName): + """ + Private method to write the requirements text to a file. + + @param fileName name of the file to write to + @type str + """ + if os.path.exists(fileName): + ok = E5MessageBox.warning( + self, + self.tr("Generate Requirements"), + self.tr("""The file <b>{0}</b> already exists. Do you want""" + """ to overwrite it?""").format(fileName)) + if not ok: + return + + try: + f = open(fileName, "w") + f.write(self.requirementsEdit.toPlainText()) + f.close() + except (OSError, IOError) as err: + E5MessageBox.critical( + self, + self.tr("Generate Requirements"), + self.tr("""<p>The requirements could not be written""" + """ to <b>{0}</b>.</p><p>Reason: {1}</p>""") + .format(fileName, str(err))) + + @pyqtSlot() + def on_saveButton_clicked(self): + """ + Private slot to save the requirements text to the requirements file. + """ + fileName = self.requirementsFilePicker.text() + self.__writeToFile(fileName) + + @pyqtSlot() + def on_saveToButton_clicked(self): + """ + Private slot to write the requirements text to a new file. + """ + fileName, selectedFilter = E5FileDialog.getSaveFileNameAndFilter( + self, + self.tr("Generate Requirements"), + os.path.expanduser("~"), + self.tr("Text Files (*.txt);;All Files (*)"), + None, + E5FileDialog.Options(E5FileDialog.DontConfirmOverwrite) + ) + if fileName: + ext = os.path.splitext(fileName)[1] + if not ext: + ex = selectedFilter.split("(*")[1].split(")")[0] + if ex: + fileName += ex + self.__writeToFile(fileName) + + @pyqtSlot() + def on_copyButton_clicked(self): + """ + Private slot to copy the requirements text to the clipboard. + """ + txt = self.requirementsEdit.toPlainText() + cb = QApplication.clipboard() + cb.setText(txt) + + @pyqtSlot() + def on_insertButton_clicked(self): + """ + Private slot to insert the requirements text at the cursor position + of the current editor. + """ + aw = e5App().getObject("ViewManager").activeWindow() + if aw: + aw.beginUndoAction() + aw.insert(self.requirementsEdit.toPlainText()) + aw.endUndoAction() + + @pyqtSlot() + def on_replaceSelectionButton_clicked(self): + """ + Private slot to replace the selected text of the current editor + with the requirements text. + """ + aw = e5App().getObject("ViewManager").activeWindow() + if aw: + aw.beginUndoAction() + aw.replaceSelectedText(self.requirementsEdit.toPlainText()) + aw.endUndoAction() + + @pyqtSlot() + def on_replaceAllButton_clicked(self): + """ + Private slot to replace the text of the current editor with the + requirements text. + """ + aw = e5App().getObject("ViewManager").activeWindow() + if aw: + aw.setText(self.requirementsEdit.toPlainText())
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/PipInterface/PipFreezeDialog.ui Sat Feb 23 15:46:15 2019 +0100 @@ -0,0 +1,207 @@ +<?xml version="1.0" encoding="UTF-8"?> +<ui version="4.0"> + <class>PipFreezeDialog</class> + <widget class="QDialog" name="PipFreezeDialog"> + <property name="geometry"> + <rect> + <x>0</x> + <y>0</y> + <width>600</width> + <height>550</height> + </rect> + </property> + <property name="windowTitle"> + <string>Generate Requirements</string> + </property> + <property name="toolTip"> + <string>Replace the current selection with the requirements text</string> + </property> + <property name="sizeGripEnabled"> + <bool>true</bool> + </property> + <layout class="QVBoxLayout" name="verticalLayout"> + <item> + <widget class="QCheckBox" name="localCheckBox"> + <property name="toolTip"> + <string>Select to show requirements for locally-installed packages only</string> + </property> + <property name="text"> + <string>Local packages only</string> + </property> + <property name="checked"> + <bool>true</bool> + </property> + </widget> + </item> + <item> + <layout class="QHBoxLayout" name="horizontalLayout"> + <item> + <widget class="QLabel" name="label"> + <property name="text"> + <string>Requirements File:</string> + </property> + </widget> + </item> + <item> + <widget class="E5PathPicker" name="requirementsFilePicker" native="true"> + <property name="sizePolicy"> + <sizepolicy hsizetype="Expanding" vsizetype="Preferred"> + <horstretch>0</horstretch> + <verstretch>0</verstretch> + </sizepolicy> + </property> + <property name="focusPolicy"> + <enum>Qt::StrongFocus</enum> + </property> + </widget> + </item> + </layout> + </item> + <item> + <layout class="QGridLayout" name="gridLayout"> + <item row="0" column="1"> + <widget class="QPushButton" name="saveButton"> + <property name="toolTip"> + <string>Press to save to the requirements file</string> + </property> + <property name="text"> + <string>Save</string> + </property> + </widget> + </item> + <item row="1" column="1"> + <widget class="QPushButton" name="saveToButton"> + <property name="toolTip"> + <string>Save to a new file</string> + </property> + <property name="text"> + <string>Save To</string> + </property> + </widget> + </item> + <item row="2" column="1"> + <widget class="QPushButton" name="copyButton"> + <property name="toolTip"> + <string>Copy the requirements text to the clipboard</string> + </property> + <property name="text"> + <string>Copy</string> + </property> + </widget> + </item> + <item row="3" column="1"> + <widget class="QPushButton" name="insertButton"> + <property name="toolTip"> + <string>Insert the requirements text at the cursor position</string> + </property> + <property name="text"> + <string>Insert</string> + </property> + </widget> + </item> + <item row="4" column="1"> + <widget class="QPushButton" name="replaceSelectionButton"> + <property name="text"> + <string>Replace Selection</string> + </property> + </widget> + </item> + <item row="5" column="1"> + <widget class="QPushButton" name="replaceAllButton"> + <property name="toolTip"> + <string>Replace all text with the requirements text</string> + </property> + <property name="text"> + <string>Replace All</string> + </property> + </widget> + </item> + <item row="6" column="1"> + <spacer name="verticalSpacer"> + <property name="orientation"> + <enum>Qt::Vertical</enum> + </property> + <property name="sizeHint" stdset="0"> + <size> + <width>20</width> + <height>40</height> + </size> + </property> + </spacer> + </item> + <item row="0" column="0" rowspan="7"> + <widget class="QPlainTextEdit" name="requirementsEdit"> + <property name="tabChangesFocus"> + <bool>true</bool> + </property> + </widget> + </item> + </layout> + </item> + <item> + <widget class="QDialogButtonBox" name="buttonBox"> + <property name="orientation"> + <enum>Qt::Horizontal</enum> + </property> + <property name="standardButtons"> + <set>QDialogButtonBox::Close</set> + </property> + </widget> + </item> + </layout> + </widget> + <customwidgets> + <customwidget> + <class>E5PathPicker</class> + <extends>QWidget</extends> + <header>E5Gui/E5PathPicker.h</header> + <container>1</container> + </customwidget> + </customwidgets> + <tabstops> + <tabstop>localCheckBox</tabstop> + <tabstop>requirementsFilePicker</tabstop> + <tabstop>requirementsEdit</tabstop> + <tabstop>saveButton</tabstop> + <tabstop>saveToButton</tabstop> + <tabstop>copyButton</tabstop> + <tabstop>insertButton</tabstop> + <tabstop>replaceSelectionButton</tabstop> + <tabstop>replaceAllButton</tabstop> + </tabstops> + <resources/> + <connections> + <connection> + <sender>buttonBox</sender> + <signal>accepted()</signal> + <receiver>PipFreezeDialog</receiver> + <slot>accept()</slot> + <hints> + <hint type="sourcelabel"> + <x>248</x> + <y>254</y> + </hint> + <hint type="destinationlabel"> + <x>157</x> + <y>274</y> + </hint> + </hints> + </connection> + <connection> + <sender>buttonBox</sender> + <signal>rejected()</signal> + <receiver>PipFreezeDialog</receiver> + <slot>reject()</slot> + <hints> + <hint type="sourcelabel"> + <x>316</x> + <y>260</y> + </hint> + <hint type="destinationlabel"> + <x>286</x> + <y>274</y> + </hint> + </hints> + </connection> + </connections> +</ui>
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/PipInterface/PipPackageDetailsDialog.py Sat Feb 23 15:46:15 2019 +0100 @@ -0,0 +1,227 @@ +# -*- coding: utf-8 -*- + +# Copyright (c) 2015 - 2019 Detlev Offenbach <detlev@die-offenbachs.de> +# + +""" +Module implementing a dialog to show details about a package. +""" + +from __future__ import unicode_literals +try: + basestring # __IGNORE_WARNING__ +except NameError: + basestring = str + +from PyQt5.QtCore import Qt, QLocale +from PyQt5.QtWidgets import QDialog, QDialogButtonBox, QTreeWidgetItem, \ + QLabel, QHeaderView + +from .Ui_PipPackageDetailsDialog import Ui_PipPackageDetailsDialog + + +class PipPackageDetailsDialog(QDialog, Ui_PipPackageDetailsDialog): + """ + Class implementing a dialog to show details about a package. + """ + def __init__(self, detailsData, parent=None): + """ + Constructor + + @param detailsData package details + @type dict + @param parent reference to the parent widget + @type QWidget + """ + super(PipPackageDetailsDialog, self).__init__(parent) + self.setupUi(self) + self.setWindowFlags(Qt.Window) + + self.__locale = QLocale() + self.__packageTypeMap = { + "sdist": self.tr("Source"), + "bdist_wheel": self.tr("Python Wheel"), + "bdist_egg": self.tr("Python Egg"), + "bdist_wininst": self.tr("MS Windows Installer"), + "bdist_msi": self.tr("MS Windows Installer"), + "bdist_rpm": self.tr("Unix Installer"), + "bdist_deb": self.tr("Unix Installer"), + "bdist_dumb": self.tr("Archive"), + } + + self.__populateDetails(detailsData["info"]) + self.__populateDownloadUrls(detailsData["urls"]) + self.__populateRequiresProvides(detailsData["info"]) + + def __populateDetails(self, detailsData): + """ + Private method to populate the details tab. + + @param detailsData package details + @type dict + """ + self.packageNameLabel.setText( + "<h1>{0} {1}</h1".format(self.__sanitize(detailsData["name"]), + self.__sanitize(detailsData["version"]))) + self.summaryLabel.setText( + self.__sanitize(detailsData["summary"][:240])) + self.descriptionEdit.setPlainText( + self.__sanitize(detailsData["description"])) + self.authorLabel.setText(self.__sanitize(detailsData["author"])) + self.authorEmailLabel.setText( + '<a href="mailto:{0}">{0}</a>'.format( + self.__sanitize(detailsData["author_email"]))) + self.licenseLabel.setText(self.__sanitize(detailsData["license"])) + self.platformLabel.setText(self.__sanitize(detailsData["platform"])) + self.homePageLabel.setText( + '<a href="{0}">{0}</a>'.format( + self.__sanitize(detailsData["home_page"], forUrl=True))) + self.packageUrlLabel.setText( + '<a href="{0}">{0}</a>'.format( + self.__sanitize(detailsData["package_url"], forUrl=True))) + self.releaseUrlLabel.setText( + '<a href="{0}">{0}</a>'.format( + self.__sanitize(detailsData["release_url"], forUrl=True))) + self.docsUrlLabel.setText( + '<a href="{0}">{0}</a>'.format( + self.__sanitize(detailsData["docs_url"], forUrl=True))) + self.downloadsDayLabel.setText(self.__locale.toString( + detailsData["downloads"]["last_day"])) + self.downloadsWeekLabel.setText(self.__locale.toString( + detailsData["downloads"]["last_week"])) + self.downloadsMonthLabel.setText(self.__locale.toString( + detailsData["downloads"]["last_month"])) + self.classifiersList.addItems(detailsData["classifiers"]) + + self.buttonBox.button(QDialogButtonBox.Close).setDefault(True) + self.buttonBox.button(QDialogButtonBox.Close).setFocus( + Qt.OtherFocusReason) + + def __populateDownloadUrls(self, downloadsData): + """ + Private method to populate the download URLs tab. + + @param downloadsData downloads information + @type dict + """ + index = self.infoWidget.indexOf(self.urls) + if downloadsData: + self.infoWidget.setTabEnabled(index, True) + for download in downloadsData: + itm = QTreeWidgetItem(self.downloadUrlsList, [ + "", + self.__packageTypeMap[download["packagetype"]] + if download["packagetype"] in self.__packageTypeMap + else "", + download["python_version"] + if download["python_version"] != "source" + else "", + self.__locale.toString(download["downloads"]), + self.__formatUploadDate(download["upload_time"]), + self.__formatSize(download["size"]), + ]) + if download["has_sig"]: + pgpLink = ' (<a href="{0}">pgp</a>)'.format( + download["url"] + ".asc") + else: + pgpLink = "" + urlLabel = QLabel('<a href="{0}#md5={2}">{1}</a>{3}'.format( + download["url"], download["filename"], + download["md5_digest"], pgpLink)) + urlLabel.setTextInteractionFlags(Qt.LinksAccessibleByMouse) + urlLabel.setOpenExternalLinks(True) + self.downloadUrlsList.setItemWidget(itm, 0, urlLabel) + header = self.downloadUrlsList.header() + header.resizeSections(QHeaderView.ResizeToContents) + else: + self.infoWidget.setTabEnabled(index, False) + + def __populateRequiresProvides(self, detailsData): + """ + Private method to populate the requires/provides tab. + + @param detailsData package details + @type dict + """ + populatedItems = 0 + + if "requires" in detailsData and detailsData["requires"]: + self.requiredPackagesList.addItems(detailsData["requires"]) + populatedItems += len(detailsData["requires"]) + if "requires_dist" in detailsData and detailsData["requires_dist"]: + self.requiredDistributionsList.addItems( + detailsData["requires_dist"]) + populatedItems += len(detailsData["requires_dist"]) + if "provides" in detailsData and detailsData["provides"]: + self.providedPackagesList.addItems(detailsData["provides"]) + populatedItems += len(detailsData["provides"]) + if "provides_dist" in detailsData and detailsData["provides_dist"]: + self.providedDistributionsList.addItems( + detailsData["provides_dist"]) + populatedItems += len(detailsData["provides_dist"]) + + index = self.infoWidget.indexOf(self.requires) + self.infoWidget.setTabEnabled(index, populatedItems > 0) + + def __sanitize(self, text, forUrl=False): + """ + Private method to clean-up the given text. + + @param text raw text + @type str + @param forUrl flag indicating to sanitize an URL text + @type bool + @return processed text + @rtype str + """ + if text == "UNKNOWN": + text = "" + elif text == "any": + text = self.tr("any") + elif text is None: + text = "" + if forUrl: + if not isinstance(text, basestring) or \ + not text.startswith(("http://", "https://", "ftp://")): + # ignore if the schema is not one of the listed ones + text = "" + + return text + + def __formatUploadDate(self, datetime): + """ + Private method to format the upload date. + + @param datetime upload date and time + @type xmlrpc.DateTime or str + @return formatted date string + @rtype str + """ + if isinstance(datetime, str): + return datetime.split("T")[0] + else: + date = datetime.value.split("T")[0] + return "{0}-{1}-{2}".format(date[:4], date[4:6], date[6:]) + + def __formatSize(self, size): + """ + Private slot to format the size. + + @param size size to be formatted + @type int + @return formatted size + @rtype str + """ + unit = "" + if size < 1024: + unit = self.tr("B") + elif size < 1024 * 1024: + size /= 1024 + unit = self.tr("KB") + elif size < 1024 * 1024 * 1024: + size /= 1024 * 1024 + unit = self.tr("MB") + else: + size /= 1024 * 1024 * 1024 + unit = self.tr("GB") + return self.tr("{0:.1f} {1}", "value, unit").format(size, unit)
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/PipInterface/PipPackageDetailsDialog.ui Sat Feb 23 15:46:15 2019 +0100 @@ -0,0 +1,517 @@ +<?xml version="1.0" encoding="UTF-8"?> +<ui version="4.0"> + <class>PipPackageDetailsDialog</class> + <widget class="QDialog" name="PipPackageDetailsDialog"> + <property name="geometry"> + <rect> + <x>0</x> + <y>0</y> + <width>800</width> + <height>700</height> + </rect> + </property> + <property name="windowTitle"> + <string>Package Details</string> + </property> + <property name="sizeGripEnabled"> + <bool>true</bool> + </property> + <layout class="QVBoxLayout" name="verticalLayout"> + <item> + <widget class="QLabel" name="packageNameLabel"/> + </item> + <item> + <widget class="QTabWidget" name="infoWidget"> + <property name="currentIndex"> + <number>0</number> + </property> + <widget class="QWidget" name="details"> + <attribute name="title"> + <string>Details</string> + </attribute> + <attribute name="toolTip"> + <string>Lists package informations</string> + </attribute> + <layout class="QGridLayout" name="gridLayout_2"> + <item row="0" column="1"> + <widget class="QLabel" name="summaryLabel"> + <property name="wordWrap"> + <bool>true</bool> + </property> + </widget> + </item> + <item row="1" column="0"> + <widget class="QLabel" name="label_3"> + <property name="text"> + <string>Description:</string> + </property> + <property name="alignment"> + <set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop</set> + </property> + </widget> + </item> + <item row="3" column="1"> + <widget class="QLabel" name="authorEmailLabel"> + <property name="openExternalLinks"> + <bool>true</bool> + </property> + </widget> + </item> + <item row="1" column="1"> + <widget class="QPlainTextEdit" name="descriptionEdit"> + <property name="sizePolicy"> + <sizepolicy hsizetype="Expanding" vsizetype="Expanding"> + <horstretch>0</horstretch> + <verstretch>5</verstretch> + </sizepolicy> + </property> + <property name="tabChangesFocus"> + <bool>true</bool> + </property> + <property name="readOnly"> + <bool>true</bool> + </property> + </widget> + </item> + <item row="2" column="0"> + <widget class="QLabel" name="label_4"> + <property name="text"> + <string>Author:</string> + </property> + </widget> + </item> + <item row="2" column="1"> + <widget class="QLabel" name="authorLabel"/> + </item> + <item row="3" column="0"> + <widget class="QLabel" name="label_5"> + <property name="text"> + <string>Author Email:</string> + </property> + </widget> + </item> + <item row="7" column="1"> + <widget class="QLabel" name="packageUrlLabel"> + <property name="openExternalLinks"> + <bool>true</bool> + </property> + </widget> + </item> + <item row="4" column="0"> + <widget class="QLabel" name="label_6"> + <property name="text"> + <string>License:</string> + </property> + </widget> + </item> + <item row="4" column="1"> + <widget class="QLabel" name="licenseLabel"/> + </item> + <item row="0" column="0"> + <widget class="QLabel" name="label"> + <property name="text"> + <string>Summary:</string> + </property> + <property name="alignment"> + <set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop</set> + </property> + </widget> + </item> + <item row="5" column="0"> + <widget class="QLabel" name="label_7"> + <property name="text"> + <string>Platform:</string> + </property> + </widget> + </item> + <item row="5" column="1"> + <widget class="QLabel" name="platformLabel"/> + </item> + <item row="6" column="0"> + <widget class="QLabel" name="label_8"> + <property name="text"> + <string>Home Page:</string> + </property> + </widget> + </item> + <item row="6" column="1"> + <widget class="QLabel" name="homePageLabel"> + <property name="openExternalLinks"> + <bool>true</bool> + </property> + </widget> + </item> + <item row="7" column="0"> + <widget class="QLabel" name="label_9"> + <property name="text"> + <string>Package URL:</string> + </property> + </widget> + </item> + <item row="8" column="0"> + <widget class="QLabel" name="label_10"> + <property name="text"> + <string>Release URL:</string> + </property> + </widget> + </item> + <item row="8" column="1"> + <widget class="QLabel" name="releaseUrlLabel"> + <property name="openExternalLinks"> + <bool>true</bool> + </property> + </widget> + </item> + <item row="9" column="0"> + <widget class="QLabel" name="label_11"> + <property name="text"> + <string>Documentation URL:</string> + </property> + </widget> + </item> + <item row="9" column="1"> + <widget class="QLabel" name="docsUrlLabel"> + <property name="openExternalLinks"> + <bool>true</bool> + </property> + </widget> + </item> + <item row="10" column="0"> + <widget class="QLabel" name="label_12"> + <property name="text"> + <string>Downloads:</string> + </property> + <property name="alignment"> + <set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop</set> + </property> + </widget> + </item> + <item row="10" column="1"> + <layout class="QGridLayout" name="gridLayout"> + <item row="0" column="0"> + <widget class="QLabel" name="label_13"> + <property name="text"> + <string>Last Day:</string> + </property> + </widget> + </item> + <item row="0" column="1"> + <widget class="QLabel" name="downloadsDayLabel"> + <property name="alignment"> + <set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set> + </property> + </widget> + </item> + <item row="0" column="2"> + <spacer name="horizontalSpacer"> + <property name="orientation"> + <enum>Qt::Horizontal</enum> + </property> + <property name="sizeHint" stdset="0"> + <size> + <width>40</width> + <height>20</height> + </size> + </property> + </spacer> + </item> + <item row="1" column="0"> + <widget class="QLabel" name="label_14"> + <property name="text"> + <string>Last Week:</string> + </property> + </widget> + </item> + <item row="1" column="1"> + <widget class="QLabel" name="downloadsWeekLabel"> + <property name="alignment"> + <set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set> + </property> + </widget> + </item> + <item row="2" column="0"> + <widget class="QLabel" name="label_15"> + <property name="text"> + <string>Last Month:</string> + </property> + </widget> + </item> + <item row="2" column="1"> + <widget class="QLabel" name="downloadsMonthLabel"> + <property name="alignment"> + <set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set> + </property> + </widget> + </item> + </layout> + </item> + <item row="11" column="0"> + <widget class="QLabel" name="label_16"> + <property name="text"> + <string>Classifiers:</string> + </property> + <property name="alignment"> + <set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop</set> + </property> + </widget> + </item> + <item row="11" column="1"> + <widget class="QListWidget" name="classifiersList"> + <property name="sizePolicy"> + <sizepolicy hsizetype="Expanding" vsizetype="Expanding"> + <horstretch>0</horstretch> + <verstretch>1</verstretch> + </sizepolicy> + </property> + <property name="alternatingRowColors"> + <bool>true</bool> + </property> + <property name="selectionMode"> + <enum>QAbstractItemView::NoSelection</enum> + </property> + <property name="sortingEnabled"> + <bool>true</bool> + </property> + </widget> + </item> + </layout> + </widget> + <widget class="QWidget" name="urls"> + <attribute name="title"> + <string>Download URLs</string> + </attribute> + <attribute name="toolTip"> + <string>Lists the download URLs</string> + </attribute> + <layout class="QVBoxLayout" name="verticalLayout_2"> + <item> + <widget class="QTreeWidget" name="downloadUrlsList"> + <property name="alternatingRowColors"> + <bool>true</bool> + </property> + <property name="selectionMode"> + <enum>QAbstractItemView::NoSelection</enum> + </property> + <property name="rootIsDecorated"> + <bool>false</bool> + </property> + <property name="itemsExpandable"> + <bool>false</bool> + </property> + <attribute name="headerStretchLastSection"> + <bool>false</bool> + </attribute> + <column> + <property name="text"> + <string>File</string> + </property> + </column> + <column> + <property name="text"> + <string>Type</string> + </property> + </column> + <column> + <property name="text"> + <string>Py Version</string> + </property> + </column> + <column> + <property name="text"> + <string>Downloads</string> + </property> + </column> + <column> + <property name="text"> + <string>Uploaded on</string> + </property> + </column> + <column> + <property name="text"> + <string>Size</string> + </property> + </column> + </widget> + </item> + </layout> + </widget> + <widget class="QWidget" name="requires"> + <attribute name="title"> + <string>Requires/Provides</string> + </attribute> + <attribute name="toolTip"> + <string>Lists required and provided packages</string> + </attribute> + <layout class="QVBoxLayout" name="verticalLayout_3"> + <item> + <widget class="QGroupBox" name="groupBox"> + <property name="title"> + <string>Requires</string> + </property> + <layout class="QGridLayout" name="gridLayout_4"> + <item row="0" column="0"> + <widget class="QLabel" name="label_17"> + <property name="text"> + <string>Required Packages:</string> + </property> + <property name="alignment"> + <set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop</set> + </property> + </widget> + </item> + <item row="0" column="1"> + <widget class="QListWidget" name="requiredPackagesList"> + <property name="alternatingRowColors"> + <bool>true</bool> + </property> + <property name="selectionMode"> + <enum>QAbstractItemView::NoSelection</enum> + </property> + <property name="sortingEnabled"> + <bool>true</bool> + </property> + </widget> + </item> + <item row="1" column="0"> + <widget class="QLabel" name="label_18"> + <property name="text"> + <string>Required Distributions:</string> + </property> + <property name="alignment"> + <set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop</set> + </property> + </widget> + </item> + <item row="1" column="1"> + <widget class="QListWidget" name="requiredDistributionsList"> + <property name="alternatingRowColors"> + <bool>true</bool> + </property> + <property name="selectionMode"> + <enum>QAbstractItemView::NoSelection</enum> + </property> + <property name="sortingEnabled"> + <bool>true</bool> + </property> + </widget> + </item> + </layout> + </widget> + </item> + <item> + <widget class="QGroupBox" name="groupBox_2"> + <property name="title"> + <string>Provides</string> + </property> + <layout class="QGridLayout" name="gridLayout_3"> + <item row="0" column="0"> + <widget class="QLabel" name="label_20"> + <property name="text"> + <string>Provided Packages:</string> + </property> + <property name="alignment"> + <set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop</set> + </property> + </widget> + </item> + <item row="0" column="1"> + <widget class="QListWidget" name="providedPackagesList"> + <property name="alternatingRowColors"> + <bool>true</bool> + </property> + <property name="selectionMode"> + <enum>QAbstractItemView::NoSelection</enum> + </property> + <property name="sortingEnabled"> + <bool>true</bool> + </property> + </widget> + </item> + <item row="1" column="0"> + <widget class="QLabel" name="label_19"> + <property name="text"> + <string>Provided Distributions:</string> + </property> + <property name="alignment"> + <set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop</set> + </property> + </widget> + </item> + <item row="1" column="1"> + <widget class="QListWidget" name="providedDistributionsList"> + <property name="alternatingRowColors"> + <bool>true</bool> + </property> + <property name="selectionMode"> + <enum>QAbstractItemView::NoSelection</enum> + </property> + <property name="sortingEnabled"> + <bool>true</bool> + </property> + </widget> + </item> + </layout> + </widget> + </item> + </layout> + </widget> + </widget> + </item> + <item> + <widget class="QDialogButtonBox" name="buttonBox"> + <property name="orientation"> + <enum>Qt::Horizontal</enum> + </property> + <property name="standardButtons"> + <set>QDialogButtonBox::Close</set> + </property> + </widget> + </item> + </layout> + </widget> + <tabstops> + <tabstop>infoWidget</tabstop> + <tabstop>descriptionEdit</tabstop> + <tabstop>classifiersList</tabstop> + <tabstop>downloadUrlsList</tabstop> + <tabstop>requiredPackagesList</tabstop> + <tabstop>requiredDistributionsList</tabstop> + <tabstop>providedPackagesList</tabstop> + <tabstop>providedDistributionsList</tabstop> + </tabstops> + <resources/> + <connections> + <connection> + <sender>buttonBox</sender> + <signal>accepted()</signal> + <receiver>PipPackageDetailsDialog</receiver> + <slot>accept()</slot> + <hints> + <hint type="sourcelabel"> + <x>248</x> + <y>254</y> + </hint> + <hint type="destinationlabel"> + <x>157</x> + <y>274</y> + </hint> + </hints> + </connection> + <connection> + <sender>buttonBox</sender> + <signal>rejected()</signal> + <receiver>PipPackageDetailsDialog</receiver> + <slot>reject()</slot> + <hints> + <hint type="sourcelabel"> + <x>316</x> + <y>260</y> + </hint> + <hint type="destinationlabel"> + <x>286</x> + <y>274</y> + </hint> + </hints> + </connection> + </connections> +</ui>
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/PipInterface/PipPackagesInputDialog.py Sat Feb 23 15:46:15 2019 +0100 @@ -0,0 +1,70 @@ +# -*- coding: utf-8 -*- + +# Copyright (c) 2015 - 2019 Detlev Offenbach <detlev@die-offenbachs.de> +# + +""" +Module implementing a dialog to enter package specifications. +""" + +from __future__ import unicode_literals + +from PyQt5.QtCore import pyqtSlot +from PyQt5.QtWidgets import QDialog, QDialogButtonBox + +from .Ui_PipPackagesInputDialog import Ui_PipPackagesInputDialog + + +class PipPackagesInputDialog(QDialog, Ui_PipPackagesInputDialog): + """ + Class implementing a dialog to enter package specifications. + """ + def __init__(self, pip, title, install=True, parent=None): + """ + Constructor + + @param pip reference to the pip object + @type Pip + @param title dialog title + @type str + @param install flag indicating an install action + @type bool + @param parent reference to the parent widget + @type QWidget + """ + super(PipPackagesInputDialog, self).__init__(parent) + self.setupUi(self) + + self.setWindowTitle(title) + + self.buttonBox.button(QDialogButtonBox.Ok).setEnabled(False) + + self.userCheckBox.setVisible(install) + + msh = self.minimumSizeHint() + self.resize(max(self.width(), msh.width()), msh.height()) + + @pyqtSlot(str) + def on_packagesEdit_textChanged(self, txt): + """ + Private slot handling entering package names. + + @param txt name of the requirements file + @type str + """ + self.buttonBox.button(QDialogButtonBox.Ok).setEnabled(bool(txt)) + + def getData(self): + """ + Public method to get the entered data. + + @return tuple with the list of package specifications and a flag + indicating to install to the user install directory + @rtype tuple of (list of str, bool) + """ + packages = [p.strip() for p in self.packagesEdit.text().split()] + + return ( + packages, + self.userCheckBox.isChecked() + )
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/PipInterface/PipPackagesInputDialog.ui Sat Feb 23 15:46:15 2019 +0100 @@ -0,0 +1,87 @@ +<?xml version="1.0" encoding="UTF-8"?> +<ui version="4.0"> + <class>PipPackagesInputDialog</class> + <widget class="QDialog" name="PipPackagesInputDialog"> + <property name="geometry"> + <rect> + <x>0</x> + <y>0</y> + <width>600</width> + <height>130</height> + </rect> + </property> + <property name="windowTitle"> + <string>Packages </string> + </property> + <property name="sizeGripEnabled"> + <bool>true</bool> + </property> + <layout class="QVBoxLayout" name="verticalLayout"> + <item> + <widget class="QLabel" name="label_2"> + <property name="text"> + <string>Package Specifications (separated by whitespace):</string> + </property> + </widget> + </item> + <item> + <widget class="QLineEdit" name="packagesEdit"/> + </item> + <item> + <widget class="QCheckBox" name="userCheckBox"> + <property name="toolTip"> + <string>Select to install to the Python user install directory</string> + </property> + <property name="text"> + <string>Install into User Directory</string> + </property> + </widget> + </item> + <item> + <widget class="QDialogButtonBox" name="buttonBox"> + <property name="orientation"> + <enum>Qt::Horizontal</enum> + </property> + <property name="standardButtons"> + <set>QDialogButtonBox::Cancel|QDialogButtonBox::Ok</set> + </property> + </widget> + </item> + </layout> + </widget> + <resources/> + <connections> + <connection> + <sender>buttonBox</sender> + <signal>accepted()</signal> + <receiver>PipPackagesInputDialog</receiver> + <slot>accept()</slot> + <hints> + <hint type="sourcelabel"> + <x>248</x> + <y>254</y> + </hint> + <hint type="destinationlabel"> + <x>157</x> + <y>274</y> + </hint> + </hints> + </connection> + <connection> + <sender>buttonBox</sender> + <signal>rejected()</signal> + <receiver>PipPackagesInputDialog</receiver> + <slot>reject()</slot> + <hints> + <hint type="sourcelabel"> + <x>316</x> + <y>260</y> + </hint> + <hint type="destinationlabel"> + <x>286</x> + <y>274</y> + </hint> + </hints> + </connection> + </connections> +</ui>
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/PipInterface/PipPackagesWidget.py Sat Feb 23 15:46:15 2019 +0100 @@ -0,0 +1,1129 @@ +# -*- coding: utf-8 -*- + +# Copyright (c) 2019 Detlev Offenbach <detlev@die-offenbachs.de> +# + +""" +Module implementing the pip packages management widget. +""" + +from __future__ import unicode_literals + +import textwrap +import os + +from PyQt5.QtCore import pyqtSlot, Qt, QEventLoop, QRegExp +from PyQt5.QtGui import QCursor +from PyQt5.QtWidgets import QWidget, QToolButton, QApplication, QHeaderView, \ + QTreeWidgetItem, QInputDialog, QMenu, QDialog + +from E5Gui.E5Application import e5App +from E5Gui import E5MessageBox + +from E5Network.E5XmlRpcClient import E5XmlRpcClient + +from .Ui_PipPackagesWidget import Ui_PipPackagesWidget + +import UI.PixmapCache + +from .Pip import Pip + + +class PipPackagesWidget(QWidget, Ui_PipPackagesWidget): + """ + Class implementing the pip packages management widget. + """ + ShowProcessGeneralMode = 0 + ShowProcessClassifiersMode = 1 + ShowProcessEntryPointsMode = 2 + ShowProcessFilesListMode = 3 + + SearchStopwords = { + "a", "and", "are", "as", "at", "be", "but", "by", + "for", "if", "in", "into", "is", "it", + "no", "not", "of", "on", "or", "such", + "that", "the", "their", "then", "there", "these", + "they", "this", "to", "was", "will", + } + SearchVersionRole = Qt.UserRole + 1 + + def __init__(self, parent=None): + """ + Constructor + + @param parent reference to the parent widget + @type QWidget + """ + super(PipPackagesWidget, self).__init__(parent) + self.setupUi(self) + + self.pipMenuButton.setObjectName( + "navigation_supermenu_button") + self.pipMenuButton.setIcon(UI.PixmapCache.getIcon("superMenu")) + self.pipMenuButton.setToolTip(self.tr("pip Menu")) + self.pipMenuButton.setPopupMode(QToolButton.InstantPopup) + self.pipMenuButton.setToolButtonStyle(Qt.ToolButtonIconOnly) + self.pipMenuButton.setFocusPolicy(Qt.NoFocus) + self.pipMenuButton.setAutoRaise(True) + self.pipMenuButton.setShowMenuInside(True) + + self.refreshButton.setIcon(UI.PixmapCache.getIcon("reload")) + self.upgradeButton.setIcon(UI.PixmapCache.getIcon("1uparrow")) + self.upgradeAllButton.setIcon(UI.PixmapCache.getIcon("2uparrow")) + self.uninstallButton.setIcon(UI.PixmapCache.getIcon("minus")) + self.showPackageDetailsButton.setIcon(UI.PixmapCache.getIcon("info")) + self.searchToggleButton.setIcon(UI.PixmapCache.getIcon("find")) + self.searchButton.setIcon(UI.PixmapCache.getIcon("findNext")) + self.installButton.setIcon(UI.PixmapCache.getIcon("plus")) + self.installUserSiteButton.setIcon(UI.PixmapCache.getIcon("addUser")) + self.showDetailsButton.setIcon(UI.PixmapCache.getIcon("info")) + + self.__pip = Pip(self) + self.__client = E5XmlRpcClient(self.__pip.getIndexUrlXml(), self) + + self.packagesList.header().setSortIndicator(0, Qt.AscendingOrder) + + self.__infoLabels = { + "name": self.tr("Name:"), + "version": self.tr("Version:"), + "location": self.tr("Location:"), + "requires": self.tr("Requires:"), + "summary": self.tr("Summary:"), + "home-page": self.tr("Homepage:"), + "author": self.tr("Author:"), + "author-email": self.tr("Author Email:"), + "license": self.tr("License:"), + "metadata-version": self.tr("Metadata Version:"), + "installer": self.tr("Installer:"), + "classifiers": self.tr("Classifiers:"), + "entry-points": self.tr("Entry Points:"), + "files": self.tr("Files:"), + } + self.infoWidget.setHeaderLabels(["Key", "Value"]) + + venvManager = e5App().getObject("VirtualEnvManager") + venvManager.virtualEnvironmentAdded.connect( + self.on_refreshButton_clicked) + venvManager.virtualEnvironmentRemoved.connect( + self.on_refreshButton_clicked) + + project = e5App().getObject("Project") + project.projectOpened.connect( + self.on_refreshButton_clicked) + project.projectClosed.connect( + self.on_refreshButton_clicked) + + self.__initPipMenu() + self.__populateEnvironments() + self.__updateActionButtons() + + self.statusLabel.hide() + self.searchWidget.hide() + + self.__queryName = [] + self.__querySummary = [] + + self.__packageDetailsDialog = None + + def __populateEnvironments(self): + """ + Private method to get a list of environments and populate the selector. + """ + self.environmentsComboBox.addItem("") + projectVenv = self.__pip.getProjectEnvironmentString() + if projectVenv: + self.environmentsComboBox.addItem(projectVenv) + self.environmentsComboBox.addItems(self.__pip.getVirtualenvNames()) + + def __isPipAvailable(self): + """ + Private method to check, if the pip package is available for the + selected environment. + + @return flag indicating availability + @rtype bool + """ + available = False + + venvName = self.environmentsComboBox.currentText() + if venvName: + available = len(self.packagesList.findItems( + "pip", Qt.MatchExactly | Qt.MatchCaseSensitive)) == 1 + + return available + + ####################################################################### + ## Slots handling widget signals below + ####################################################################### + + def __selectedUpdateableItems(self): + """ + Private method to get a list of selected items that can be updated. + + @return list of selected items that can be updated + @rtype list of QTreeWidgetItem + """ + return [ + itm for itm in self.packagesList.selectedItems() + if bool(itm.text(2)) + ] + + def __allUpdateableItems(self): + """ + Private method to get a list of all items that can be updated. + + @return list of all items that can be updated + @rtype list of QTreeWidgetItem + """ + updateableItems = [] + for index in range(self.packagesList.topLevelItemCount()): + itm = self.packagesList.topLevelItem(index) + if itm.text(2): + updateableItems.append(itm) + + return updateableItems + + def __updateActionButtons(self): + """ + Private method to set the state of the action buttons. + """ + if self.__isPipAvailable(): + self.upgradeButton.setEnabled( + bool(self.__selectedUpdateableItems())) + self.uninstallButton.setEnabled( + bool(self.packagesList.selectedItems())) + self.upgradeAllButton.setEnabled( + bool(self.__allUpdateableItems())) + self.showPackageDetailsButton.setEnabled( + len(self.packagesList.selectedItems()) == 1) + else: + self.upgradeButton.setEnabled(False) + self.uninstallButton.setEnabled(False) + self.upgradeAllButton.setEnabled(False) + self.showPackageDetailsButton.setEnabled(False) + + def __refreshPackagesList(self): + """ + Private method to referesh the packages list. + """ + self.packagesList.clear() + venvName = self.environmentsComboBox.currentText() + if venvName: + interpreter = self.__pip.getVirtualenvInterpreter(venvName) + if interpreter: + QApplication.setOverrideCursor(QCursor(Qt.WaitCursor)) + self.statusLabel.show() + self.statusLabel.setText( + self.tr("Getting installed packages...")) + QApplication.processEvents() + + # 1. populate with installed packages + self.packagesList.setUpdatesEnabled(False) + installedPackages = self.__pip.getInstalledPackages( + venvName, + localPackages=self.localCheckBox.isChecked(), + notRequired=self.notRequiredCheckBox.isChecked(), + usersite=self.userCheckBox.isChecked(), + ) + for package, version in installedPackages: + QTreeWidgetItem(self.packagesList, [package, version]) + self.packagesList.setUpdatesEnabled(True) + self.statusLabel.setText( + self.tr("Getting outdated packages...")) + QApplication.processEvents() + + # 2. update with update information + self.packagesList.setUpdatesEnabled(False) + outdatedPackages = self.__pip.getOutdatedPackages( + venvName, + localPackages=self.localCheckBox.isChecked(), + notRequired=self.notRequiredCheckBox.isChecked(), + usersite=self.userCheckBox.isChecked(), + ) + for package, _version, latest in outdatedPackages: + items = self.packagesList.findItems( + package, Qt.MatchExactly | Qt.MatchCaseSensitive) + if items: + itm = items[0] + itm.setText(2, latest) + + self.packagesList.sortItems(0, Qt.AscendingOrder) + for col in range(self.packagesList.columnCount()): + self.packagesList.resizeColumnToContents(col) + self.packagesList.setUpdatesEnabled(True) + QApplication.restoreOverrideCursor() + self.statusLabel.hide() + + self.__updateActionButtons() + self.__updateSearchActionButtons() + self.__updateSearchButton() + + @pyqtSlot(int) + def on_environmentsComboBox_currentIndexChanged(self, index): + """ + Private slot handling the selection of a conda environment. + + @param index index of the selected conda environment + @type int + """ + self.__refreshPackagesList() + + @pyqtSlot(bool) + def on_localCheckBox_clicked(self, checked): + """ + Private slot handling the switching of the local mode. + + @param checked state of the local check box + @type bool + """ + self.__refreshPackagesList() + + @pyqtSlot(bool) + def on_notRequiredCheckBox_clicked(self, checked): + """ + Private slot handling the switching of the 'not required' mode. + + @param checked state of the 'not required' check box + @type bool + """ + self.__refreshPackagesList() + + @pyqtSlot(bool) + def on_userCheckBox_clicked(self, checked): + """ + Private slot handling the switching of the 'user-site' mode. + + @param checked state of the 'user-site' check box + @type bool + """ + self.__refreshPackagesList() + + @pyqtSlot() + def on_packagesList_itemSelectionChanged(self): + """ + Private slot handling the selection of a package. + """ + self.infoWidget.clear() + + if len(self.packagesList.selectedItems()) == 1: + itm = self.packagesList.selectedItems()[0] + + environment = self.environmentsComboBox.currentText() + interpreter = self.__pip.getVirtualenvInterpreter(environment) + if not interpreter: + return + + QApplication.setOverrideCursor(Qt.WaitCursor) + + args = ["-m", "pip", "show"] + if self.verboseCheckBox.isChecked(): + args.append("--verbose") + if self.installedFilesCheckBox.isChecked(): + args.append("--files") + args.append(itm.text(0)) + success, output = self.__pip.runProcess(args, interpreter) + + if success and output: + mode = self.ShowProcessGeneralMode + for line in output.splitlines(): + line = line.rstrip() + if line != "---": + if mode != self.ShowProcessGeneralMode: + if line[0] == " ": + QTreeWidgetItem( + self.infoWidget, + [" ", line.strip()]) + else: + mode = self.ShowProcessGeneralMode + if mode == self.ShowProcessGeneralMode: + try: + label, info = line.split(": ", 1) + except ValueError: + label = line[:-1] + info = "" + label = label.lower() + if label in self.__infoLabels: + QTreeWidgetItem( + self.infoWidget, + [self.__infoLabels[label], info]) + if label == "files": + mode = self.ShowProcessFilesListMode + elif label == "classifiers": + mode = self.ShowProcessClassifiersMode + elif label == "entry-points": + mode = self.ShowProcessEntryPointsMode + self.infoWidget.scrollToTop() + + header = self.infoWidget.header() + header.setStretchLastSection(False) + header.resizeSections(QHeaderView.ResizeToContents) + if header.sectionSize(0) + header.sectionSize(1) < header.width(): + header.setStretchLastSection(True) + + QApplication.restoreOverrideCursor() + + self.__updateActionButtons() + + @pyqtSlot(QTreeWidgetItem, int) + def on_packagesList_itemActivated(self, item, column): + """ + Private slot reacting on a package item activation. + + @param item reference to the activated item + @type QTreeWidgetItem + @param column activated column + @type int + """ + packageName = item.text(0) + if column == 1: + # show details for installed version + packageVersion = item.text(1) + else: + # show details for available version or installed one + if item.text(2): + packageVersion = item.text(2) + else: + packageVersion = item.text(1) + + self.__showPackageDetails(packageName, packageVersion) + + @pyqtSlot(bool) + def on_verboseCheckBox_clicked(self, checked): + """ + Private slot to handle a change of the verbose package information + checkbox. + + @param checked state of the checkbox + @type bool + """ + self.on_packagesList_itemSelectionChanged() + + @pyqtSlot(bool) + def on_installedFilesCheckBox_clicked(self, checked): + """ + Private slot to handle a change of the installed files information + checkbox. + + @param checked state of the checkbox + @type bool + """ + self.on_packagesList_itemSelectionChanged() + + @pyqtSlot() + def on_refreshButton_clicked(self): + """ + Private slot to refresh the display. + """ + currentEnvironment = self.environmentsComboBox.currentText() + self.environmentsComboBox.clear() + self.packagesList.clear() + + QApplication.setOverrideCursor(QCursor(Qt.WaitCursor)) + QApplication.processEvents() + + self.__populateEnvironments() + + index = self.environmentsComboBox.findText( + currentEnvironment, Qt.MatchExactly | Qt.MatchCaseSensitive) + if index != -1: + self.environmentsComboBox.setCurrentIndex(index) + + QApplication.restoreOverrideCursor() + self.__updateActionButtons() + + @pyqtSlot() + def on_upgradeButton_clicked(self): + """ + Private slot to upgrade selected packages of the selected environment. + """ + packages = [itm.text(0) for itm in self.__selectedUpdateableItems()] + if packages: + ok = self.__executeUpgradePackages(packages) + if ok: + self.on_refreshButton_clicked() + + @pyqtSlot() + def on_upgradeAllButton_clicked(self): + """ + Private slot to upgrade all packages of the selected environment. + """ + packages = [itm.text(0) for itm in self.__allUpdateableItems()] + if packages: + ok = self.__executeUpgradePackages(packages) + if ok: + self.on_refreshButton_clicked() + + @pyqtSlot() + def on_uninstallButton_clicked(self): + """ + Private slot to remove selected packages of the selected environment. + """ + packages = [itm.text(0) for itm in self.packagesList.selectedItems()] + if packages: + ok = self.__pip.uninstallPackages( + packages, + venvName=self.environmentsComboBox.currentText()) + if ok: + self.on_refreshButton_clicked() + + def __executeUpgradePackages(self, packages): + """ + Private method to execute the pip upgrade command. + + @param packages list of package names to be upgraded + @type list of str + @return flag indicating success + @rtype bool + """ + ok = self.__pip.upgradePackages( + packages, venvName=self.environmentsComboBox.currentText(), + userSite=self.userCheckBox.isChecked()) + return ok + + @pyqtSlot() + def on_showPackageDetailsButton_clicked(self): + """ + Private slot to show information for the selected package. + """ + item = self.packagesList.selectedItems()[0] + if item: + packageName = item.text(0) + # show details for available version or installed one + if item.text(2): + packageVersion = item.text(2) + else: + packageVersion = item.text(1) + + self.__showPackageDetails(packageName, packageVersion) + + ####################################################################### + ## Search widget related methods below + ####################################################################### + + def __updateSearchActionButtons(self): + """ + Private method to update the action button states of the search widget. + """ + installEnable = ( + len(self.searchResultList.selectedItems()) > 0 and + self.environmentsComboBox.currentIndex() > 0 and + self.__isPipAvailable() + ) + self.installButton.setEnabled(installEnable) + self.installUserSiteButton.setEnabled(installEnable) + + self.showDetailsButton.setEnabled( + len(self.searchResultList.selectedItems()) == 1 and + self.__isPipAvailable() + ) + + def __updateSearchButton(self): + """ + Private method to update the state of the search button. + """ + self.searchButton.setEnabled( + (bool(self.searchEditName.text()) or + bool(self.searchEditSummary.text())) and + self.__isPipAvailable() + ) + + @pyqtSlot(bool) + def on_searchToggleButton_toggled(self, checked): + """ + Private slot to togle the search widget. + + @param checked state of the search widget button + @type bool + """ + self.searchWidget.setVisible(checked) + + if checked: + self.searchEditName.setFocus(Qt.OtherFocusReason) + self.searchEditName.selectAll() + + self.__updateSearchActionButtons() + self.__updateSearchButton() + + @pyqtSlot(str) + def on_searchEditName_textChanged(self, txt): + """ + Private slot handling a change of the search term. + + @param txt search term + @type str + """ + self.__updateSearchButton() + + @pyqtSlot() + def on_searchEditName_returnPressed(self): + """ + Private slot initiating a search via a press of the Return key. + """ + self.__search() + + @pyqtSlot(str) + def on_searchEditSummary_textChanged(self, txt): + """ + Private slot handling a change of the search term. + + @param txt search term + @type str + """ + self.__updateSearchButton() + + @pyqtSlot() + def on_searchEditSummary_returnPressed(self): + """ + Private slot initiating a search via a press of the Return key. + """ + self.__search() + + @pyqtSlot() + def on_searchButton_clicked(self): + """ + Private slot handling a press of the search button. + """ + self.__search() + + @pyqtSlot() + def on_searchResultList_itemSelectionChanged(self): + """ + Private slot handling changes of the search result selection. + """ + self.__updateSearchActionButtons() + + def __search(self): + """ + Private method to perform the search. + """ + self.searchResultList.clear() + self.searchInfoLabel.clear() + + self.searchButton.setEnabled(False) + QApplication.setOverrideCursor(Qt.WaitCursor) + QApplication.processEvents(QEventLoop.ExcludeUserInputEvents) + + self.__queryName = [ + term for term in self.searchEditName.text().strip().split() + if term not in self.SearchStopwords + ] + self.__querySummary = [ + term for term in self.searchEditSummary.text().strip().split() + if term not in self.SearchStopwords + ] + self.__client.call( + "search", + ({"name": self.__queryName, + "summary": self.__querySummary}, + self.searchTermCombineComboBox.currentText()), + self.__processSearchResult, + self.__searchError + ) + + def __processSearchResult(self, data): + """ + Private method to process the search result data from PyPI. + + @param data result data with hits in the first element + @type tuple + """ + if data: + packages = self.__transformHits(data[0]) + if packages: + self.searchInfoLabel.setText( + self.tr("%n package(s) found.", "", len(packages))) + wrapper = textwrap.TextWrapper(width=80) + count = 0 + total = 0 + for package in packages: + itm = QTreeWidgetItem( + self.searchResultList, [ + package['name'].strip(), + "{0:4d}".format(package['score']), + "\n".join([ + wrapper.fill(line) for line in + package['summary'].strip().splitlines() + ]) + ]) + itm.setData(0, self.SearchVersionRole, package['version']) + count += 1 + total += 1 + if count == 100: + count = 0 + QApplication.processEvents() + else: + QApplication.restoreOverrideCursor() + E5MessageBox.warning( + self, + self.tr("Search PyPI"), + self.tr("""<p>The package search did not return""" + """ anything.</p>""")) + self.searchInfoLabel.setText( + self.tr("""<p>The package search did not return""" + """ anything.</p>""")) + else: + QApplication.restoreOverrideCursor() + E5MessageBox.warning( + self, + self.tr("Search PyPI"), + self.tr("""<p>The package search did not return anything.""" + """</p>""")) + self.searchInfoLabel.setText( + self.tr("""<p>The package search did not return anything.""" + """</p>""")) + + header = self.searchResultList.header() + self.searchResultList.sortItems(1, Qt.DescendingOrder) + header.setStretchLastSection(False) + header.resizeSections(QHeaderView.ResizeToContents) + headerSize = 0 + for col in range(header.count()): + headerSize += header.sectionSize(col) + if headerSize < header.width(): + header.setStretchLastSection(True) + + self.__finishSearch() + + def __finishSearch(self): + """ + Private slot performing the search finishing actions. + """ + QApplication.restoreOverrideCursor() + + self.__updateSearchActionButtons() + self.__updateSearchButton() + + self.searchEditName.setFocus(Qt.OtherFocusReason) + + def __searchError(self, errorCode, errorString): + """ + Private method handling a search error. + + @param errorCode code of the error + @type int + @param errorString error message + @type str + """ + self.__finish() + E5MessageBox.warning( + self, + self.tr("Search PyPI"), + self.tr("""<p>The package search failed.</p><p>Reason: {0}</p>""") + .format(errorString)) + self.searchInfoLabel.setText(self.tr("Error: {0}").format(errorString)) + + def __transformHits(self, hits): + """ + Private method to convert the list returned from pypi into a + packages list. + + @param hits list returned from pypi + @type list of dict + @return list of packages + @rtype list of dict + """ + # we only include the record with the highest score + packages = {} + for hit in hits: + name = hit['name'].strip() + summary = (hit['summary'] or "").strip() + version = hit['version'].strip() + score = self.__score(name, summary) + # cleanup the summary + if summary in ["UNKNOWN", "."]: + summary = "" + + if name not in packages: + packages[name] = { + 'name': name, + 'summary': summary, + 'version': [version.strip()], + 'score': score} + else: + if score > packages[name]['score']: + packages[name]['score'] = score + packages[name]['summary'] = summary + packages[name]['version'].append(version.strip()) + + return list(packages.values()) + + def __score(self, name, summary): + """ + Private method to calculate some score for a search result. + + @param name name of the returned package + @type str + @param summary summary text for the package + @type str + @return score value + @rtype int + """ + score = 0 + for queryTerm in self.__queryName: + if queryTerm.lower() in name.lower(): + score += 4 + if queryTerm.lower() == name.lower(): + score += 4 + + for queryTerm in self.__querySummary: + if queryTerm.lower() in summary.lower(): + if QRegExp(r'\b{0}\b'.format(QRegExp.escape(queryTerm)), + Qt.CaseInsensitive).indexIn(summary) != -1: + # word match gets even higher score + score += 2 + else: + score += 1 + + return score + + @pyqtSlot() + def on_installButton_clicked(self): + """ + Private slot to handle pressing the Install button.. + """ + self.__install() + + @pyqtSlot() + def on_installUserSiteButton_clicked(self): + """ + Private slot to handle pressing the Install to User-Site button.. + """ + self.__install(userSite=True) + + def __install(self, userSite=False): + """ + Private slot to install the selected packages. + + @param userSite flag indicating to install to the user directory + @type bool + """ + venvName = self.environmentsComboBox.currentText() + if venvName: + packages = [] + for itm in self.searchResultList.selectedItems(): + packages.append(itm.text(0).strip()) + if packages: + self.__pip.installPackages(packages, venvName=venvName, + userSite=userSite) + + @pyqtSlot() + def on_showDetailsButton_clicked(self): + """ + Private slot to handle pressing the Show Details button. + """ + self.__showSearchedDetails() + + @pyqtSlot(QTreeWidgetItem, int) + def on_searchResultList_itemActivated(self, item, column): + """ + Private slot reacting on an search result item activation. + + @param item reference to the activated item + @type QTreeWidgetItem + @param column activated column + @type int + """ + self.__showDetails(item) + + def __showSearchedDetails(self, item=None): + """ + Private slot to show details about the selected search result package. + + @param item reference to the search result item to show details for + @type QTreeWidgetItem + """ + self.showDetailsButton.setEnabled(False) + + if not item: + item = self.searchResultList.selectedItems()[0] + + packageVersions = item.data(0, self.SearchVersionRole) + if len(packageVersions) == 1: + packageVersion = packageVersions[0] + elif len(packageVersions) == 0: + packageVersion = "" + else: + packageVersion, ok = QInputDialog.getItem( + self, + self.tr("Show Package Details"), + self.tr("Select the package version:"), + packageVersions, + 0, False) + if not ok: + return + packageName = item.text(0) + + self.__showPackageDetails(packageName, packageVersion) + + def __showPackageDetails(self, packageName, packageVersion): + """ + Private method to populate the package details dialog. + + @param packageName name of the package to show details for + @type str + @param packageVersion version of the package + @type str + """ + QApplication.setOverrideCursor(Qt.WaitCursor) + QApplication.processEvents(QEventLoop.ExcludeUserInputEvents) + + packageData = self.__pip.getPackageDetails(packageName, packageVersion) + + QApplication.restoreOverrideCursor() + if packageData: + from .PipPackageDetailsDialog import PipPackageDetailsDialog + + self.showDetailsButton.setEnabled(True) + + if self.__packageDetailsDialog is not None: + self.__packageDetailsDialog.close() + + self.__packageDetailsDialog = \ + PipPackageDetailsDialog(packageData, self) + self.__packageDetailsDialog.show() + else: + E5MessageBox.warning( + self, + self.tr("Search PyPI"), + self.tr("""<p>No package details info for <b>{0}</b>""" + """ available.</p>""").format(packageName)) + + ####################################################################### + ## Menu related methods below + ####################################################################### + + def __initPipMenu(self): + """ + Private method to create the super menu and attach it to the super + menu button. + """ + self.__pipMenu = QMenu() + self.__installPipAct = self.__pipMenu.addAction( + self.tr("Install Pip"), + self.__installPip) + self.__installPipUserAct = self.__pipMenu.addAction( + self.tr("Install Pip to User-Site"), + self.__installPipUser) + self.__repairPipAct = self.__pipMenu.addAction( + self.tr("Repair Pip"), + self.__repairPip) + self.__pipMenu.addSeparator() + self.__installPackagesAct = self.__pipMenu.addAction( + self.tr("Install Packages"), + self.__installPackages) + self.__installLocalPackageAct = self.__pipMenu.addAction( + self.tr("Install Local Package"), + self.__installLocalPackage) + self.__pipMenu.addSeparator() + self.__installRequirementsAct = self.__pipMenu.addAction( + self.tr("Install Requirements"), + self.__installRequirements) + self.__uninstallRequirementsAct = self.__pipMenu.addAction( + self.tr("Uninstall Requirements"), + self.__uninstallRequirements) + self.__generateRequirementsAct = self.__pipMenu.addAction( + self.tr("Generate Requirements..."), + self.__generateRequirements) + self.__pipMenu.addSeparator() + # editUserConfigAct + self.__pipMenu.addAction( + self.tr("Edit User Configuration..."), + self.__editUserConfiguration) + self.__editVirtualenvConfigAct = self.__pipMenu.addAction( + self.tr("Edit Current Virtualenv Configuration..."), + self.__editVirtualenvConfiguration) + self.__pipMenu.addSeparator() + # pipConfigAct + self.__pipMenu.addAction( + self.tr("Configure..."), + self.__pipConfigure) + + self.__pipMenu.aboutToShow.connect(self.__aboutToShowPipMenu) + + self.pipMenuButton.setMenu(self.__pipMenu) + + def __aboutToShowPipMenu(self): + """ + Private slot to set the action enabled status. + """ + enable = bool(self.environmentsComboBox.currentText()) + enablePip = self.__isPipAvailable() + + self.__installPipAct.setEnabled(not enablePip) + self.__installPipUserAct.setEnabled(not enablePip) + self.__repairPipAct.setEnabled(enablePip) + + self.__installPackagesAct.setEnabled(enablePip) + self.__installLocalPackageAct.setEnabled(enablePip) + + self.__installRequirementsAct.setEnabled(enablePip) + self.__uninstallRequirementsAct.setEnabled(enablePip) + self.__generateRequirementsAct.setEnabled(enablePip) + + self.__editVirtualenvConfigAct.setEnabled(enable) + + @pyqtSlot() + def __installPip(self): + """ + Private slot to install pip into the selected environment. + """ + venvName = self.environmentsComboBox.currentText() + if venvName: + self.__pip.installPip(venvName) + + @pyqtSlot() + def __installPipUser(self): + """ + Private slot to install pip into the user site for the selected + environment. + """ + venvName = self.environmentsComboBox.currentText() + if venvName: + self.__pip.installPip(venvName, userSite=True) + + @pyqtSlot() + def __repairPip(self): + """ + Private slot to repair the pip installation of the selected + environment. + """ + venvName = self.environmentsComboBox.currentText() + if venvName: + self.__pip.repairPip(venvName) + + @pyqtSlot() + def __installPackages(self): + """ + Private slot to install packages to be given by the user. + """ + venvName = self.environmentsComboBox.currentText() + if venvName: + from .PipPackagesInputDialog import PipPackagesInputDialog + dlg = PipPackagesInputDialog(self, self.tr("Install Packages")) + if dlg.exec_() == QDialog.Accepted: + packages, user = dlg.getData() + if packages: + self.__pip.installPackages(packages, venvName=venvName, + userSite=user) + + @pyqtSlot() + def __installLocalPackage(self): + """ + Private slot to install a package available on local storage. + """ + venvName = self.environmentsComboBox.currentText() + if venvName: + from .PipFileSelectionDialog import PipFileSelectionDialog + dlg = PipFileSelectionDialog(self, "package") + if dlg.exec_() == QDialog.Accepted: + package, user = dlg.getData() + if package and os.path.exists(package): + self.__pip.installPackages([package], venvName=venvName, + userSite=user) + + @pyqtSlot() + def __installRequirements(self): + """ + Private slot to install packages as given in a requirements file. + """ + venvName = self.environmentsComboBox.currentText() + if venvName: + self.__pip.installRequirements(venvName) + + @pyqtSlot() + def __uninstallRequirements(self): + """ + Private slot to uninstall packages as given in a requirements file. + """ + venvName = self.environmentsComboBox.currentText() + if venvName: + self.__pip.uninstallRequirements(venvName) + + @pyqtSlot() + def __generateRequirements(self): + """ + Private slot to generate the contents for a requirements file. + """ + venvName = self.environmentsComboBox.currentText() + if venvName: + from .PipFreezeDialog import PipFreezeDialog + self.__freezeDialog = PipFreezeDialog(self.__pip, self) + self.__freezeDialog.show() + self.__freezeDialog.start(venvName) + + @pyqtSlot() + def __editUserConfiguration(self): + """ + Private slot to edit the user configuration. + """ + self.__editConfiguration() + + @pyqtSlot() + def __editVirtualenvConfiguration(self): + """ + Private slot to edit the configuration of the selected environment. + """ + venvName = self.environmentsComboBox.currentText() + if venvName: + self.__editConfiguration(venvName=venvName) + + def __editConfiguration(self, venvName=""): + """ + Private method to edit a configuration. + + @param venvName name of the environment to act upon + @type str + """ + from QScintilla.MiniEditor import MiniEditor + if venvName: + cfgFile = self.__pip.getVirtualenvConfig(venvName) + if not cfgFile: + return + else: + cfgFile = self.__pip.getUserConfig() + cfgDir = os.path.dirname(cfgFile) + if not cfgDir: + E5MessageBox.critical( + None, + self.tr("Edit Configuration"), + self.tr("""No valid configuration path determined.""" + """ Aborting""")) + return + + try: + if not os.path.isdir(cfgDir): + os.makedirs(cfgDir) + except OSError: + E5MessageBox.critical( + None, + self.tr("Edit Configuration"), + self.tr("""No valid configuration path determined.""" + """ Aborting""")) + return + + if not os.path.exists(cfgFile): + try: + f = open(cfgFile, "w") + f.write("[global]\n") + f.close() + except (IOError, OSError): + # ignore these + pass + + # check, if the destination is writeable + if not os.access(cfgFile, os.W_OK): + E5MessageBox.critical( + None, + self.tr("Edit Configuration"), + self.tr("""No valid configuartion path determined.""" + """ Aborting""")) + return + + self.__editor = MiniEditor(cfgFile, "Properties") + self.__editor.show() + + def __pipConfigure(self): + """ + Private slot to open the configuration page. + """ + e5App().getObject("UserInterface").showPreferences("pipPage")
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/PipInterface/PipPackagesWidget.ui Sat Feb 23 15:46:15 2019 +0100 @@ -0,0 +1,520 @@ +<?xml version="1.0" encoding="UTF-8"?> +<ui version="4.0"> + <class>PipPackagesWidget</class> + <widget class="QWidget" name="PipPackagesWidget"> + <property name="geometry"> + <rect> + <x>0</x> + <y>0</y> + <width>503</width> + <height>700</height> + </rect> + </property> + <layout class="QVBoxLayout" name="verticalLayout_5"> + <item> + <widget class="QWidget" name="baseWidget" native="true"> + <layout class="QVBoxLayout" name="verticalLayout_4"> + <property name="leftMargin"> + <number>0</number> + </property> + <property name="topMargin"> + <number>0</number> + </property> + <property name="rightMargin"> + <number>0</number> + </property> + <property name="bottomMargin"> + <number>0</number> + </property> + <item> + <layout class="QHBoxLayout" name="horizontalLayout"> + <item> + <widget class="QComboBox" name="environmentsComboBox"/> + </item> + <item> + <widget class="E5ToolButton" name="pipMenuButton"/> + </item> + </layout> + </item> + <item> + <layout class="QGridLayout" name="gridLayout_2"> + <item row="0" column="0"> + <widget class="QCheckBox" name="localCheckBox"> + <property name="toolTip"> + <string>Select to show only locally-installed packages</string> + </property> + <property name="text"> + <string>Local packages only</string> + </property> + <property name="checked"> + <bool>true</bool> + </property> + </widget> + </item> + <item row="0" column="1"> + <widget class="QCheckBox" name="notRequiredCheckBox"> + <property name="toolTip"> + <string>Select to list packages that are not dependencies of installed packages</string> + </property> + <property name="text"> + <string>Not required Packages</string> + </property> + </widget> + </item> + <item row="1" column="0"> + <widget class="QCheckBox" name="userCheckBox"> + <property name="toolTip"> + <string>Select to show only packages installed to the user-site</string> + </property> + <property name="text"> + <string>User-Site only</string> + </property> + </widget> + </item> + </layout> + </item> + <item> + <widget class="QLabel" name="statusLabel"/> + </item> + <item> + <widget class="QSplitter" name="splitter"> + <property name="orientation"> + <enum>Qt::Vertical</enum> + </property> + <widget class="QTreeWidget" name="packagesList"> + <property name="sizePolicy"> + <sizepolicy hsizetype="Expanding" vsizetype="Expanding"> + <horstretch>0</horstretch> + <verstretch>3</verstretch> + </sizepolicy> + </property> + <property name="alternatingRowColors"> + <bool>true</bool> + </property> + <property name="selectionMode"> + <enum>QAbstractItemView::ExtendedSelection</enum> + </property> + <property name="rootIsDecorated"> + <bool>false</bool> + </property> + <property name="itemsExpandable"> + <bool>false</bool> + </property> + <property name="sortingEnabled"> + <bool>true</bool> + </property> + <attribute name="headerDefaultSectionSize"> + <number>150</number> + </attribute> + <column> + <property name="text"> + <string>Package</string> + </property> + </column> + <column> + <property name="text"> + <string>Installed Version</string> + </property> + </column> + <column> + <property name="text"> + <string>Available Version</string> + </property> + </column> + </widget> + <widget class="QWidget" name="widget" native="true"> + <property name="sizePolicy"> + <sizepolicy hsizetype="Preferred" vsizetype="Preferred"> + <horstretch>0</horstretch> + <verstretch>1</verstretch> + </sizepolicy> + </property> + <layout class="QVBoxLayout" name="verticalLayout_3"> + <property name="leftMargin"> + <number>0</number> + </property> + <property name="topMargin"> + <number>0</number> + </property> + <property name="rightMargin"> + <number>0</number> + </property> + <property name="bottomMargin"> + <number>0</number> + </property> + <item> + <layout class="QHBoxLayout" name="horizontalLayout_7"> + <item> + <widget class="QCheckBox" name="verboseCheckBox"> + <property name="toolTip"> + <string>Select to show verbose package information</string> + </property> + <property name="text"> + <string>Verbose Package Information</string> + </property> + </widget> + </item> + <item> + <widget class="QCheckBox" name="installedFilesCheckBox"> + <property name="toolTip"> + <string>Select to show information about installed files</string> + </property> + <property name="text"> + <string>Installed Files Information</string> + </property> + </widget> + </item> + </layout> + </item> + <item> + <widget class="QTreeWidget" name="infoWidget"> + <property name="sizePolicy"> + <sizepolicy hsizetype="Expanding" vsizetype="Expanding"> + <horstretch>0</horstretch> + <verstretch>1</verstretch> + </sizepolicy> + </property> + <property name="alternatingRowColors"> + <bool>true</bool> + </property> + <property name="rootIsDecorated"> + <bool>false</bool> + </property> + <property name="itemsExpandable"> + <bool>false</bool> + </property> + <property name="allColumnsShowFocus"> + <bool>true</bool> + </property> + <property name="wordWrap"> + <bool>true</bool> + </property> + <property name="columnCount"> + <number>2</number> + </property> + <attribute name="headerVisible"> + <bool>false</bool> + </attribute> + <attribute name="headerStretchLastSection"> + <bool>false</bool> + </attribute> + <column> + <property name="text"> + <string notr="true">1</string> + </property> + </column> + <column> + <property name="text"> + <string notr="true">2</string> + </property> + </column> + </widget> + </item> + </layout> + </widget> + </widget> + </item> + <item> + <layout class="QHBoxLayout" name="horizontalLayout_2"> + <item> + <spacer name="horizontalSpacer"> + <property name="orientation"> + <enum>Qt::Horizontal</enum> + </property> + <property name="sizeHint" stdset="0"> + <size> + <width>40</width> + <height>20</height> + </size> + </property> + </spacer> + </item> + <item> + <widget class="QToolButton" name="refreshButton"> + <property name="toolTip"> + <string>Press to refresh the lists</string> + </property> + </widget> + </item> + <item> + <widget class="QToolButton" name="upgradeButton"> + <property name="toolTip"> + <string>Press to upgrade the selected packages</string> + </property> + </widget> + </item> + <item> + <widget class="QToolButton" name="upgradeAllButton"> + <property name="toolTip"> + <string>Press to upgrade all listed packages</string> + </property> + </widget> + </item> + <item> + <widget class="QToolButton" name="uninstallButton"> + <property name="toolTip"> + <string>Press to uninstall the selected package</string> + </property> + </widget> + </item> + <item> + <widget class="QToolButton" name="showPackageDetailsButton"> + <property name="toolTip"> + <string>Press to show details for the selected entry</string> + </property> + </widget> + </item> + <item> + <spacer name="horizontalSpacer_2"> + <property name="orientation"> + <enum>Qt::Horizontal</enum> + </property> + <property name="sizeHint" stdset="0"> + <size> + <width>40</width> + <height>20</height> + </size> + </property> + </spacer> + </item> + <item> + <widget class="QToolButton" name="searchToggleButton"> + <property name="toolTip"> + <string>Toggle to show or hide the search window</string> + </property> + <property name="checkable"> + <bool>true</bool> + </property> + </widget> + </item> + </layout> + </item> + </layout> + </widget> + </item> + <item> + <widget class="QWidget" name="searchWidget" native="true"> + <layout class="QVBoxLayout" name="verticalLayout_2"> + <property name="leftMargin"> + <number>0</number> + </property> + <property name="topMargin"> + <number>0</number> + </property> + <property name="rightMargin"> + <number>0</number> + </property> + <property name="bottomMargin"> + <number>0</number> + </property> + <item> + <layout class="QGridLayout" name="gridLayout"> + <item row="0" column="0"> + <widget class="QLabel" name="label"> + <property name="text"> + <string>Name:</string> + </property> + </widget> + </item> + <item row="0" column="1"> + <widget class="QLineEdit" name="searchEditName"> + <property name="toolTip"> + <string>Enter the search term for the package name</string> + </property> + <property name="placeholderText"> + <string>Enter search term</string> + </property> + </widget> + </item> + <item row="0" column="2" rowspan="2"> + <widget class="QComboBox" name="searchTermCombineComboBox"> + <property name="toolTip"> + <string>Select the search term combination operation</string> + </property> + <item> + <property name="text"> + <string notr="true">and</string> + </property> + </item> + <item> + <property name="text"> + <string notr="true">or</string> + </property> + </item> + </widget> + </item> + <item row="1" column="0"> + <widget class="QLabel" name="label_2"> + <property name="text"> + <string>Summary:</string> + </property> + </widget> + </item> + <item row="1" column="1"> + <widget class="QLineEdit" name="searchEditSummary"> + <property name="toolTip"> + <string>Enter the search term for the package summary</string> + </property> + <property name="placeholderText"> + <string>Enter search term</string> + </property> + </widget> + </item> + <item row="0" column="3" rowspan="2"> + <widget class="QToolButton" name="searchButton"> + <property name="enabled"> + <bool>false</bool> + </property> + <property name="toolTip"> + <string>Press to start the search</string> + </property> + </widget> + </item> + </layout> + </item> + <item> + <widget class="QWidget" name="searchOptionsWidget" native="true"> + <layout class="QVBoxLayout" name="verticalLayout"> + <property name="leftMargin"> + <number>0</number> + </property> + <property name="topMargin"> + <number>0</number> + </property> + <property name="rightMargin"> + <number>0</number> + </property> + <property name="bottomMargin"> + <number>0</number> + </property> + </layout> + </widget> + </item> + <item> + <widget class="QTreeWidget" name="searchResultList"> + <property name="alternatingRowColors"> + <bool>true</bool> + </property> + <property name="selectionMode"> + <enum>QAbstractItemView::ExtendedSelection</enum> + </property> + <property name="sortingEnabled"> + <bool>true</bool> + </property> + <property name="allColumnsShowFocus"> + <bool>true</bool> + </property> + <property name="wordWrap"> + <bool>true</bool> + </property> + <column> + <property name="text"> + <string>Package</string> + </property> + </column> + <column> + <property name="text"> + <string>Score</string> + </property> + </column> + <column> + <property name="text"> + <string>Description</string> + </property> + </column> + </widget> + </item> + <item> + <widget class="QLabel" name="searchInfoLabel"/> + </item> + <item> + <layout class="QHBoxLayout" name="horizontalLayout_3"> + <item> + <spacer name="horizontalSpacer_3"> + <property name="orientation"> + <enum>Qt::Horizontal</enum> + </property> + <property name="sizeHint" stdset="0"> + <size> + <width>40</width> + <height>20</height> + </size> + </property> + </spacer> + </item> + <item> + <widget class="QToolButton" name="installButton"> + <property name="toolTip"> + <string>Press to install the selected package</string> + </property> + </widget> + </item> + <item> + <widget class="QToolButton" name="installUserSiteButton"> + <property name="toolTip"> + <string>Press to install the selected package to the user site</string> + </property> + </widget> + </item> + <item> + <widget class="QToolButton" name="showDetailsButton"> + <property name="toolTip"> + <string>Press to show details for the selected entry</string> + </property> + </widget> + </item> + <item> + <spacer name="horizontalSpacer_4"> + <property name="orientation"> + <enum>Qt::Horizontal</enum> + </property> + <property name="sizeHint" stdset="0"> + <size> + <width>40</width> + <height>20</height> + </size> + </property> + </spacer> + </item> + </layout> + </item> + </layout> + </widget> + </item> + </layout> + </widget> + <customwidgets> + <customwidget> + <class>E5ToolButton</class> + <extends>QToolButton</extends> + <header>E5Gui/E5ToolButton.h</header> + </customwidget> + </customwidgets> + <tabstops> + <tabstop>environmentsComboBox</tabstop> + <tabstop>pipMenuButton</tabstop> + <tabstop>localCheckBox</tabstop> + <tabstop>notRequiredCheckBox</tabstop> + <tabstop>userCheckBox</tabstop> + <tabstop>packagesList</tabstop> + <tabstop>verboseCheckBox</tabstop> + <tabstop>installedFilesCheckBox</tabstop> + <tabstop>infoWidget</tabstop> + <tabstop>refreshButton</tabstop> + <tabstop>upgradeButton</tabstop> + <tabstop>upgradeAllButton</tabstop> + <tabstop>uninstallButton</tabstop> + <tabstop>showPackageDetailsButton</tabstop> + <tabstop>searchToggleButton</tabstop> + <tabstop>searchEditName</tabstop> + <tabstop>searchTermCombineComboBox</tabstop> + <tabstop>searchEditSummary</tabstop> + <tabstop>searchButton</tabstop> + <tabstop>searchResultList</tabstop> + <tabstop>installButton</tabstop> + <tabstop>installUserSiteButton</tabstop> + <tabstop>showDetailsButton</tabstop> + </tabstops> + <resources/> + <connections/> +</ui>
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/PipInterface/__init__.py Sat Feb 23 15:46:15 2019 +0100 @@ -0,0 +1,8 @@ +# -*- coding: utf-8 -*- + +# Copyright (c) 2015 - 2019 Detlev Offenbach <detlev@die-offenbachs.de> +# + +""" +Package implementing the various pip dialogs and data. +"""
--- a/Plugins/PluginPipInterface.py Sat Feb 23 13:05:18 2019 +0100 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,235 +0,0 @@ -# -*- coding: utf-8 -*- - -# Copyright (c) 2015 - 2019 Detlev Offenbach <detlev@die-offenbachs.de> -# - -""" -Module implementing the pip interface plug-in. -""" - -from __future__ import unicode_literals - - -from PyQt5.QtCore import pyqtSignal, QObject, QCoreApplication - -from E5Gui.E5Application import e5App - -import Preferences -import UI.Info - -# Start-Of-Header -name = "pip Interface Plug-in" -author = "Detlev Offenbach <detlev@die-offenbachs.de>" -autoactivate = True -deactivateable = True -version = UI.Info.VersionOnly -className = "PipInterfacePlugin" -packageName = "__core__" -shortDescription = "Plug-in implementing a simple GUI for the pip command." -longDescription = ( - """Plug-in implementing a simple GUI for the pip command.""" -) -needsRestart = False -pyqtApi = 2 -python2Compatible = True -# End-Of-Header - -error = "" - -pipPluginObject = None - - -def exeDisplayDataList(): - """ - Module function to support the display of some executable info. - - @return list of dictionaries containing the data to query the presence of - the executable - """ - global pipPluginObject - - dataList = [] - data = { - "programEntry": True, - "header": QCoreApplication.translate( - "PipInterfacePlugin", "Package Management - pip"), - "exe": "dummyExe", - "versionCommand": "--version", - "versionStartsWith": "pip", - "versionPosition": 1, - "version": "", - "versionCleanup": None, - "exeModule": ["-m", "pip"], - } - virtualenvManager = e5App().getObject("VirtualEnvManager") - for venvName in virtualenvManager.getVirtualenvNames(): - interpreter = virtualenvManager.getVirtualenvInterpreter(venvName) - data["exe"] = interpreter - dataList.append(data.copy()) - return dataList - - -def createPipPage(configDlg): - """ - Module function to create the pip configuration page. - - @param configDlg reference to the configuration dialog - @return reference to the configuration page - """ - global pipPluginObject - from UiExtensionPlugins.PipInterface.ConfigurationPage.PipPage import \ - PipPage - page = PipPage(pipPluginObject) - return page - - -def getConfigData(): - """ - Module function returning data as required by the configuration dialog. - - @return dictionary containing the relevant data - """ - return { - "pipPage": [ - QCoreApplication.translate( - "PipInterfacePlugin", "Python Package Management"), - "pypi.png", - createPipPage, None, None - ], - } - - -def prepareUninstall(): - """ - Module function to prepare for an un-installation. - """ - Preferences.Prefs.settings.remove(PipInterfacePlugin.PreferencesKey) - - -class PipInterfacePlugin(QObject): - """ - Class implementing the pip interface plug-in. - - @signal currentEnvironmentChanged(str) emitted to signal a change of the - currently selected virtual environment - """ - PreferencesKey = "PipPlugin" - - currentEnvironmentChanged = pyqtSignal(str) - - def __init__(self, ui): - """ - Constructor - - @param ui reference to the user interface object (UI.UserInterface) - """ - super(PipInterfacePlugin, self).__init__(ui) - self.__ui = ui - self.__initialize() - - self.__defaults = { - "CurrentEnvironment": "", - "PipSearchIndex": "", # used by the search command - } - - def __initialize(self): - """ - Private slot to (re)initialize the plugin. - """ - self.__object = None - - self.__mainAct = None - self.__mainMenu = None - - def activate(self): - """ - Public method to activate this plugin. - - @return tuple of None and activation status - @rtype tuple of (None, bool) - """ - global error - error = "" # clear previous error - - global pipPluginObject - pipPluginObject = self - - from UiExtensionPlugins.PipInterface.Pip import Pip - self.__object = Pip(self, self.__ui) - self.__object.initActions() - e5App().registerPluginObject("PipGui", self.__object) - - menu = self.__ui.getMenu("extras") - self.__mainMenu = self.__object.initMenu() - self.__mainAct = menu.addMenu(self.__mainMenu) - - return None, True - - def deactivate(self): - """ - Public method to deactivate this plugin. - """ - e5App().unregisterPluginObject("PipGui") - - menu = self.__ui.getMenu("extras") - menu.removeAction(self.__mainAct) - self.__mainAct = None - - self.__initialize() - - def getPreferences(self, key): - """ - Public method to retrieve the various pip related settings. - - @param key the key of the value to get - @type str - @return the requested setting - @rtype any - """ - return Preferences.Prefs.settings.value( - self.PreferencesKey + "/" + key, self.__defaults[key]) - - def setPreferences(self, key, value): - """ - Public method to store the various pip related settings. - - @param key the key of the setting to be set - @type str - @param value the value to be set - @type any - """ - Preferences.Prefs.settings.setValue( - self.PreferencesKey + "/" + key, value) - - if key == "CurrentEnvironment": - self.currentEnvironmentChanged.emit(value) - - def getMenu(self, name): - """ - Public method to get a reference to the requested menu. - - @param name name of the menu - @type str - @return reference to the menu or None, if no - menu with the given name exists - @rtype QMenu or None - """ - if self.__object is not None: - return self.__object.getMenu(name) - else: - return None - - def getMenuNames(self): - """ - Public method to get the names of all menus. - - @return menu names - @rtype list of str - """ - if self.__object is not None: - return list(self.__menus.keys()) - else: - return [] - -# -# eflag: noqa = M801
--- a/Plugins/UiExtensionPlugins/PipInterface/ConfigurationPage/PipPage.py Sat Feb 23 13:05:18 2019 +0100 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,49 +0,0 @@ -# -*- coding: utf-8 -*- - -# Copyright (c) 2015 - 2019 Detlev Offenbach <detlev@die-offenbachs.de> -# - -""" -Package implementing the pip configuration page. -""" - -from __future__ import unicode_literals - -from Preferences.ConfigurationPages.ConfigurationPageBase import \ - ConfigurationPageBase -from .Ui_PipPage import Ui_PipPage - -from .. import DefaultPyPiUrl - - -class PipPage(ConfigurationPageBase, Ui_PipPage): - """ - Class implementing the pip configuration page. - """ - def __init__(self, plugin): - """ - Constructor - - @param plugin reference to the plugin object - @type PipInterfacePlugin - """ - super(PipPage, self).__init__() - self.setupUi(self) - self.setObjectName("PipPage") - - self.__plugin = plugin - - self.indexLabel.setText(self.tr( - '<b>Note:</b> Leave empty to use the default index URL (' - '<a href="{0}">{0}</a>).') - .format(DefaultPyPiUrl)) - - # set initial values - self.indexEdit.setText(self.__plugin.getPreferences("PipSearchIndex")) - - def save(self): - """ - Public slot to save the pip configuration. - """ - self.__plugin.setPreferences( - "PipSearchIndex", self.indexEdit.text().strip())
--- a/Plugins/UiExtensionPlugins/PipInterface/ConfigurationPage/PipPage.ui Sat Feb 23 13:05:18 2019 +0100 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,80 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<ui version="4.0"> - <class>PipPage</class> - <widget class="QWidget" name="PipPage"> - <property name="geometry"> - <rect> - <x>0</x> - <y>0</y> - <width>602</width> - <height>389</height> - </rect> - </property> - <layout class="QVBoxLayout" name="verticalLayout_2"> - <item> - <widget class="QLabel" name="headerLabel"> - <property name="text"> - <string><b>Configure pip</b></string> - </property> - </widget> - </item> - <item> - <widget class="Line" name="line9_3"> - <property name="frameShape"> - <enum>QFrame::HLine</enum> - </property> - <property name="frameShadow"> - <enum>QFrame::Sunken</enum> - </property> - <property name="orientation"> - <enum>Qt::Horizontal</enum> - </property> - </widget> - </item> - <item> - <widget class="QGroupBox" name="groupBox_2"> - <property name="title"> - <string>Index URL</string> - </property> - <layout class="QVBoxLayout" name="verticalLayout"> - <item> - <widget class="QLineEdit" name="indexEdit"> - <property name="toolTip"> - <string>Enter the URL of the package index or leave empty to use the default</string> - </property> - </widget> - </item> - <item> - <widget class="QLabel" name="indexLabel"> - <property name="text"> - <string/> - </property> - <property name="openExternalLinks"> - <bool>true</bool> - </property> - </widget> - </item> - </layout> - </widget> - </item> - <item> - <spacer name="verticalSpacer"> - <property name="orientation"> - <enum>Qt::Vertical</enum> - </property> - <property name="sizeHint" stdset="0"> - <size> - <width>20</width> - <height>234</height> - </size> - </property> - </spacer> - </item> - </layout> - </widget> - <tabstops> - <tabstop>indexEdit</tabstop> - </tabstops> - <resources/> - <connections/> -</ui>
--- a/Plugins/UiExtensionPlugins/PipInterface/ConfigurationPage/__init__.py Sat Feb 23 13:05:18 2019 +0100 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,8 +0,0 @@ -# -*- coding: utf-8 -*- - -# Copyright (c) 2015 - 2019 Detlev Offenbach <detlev@die-offenbachs.de> -# - -""" -Package implementing the configuration page. -"""
--- a/Plugins/UiExtensionPlugins/PipInterface/Pip.py Sat Feb 23 13:05:18 2019 +0100 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,1144 +0,0 @@ -# -*- coding: utf-8 -*- - -# Copyright (c) 2015 - 2019 Detlev Offenbach <detlev@die-offenbachs.de> -# - -""" -Package implementing the pip GUI logic. -""" - -from __future__ import unicode_literals -try: - str = unicode # __IGNORE_EXCEPTION__ -except NameError: - pass - -import os -import sys - -from PyQt5.QtCore import pyqtSlot, QObject, QProcess -from PyQt5.QtWidgets import QMenu, QInputDialog, QDialog - -from E5Gui import E5MessageBox -from E5Gui.E5Action import E5Action -from E5Gui.E5Application import e5App - -from .PipDialog import PipDialog -from . import DefaultIndexUrlXml - -import Preferences -import Globals - -import UI.PixmapCache - - -class Pip(QObject): - """ - Class implementing the pip GUI logic. - """ - def __init__(self, plugin, parent=None): - """ - Constructor - - @param plugin reference to the plugin object - @type PipInterfacePlugin - @param parent parent - @type QObject - """ - super(Pip, self).__init__(parent) - - self.__plugin = plugin - self.__ui = parent - - self.__virtualenvManager = e5App().getObject("VirtualEnvManager") - self.__project = e5App().getObject("Project") - - self.__menus = {} # dictionary with references to menus - - self.__plugin.currentEnvironmentChanged.connect( - self.__handleTearOffMenu) - - def initActions(self): - """ - Public method to define the actions. - """ - self.actions = [] - - self.selectEnvironmentAct = E5Action( - self.tr('Virtual Environment for pip'), - self.tr('&Virtual Environment for pip'), - 0, 0, - self, 'pip_select_environment') - self.selectEnvironmentAct.setStatusTip(self.tr( - 'Selects the virtual environment to be used for pip')) - self.selectEnvironmentAct.setWhatsThis(self.tr( - """<b>Virtual Environment for pip</b>""" - """<p>This selects the virtual environment to be used for pip.""" - """</p>""" - )) - self.selectEnvironmentAct.triggered.connect(self.__selectPipVirtualenv) - self.actions.append(self.selectEnvironmentAct) - - ############################################## - ## Actions for listing packages - ############################################## - - self.listPackagesAct = E5Action( - self.tr('List Installed Packages'), - self.tr('&List Installed Packages...'), - 0, 0, - self, 'pip_list_packages') - self.listPackagesAct.setStatusTip(self.tr( - 'List all installed packages with versions')) - self.listPackagesAct.setWhatsThis(self.tr( - """<b>List Installed Packages</b>""" - """<p>This lists all the installed packages together""" - """ with their versions.</p>""" - )) - self.listPackagesAct.triggered.connect(self.__listPackages) - self.actions.append(self.listPackagesAct) - - self.listUptodatePackagesAct = E5Action( - self.tr('List Up-to-date Packages'), - self.tr('List Up-to-&date Packages...'), - 0, 0, - self, 'pip_list_uptodate_packages') - self.listUptodatePackagesAct.setStatusTip(self.tr( - 'List all installed, up-to-date packages with versions')) - self.listUptodatePackagesAct.setWhatsThis(self.tr( - """<b>List Up-to-date Packages</b>""" - """<p>This lists all the installed, up-to-date packages together""" - """ with their versions.</p>""" - )) - self.listUptodatePackagesAct.triggered.connect( - self.__listUptodatePackages) - self.actions.append(self.listUptodatePackagesAct) - - self.listOutdatedPackagesAct = E5Action( - self.tr('List Outdated Packages'), - self.tr('List &Outdated Packages...'), - 0, 0, - self, 'pip_list_outdated_packages') - self.listOutdatedPackagesAct.setStatusTip(self.tr( - 'List all installed, outdated packages with versions')) - self.listOutdatedPackagesAct.setWhatsThis(self.tr( - """<b>List Up-to-date Packages</b>""" - """<p>This lists all the installed, outdated packages together""" - """ with their current and latest versions.</p>""" - )) - self.listOutdatedPackagesAct.triggered.connect( - self.__listOutdatedPackages) - self.actions.append(self.listOutdatedPackagesAct) - - ############################################## - ## Actions for installing packages - ############################################## - - self.installPackagesAct = E5Action( - self.tr('Install Packages'), - self.tr('&Install Packages'), - 0, 0, - self, 'pip_install_packages') - self.installPackagesAct.setStatusTip(self.tr( - 'Install packages according to user input')) - self.installPackagesAct.setWhatsThis(self.tr( - """<b>Install Packages</b>""" - """<p>This installs packages according to user input.</p>""" - )) - self.installPackagesAct.triggered.connect(self.__installPackages) - self.actions.append(self.installPackagesAct) - - self.installLocalPackageAct = E5Action( - self.tr('Install Local Package'), - self.tr('Install Local Package'), - 0, 0, - self, 'pip_install_local_package') - self.installLocalPackageAct.setStatusTip(self.tr( - 'Install a package from local storage')) - self.installLocalPackageAct.setWhatsThis(self.tr( - """<b>Install Local Package</b>""" - """<p>This installs a package available on local storage.</p>""" - )) - self.installLocalPackageAct.triggered.connect( - self.__installLocalPackage) - self.actions.append(self.installLocalPackageAct) - - self.installRequirementsAct = E5Action( - self.tr('Install Requirements'), - self.tr('Install Requirements'), - 0, 0, - self, 'pip_install_requirements') - self.installRequirementsAct.setStatusTip(self.tr( - 'Install packages according to a requirements file')) - self.installRequirementsAct.setWhatsThis(self.tr( - """<b>Install Requirements</b>""" - """<p>This installs packages according to a requirements""" - """ file.</p>""" - )) - self.installRequirementsAct.triggered.connect( - self.__installRequirements) - self.actions.append(self.installRequirementsAct) - - self.installPipAct = E5Action( - self.tr('Install Pip'), - self.tr('Install Pip'), - 0, 0, - self, 'pip_install_pip') - self.installPipAct.setStatusTip(self.tr( - 'Install the pip package itself')) - self.installPipAct.setWhatsThis(self.tr( - """<b>Install Pip</b>""" - """<p>This installs the pip package itself.</p>""" - )) - self.installPipAct.triggered.connect(self.__installPip) - self.actions.append(self.installPipAct) - - self.repairPipAct = E5Action( - self.tr('Repair Pip'), - self.tr('Repair Pip'), - 0, 0, - self, 'pip_repair_pip') - self.repairPipAct.setStatusTip(self.tr( - 'Repair the pip package')) - self.repairPipAct.setWhatsThis(self.tr( - """<b>Repair Pip</b>""" - """<p>This repairs the pip package by re-installing it.</p>""" - )) - self.repairPipAct.triggered.connect(self.__repairPip) - self.actions.append(self.repairPipAct) - - self.upgradePipAct = E5Action( - self.tr('Upgrade Pip'), - self.tr('Upgrade &Pip'), - 0, 0, - self, 'pip_upgrade_pip') - self.upgradePipAct.setStatusTip(self.tr( - 'Upgrade the pip package itself')) - self.upgradePipAct.setWhatsThis(self.tr( - """<b>Upgrade Pip</b>""" - """<p>This upgrades the pip package itself.</p>""" - )) - self.upgradePipAct.triggered.connect(self.upgradePip) - self.actions.append(self.upgradePipAct) - - self.upgradePackagesAct = E5Action( - self.tr('Upgrade Packages'), - self.tr('&Upgrade Packages'), - 0, 0, - self, 'pip_upgrade_packages') - self.upgradePackagesAct.setStatusTip(self.tr( - 'Upgrade packages according to user input')) - self.upgradePackagesAct.setWhatsThis(self.tr( - """<b>Upgrade Packages</b>""" - """<p>This upgrades packages according to user input.</p>""" - )) - self.upgradePackagesAct.triggered.connect(self.__upgradePackages) - self.actions.append(self.upgradePackagesAct) - - ############################################## - ## Actions for uninstalling packages - ############################################## - - self.uninstallPackagesAct = E5Action( - self.tr('Uninstall Packages'), - self.tr('Uninstall Packages'), - 0, 0, - self, 'pip_uninstall_packages') - self.uninstallPackagesAct.setStatusTip(self.tr( - 'Uninstall packages according to user input')) - self.uninstallPackagesAct.setWhatsThis(self.tr( - """<b>Uninstall Packages</b>""" - """<p>This uninstalls packages according to user input.</p>""" - )) - self.uninstallPackagesAct.triggered.connect(self.__uninstallPackages) - self.actions.append(self.uninstallPackagesAct) - - self.uninstallRequirementsAct = E5Action( - self.tr('Uninstall Requirements'), - self.tr('Uninstall Requirements'), - 0, 0, - self, 'pip_uninstall_requirements') - self.uninstallRequirementsAct.setStatusTip(self.tr( - 'Uninstall packages according to a requirements file')) - self.uninstallRequirementsAct.setWhatsThis(self.tr( - """<b>Uninstall Requirements</b>""" - """<p>This uninstalls packages according to a requirements""" - """ file.</p>""" - )) - self.uninstallRequirementsAct.triggered.connect( - self.__uninstallRequirements) - self.actions.append(self.uninstallRequirementsAct) - - ############################################## - ## Actions for generating requirements files - ############################################## - - self.generateRequirementsAct = E5Action( - self.tr('Generate Requirements'), - self.tr('&Generate Requirements...'), - 0, 0, - self, 'pip_generate_requirements') - self.generateRequirementsAct.setStatusTip(self.tr( - 'Generate the contents of a requirements file')) - self.generateRequirementsAct.setWhatsThis(self.tr( - """<b>Generate Requirements</b>""" - """<p>This generates the contents of a requirements file.</p>""" - )) - self.generateRequirementsAct.triggered.connect( - self.__generateRequirements) - self.actions.append(self.generateRequirementsAct) - - ############################################## - ## Actions for generating requirements files - ############################################## - - self.searchPyPIAct = E5Action( - self.tr('Search PyPI'), - self.tr('&Search PyPI...'), - 0, 0, - self, 'pip_search_pypi') - self.searchPyPIAct.setStatusTip(self.tr( - 'Open a dialog to search the Python Package Index')) - self.searchPyPIAct.setWhatsThis(self.tr( - """<b>Search PyPI</b>""" - """<p>This opens a dialog to search the Python Package""" - """ Index.</p>""" - )) - self.searchPyPIAct.triggered.connect(self.__searchPyPI) - self.actions.append(self.searchPyPIAct) - - ############################################## - ## Actions for editing configuration files - ############################################## - - self.editUserConfigAct = E5Action( - self.tr('Edit User Configuration'), - self.tr('Edit User Configuration...'), - 0, 0, - self, 'pip_edit_user_config') - self.editUserConfigAct.setStatusTip(self.tr( - 'Open the per user configuration file in an editor')) - self.editUserConfigAct.setWhatsThis(self.tr( - """<b>Edit User Configuration</b>""" - """<p>This opens the per user configuration file in an editor.""" - """</p>""" - )) - self.editUserConfigAct.triggered.connect(self.__editUserConfiguration) - self.actions.append(self.editUserConfigAct) - - self.editVirtualenvConfigAct = E5Action( - self.tr('Edit Current Virtualenv Configuration'), - self.tr('Edit Current Virtualenv Configuration...'), - 0, 0, - self, 'pip_edit_virtualenv_config') - self.editVirtualenvConfigAct.setStatusTip(self.tr( - 'Open the current virtualenv configuration file in an editor')) - self.editVirtualenvConfigAct.setWhatsThis(self.tr( - """<b>Edit Current Virtualenv Configuration</b>""" - """<p>This opens the current virtualenv configuration file in""" - """ an editor. </p>""" - )) - self.editVirtualenvConfigAct.triggered.connect( - self.__editVirtualenvConfiguration) - self.actions.append(self.editVirtualenvConfigAct) - - self.pipConfigAct = E5Action( - self.tr('Configure'), - self.tr('Configure...'), - 0, 0, self, 'pip_configure') - self.pipConfigAct.setStatusTip(self.tr( - 'Show the configuration dialog with the Python Package Management' - ' page selected' - )) - self.pipConfigAct.setWhatsThis(self.tr( - """<b>Configure</b>""" - """<p>Show the configuration dialog with the Python Package""" - """ Management page selected.</p>""" - )) - self.pipConfigAct.triggered.connect(self.__pipConfigure) - self.actions.append(self.pipConfigAct) - - def initMenu(self): - """ - Public slot to initialize the menu. - - @return the menu generated - @rtype QMenu - """ - self.__menus = {} # clear menus references - - menu = QMenu(self.tr('P&ython Package Management'), self.__ui) - menu.setTearOffEnabled(True) - menu.setIcon(UI.PixmapCache.getIcon("pypi.png")) - - menu.addAction(self.selectEnvironmentAct) - menu.addSeparator() - menu.addAction(self.listPackagesAct) - menu.addAction(self.listUptodatePackagesAct) - menu.addAction(self.listOutdatedPackagesAct) - menu.addSeparator() - menu.addAction(self.installPipAct) - menu.addSeparator() - menu.addAction(self.installPackagesAct) - menu.addAction(self.installLocalPackageAct) - menu.addAction(self.installRequirementsAct) - menu.addSeparator() - menu.addAction(self.upgradePipAct) - menu.addAction(self.upgradePackagesAct) - menu.addSeparator() - menu.addAction(self.uninstallPackagesAct) - menu.addAction(self.uninstallRequirementsAct) - menu.addSeparator() - menu.addAction(self.generateRequirementsAct) - menu.addSeparator() - menu.addAction(self.searchPyPIAct) - menu.addSeparator() - menu.addAction(self.repairPipAct) - menu.addSeparator() - menu.addAction(self.editUserConfigAct) - menu.addAction(self.editVirtualenvConfigAct) - menu.addSeparator() - menu.addAction(self.pipConfigAct) - - self.__menus["main"] = menu - - menu.aboutToShow.connect(self.__aboutToShowMenu) - - return menu - - def __aboutToShowMenu(self): - """ - Private slot to set the action enabled status. - """ - enable = bool(self.__plugin.getPreferences("CurrentEnvironment")) - for act in self.actions: - if act not in [self.selectEnvironmentAct, - self.installPipAct, - self.editUserConfigAct, - self.editVirtualenvConfigAct, - self.pipConfigAct]: - act.setEnabled(enable) - - def getMenu(self, name): - """ - Public method to get a reference to the requested menu. - - @param name name of the menu - @type str - @return reference to the menu or None, if no - menu with the given name exists - @rtype QMenu or None - """ - if name in self.__menus: - return self.__menus[name] - else: - return None - - def getMenuNames(self): - """ - Public method to get the names of all menus. - - @return menu names - @rtype list of str - """ - return list(self.__menus.keys()) - - def __handleTearOffMenu(self, venvName): - """ - Private slot to handle a change of the selected virtual environment. - - @param venvName logical name of the virtual environment - @type str - """ - if self.__menus["main"].isTearOffMenuVisible(): - # determine, if torn off menu needs to be refreshed - enabled = self.listPackagesAct.isEnabled() - if ((bool(venvName) and not enabled) or - (not bool(venvName) and enabled)): - self.__menus["main"].hideTearOffMenu() - - ########################################################################## - ## Methods below implement some utility functions - ########################################################################## - - def runProcess(self, args, interpreter): - """ - Public method to execute the current pip with the given arguments. - - The selected pip executable is called with the given arguments and - waited for its end. - - @param args list of command line arguments - @type list of str - @param interpreter path of the Python interpreter to be used - @type str - @return tuple containing a flag indicating success and the output - of the process - @rtype tuple of (bool, str) - """ - ioEncoding = Preferences.getSystem("IOEncoding") - - process = QProcess() - process.start(interpreter, args) - procStarted = process.waitForStarted() - if procStarted: - finished = process.waitForFinished(30000) - if finished: - if process.exitCode() == 0: - output = str(process.readAllStandardOutput(), ioEncoding, - 'replace') - return True, output - else: - return (False, - self.tr("python exited with an error ({0}).") - .format(process.exitCode())) - else: - process.terminate() - process.waitForFinished(2000) - process.kill() - process.waitForFinished(3000) - return False, self.tr("python did not finish within" - " 30 seconds.") - - return False, self.tr("python could not be started.") - - def __getUserConfig(self): - """ - Private method to get the name of the user configuration file. - - @return path of the user configuration file - @rtype str - """ - # Unix: ~/.config/pip/pip.conf - # OS X: ~/Library/Application Support/pip/pip.conf - # Windows: %APPDATA%\pip\pip.ini - # Environment: $PIP_CONFIG_FILE - - try: - return os.environ["PIP_CONFIG_FILE"] - except KeyError: - pass - - if Globals.isWindowsPlatform(): - config = os.path.join(os.environ["APPDATA"], "pip", "pip.ini") - elif Globals.isMacPlatform(): - config = os.path.expanduser( - "~/Library/Application Support/pip/pip.conf") - else: - config = os.path.expanduser("~/.config/pip/pip.conf") - - return config - - def __getVirtualenvConfig(self): - """ - Private method to get the name of the virtualenv configuration file. - - @return path of the virtualenv configuration file - @rtype str - """ - # Unix, OS X: $VIRTUAL_ENV/pip.conf - # Windows: %VIRTUAL_ENV%\pip.ini - - if Globals.isWindowsPlatform(): - pip = "pip.ini" - else: - pip = "pip.conf" - try: - venvDirectory = os.environ["VIRTUAL_ENV"] - except KeyError: - venvName = self.__plugin.getPreferences("CurrentEnvironment") - if not venvName: - self.__selectPipVirtualenv() - venvName = self.__plugin.getPreferences("CurrentEnvironment") - if self.__virtualenvManager.isGlobalEnvironment(venvName): - venvDirectory = self.__getUserConfig() - else: - venvDirectory = \ - self.__virtualenvManager.getVirtualenvDirectory(venvName) - - return os.path.join(venvDirectory, pip) - - def getDefaultEnvironmentString(self): - """ - Public method to get the string for the default environment. - - @return string for the default environment - @rtype str - """ - return self.tr("<standard>") - - def getProjectEnvironmentString(self): - """ - Public method to get the string for the project environment. - - @return string for the project environment - @rtype str - """ - if self.__project.isOpen(): - return self.tr("<project>") - else: - return "" - - def getVirtualenvInterpreter(self, venvName): - """ - Public method to get the interpreter for a virtual environment. - - @param venvName logical name for the virtual environment - @type str - @return interpreter path - @rtype str - """ - if venvName == self.getDefaultEnvironmentString(): - venvName = self.__plugin.getPreferences("CurrentEnvironment") - elif venvName == self.getProjectEnvironmentString(): - venvName = self.__project.getDebugProperty("VIRTUALENV") - if not venvName: - # fall back to standard if not defined - venvName = self.__plugin.getPreferences("CurrentEnvironment") - - interpreter = self.__virtualenvManager.getVirtualenvInterpreter( - venvName) - if not interpreter: - E5MessageBox.critical( - None, - self.tr("Interpreter for Virtual Environment"), - self.tr("""No interpreter configured for the selected""" - """ virtual environment.""")) - - return interpreter - - def getVirtualenvNames(self): - """ - Public method to get a sorted list of virtual environment names. - - @return sorted list of virtual environment names - @rtype list of str - """ - return sorted(self.__virtualenvManager.getVirtualenvNames()) - - ########################################################################## - ## Methods below implement the individual menu entries - ########################################################################## - - def __selectPipVirtualenv(self): - """ - Private method to select the virtual environment to be used. - """ - environments = self.getVirtualenvNames() - if environments: - currentEnvironment = self.__plugin.getPreferences( - "CurrentEnvironment") - try: - index = environments.index(currentEnvironment) - except ValueError: - index = 0 - environment, ok = QInputDialog.getItem( - None, - self.tr("Virtual Environment for pip"), - self.tr("Select the virtual environment to be used:"), - environments, index, False) - - if ok and environment: - self.__plugin.setPreferences("CurrentEnvironment", - environment) - else: - E5MessageBox.warning( - None, - self.tr("Virtual Environment for pip"), - self.tr("""No virtual environments have been configured yet.""" - """ Please use the Virtualenv Manager to do that.""")) - - def __listPackages(self): - """ - Private slot to list all installed packages. - """ - from .PipListDialog import PipListDialog - self.__listDialog = PipListDialog( - self, "list", self.__plugin.getPreferences("PipSearchIndex"), - self.tr("Installed Packages")) - self.__listDialog.show() - self.__listDialog.start() - - def __listUptodatePackages(self): - """ - Private slot to list all installed, up-to-date packages. - """ - from .PipListDialog import PipListDialog - self.__listUptodateDialog = PipListDialog( - self, "uptodate", self.__plugin.getPreferences("PipSearchIndex"), - self.tr("Up-to-date Packages")) - self.__listUptodateDialog.show() - self.__listUptodateDialog.start() - - def __listOutdatedPackages(self): - """ - Private slot to list all installed, up-to-date packages. - """ - from .PipListDialog import PipListDialog - self.__listOutdatedDialog = PipListDialog( - self, "outdated", self.__plugin.getPreferences("PipSearchIndex"), - self.tr("Outdated Packages")) - self.__listOutdatedDialog.show() - self.__listOutdatedDialog.start() - - def __editUserConfiguration(self): - """ - Private slot to edit the user configuration. - """ - self.__editConfiguration() - - def __editVirtualenvConfiguration(self): - """ - Private slot to edit the current virtualenv configuration. - """ - self.__editConfiguration(virtualenv=True) - - def __editConfiguration(self, virtualenv=False): - """ - Private method to edit a configuration. - - @param virtualenv flag indicating to edit the current virtualenv - configuration file - @type bool - """ - from QScintilla.MiniEditor import MiniEditor - if virtualenv: - cfgFile = self.__getVirtualenvConfig() - else: - cfgFile = self.__getUserConfig() - cfgDir = os.path.dirname(cfgFile) - if not cfgDir: - E5MessageBox.critical( - None, - self.tr("Edit Configuration"), - self.tr("""No valid configuration path determined.""" - """ Is a virtual environment selected? Aborting""")) - return - - try: - if not os.path.isdir(cfgDir): - os.makedirs(cfgDir) - except OSError: - E5MessageBox.critical( - None, - self.tr("Edit Configuration"), - self.tr("""No valid configuration path determined.""" - """ Is a virtual environment selected? Aborting""")) - return - - if not os.path.exists(cfgFile): - try: - f = open(cfgFile, "w") - f.write("[global]\n") - f.close() - except (IOError, OSError): - # ignore these - pass - - # check, if the destination is writeable - if not os.access(cfgFile, os.W_OK): - E5MessageBox.critical( - None, - self.tr("Edit Configuration"), - self.tr("""No valid configuartion path determined.""" - """ Is a virtual environment selected? Aborting""")) - return - - self.__editor = MiniEditor(cfgFile, "Properties") - self.__editor.show() - - def __installPip(self, userSite=False): - """ - Private slot to install pip. - - @param userSite flag indicating an install to the user install - directory - @type bool - """ - from .PipSelectionDialog import PipSelectionDialog - dlg = PipSelectionDialog(self) - if dlg.exec_() != QDialog.Accepted: - return - - venvName, userSite = dlg.getData() - interpreter = self.getVirtualenvInterpreter(venvName) - if not interpreter: - return - - dia = PipDialog(self.tr('Install PIP')) - if userSite: - commands = [(interpreter, ["-m", "ensurepip", "--user"])] - else: - commands = [(interpreter, ["-m", "ensurepip"])] - if self.__plugin.getPreferences("PipSearchIndex"): - indexUrl = \ - self.__plugin.getPreferences("PipSearchIndex") + "/simple" - args = ["-m", "pip", "install", "--index-url", indexUrl, - "--upgrade"] - else: - args = ["-m", "pip", "install", "--upgrade"] - if userSite: - args.append("--user") - args.append("pip") - commands.append((interpreter, args[:])) - - res = dia.startProcesses(commands) - if res: - dia.exec_() - - @pyqtSlot() - def upgradePip(self, venvName="", userSite=False): - """ - Public method to upgrade pip itself. - - @param venvName name of the virtual environment to be used - @type str - @param userSite flag indicating an install to the user install - directory - @type bool - @return flag indicating a successful execution - @rtype bool - """ - # Upgrading pip needs to be treated specially because - # it must be done using the python executable - - if not venvName: - from .PipSelectionDialog import PipSelectionDialog - dlg = PipSelectionDialog(self) - if dlg.exec_() != QDialog.Accepted: - return - - venvName, userSite = dlg.getData() - - interpreter = self.getVirtualenvInterpreter(venvName) - if not interpreter: - return - - if self.__plugin.getPreferences("PipSearchIndex"): - indexUrl = \ - self.__plugin.getPreferences("PipSearchIndex") + "/simple" - args = ["-m", "pip", "install", "--index-url", indexUrl, - "--upgrade"] - else: - args = ["-m", "pip", "install", "--upgrade"] - if userSite: - args.append("--user") - args.append("pip") - - dia = PipDialog(self.tr('Upgrade PIP')) - res = dia.startProcess(interpreter, args) - if res: - dia.exec_() - return res - - @pyqtSlot() - def __repairPip(self): - """ - Private method to repair the pip installation. - - @return flag indicating a successful execution - @rtype bool - """ - from .PipSelectionDialog import PipSelectionDialog - dlg = PipSelectionDialog(self) - if dlg.exec_() != QDialog.Accepted: - return False - - venvName, userSite = dlg.getData() - interpreter = self.getVirtualenvInterpreter(venvName) - if not interpreter: - return - - # python -m pip install --ignore-installed pip - if self.__plugin.getPreferences("PipSearchIndex"): - indexUrl = \ - self.__plugin.getPreferences("PipSearchIndex") + "/simple" - args = ["-m", "pip", "install", "--index-url", indexUrl, - "--ignore-installed"] - else: - args = ["-m", "pip", "install", "--ignore-installed"] - if userSite: - args.append("--user") - args.append("pip") - - dia = PipDialog(self.tr('Repair PIP')) - res = dia.startProcess(interpreter, args) - if res: - dia.exec_() - - def __checkUpgradePyQt(self, packages): - """ - Private method to check, if an upgrade of PyQt packages is attempted. - - @param packages list of packages to upgrade - @type list of str - @return flag indicating to abort the upgrade attempt - @rtype bool - """ - pyqtPackages = [p for p in packages - if p.lower() in ["pyqt5", "qscintilla", "sip"]] - - if bool(pyqtPackages): - abort = not E5MessageBox.yesNo( - None, - self.tr("Upgrade Packages"), - self.tr( - """You are trying to upgrade PyQt packages. This will""" - """ not work for the current instance of Python ({0}).""" - """ Do you want to continue?""").format(sys.executable), - icon=E5MessageBox.Critical) - else: - abort = False - - return abort - - def upgradePackages(self, packages, venvName="", userSite=False): - """ - Public method to upgrade the given list of packages. - - @param packages list of packages to upgrade - @type list of str - @param venvName name of the virtual environment to be used - @type str - @param userSite flag indicating an install to the user install - directory - @type bool - @return flag indicating a successful execution - @rtype bool - """ - if self.__checkUpgradePyQt(packages): - return False - - if not venvName: - venvName = self.__plugin.getPreferences("CurrentEnvironment") - interpreter = self.getVirtualenvInterpreter(venvName) - if not interpreter: - return - - if self.__plugin.getPreferences("PipSearchIndex"): - indexUrl = \ - self.__plugin.getPreferences("PipSearchIndex") + "/simple" - args = ["-m", "pip", "install", "--index-url", indexUrl, - "--upgrade"] - else: - args = ["-m", "pip", "install", "--upgrade"] - if userSite: - args.append("--user") - args += packages - dia = PipDialog(self.tr('Upgrade Packages')) - res = dia.startProcess(interpreter, args) - if res: - dia.exec_() - return res - - def __upgradePackages(self): - """ - Private slot to upgrade packages to be given by the user. - """ - from .PipPackagesInputDialog import PipPackagesInputDialog - dlg = PipPackagesInputDialog(self, self.tr("Upgrade Packages")) - if dlg.exec_() == QDialog.Accepted: - venvName, packages, user = dlg.getData() - if packages: - self.upgradePackages(packages, venvName=venvName, - userSite=user) - - def installPackages(self, packages, venvName="", userSite=False): - """ - Public method to install the given list of packages. - - @param packages list of packages to install - @type list of str - @param venvName name of the virtual environment to be used - @type str - @param userSite flag indicating an install to the user install - directory - @type bool - """ - if not venvName: - venvName = self.__plugin.getPreferences("CurrentEnvironment") - interpreter = self.getVirtualenvInterpreter(venvName) - if not interpreter: - return - - if self.__plugin.getPreferences("PipSearchIndex"): - indexUrl = \ - self.__plugin.getPreferences("PipSearchIndex") + "/simple" - args = ["-m", "pip", "install", "--index-url", indexUrl] - else: - args = ["-m", "pip", "install"] - if userSite: - args.append("--user") - args += packages - dia = PipDialog(self.tr('Install Packages')) - res = dia.startProcess(interpreter, args) - if res: - dia.exec_() - - def __installPackages(self): - """ - Private slot to install packages to be given by the user. - """ - from .PipPackagesInputDialog import PipPackagesInputDialog - dlg = PipPackagesInputDialog( - self, self.tr("Install Packages")) - if dlg.exec_() == QDialog.Accepted: - venvName, packages, user = dlg.getData() - if packages: - self.installPackages(packages, venvName=venvName, - userSite=user) - - def __installLocalPackage(self): - """ - Private slot to install a package available on local storage. - """ - from .PipFileSelectionDialog import PipFileSelectionDialog - dlg = PipFileSelectionDialog(self, "package") - if dlg.exec_() == QDialog.Accepted: - venvName, package, user = dlg.getData() - if package and os.path.exists(package): - self.installPackages([package], venvName=venvName, - userSite=user) - - def __installRequirements(self): - """ - Private slot to install packages as given in a requirements file. - """ - from .PipFileSelectionDialog import PipFileSelectionDialog - dlg = PipFileSelectionDialog(self, "requirements") - if dlg.exec_() == QDialog.Accepted: - venvName, requirements, user = dlg.getData() - if requirements and os.path.exists(requirements): - interpreter = self.getVirtualenvInterpreter(venvName) - if not interpreter: - return - if self.__plugin.getPreferences("PipSearchIndex"): - indexUrl = \ - self.__plugin.getPreferences("PipSearchIndex") + \ - "/simple" - args = ["-m", "pip", "install", "--index-url", indexUrl] - else: - args = ["-m", "pip", "install"] - if user: - args.append("--user") - args += ["--requirement", requirements] - dia = PipDialog(self.tr('Install Packages from Requirements')) - res = dia.startProcess(interpreter, args) - if res: - dia.exec_() - - def uninstallPackages(self, packages, venvName=""): - """ - Public method to uninstall the given list of packages. - - @param packages list of packages to uninstall - @type list of str - @param venvName name of the virtual environment to be used - @type str - @return flag indicating a successful execution - @rtype bool - """ - res = False - if packages: - from UI.DeleteFilesConfirmationDialog import \ - DeleteFilesConfirmationDialog - dlg = DeleteFilesConfirmationDialog( - self.parent(), - self.tr("Uninstall Packages"), - self.tr( - "Do you really want to uninstall these packages?"), - packages) - if dlg.exec_() == QDialog.Accepted: - if not venvName: - venvName = self.__plugin.getPreferences( - "CurrentEnvironment") - interpreter = self.getVirtualenvInterpreter(venvName) - if not interpreter: - return - args = ["-m", "pip", "uninstall", "--yes"] + packages - dia = PipDialog(self.tr('Uninstall Packages')) - res = dia.startProcess(interpreter, args) - if res: - dia.exec_() - return res - - def __uninstallPackages(self): - """ - Private slot to uninstall packages to be given by the user. - """ - from .PipPackagesInputDialog import PipPackagesInputDialog - dlg = PipPackagesInputDialog( - self, self.tr("Uninstall Packages"), install=False) - if dlg.exec_() == QDialog.Accepted: - venvName, packages, _user = dlg.getData() - if packages: - self.uninstallPackages(packages, venvName=venvName) - - def __uninstallRequirements(self): - """ - Private slot to uninstall packages as given in a requirements file. - """ - from .PipFileSelectionDialog import PipFileSelectionDialog - dlg = PipFileSelectionDialog(self, "requirements", - install=False) - if dlg.exec_() == QDialog.Accepted: - venvName, requirements, _user = dlg.getData() - if requirements and os.path.exists(requirements): - try: - f = open(requirements, "r") - reqs = f.read().splitlines() - f.close() - except (OSError, IOError): - return - - from UI.DeleteFilesConfirmationDialog import \ - DeleteFilesConfirmationDialog - dlg = DeleteFilesConfirmationDialog( - self.parent(), - self.tr("Uninstall Packages"), - self.tr( - "Do you really want to uninstall these packages?"), - reqs) - if dlg.exec_() == QDialog.Accepted: - if not venvName: - venvName = self.__plugin.getPreferences( - "CurrentEnvironment") - interpreter = self.getVirtualenvInterpreter(venvName) - if not interpreter: - return - args = ["-m", "pip", "uninstall", "--requirement", - requirements] - dia = PipDialog( - self.tr('Uninstall Packages from Requirements')) - res = dia.startProcess(interpreter, args) - if res: - dia.exec_() - - def __generateRequirements(self): - """ - Private slot to generate the contents for a requirements file. - """ - from .PipFreezeDialog import PipFreezeDialog - self.__freezeDialog = PipFreezeDialog(self) - self.__freezeDialog.show() - self.__freezeDialog.start() - - def __searchPyPI(self): - """ - Private slot to search the Python Package Index. - """ - from .PipSearchDialog import PipSearchDialog - - if self.__plugin.getPreferences("PipSearchIndex"): - indexUrl = self.__plugin.getPreferences("PipSearchIndex") + "/pypi" - else: - indexUrl = DefaultIndexUrlXml - - self.__searchDialog = PipSearchDialog(self, indexUrl) - self.__searchDialog.show() - - def __pipConfigure(self): - """ - Private slot to open the configuration page. - """ - e5App().getObject("UserInterface").showPreferences("pipPage")
--- a/Plugins/UiExtensionPlugins/PipInterface/PipDialog.py Sat Feb 23 13:05:18 2019 +0100 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,205 +0,0 @@ -# -*- coding: utf-8 -*- - -# Copyright (c) 2015 - 2019 Detlev Offenbach <detlev@die-offenbachs.de> -# - -""" -Module implementing a dialog showing the output of a pip command. -""" - -from __future__ import unicode_literals -try: - str = unicode # __IGNORE_EXCEPTION__ -except NameError: - pass - -from PyQt5.QtCore import pyqtSlot, Qt, QCoreApplication, QTimer, \ - QProcess -from PyQt5.QtWidgets import QDialog, QDialogButtonBox, QAbstractButton - -from E5Gui import E5MessageBox - -from .Ui_PipDialog import Ui_PipDialog - -import Preferences - - -class PipDialog(QDialog, Ui_PipDialog): - """ - Class implementing a dialog showing the output of a 'python -m pip' - command. - """ - def __init__(self, text, parent=None): - """ - Constructor - - @param text text to be shown by the label - @type str - @param parent reference to the parent widget - @type QWidget - """ - super(PipDialog, self).__init__(parent) - self.setupUi(self) - - self.proc = None - self.__processQueue = [] - self.__ioEncoding = Preferences.getSystem("IOEncoding") - - self.outputGroup.setTitle(text) - - self.show() - QCoreApplication.processEvents() - - def closeEvent(self, e): - """ - Protected slot implementing a close event handler. - - @param e close event - @type QCloseEvent - """ - self.__processQueue = [] - - if self.proc is not None and \ - self.proc.state() != QProcess.NotRunning: - self.proc.terminate() - QTimer.singleShot(2000, self.proc.kill) - self.proc.waitForFinished(3000) - - self.proc = None - - e.accept() - - def __finish(self): - """ - Private slot called when the process finished or the user pressed - the button. - """ - if self.proc is not None and \ - self.proc.state() != QProcess.NotRunning: - self.proc.terminate() - QTimer.singleShot(2000, self.proc.kill) - self.proc.waitForFinished(3000) - - self.proc = None - - self.buttonBox.button(QDialogButtonBox.Close).setEnabled(True) - self.buttonBox.button(QDialogButtonBox.Close).setFocus( - Qt.OtherFocusReason) - - if self.__processQueue: - cmd, args = self.__processQueue.pop(0) - self.__addOutput("\n\n") - self.startProcess(cmd, args) - - @pyqtSlot(QAbstractButton) - def on_buttonBox_clicked(self, button): - """ - Private slot called by a button of the button box clicked. - - @param button button that was clicked - @type QAbstractButton - """ - if button == self.buttonBox.button(QDialogButtonBox.Close): - self.close() - - def __procFinished(self, exitCode, exitStatus): - """ - Private slot connected to the finished signal. - - @param exitCode exit code of the process - @type int - @param exitStatus exit status of the process - @type QProcess.ExitStatus - """ - self.__finish() - - def startProcess(self, cmd, args, showArgs=True): - """ - Public slot used to start the process. - - @param cmd name of the pip executable to be used - @type str - @param args list of arguments for the process - @type list of str - @keyparam showArgs flag indicating to show the arguments - @type bool - @return flag indicating a successful start of the process - @rtype bool - """ - if len(self.errors.toPlainText()) == 0: - self.errorGroup.hide() - - if showArgs: - self.resultbox.append(cmd + ' ' + ' '.join(args)) - self.resultbox.append('') - - self.proc = QProcess() - self.proc.finished.connect(self.__procFinished) - self.proc.readyReadStandardOutput.connect(self.__readStdout) - self.proc.readyReadStandardError.connect(self.__readStderr) - self.proc.start(cmd, args) - procStarted = self.proc.waitForStarted(5000) - if not procStarted: - self.buttonBox.setFocus() - E5MessageBox.critical( - self, - self.tr('Process Generation Error'), - self.tr( - 'The process {0} could not be started.' - ).format(cmd)) - return procStarted - - def startProcesses(self, processParams): - """ - Public method to issue a list of commands to be executed. - - @param processParams list of tuples containing the command - and arguments - @type list of tuples of (str, list of str) - @return flag indicating a successful start of the first process - @rtype bool - """ - if len(processParams) > 1: - for cmd, args in processParams[1:]: - self.__processQueue.append((cmd, args[:])) - cmd, args = processParams[0] - return self.startProcess(cmd, args) - - def __readStdout(self): - """ - Private slot to handle the readyReadStandardOutput signal. - - It reads the output of the process, formats it and inserts it into - the contents pane. - """ - if self.proc is not None: - txt = str(self.proc.readAllStandardOutput(), - self.__ioEncoding, 'replace') - self.__addOutput(txt) - - def __addOutput(self, txt): - """ - Private method to add some text to the output pane. - - @param txt text to be added - @type str - """ - self.resultbox.insertPlainText(txt) - self.resultbox.ensureCursorVisible() - QCoreApplication.processEvents() - - def __readStderr(self): - """ - Private slot to handle the readyReadStandardError signal. - - It reads the error output of the process and inserts it into the - error pane. - """ - if self.proc is not None: - s = str(self.proc.readAllStandardError(), - self.__ioEncoding, 'replace') - self.errorGroup.show() - self.errors.insertPlainText(s) - self.errors.ensureCursorVisible() - - QCoreApplication.processEvents()
--- a/Plugins/UiExtensionPlugins/PipInterface/PipDialog.ui Sat Feb 23 13:05:18 2019 +0100 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,91 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<ui version="4.0"> - <class>PipDialog</class> - <widget class="QDialog" name="PipDialog"> - <property name="geometry"> - <rect> - <x>0</x> - <y>0</y> - <width>600</width> - <height>500</height> - </rect> - </property> - <property name="windowTitle"> - <string>pip</string> - </property> - <property name="sizeGripEnabled"> - <bool>true</bool> - </property> - <layout class="QVBoxLayout"> - <item> - <widget class="QGroupBox" name="outputGroup"> - <property name="sizePolicy"> - <sizepolicy hsizetype="Preferred" vsizetype="Expanding"> - <horstretch>0</horstretch> - <verstretch>2</verstretch> - </sizepolicy> - </property> - <property name="title"> - <string>Output</string> - </property> - <layout class="QVBoxLayout"> - <item> - <widget class="QTextEdit" name="resultbox"> - <property name="readOnly"> - <bool>true</bool> - </property> - <property name="acceptRichText"> - <bool>false</bool> - </property> - </widget> - </item> - </layout> - </widget> - </item> - <item> - <widget class="QGroupBox" name="errorGroup"> - <property name="sizePolicy"> - <sizepolicy hsizetype="Preferred" vsizetype="Expanding"> - <horstretch>0</horstretch> - <verstretch>1</verstretch> - </sizepolicy> - </property> - <property name="title"> - <string>Errors</string> - </property> - <layout class="QVBoxLayout"> - <item> - <widget class="QTextEdit" name="errors"> - <property name="readOnly"> - <bool>true</bool> - </property> - <property name="acceptRichText"> - <bool>false</bool> - </property> - </widget> - </item> - </layout> - </widget> - </item> - <item> - <widget class="QDialogButtonBox" name="buttonBox"> - <property name="orientation"> - <enum>Qt::Horizontal</enum> - </property> - <property name="standardButtons"> - <set>QDialogButtonBox::Close</set> - </property> - </widget> - </item> - </layout> - </widget> - <layoutdefault spacing="6" margin="11"/> - <pixmapfunction>qPixmapFromMimeSource</pixmapfunction> - <tabstops> - <tabstop>resultbox</tabstop> - <tabstop>errors</tabstop> - <tabstop>buttonBox</tabstop> - </tabstops> - <resources/> - <connections/> -</ui>
--- a/Plugins/UiExtensionPlugins/PipInterface/PipFileSelectionDialog.py Sat Feb 23 13:05:18 2019 +0100 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,110 +0,0 @@ -# -*- coding: utf-8 -*- - -# Copyright (c) 2015 - 2019 Detlev Offenbach <detlev@die-offenbachs.de> -# - - -""" -Module implementing a dialog to enter a file to be processed. -""" - -from __future__ import unicode_literals - -import os - -from PyQt5.QtCore import pyqtSlot -from PyQt5.QtWidgets import QDialog, QDialogButtonBox - -from E5Gui.E5PathPicker import E5PathPickerModes - -from .Ui_PipFileSelectionDialog import Ui_PipFileSelectionDialog - -import Utilities - - -class PipFileSelectionDialog(QDialog, Ui_PipFileSelectionDialog): - """ - Class implementing a dialog to enter a file to be processed. - """ - def __init__(self, pip, mode, install=True, parent=None): - """ - Constructor - - @param pip reference to the pip object - @type Pip - @param mode mode of the dialog - @type str - @param install flag indicating an install action - @type bool - @param parent reference to the parent widget - @type QWidget - """ - super(PipFileSelectionDialog, self).__init__(parent) - self.setupUi(self) - - if mode == "requirements": - self.fileLabel.setText(self.tr("Enter requirements file:")) - self.filePicker.setMode(E5PathPickerModes.OpenFileMode) - self.filePicker.setToolTip(self.tr( - "Press to select the requirements file through a file" - " selection dialog.")) - self.filePicker.setFilters( - self.tr("Text Files (*.txt);;All Files (*)")) - elif mode == "package": - self.fileLabel.setText(self.tr("Enter package file:")) - self.filePicker.setMode(E5PathPickerModes.OpenFileMode) - self.filePicker.setToolTip(self.tr( - "Press to select the package file through a file" - " selection dialog.")) - self.filePicker.setFilters( - self.tr("Python Wheel (*.whl);;" - "Archive Files (*.tar.gz *.zip);;" - "All Files (*)")) - else: - self.fileLabel.setText(self.tr("Enter file name:")) - self.filePicker.setMode(E5PathPickerModes.OpenFileMode) - self.filePicker.setToolTip(self.tr( - "Press to select a file through a file selection dialog.")) - self.filePicker.setFilters(self.tr("All Files (*)")) - self.filePicker.setDefaultDirectory(os.path.expanduser("~")) - - self.buttonBox.button(QDialogButtonBox.Ok).setEnabled(False) - - self.venvComboBox.addItem(pip.getDefaultEnvironmentString()) - projectVenv = pip.getProjectEnvironmentString() - if projectVenv: - self.venvComboBox.addItem(projectVenv) - self.venvComboBox.addItems(pip.getVirtualenvNames()) - - self.userCheckBox.setVisible(install) - - msh = self.minimumSizeHint() - self.resize(max(self.width(), msh.width()), msh.height()) - - @pyqtSlot(str) - def on_filePicker_textChanged(self, txt): - """ - Private slot to handle entering the name of a file. - - @param txt name of the file - @type str - """ - self.buttonBox.button(QDialogButtonBox.Ok).setEnabled( - bool(txt) and - os.path.exists(Utilities.toNativeSeparators(txt)) - ) - - def getData(self): - """ - Public method to get the entered data. - - @return tuple with the environment name, the name of the - selected file and a flag indicating to install to the - user install directory - @rtype tuple of (str, str, bool) - """ - return ( - self.venvComboBox.currentText(), - self.filePicker.text(), - self.userCheckBox.isChecked() - )
--- a/Plugins/UiExtensionPlugins/PipInterface/PipFileSelectionDialog.ui Sat Feb 23 13:05:18 2019 +0100 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,113 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<ui version="4.0"> - <class>PipFileSelectionDialog</class> - <widget class="QDialog" name="PipFileSelectionDialog"> - <property name="geometry"> - <rect> - <x>0</x> - <y>0</y> - <width>600</width> - <height>170</height> - </rect> - </property> - <property name="windowTitle"> - <string>Select File</string> - </property> - <property name="sizeGripEnabled"> - <bool>true</bool> - </property> - <layout class="QVBoxLayout" name="verticalLayout"> - <item> - <widget class="QLabel" name="label"> - <property name="text"> - <string>Virtual Environment:</string> - </property> - </widget> - </item> - <item> - <widget class="QComboBox" name="venvComboBox"> - <property name="toolTip"> - <string>Select the virtual environment to be used</string> - </property> - </widget> - </item> - <item> - <widget class="QLabel" name="fileLabel"> - <property name="text"> - <string>File Name:</string> - </property> - </widget> - </item> - <item> - <widget class="E5PathPicker" name="filePicker" native="true"> - <property name="focusPolicy"> - <enum>Qt::StrongFocus</enum> - </property> - </widget> - </item> - <item> - <widget class="QCheckBox" name="userCheckBox"> - <property name="toolTip"> - <string>Select to install to the Python user install directory</string> - </property> - <property name="text"> - <string>Install into User Directory</string> - </property> - </widget> - </item> - <item> - <widget class="QDialogButtonBox" name="buttonBox"> - <property name="orientation"> - <enum>Qt::Horizontal</enum> - </property> - <property name="standardButtons"> - <set>QDialogButtonBox::Cancel|QDialogButtonBox::Ok</set> - </property> - </widget> - </item> - </layout> - </widget> - <customwidgets> - <customwidget> - <class>E5PathPicker</class> - <extends>QWidget</extends> - <header>E5Gui/E5PathPicker.h</header> - <container>1</container> - </customwidget> - </customwidgets> - <resources/> - <connections> - <connection> - <sender>buttonBox</sender> - <signal>accepted()</signal> - <receiver>PipFileSelectionDialog</receiver> - <slot>accept()</slot> - <hints> - <hint type="sourcelabel"> - <x>248</x> - <y>254</y> - </hint> - <hint type="destinationlabel"> - <x>157</x> - <y>274</y> - </hint> - </hints> - </connection> - <connection> - <sender>buttonBox</sender> - <signal>rejected()</signal> - <receiver>PipFileSelectionDialog</receiver> - <slot>reject()</slot> - <hints> - <hint type="sourcelabel"> - <x>316</x> - <y>260</y> - </hint> - <hint type="destinationlabel"> - <x>286</x> - <y>274</y> - </hint> - </hints> - </connection> - </connections> -</ui>
--- a/Plugins/UiExtensionPlugins/PipInterface/PipFreezeDialog.py Sat Feb 23 13:05:18 2019 +0100 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,300 +0,0 @@ -# -*- coding: utf-8 -*- - -# Copyright (c) 2015 - 2019 Detlev Offenbach <detlev@die-offenbachs.de> -# - -""" -Module implementing a dialog to generate a requirements file. -""" - -from __future__ import unicode_literals -try: - str = unicode # __IGNORE_EXCEPTION__ -except NameError: - pass - -import os - -from PyQt5.QtCore import pyqtSlot, Qt -from PyQt5.QtWidgets import QDialog, QDialogButtonBox, QAbstractButton, \ - QApplication - -from E5Gui import E5MessageBox, E5FileDialog -from E5Gui.E5PathPicker import E5PathPickerModes -from E5Gui.E5Application import e5App - -from .Ui_PipFreezeDialog import Ui_PipFreezeDialog - -import Utilities - - -class PipFreezeDialog(QDialog, Ui_PipFreezeDialog): - """ - Class implementing a dialog to generate a requirements file. - """ - def __init__(self, pip, parent=None): - """ - Constructor - - @param pip reference to the master object - @type Pip - @param parent reference to the parent widget - @type QWidget - """ - super(PipFreezeDialog, self).__init__(parent) - self.setupUi(self) - self.setWindowFlags(Qt.Window) - - self.__refreshButton = self.buttonBox.addButton( - self.tr("&Refresh"), QDialogButtonBox.ActionRole) - - self.requirementsFilePicker.setMode(E5PathPickerModes.SaveFileMode) - self.requirementsFilePicker.setFilters( - self.tr("Text Files (*.txt);;All Files (*)")) - - self.__pip = pip - - self.venvComboBox.addItem(pip.getDefaultEnvironmentString()) - projectVenv = self.__pip.getProjectEnvironmentString() - if projectVenv: - self.venvComboBox.addItem(projectVenv) - self.venvComboBox.addItems(pip.getVirtualenvNames()) - - self.__requirementsEdited = False - self.__requirementsAvailable = False - - self.__updateButtons() - - def closeEvent(self, e): - """ - Protected slot implementing a close event handler. - - @param e close event - @type QCloseEvent - """ - QApplication.restoreOverrideCursor() - e.accept() - - @pyqtSlot(str) - def on_venvComboBox_activated(self, txt): - """ - Private slot handling the selection of a virtual environment. - - @param txt virtual environment - @type str - """ - self.__refresh() - - @pyqtSlot(bool) - def on_localCheckBox_clicked(self, checked): - """ - Private slot handling the switching of the local mode. - - @param checked state of the local check box - @type bool - """ - self.__refresh() - - @pyqtSlot(str) - def on_requirementsFilePicker_textChanged(self, txt): - """ - Private slot handling a change of the requirements file name. - - @param txt name of the requirements file - @type str - """ - self.__updateButtons() - - @pyqtSlot() - def on_requirementsEdit_textChanged(self): - """ - Private slot handling changes of the requirements text. - """ - self.__requirementsEdited = True - - @pyqtSlot(QAbstractButton) - def on_buttonBox_clicked(self, button): - """ - Private slot called by a button of the button box clicked. - - @param button button that was clicked - @type QAbstractButton - """ - if button == self.buttonBox.button(QDialogButtonBox.Close): - self.close() - elif button == self.__refreshButton: - self.__refresh() - - def __refresh(self): - """ - Private slot to refresh the displayed list. - """ - if self.__requirementsEdited: - ok = E5MessageBox.yesNo( - self, - self.tr("Generate Requirements"), - self.tr("""The requirements were changed. Do you want""" - """ to overwrite these changes?""")) - else: - ok = True - if ok: - self.start() - - def start(self): - """ - Public method to start the command. - """ - self.requirementsEdit.clear() - self.__requirementsAvailable = False - - venvName = self.venvComboBox.currentText() - interpreter = self.__pip.getVirtualenvInterpreter(venvName) - if not interpreter: - return - - args = ["-m", "pip", "freeze"] - if self.localCheckBox.isChecked(): - args.append("--local") - if self.requirementsFilePicker.text(): - fileName = Utilities.toNativeSeparators( - self.requirementsFilePicker.text()) - if os.path.exists(fileName): - args.append("--requirement") - args.append(fileName) - - QApplication.setOverrideCursor(Qt.WaitCursor) - success, output = self.__pip.runProcess(args, interpreter) - - if success: - self.requirementsEdit.setPlainText(output) - self.__requirementsAvailable = True - else: - self.requirementsEdit.setPlainText( - self.tr("No output generated by 'pip freeze'.")) - - QApplication.restoreOverrideCursor() - self.__updateButtons() - - self.__requirementsEdited = False - - def __updateButtons(self): - """ - Private method to set the state of the various buttons. - """ - self.saveButton.setEnabled( - self.__requirementsAvailable and - bool(self.requirementsFilePicker.text()) - ) - self.saveToButton.setEnabled(self.__requirementsAvailable) - self.copyButton.setEnabled(self.__requirementsAvailable) - - aw = e5App().getObject("ViewManager").activeWindow() - if aw and self.__requirementsAvailable: - self.insertButton.setEnabled(True) - self.replaceAllButton.setEnabled(True) - self.replaceSelectionButton.setEnabled( - aw.hasSelectedText()) - else: - self.insertButton.setEnabled(False) - self.replaceAllButton.setEnabled(False) - self.replaceSelectionButton.setEnabled(False) - - def __writeToFile(self, fileName): - """ - Private method to write the requirements text to a file. - - @param fileName name of the file to write to - @type str - """ - if os.path.exists(fileName): - ok = E5MessageBox.warning( - self, - self.tr("Generate Requirements"), - self.tr("""The file <b>{0}</b> already exists. Do you want""" - """ to overwrite it?""").format(fileName)) - if not ok: - return - - try: - f = open(fileName, "w") - f.write(self.requirementsEdit.toPlainText()) - f.close() - except (OSError, IOError) as err: - E5MessageBox.critical( - self, - self.tr("Generate Requirements"), - self.tr("""<p>The requirements could not be written""" - """ to <b>{0}</b>.</p><p>Reason: {1}</p>""") - .format(fileName, str(err))) - - @pyqtSlot() - def on_saveButton_clicked(self): - """ - Private slot to save the requirements text to the requirements file. - """ - fileName = self.requirementsFilePicker.text() - self.__writeToFile(fileName) - - @pyqtSlot() - def on_saveToButton_clicked(self): - """ - Private slot to write the requirements text to a new file. - """ - fileName, selectedFilter = E5FileDialog.getSaveFileNameAndFilter( - self, - self.tr("Generate Requirements"), - os.path.expanduser("~"), - self.tr("Text Files (*.txt);;All Files (*)"), - None, - E5FileDialog.Options(E5FileDialog.DontConfirmOverwrite) - ) - if fileName: - ext = os.path.splitext(fileName)[1] - if not ext: - ex = selectedFilter.split("(*")[1].split(")")[0] - if ex: - fileName += ex - self.__writeToFile(fileName) - - @pyqtSlot() - def on_copyButton_clicked(self): - """ - Private slot to copy the requirements text to the clipboard. - """ - txt = self.requirementsEdit.toPlainText() - cb = QApplication.clipboard() - cb.setText(txt) - - @pyqtSlot() - def on_insertButton_clicked(self): - """ - Private slot to insert the requirements text at the cursor position - of the current editor. - """ - aw = e5App().getObject("ViewManager").activeWindow() - if aw: - aw.beginUndoAction() - aw.insert(self.requirementsEdit.toPlainText()) - aw.endUndoAction() - - @pyqtSlot() - def on_replaceSelectionButton_clicked(self): - """ - Private slot to replace the selected text of the current editor - with the requirements text. - """ - aw = e5App().getObject("ViewManager").activeWindow() - if aw: - aw.beginUndoAction() - aw.replaceSelectedText(self.requirementsEdit.toPlainText()) - aw.endUndoAction() - - @pyqtSlot() - def on_replaceAllButton_clicked(self): - """ - Private slot to replace the text of the current editor with the - requirements text. - """ - aw = e5App().getObject("ViewManager").activeWindow() - if aw: - aw.setText(self.requirementsEdit.toPlainText())
--- a/Plugins/UiExtensionPlugins/PipInterface/PipFreezeDialog.ui Sat Feb 23 13:05:18 2019 +0100 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,232 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<ui version="4.0"> - <class>PipFreezeDialog</class> - <widget class="QDialog" name="PipFreezeDialog"> - <property name="geometry"> - <rect> - <x>0</x> - <y>0</y> - <width>600</width> - <height>550</height> - </rect> - </property> - <property name="windowTitle"> - <string>Generate Requirements</string> - </property> - <property name="toolTip"> - <string>Replace the current selection with the requirements text</string> - </property> - <property name="sizeGripEnabled"> - <bool>true</bool> - </property> - <layout class="QVBoxLayout" name="verticalLayout"> - <item> - <layout class="QHBoxLayout" name="horizontalLayout_2"> - <item> - <widget class="QLabel" name="label_2"> - <property name="text"> - <string>Virtual Environment:</string> - </property> - </widget> - </item> - <item> - <widget class="QComboBox" name="venvComboBox"> - <property name="sizePolicy"> - <sizepolicy hsizetype="Expanding" vsizetype="Fixed"> - <horstretch>0</horstretch> - <verstretch>0</verstretch> - </sizepolicy> - </property> - <property name="toolTip"> - <string>Select the virtual environment to be used</string> - </property> - </widget> - </item> - </layout> - </item> - <item> - <widget class="QCheckBox" name="localCheckBox"> - <property name="toolTip"> - <string>Select to show requirements for locally-installed packages only</string> - </property> - <property name="text"> - <string>Local packages only</string> - </property> - <property name="checked"> - <bool>true</bool> - </property> - </widget> - </item> - <item> - <layout class="QHBoxLayout" name="horizontalLayout"> - <item> - <widget class="QLabel" name="label"> - <property name="text"> - <string>Requirements File:</string> - </property> - </widget> - </item> - <item> - <widget class="E5PathPicker" name="requirementsFilePicker" native="true"> - <property name="sizePolicy"> - <sizepolicy hsizetype="Expanding" vsizetype="Preferred"> - <horstretch>0</horstretch> - <verstretch>0</verstretch> - </sizepolicy> - </property> - <property name="focusPolicy"> - <enum>Qt::StrongFocus</enum> - </property> - </widget> - </item> - </layout> - </item> - <item> - <layout class="QGridLayout" name="gridLayout"> - <item row="0" column="1"> - <widget class="QPushButton" name="saveButton"> - <property name="toolTip"> - <string>Press to save to the requirements file</string> - </property> - <property name="text"> - <string>Save</string> - </property> - </widget> - </item> - <item row="1" column="1"> - <widget class="QPushButton" name="saveToButton"> - <property name="toolTip"> - <string>Save to a new file</string> - </property> - <property name="text"> - <string>Save To</string> - </property> - </widget> - </item> - <item row="2" column="1"> - <widget class="QPushButton" name="copyButton"> - <property name="toolTip"> - <string>Copy the requirements text to the clipboard</string> - </property> - <property name="text"> - <string>Copy</string> - </property> - </widget> - </item> - <item row="3" column="1"> - <widget class="QPushButton" name="insertButton"> - <property name="toolTip"> - <string>Insert the requirements text at the cursor position</string> - </property> - <property name="text"> - <string>Insert</string> - </property> - </widget> - </item> - <item row="4" column="1"> - <widget class="Q