added plugins_index documentation and generated plugins_index file

--HG--
branch : plugins-index
This commit is contained in:
Bruno Oliveira 2013-10-11 19:47:40 -03:00
parent 7e793b9419
commit d92322a574
2 changed files with 138 additions and 36 deletions

View File

@ -1,4 +1,11 @@
'''
Script to generate the file `plugins_index.txt` with information about pytest plugins taken directly
from a live pypi server.
This will evolve to include test compatibility (pythons and pytest versions) information also.
'''
from collections import namedtuple
import datetime
from distutils.version import LooseVersion
import itertools
import os
@ -7,10 +14,16 @@ import xmlrpclib
#===================================================================================================
# iter_pypi_plugins
# iter_plugins
#===================================================================================================
def iter_pypi_plugins(client):
for plug_data in client.search({'name' : 'pytest-'}):
def iter_plugins(client, search='pytest-'):
'''
Returns an iterator of (name, version) from pypi.
:param client: xmlrpclib.ServerProxy
:param search: package names to search for
'''
for plug_data in client.search({'name' : search}):
yield plug_data['name'], plug_data['version']
@ -18,6 +31,11 @@ def iter_pypi_plugins(client):
# get_latest_versions
#===================================================================================================
def get_latest_versions(plugins):
'''
Returns an iterator of (name, version) from the given list of (name, version), but returning
only the latest version of the package. Uses distutils.LooseVersion to ensure compatibility
with PEP386.
'''
plugins = [(name, LooseVersion(version)) for (name, version) in plugins]
for name, grouped_plugins in itertools.groupby(plugins, key=lambda x: x[0]):
name, loose_version = list(grouped_plugins)[-1]
@ -28,19 +46,27 @@ def get_latest_versions(plugins):
# obtain_plugins_table
#===================================================================================================
def obtain_plugins_table(plugins, client):
'''
Returns information to populate a table of plugins, their versions, authors, etc.
The returned information is a list of columns of `ColumnData` namedtuples(text, link). Link
can be None if the text for that column should not be linked to anything.
:param plugins: list of (name, version)
:param client: xmlrpclib.ServerProxy
'''
rows = []
RowData = namedtuple('RowData', 'text link')
ColumnData = namedtuple('ColumnData', 'text link')
headers = ['Name', 'Version', 'Author', 'Summary']
# pluginname and latest version, pypi link, maintainer/author, repository link,
# one-line description, test status py27/py33
for package_name, version in plugins:
release_data = client.release_data(package_name, version)
row = (
RowData(package_name, release_data['package_url']),
RowData(version, release_data['release_url']),
RowData(release_data['author'], release_data['author_email']),
RowData(release_data['summary'], None),
ColumnData(package_name, release_data['package_url']),
ColumnData(version, release_data['release_url']),
ColumnData(release_data['author'], release_data['author_email']),
ColumnData(release_data['summary'], None),
)
assert len(row) == len(headers)
rows.append(row)
@ -51,56 +77,71 @@ def obtain_plugins_table(plugins, client):
#===================================================================================================
# generate_plugins_index_from_table
#===================================================================================================
def generate_plugins_index_from_table(headers, rows, basename):
def generate_plugins_index_from_table(filename, headers, rows):
'''
Generates a RST file with the table data given.
:param filename: output filename
:param headers: see `obtain_plugins_table`
:param rows: see `obtain_plugins_table`
'''
# creates a list of rows, each being a str containing appropriate column text and link
table_texts = []
for row in rows:
column_texts = []
for i, col_data in enumerate(row):
text = '`%s <%s>`_' % (col_data.text, col_data.link) if col_data.link else col_data.text
column_texts.append(text)
table_texts.append(column_texts)
# compute max length of each column so we can build the rst table
column_lengths = [len(x) for x in headers]
for column_texts in table_texts:
for i, row_text in enumerate(column_texts):
column_lengths[i] = max(column_lengths[i], len(row_text) + 2)
def get_row_limiter(char):
return ' '.join(char * length for length in column_lengths)
def ref(s, link):
return s + '_' if link else s
table_texts = []
for row in rows:
row_texts = []
for i, row_data in enumerate(row):
text = '`%s <%s>`_' % (row_data.text, row_data.link) if row_data.link else row_data.text
row_texts.append(text)
table_texts.append(row_texts)
column_lengths = [len(x) for x in headers]
for row_texts in table_texts:
for i, row_text in enumerate(row_texts):
column_lengths[i] = max(column_lengths[i], len(row_text) + 2)
with file(basename, 'w') as f:
with file(filename, 'w') as f:
# write welcome
print >> f, '.. _plugins_index:'
print >> f
print >> f, 'List of Third-Party Plugins'
print >> f, '==========================='
print >> f
print >> f
# table
print >> f, get_row_limiter('=')
for i, header in enumerate(headers):
print >> f, '{:^{fill}}'.format(header, fill=column_lengths[i]),
print >> f
print >> f, get_row_limiter('=')
for row_texts in table_texts:
for i, row_text in enumerate(row_texts):
for column_texts in table_texts:
for i, row_text in enumerate(column_texts):
print >> f, '{:^{fill}}'.format(row_text, fill=column_lengths[i]),
print >> f
print >> f
print >> f, get_row_limiter('=')
print >> f
print >> f, '*(Last updated: %s)*' % datetime.date.today().strftime('%Y-%m-%d')
#===================================================================================================
# generate_plugins_index
#===================================================================================================
def generate_plugins_index(client, basename):
plugins = get_latest_versions(iter_pypi_plugins(client))
def generate_plugins_index(client, filename):
'''
Generates an RST file with a table of the latest pytest plugins found in pypi.
:param client: xmlrpclib.ServerProxy
:param filename: output filename
'''
plugins = get_latest_versions(iter_plugins(client))
headers, rows = obtain_plugins_table(plugins, client)
generate_plugins_index_from_table(headers, rows, basename)
generate_plugins_index_from_table(filename, headers, rows)
#===================================================================================================
@ -108,8 +149,8 @@ def generate_plugins_index(client, basename):
#===================================================================================================
def main(argv):
client = xmlrpclib.ServerProxy('http://pypi.python.org/pypi')
basename = os.path.join(os.path.dirname(__file__), 'plugins_index.txt')
generate_plugins_index(client, basename)
filename = os.path.join(os.path.dirname(__file__), 'plugins_index.txt')
generate_plugins_index(client, filename)
print 'OK'
return 0

61
doc/en/plugins_index.txt Normal file
View File

@ -0,0 +1,61 @@
.. _plugins_index:
List of Third-Party Plugins
===========================
================================================================================== ============================================================================ ==================================================================================== =============================================================================================================================================
Name Version Author Summary
================================================================================== ============================================================================ ==================================================================================== =============================================================================================================================================
`pytest-bdd <http://pypi.python.org/pypi/pytest-bdd>`_ `0.6.1 <http://pypi.python.org/pypi/pytest-bdd/0.6.1>`_ `Oleg Pidsadnyi <oleg.podsadny@gmail.com>`_ BDD for pytest
`pytest-bdd-splinter <http://pypi.python.org/pypi/pytest-bdd-splinter>`_ `0.5.2 <http://pypi.python.org/pypi/pytest-bdd-splinter/0.5.2>`_ `Oleg Pidsadnyi <oleg.podsadny@gmail.com>`_ Splinter subplugin for Pytest BDD plugin
`pytest-bench <http://pypi.python.org/pypi/pytest-bench>`_ `0.1.0 <http://pypi.python.org/pypi/pytest-bench/0.1.0>`_ `Concordus Applications <support@concordusapps.com>`_ Benchmark utility that plugs into pytest.
`pytest-blockage <http://pypi.python.org/pypi/pytest-blockage>`_ `0.1 <http://pypi.python.org/pypi/pytest-blockage/0.1>`_ `UNKNOWN <UNKNOWN>`_ Disable network requests during a test run.
`pytest-browsermob-proxy <http://pypi.python.org/pypi/pytest-browsermob-proxy>`_ `0.1 <http://pypi.python.org/pypi/pytest-browsermob-proxy/0.1>`_ `Dave Hunt <dhunt@mozilla.com>`_ BrowserMob proxy plugin for py.test.
`pytest-bugzilla <http://pypi.python.org/pypi/pytest-bugzilla>`_ `0.2 <http://pypi.python.org/pypi/pytest-bugzilla/0.2>`_ `Noufal Ibrahim <noufal@nibrahim.net.in>`_ py.test bugzilla integration plugin
`pytest-cache <http://pypi.python.org/pypi/pytest-cache>`_ `1.0 <http://pypi.python.org/pypi/pytest-cache/1.0>`_ `Holger Krekel <holger.krekel@gmail.com>`_ pytest plugin with mechanisms for caching across test runs
`pytest-capturelog <http://pypi.python.org/pypi/pytest-capturelog>`_ `0.7 <http://pypi.python.org/pypi/pytest-capturelog/0.7>`_ `Meme Dough <memedough@gmail.com>`_ py.test plugin to capture log messages
`pytest-codecheckers <http://pypi.python.org/pypi/pytest-codecheckers>`_ `0.2 <http://pypi.python.org/pypi/pytest-codecheckers/0.2>`_ `Ronny Pfannschmidt <Ronny.Pfannschmidt@gmx.de>`_ pytest plugin to add source code sanity checks (pep8 and friends)
`pytest-contextfixture <http://pypi.python.org/pypi/pytest-contextfixture>`_ `0.1.1 <http://pypi.python.org/pypi/pytest-contextfixture/0.1.1>`_ `Andreas Pelme <andreas@pelme.se>`_ Define pytest fixtures as context managers.
`pytest-couchdbkit <http://pypi.python.org/pypi/pytest-couchdbkit>`_ `0.5.1 <http://pypi.python.org/pypi/pytest-couchdbkit/0.5.1>`_ `RonnyPfannschmidt <ronny.pfannschmidt@gmx.de>`_ py.test extension for per-test couchdb databases using couchdbkit
`pytest-cov <http://pypi.python.org/pypi/pytest-cov>`_ `1.6 <http://pypi.python.org/pypi/pytest-cov/1.6>`_ `Meme Dough <memedough@gmail.com>`_ py.test plugin for coverage reporting with support for both centralised and distributed testing, including subprocesses and multiprocessing
`pytest-dbfixtures <http://pypi.python.org/pypi/pytest-dbfixtures>`_ `0.3.8.3 <http://pypi.python.org/pypi/pytest-dbfixtures/0.3.8.3>`_ `Clearcode - The A Room <thearoom@clearcode.cc>`_ dbfixtures plugin for py.test.
`pytest-django <http://pypi.python.org/pypi/pytest-django>`_ `2.3.1 <http://pypi.python.org/pypi/pytest-django/2.3.1>`_ `Andreas Pelme <andreas@pelme.se>`_ A Django plugin for py.test.
`pytest-django-lite <http://pypi.python.org/pypi/pytest-django-lite>`_ `0.1.0 <http://pypi.python.org/pypi/pytest-django-lite/0.1.0>`_ `David Cramer <dcramer@gmail.com>`_ The bare minimum to integrate py.test with Django.
`pytest-figleaf <http://pypi.python.org/pypi/pytest-figleaf>`_ `1.0 <http://pypi.python.org/pypi/pytest-figleaf/1.0>`_ `holger krekel <py-dev@codespeak.net,holger@merlinux.eu>`_ py.test figleaf coverage plugin
`pytest-flakes <http://pypi.python.org/pypi/pytest-flakes>`_ `0.2 <http://pypi.python.org/pypi/pytest-flakes/0.2>`_ `Florian Schulze, Holger Krekel and Ronny Pfannschmidt <florian.schulze@gmx.net>`_ pytest plugin to check source code with pyflakes
`pytest-greendots <http://pypi.python.org/pypi/pytest-greendots>`_ `0.2 <http://pypi.python.org/pypi/pytest-greendots/0.2>`_ `UNKNOWN <UNKNOWN>`_ Green progress dots
`pytest-growl <http://pypi.python.org/pypi/pytest-growl>`_ `0.1 <http://pypi.python.org/pypi/pytest-growl/0.1>`_ `Anthony Long <antlong@gmail.com>`_ Growl notifications for pytest results.
`pytest-incremental <http://pypi.python.org/pypi/pytest-incremental>`_ `0.3.0 <http://pypi.python.org/pypi/pytest-incremental/0.3.0>`_ `Eduardo Naufel Schettino <schettino72@gmail.com>`_ an incremental test runner (pytest plugin)
`pytest-instafail <http://pypi.python.org/pypi/pytest-instafail>`_ `0.1.0 <http://pypi.python.org/pypi/pytest-instafail/0.1.0>`_ `Janne Vanhala <janne.vanhala@gmail.com>`_ py.test plugin to show failures instantly
`pytest-ipdb <http://pypi.python.org/pypi/pytest-ipdb>`_ `0.1-prerelease <http://pypi.python.org/pypi/pytest-ipdb/0.1-prerelease>`_ `Matthew de Verteuil <onceuponajooks@gmail.com>`_ A py.test plug-in to enable drop to ipdb debugger on test failure.
`pytest-konira <http://pypi.python.org/pypi/pytest-konira>`_ `0.2 <http://pypi.python.org/pypi/pytest-konira/0.2>`_ `Alfredo Deza <alfredodeza [at] gmail.com>`_ Run Konira DSL tests with py.test
`pytest-localserver <http://pypi.python.org/pypi/pytest-localserver>`_ `0.3 <http://pypi.python.org/pypi/pytest-localserver/0.3>`_ `Sebastian Rahlf <basti AT redtoad DOT de>`_ py.test plugin to test server connections locally.
`pytest-marker-bugzilla <http://pypi.python.org/pypi/pytest-marker-bugzilla>`_ `0.06 <http://pypi.python.org/pypi/pytest-marker-bugzilla/0.06>`_ `Eric Sammons <elsammons@gmail.com>`_ py.test bugzilla integration plugin, using markers
`pytest-markfiltration <http://pypi.python.org/pypi/pytest-markfiltration>`_ `0.8 <http://pypi.python.org/pypi/pytest-markfiltration/0.8>`_ `adam goucher <adam@element34.ca>`_ UNKNOWN
`pytest-marks <http://pypi.python.org/pypi/pytest-marks>`_ `0.4 <http://pypi.python.org/pypi/pytest-marks/0.4>`_ `adam goucher <adam@element34.ca>`_ UNKNOWN
`pytest-monkeyplus <http://pypi.python.org/pypi/pytest-monkeyplus>`_ `1.1.0 <http://pypi.python.org/pypi/pytest-monkeyplus/1.1.0>`_ `Virgil Dupras <hsoft@hardcoded.net>`_ pytest's monkeypatch subclass with extra functionalities
`pytest-mozwebqa <http://pypi.python.org/pypi/pytest-mozwebqa>`_ `1.1.1 <http://pypi.python.org/pypi/pytest-mozwebqa/1.1.1>`_ `Dave Hunt <dhunt@mozilla.com>`_ Mozilla WebQA plugin for py.test.
`pytest-oerp <http://pypi.python.org/pypi/pytest-oerp>`_ `0.2.0 <http://pypi.python.org/pypi/pytest-oerp/0.2.0>`_ `Leonardo Santagada <santagada@gmail.com>`_ pytest plugin to test OpenERP modules
`pytest-osxnotify <http://pypi.python.org/pypi/pytest-osxnotify>`_ `0.1.4 <http://pypi.python.org/pypi/pytest-osxnotify/0.1.4>`_ `Daniel Bader <mail@dbader.org>`_ OS X notifications for py.test results.
`pytest-paste-config <http://pypi.python.org/pypi/pytest-paste-config>`_ `0.1 <http://pypi.python.org/pypi/pytest-paste-config/0.1>`_ `UNKNOWN <UNKNOWN>`_ Allow setting the path to a paste config file
`pytest-pep8 <http://pypi.python.org/pypi/pytest-pep8>`_ `1.0.5 <http://pypi.python.org/pypi/pytest-pep8/1.0.5>`_ `Holger Krekel and Ronny Pfannschmidt <holger.krekel@gmail.com>`_ pytest plugin to check PEP8 requirements
`pytest-poo <http://pypi.python.org/pypi/pytest-poo>`_ `0.2 <http://pypi.python.org/pypi/pytest-poo/0.2>`_ `Andreas Pelme <andreas@pelme.se>`_ Visualize your crappy tests
`pytest-pydev <http://pypi.python.org/pypi/pytest-pydev>`_ `0.1 <http://pypi.python.org/pypi/pytest-pydev/0.1>`_ `Sebastian Rahlf <basti AT redtoad DOT de>`_ py.test plugin to connect to a remote debug server with PyDev or PyCharm.
`pytest-qt <http://pypi.python.org/pypi/pytest-qt>`_ `1.0.2 <http://pypi.python.org/pypi/pytest-qt/1.0.2>`_ `Bruno Oliveira <nicoddemus@gmail.com>`_ pytest plugin that adds fixtures for testing Qt (PyQt and PySide) applications.
`pytest-quickcheck <http://pypi.python.org/pypi/pytest-quickcheck>`_ `0.7 <http://pypi.python.org/pypi/pytest-quickcheck/0.7>`_ `Tetsuya Morimoto <tetsuya dot morimoto at gmail dot com>`_ pytest plugin to generate random data inspired by QuickCheck
`pytest-rage <http://pypi.python.org/pypi/pytest-rage>`_ `0.1 <http://pypi.python.org/pypi/pytest-rage/0.1>`_ `Leonardo Santagada <santagada@gmail.com>`_ pytest plugin to implement PEP712
`pytest-random <http://pypi.python.org/pypi/pytest-random>`_ `0.02 <http://pypi.python.org/pypi/pytest-random/0.02>`_ `Leah Klearman <lklrmn@gmail.com>`_ py.test plugin to randomize tests
`pytest-rerunfailures <http://pypi.python.org/pypi/pytest-rerunfailures>`_ `0.03 <http://pypi.python.org/pypi/pytest-rerunfailures/0.03>`_ `Leah Klearman <lklrmn@gmail.com>`_ py.test plugin to re-run tests to eliminate flakey failures
`pytest-runfailed <http://pypi.python.org/pypi/pytest-runfailed>`_ `0.3 <http://pypi.python.org/pypi/pytest-runfailed/0.3>`_ `Dimitri Merejkowsky <d.merej@gmail.com>`_ implement a --failed option for pytest
`pytest-runner <http://pypi.python.org/pypi/pytest-runner>`_ `2.0 <http://pypi.python.org/pypi/pytest-runner/2.0>`_ `Jason R. Coombs <jaraco@jaraco.com>`_ UNKNOWN
`pytest-sugar <http://pypi.python.org/pypi/pytest-sugar>`_ `0.2.2 <http://pypi.python.org/pypi/pytest-sugar/0.2.2>`_ `Teemu, Janne Vanhala <orkkiolento@gmail.com, janne.vanhala@gmail.com>`_ py.test plugin that adds instafail, ETA and neat graphics
`pytest-timeout <http://pypi.python.org/pypi/pytest-timeout>`_ `0.3 <http://pypi.python.org/pypi/pytest-timeout/0.3>`_ `Floris Bruynooghe <flub@devork.be>`_ pytest plugin to abort tests after a timeout
`pytest-twisted <http://pypi.python.org/pypi/pytest-twisted>`_ `1.4 <http://pypi.python.org/pypi/pytest-twisted/1.4>`_ `Ralf Schmitt <ralf@brainbot.com>`_ A twisted plugin for py.test.
`pytest-xdist <http://pypi.python.org/pypi/pytest-xdist>`_ `1.9 <http://pypi.python.org/pypi/pytest-xdist/1.9>`_ `holger krekel and contributors <pytest-dev@python.org,holger@merlinux.eu>`_ py.test xdist plugin for distributed testing and loop-on-failing modes
`pytest-xprocess <http://pypi.python.org/pypi/pytest-xprocess>`_ `0.8 <http://pypi.python.org/pypi/pytest-xprocess/0.8>`_ `Holger Krekel <holger@merlinux.eu>`_ pytest plugin to manage external processes across test runs
`pytest-yamlwsgi <http://pypi.python.org/pypi/pytest-yamlwsgi>`_ `0.6 <http://pypi.python.org/pypi/pytest-yamlwsgi/0.6>`_ `Ali Afshar <aafshar@gmail.com>`_ Run tests against wsgi apps defined in yaml
`pytest-zap <http://pypi.python.org/pypi/pytest-zap>`_ `0.1 <http://pypi.python.org/pypi/pytest-zap/0.1>`_ `Dave Hunt <dhunt@mozilla.com>`_ OWASP ZAP plugin for py.test.
================================================================================== ============================================================================ ==================================================================================== =============================================================================================================================================
*(Updated on 2013-10-11)*