start creating a subclass of command for producing a list of output in different formats, using prettytable as an example formatter

This commit is contained in:
Doug Hellmann 2012-04-22 16:15:37 -07:00
parent f1bb6356c5
commit 6b4add15ab
7 changed files with 139 additions and 7 deletions

View File

26
cliff/formatters/base.py Normal file
View File

@ -0,0 +1,26 @@
"""Base classes for formatters.
"""
import abc
class Formatter(object):
def __init__(self):
return
def add_argument_group(self, parser):
"""Add any options to the argument parser.
Should use our own argument group.
"""
return
class ListFormatter(Formatter):
__metaclass__ = abc.ABCMeta
@abc.abstractmethod
def emit_list(self, column_names, data, stdout):
"""Format and print the list from the iterable data source.
"""

46
cliff/formatters/table.py Normal file
View File

@ -0,0 +1,46 @@
"""Output formatters using prettytable.
"""
import prettytable
from .base import ListFormatter
class TableLister(ListFormatter):
ALIGNMENTS = {
int: 'r',
str: 'l',
unicode: 'l',
float: 'r',
}
def add_argument_group(self, parser):
group = parser.add_argument_group('Table Formatter')
group.add_argument(
'-c', '--column',
action='append',
default=[],
dest='columns',
help='specify the column(s) to include, can be repeated',
)
def emit_list(self, column_names, data, stdout, parsed_args):
x = prettytable.PrettyTable(column_names)
x.set_padding_width(1)
# Figure out the types of the columns in the
# first row and set the alignment of the
# output accordingly.
data_iter = iter(data)
first_row = next(data_iter)
for value, name in zip(first_row, column_names):
alignment = self.ALIGNMENTS.get(type(value), 'l')
x.set_field_align(name, alignment)
# Now iterate over the data and add the rows.
x.add_row(first_row)
for row in data_iter:
x.add_row(row)
formatted = x.get_string(fields=(parsed_args.columns or column_names))
stdout.write(formatted)
stdout.write('\n')
return

47
cliff/lister.py Normal file
View File

@ -0,0 +1,47 @@
"""Application base class for providing a list of data as output.
"""
import pkg_resources
from .command import Command
class Lister(Command):
"""Command base class for providing a list of data as output.
"""
def __init__(self, app, app_args):
super(Lister, self).__init__(app, app_args)
self.load_formatter_plugins()
def load_formatter_plugins(self):
self.formatters = dict(
(ep.name, ep.load()())
for ep in pkg_resources.iter_entry_points('cliff.formatter.list')
)
def get_parser(self, prog_name):
parser = super(Lister, self).get_parser(prog_name)
formatter_group = parser.add_argument_group(
title='Output Formatters',
description='List output formatter options',
)
formatter_choices = sorted(self.formatters.keys())
formatter_default = formatter_choices[0]
formatter_group.add_argument(
'-f', '--format',
dest='formatter',
action='store',
choices=formatter_choices,
default=formatter_default,
help='the output format to use, defaults to %s' % formatter_default,
)
for name, formatter in sorted(self.formatters.items()):
formatter.add_argument_group(parser)
return parser
def run(self, parsed_args):
column_names, data = self.get_data(parsed_args)
formatter = self.formatters[parsed_args.formatter]
formatter.emit_list(column_names, data, self.app.stdout, parsed_args)
return 0

16
demoapp/cliffdemo/list.py Normal file
View File

@ -0,0 +1,16 @@
import logging
import os
import stat
from cliff.lister import Lister
class Files(Lister):
"Show a list of files in the current directory."
log = logging.getLogger(__name__)
def get_data(self, parsed_args):
return (('Name', 'Size'),
((n, os.stat(n).st_size) for n in os.listdir('.'))
)

View File

@ -164,6 +164,7 @@ setup(
'simple = cliffdemo.simple:Simple',
'two_part = cliffdemo.simple:Simple',
'error = cliffdemo.simple:Error',
'files = cliffdemo.list:Files',
],
# 'virtualenvwrapper.initialize': [
# 'user_scripts = virtualenvwrapper.user_scripts:initialize',

View File

@ -158,13 +158,9 @@ setup(
),
entry_points={
# 'console_scripts': [
# 'venvw_hook = virtualenvwrapper.hook_loader:main'
# ],
# 'virtualenvwrapper.initialize': [
# 'user_scripts = virtualenvwrapper.user_scripts:initialize',
# 'project = virtualenvwrapper.project:initialize',
# ],
'cliff.formatter.list': [
'table = cliff.formatters.table:TableLister',
],
},
zip_safe=False,