diff options
author | Jussi Pakkanen <jpakkane@gmail.com> | 2021-04-26 21:04:16 +0100 |
---|---|---|
committer | GitHub <noreply@github.com> | 2021-04-26 21:04:16 +0100 |
commit | 8de47b688a2a2873ef9bb68d87b120c8156e90d9 (patch) | |
tree | ffe35275a0a8eb29cea440666fd3bd9d2a733bd4 | |
parent | cc5428488542429f0ffb6e4698bed2c02a4b1ea8 (diff) | |
parent | d3003ebb419ba867adfaa649bcfa3d45c03f0bf5 (diff) | |
download | meson-8de47b688a2a2873ef9bb68d87b120c8156e90d9.zip meson-8de47b688a2a2873ef9bb68d87b120c8156e90d9.tar.gz meson-8de47b688a2a2873ef9bb68d87b120c8156e90d9.tar.bz2 |
Merge pull request #8680 from dcbaker/submit/wrap-mconf-output
Wrap mconf output
-rw-r--r-- | mesonbuild/mconf.py | 63 |
1 files changed, 55 insertions, 8 deletions
diff --git a/mesonbuild/mconf.py b/mesonbuild/mconf.py index 7a469cb..20f31d1 100644 --- a/mesonbuild/mconf.py +++ b/mesonbuild/mconf.py @@ -12,11 +12,19 @@ # See the License for the specific language governing permissions and # limitations under the License. +import itertools +import shutil import os -from . import coredata, environment, mesonlib, build, mintro, mlog -from .ast import AstIDGenerator +import textwrap import typing as T +from . import build +from . import coredata +from . import environment +from . import mesonlib +from . import mintro +from . import mlog +from .ast import AstIDGenerator from .mesonlib import MachineChoice, OptionKey if T.TYPE_CHECKING: @@ -53,6 +61,7 @@ class Conf: self.value_col = [] self.choices_col = [] self.descr_col = [] + # XXX: is there a case where this can actually remain false? self.has_choices = False self.all_subprojects: T.Set[str] = set() self.yielding_options: T.Set[OptionKey] = set() @@ -92,16 +101,54 @@ class Conf: # are erased when Meson is executed the next time, i.e. when # Ninja is run. - def print_aligned(self): - col_widths = (max([len(i) for i in self.name_col], default=0), - max([len(i) for i in self.value_col], default=0), - max([len(i) for i in self.choices_col], default=0)) + def print_aligned(self) -> None: + """Do the actual printing. + + This prints the generated output in an aligned, pretty form. it aims + for a total width of 160 characters, but will use whatever the tty + reports it's value to be. Though this is much wider than the standard + 80 characters of terminals, and even than the newer 120, compressing + it to those lengths makes the output hard to read. + + Each column will have a specific width, and will be line wrapped. + """ + total_width = shutil.get_terminal_size(fallback=(160, 0))[0] + _col = max(total_width // 5, 20) + four_column = (_col, _col, _col, total_width - (3 * _col)) + # In this case we don't have the choices field, so we can redistribute + # the extra 40 characters to val and desc + three_column = (_col, _col * 2, total_width // 2) for line in zip(self.name_col, self.value_col, self.choices_col, self.descr_col): + if not any(line): + print('') + continue + + # This is a header, like `Subproject foo:`, + # We just want to print that and get on with it + if line[0] and not any(line[1:]): + print(line[0]) + continue + + # wrap will take a long string, and create a list of strings no + # longer than the size given. Then that list can be zipped into, to + # print each line of the output, such the that columns are printed + # to the right width, row by row. if self.has_choices: - print('{0:{width[0]}} {1:{width[1]}} {2:{width[2]}} {3}'.format(*line, width=col_widths)) + name = textwrap.wrap(line[0], four_column[0]) + val = textwrap.wrap(line[1], four_column[1]) + choice = textwrap.wrap(line[2], four_column[2]) + desc = textwrap.wrap(line[3], four_column[3]) + for l in itertools.zip_longest(name, val, choice, desc, fillvalue=''): + # We must use the length modifier here to get even rows, as + # `textwrap.wrap` will only shorten, not lengthen each item + print('{:{widths[0]}} {:{widths[1]}} {:{widths[2]}} {}'.format(*l, widths=four_column)) else: - print('{0:{width[0]}} {1:{width[1]}} {3}'.format(*line, width=col_widths)) + name = textwrap.wrap(line[0], three_column[0]) + val = textwrap.wrap(line[1], three_column[1]) + desc = textwrap.wrap(line[3], three_column[2]) + for l in itertools.zip_longest(name, val, desc, fillvalue=''): + print('{:{widths[0]}} {:{widths[1]}} {}'.format(*l, widths=three_column)) def split_options_per_subproject(self, options: 'coredata.KeyedOptionDictType') -> T.Dict[str, T.Dict[str, 'UserOption']]: result: T.Dict[str, T.Dict[str, 'UserOption']] = {} |