Add `exclude_/include_function` support
This is first step towards fixing #1046.
This commit is contained in:
parent
bc557bd656
commit
7bf025ca2b
|
@ -508,6 +508,23 @@ ascii Theme without any unicode characters at all
|
||||||
(segment is included in all modes). When there are both
|
(segment is included in all modes). When there are both
|
||||||
``exclude_modes`` overrides ``include_modes``.
|
``exclude_modes`` overrides ``include_modes``.
|
||||||
|
|
||||||
|
.. _config-themes-seg-exclude_function:
|
||||||
|
|
||||||
|
``exclude_function``, ``include_function``
|
||||||
|
Function name in a form ``{name}`` or ``{module}.{name}`` (in the first
|
||||||
|
form ``{module}`` defaults to ``powerline.selectors.{ext}``). Determines
|
||||||
|
under which condition specific segment will be included or excluded. By
|
||||||
|
default segment is always included and never excluded.
|
||||||
|
``exclude_function`` overrides ``include_function``.
|
||||||
|
|
||||||
|
.. note::
|
||||||
|
Options :ref:`exclude_/include_modes
|
||||||
|
<config-themes-seg-exclude_modes>` complement
|
||||||
|
``exclude_/include_functions``: segment will be included if it is
|
||||||
|
included by either ``include_mode`` or ``include_function`` and will
|
||||||
|
be excluded if it is excluded by either ``exclude_mode`` or
|
||||||
|
``exclude_function``.
|
||||||
|
|
||||||
.. _config-themes-seg-display:
|
.. _config-themes-seg-display:
|
||||||
|
|
||||||
``display``
|
``display``
|
||||||
|
|
|
@ -254,9 +254,15 @@ Segment dictionary contains the following keys:
|
||||||
``side``
|
``side``
|
||||||
Segment side: ``right`` or ``left``.
|
Segment side: ``right`` or ``left``.
|
||||||
|
|
||||||
``exclude_modes``, ``include_modes``
|
``display_condition```
|
||||||
:ref:`Mode display control lists <config-themes-seg-exclude_modes>`. May be
|
Contains function that takes three position parameters:
|
||||||
empty, but may not be ``None``.
|
:py:class:`powerline.PowerlineLogger` instance, :ref:`segment_info
|
||||||
|
<dev-segments-info>` dictionary and current mode and returns either ``True``
|
||||||
|
or ``False`` to indicate whether particular segment should be processed.
|
||||||
|
|
||||||
|
This key is constructed based on :ref:`exclude_/include_modes keys
|
||||||
|
<config-themes-seg-exclude_modes>` and :ref:`exclude_/include_function keys
|
||||||
|
<config-themes-seg-exclude_function>`.
|
||||||
|
|
||||||
``width``, ``align``
|
``width``, ``align``
|
||||||
:ref:`Width and align options <config-themes-seg-align>`. May be ``None``.
|
:ref:`Width and align options <config-themes-seg-align>`. May be ``None``.
|
||||||
|
|
|
@ -9,6 +9,7 @@ import logging
|
||||||
|
|
||||||
from collections import defaultdict
|
from collections import defaultdict
|
||||||
from copy import copy
|
from copy import copy
|
||||||
|
from functools import partial
|
||||||
|
|
||||||
from powerline.lint.markedjson import load
|
from powerline.lint.markedjson import load
|
||||||
from powerline import generate_config_finder, get_config_paths, load_config
|
from powerline import generate_config_finder, get_config_paths, load_config
|
||||||
|
@ -478,18 +479,18 @@ def check_matcher_func(ext, match_name, data, context, echoerr):
|
||||||
echoerr(context='Error while loading matcher functions',
|
echoerr(context='Error while loading matcher functions',
|
||||||
problem='failed to load module {0}'.format(match_module),
|
problem='failed to load module {0}'.format(match_module),
|
||||||
problem_mark=match_name.mark)
|
problem_mark=match_name.mark)
|
||||||
return True, True
|
return True, False, True
|
||||||
except AttributeError:
|
except AttributeError:
|
||||||
echoerr(context='Error while loading matcher functions',
|
echoerr(context='Error while loading matcher functions',
|
||||||
problem='failed to load matcher function {0}'.format(match_function),
|
problem='failed to load matcher function {0}'.format(match_function),
|
||||||
problem_mark=match_name.mark)
|
problem_mark=match_name.mark)
|
||||||
return True, True
|
return True, False, True
|
||||||
|
|
||||||
if not callable(func):
|
if not callable(func):
|
||||||
echoerr(context='Error while loading matcher functions',
|
echoerr(context='Error while loading matcher functions',
|
||||||
problem='loaded "function" {0} is not callable'.format(match_function),
|
problem='loaded "function" {0} is not callable'.format(match_function),
|
||||||
problem_mark=match_name.mark)
|
problem_mark=match_name.mark)
|
||||||
return True, True
|
return True, False, True
|
||||||
|
|
||||||
if hasattr(func, 'func_code') and hasattr(func.func_code, 'co_argcount'):
|
if hasattr(func, 'func_code') and hasattr(func.func_code, 'co_argcount'):
|
||||||
if func.func_code.co_argcount != 1:
|
if func.func_code.co_argcount != 1:
|
||||||
|
@ -502,7 +503,7 @@ def check_matcher_func(ext, match_name, data, context, echoerr):
|
||||||
problem_mark=match_name.mark
|
problem_mark=match_name.mark
|
||||||
)
|
)
|
||||||
|
|
||||||
return True, False
|
return True, False, False
|
||||||
|
|
||||||
|
|
||||||
def check_ext(ext, data, context, echoerr):
|
def check_ext(ext, data, context, echoerr):
|
||||||
|
@ -561,6 +562,9 @@ def check_top_theme(theme, data, context, echoerr):
|
||||||
return True, False, False
|
return True, False, False
|
||||||
|
|
||||||
|
|
||||||
|
function_name_re = '^(\w+\.)*[a-zA-Z_]\w*$'
|
||||||
|
|
||||||
|
|
||||||
divider_spec = Spec().type(unicode).len(
|
divider_spec = Spec().type(unicode).len(
|
||||||
'le', 3, (lambda value: 'Divider {0!r} is too large!'.format(value))).copy
|
'le', 3, (lambda value: 'Divider {0!r} is too large!'.format(value))).copy
|
||||||
ext_theme_spec = Spec().type(unicode).func(lambda *args: check_config('themes', *args)).copy
|
ext_theme_spec = Spec().type(unicode).func(lambda *args: check_config('themes', *args)).copy
|
||||||
|
@ -608,7 +612,8 @@ main_spec = (Spec(
|
||||||
local_themes=Spec(
|
local_themes=Spec(
|
||||||
__tabline__=ext_theme_spec(),
|
__tabline__=ext_theme_spec(),
|
||||||
).unknown_spec(
|
).unknown_spec(
|
||||||
lambda *args: check_matcher_func('vim', *args), ext_theme_spec()
|
Spec().re(function_name_re).func(partial(check_matcher_func, 'vim')),
|
||||||
|
ext_theme_spec()
|
||||||
),
|
),
|
||||||
).optional(),
|
).optional(),
|
||||||
ipython=ext_spec().update(
|
ipython=ext_spec().update(
|
||||||
|
@ -801,6 +806,7 @@ shell_colorscheme_spec = (Spec(
|
||||||
|
|
||||||
generic_keys = set((
|
generic_keys = set((
|
||||||
'exclude_modes', 'include_modes',
|
'exclude_modes', 'include_modes',
|
||||||
|
'exclude_function', 'include_function',
|
||||||
'width', 'align',
|
'width', 'align',
|
||||||
'name',
|
'name',
|
||||||
'draw_soft_divider', 'draw_hard_divider',
|
'draw_soft_divider', 'draw_hard_divider',
|
||||||
|
@ -935,7 +941,7 @@ def check_full_segment_data(segment, data, context, echoerr):
|
||||||
return check_key_compatibility(segment_copy, data, context, echoerr)
|
return check_key_compatibility(segment_copy, data, context, echoerr)
|
||||||
|
|
||||||
|
|
||||||
def import_segment(name, data, context, echoerr, module):
|
def import_function(function_type, name, data, context, echoerr, module):
|
||||||
context_has_marks(context)
|
context_has_marks(context)
|
||||||
havemarks(name, module)
|
havemarks(name, module)
|
||||||
|
|
||||||
|
@ -949,7 +955,7 @@ def import_segment(name, data, context, echoerr, module):
|
||||||
problem_mark=module.mark)
|
problem_mark=module.mark)
|
||||||
return None
|
return None
|
||||||
except AttributeError:
|
except AttributeError:
|
||||||
echoerr(context='Error while loading segment function (key {key})'.format(key=context_key(context)),
|
echoerr(context='Error while loading {0} function (key {key})'.format(function_type, key=context_key(context)),
|
||||||
problem='failed to load function {0} from module {1}'.format(name, module),
|
problem='failed to load function {0} from module {1}'.format(name, module),
|
||||||
problem_mark=name.mark)
|
problem_mark=name.mark)
|
||||||
return None
|
return None
|
||||||
|
@ -964,6 +970,10 @@ def import_segment(name, data, context, echoerr, module):
|
||||||
return func
|
return func
|
||||||
|
|
||||||
|
|
||||||
|
def import_segment(*args, **kwargs):
|
||||||
|
return import_function('segment', *args, **kwargs)
|
||||||
|
|
||||||
|
|
||||||
def check_segment_function(function_name, data, context, echoerr):
|
def check_segment_function(function_name, data, context, echoerr):
|
||||||
havemarks(function_name)
|
havemarks(function_name)
|
||||||
ext = data['ext']
|
ext = data['ext']
|
||||||
|
@ -1334,6 +1344,17 @@ def get_all_possible_functions(data, context, echoerr):
|
||||||
yield func
|
yield func
|
||||||
|
|
||||||
|
|
||||||
|
def check_exinclude_function(name, data, context, echoerr):
|
||||||
|
ext = data['ext']
|
||||||
|
module, name = name.rpartition('.')[::2]
|
||||||
|
if not module:
|
||||||
|
module = MarkedUnicode('powerline.selectors.' + ext, None)
|
||||||
|
func = import_function('selector', name, data, context, echoerr, module=module)
|
||||||
|
if not func:
|
||||||
|
return True, False, True
|
||||||
|
return True, False, False
|
||||||
|
|
||||||
|
|
||||||
args_spec = Spec(
|
args_spec = Spec(
|
||||||
pl=Spec().error('pl object must be set by powerline').optional(),
|
pl=Spec().error('pl object must be set by powerline').optional(),
|
||||||
segment_info=Spec().error('Segment info dictionary must be set by powerline').optional(),
|
segment_info=Spec().error('Segment info dictionary must be set by powerline').optional(),
|
||||||
|
@ -1341,12 +1362,15 @@ args_spec = Spec(
|
||||||
highlight_group_spec = Spec().type(unicode).copy
|
highlight_group_spec = Spec().type(unicode).copy
|
||||||
segment_module_spec = Spec().type(unicode).func(check_segment_module).optional().copy
|
segment_module_spec = Spec().type(unicode).func(check_segment_module).optional().copy
|
||||||
sub_segments_spec = Spec()
|
sub_segments_spec = Spec()
|
||||||
|
exinclude_spec = Spec().re(function_name_re).func(check_exinclude_function).copy
|
||||||
segment_spec = Spec(
|
segment_spec = Spec(
|
||||||
type=Spec().oneof(type_keys).optional(),
|
type=Spec().oneof(type_keys).optional(),
|
||||||
name=Spec().re('^[a-zA-Z_]\w*$').optional(),
|
name=Spec().re('^[a-zA-Z_]\w*$').optional(),
|
||||||
function=Spec().re('^(\w+\.)*[a-zA-Z_]\w*$').func(check_segment_function).optional(),
|
function=Spec().re(function_name_re).func(check_segment_function).optional(),
|
||||||
exclude_modes=Spec().list(vim_mode_spec()).optional(),
|
exclude_modes=Spec().list(vim_mode_spec()).optional(),
|
||||||
include_modes=Spec().list(vim_mode_spec()).optional(),
|
include_modes=Spec().list(vim_mode_spec()).optional(),
|
||||||
|
exclude_function=exinclude_spec().optional(),
|
||||||
|
include_function=exinclude_spec().optional(),
|
||||||
draw_hard_divider=Spec().type(bool).optional(),
|
draw_hard_divider=Spec().type(bool).optional(),
|
||||||
draw_soft_divider=Spec().type(bool).optional(),
|
draw_soft_divider=Spec().type(bool).optional(),
|
||||||
draw_inner_divider=Spec().type(bool).optional(),
|
draw_inner_divider=Spec().type(bool).optional(),
|
||||||
|
|
|
@ -113,13 +113,7 @@ def process_segment_lister(pl, segment_info, parsed_segments, side, mode, colors
|
||||||
subsegment['priority'] *= subsegment_update['priority_multiplier']
|
subsegment['priority'] *= subsegment_update['priority_multiplier']
|
||||||
|
|
||||||
subsegment_mode = subsegment_update.get('mode')
|
subsegment_mode = subsegment_update.get('mode')
|
||||||
if subsegment_mode and (
|
if subsegment_mode and not subsegment['display_condition'](pl, segment_info, subsegment_mode):
|
||||||
subsegment_mode in subsegment['exclude_modes']
|
|
||||||
or (
|
|
||||||
subsegment['include_modes']
|
|
||||||
and subsegment_mode not in subsegment['include_modes']
|
|
||||||
)
|
|
||||||
):
|
|
||||||
continue
|
continue
|
||||||
|
|
||||||
process_segment(
|
process_segment(
|
||||||
|
@ -218,6 +212,9 @@ def process_segment(pl, side, segment_info, parsed_segments, segment, mode, colo
|
||||||
parsed_segments.append(segment)
|
parsed_segments.append(segment)
|
||||||
|
|
||||||
|
|
||||||
|
always_true = lambda pl, segment_info, mode: True
|
||||||
|
|
||||||
|
|
||||||
def gen_segment_getter(pl, ext, common_config, theme_configs, default_module, get_module_attr, top_theme):
|
def gen_segment_getter(pl, ext, common_config, theme_configs, default_module, get_module_attr, top_theme):
|
||||||
data = {
|
data = {
|
||||||
'default_module': default_module or 'powerline.segments.' + ext,
|
'default_module': default_module or 'powerline.segments.' + ext,
|
||||||
|
@ -229,6 +226,60 @@ def gen_segment_getter(pl, ext, common_config, theme_configs, default_module, ge
|
||||||
return get_segment_key(merge, segment, theme_configs, data['segment_data'], key, function_name, name, module, default)
|
return get_segment_key(merge, segment, theme_configs, data['segment_data'], key, function_name, name, module, default)
|
||||||
data['get_key'] = get_key
|
data['get_key'] = get_key
|
||||||
|
|
||||||
|
def get_selector(function_name):
|
||||||
|
if '.' in function_name:
|
||||||
|
module, function_name = function_name.rpartition('.')[::2]
|
||||||
|
else:
|
||||||
|
module = 'powerline.selectors.' + ext
|
||||||
|
function = get_module_attr(module, function_name, prefix='segment_generator/selector_function')
|
||||||
|
if not function:
|
||||||
|
pl.error('Failed to get segment selector, ignoring it')
|
||||||
|
return function
|
||||||
|
|
||||||
|
def get_segment_selector(segment, selector_type):
|
||||||
|
try:
|
||||||
|
function_name = segment[selector_type + '_function']
|
||||||
|
except KeyError:
|
||||||
|
function = None
|
||||||
|
else:
|
||||||
|
function = get_selector(function_name)
|
||||||
|
try:
|
||||||
|
modes = segment[selector_type + '_modes']
|
||||||
|
except KeyError:
|
||||||
|
modes = None
|
||||||
|
|
||||||
|
if modes:
|
||||||
|
if function:
|
||||||
|
return lambda pl, segment_info, mode: (
|
||||||
|
mode in modes
|
||||||
|
or function(pl=pl, segment_info=segment_info, mode=mode)
|
||||||
|
)
|
||||||
|
else:
|
||||||
|
return lambda pl, segment_info, mode: mode in modes
|
||||||
|
else:
|
||||||
|
if function:
|
||||||
|
return lambda pl, segment_info, mode: (
|
||||||
|
function(pl=pl, segment_info=segment_info, mode=mode)
|
||||||
|
)
|
||||||
|
else:
|
||||||
|
return None
|
||||||
|
|
||||||
|
def gen_display_condition(segment):
|
||||||
|
include_function = get_segment_selector(segment, 'include')
|
||||||
|
exclude_function = get_segment_selector(segment, 'exclude')
|
||||||
|
if include_function:
|
||||||
|
if exclude_function:
|
||||||
|
return lambda *args: (
|
||||||
|
include_function(*args)
|
||||||
|
and not exclude_function(*args))
|
||||||
|
else:
|
||||||
|
return include_function
|
||||||
|
else:
|
||||||
|
if exclude_function:
|
||||||
|
return lambda *args: not exclude_function(*args)
|
||||||
|
else:
|
||||||
|
return always_true
|
||||||
|
|
||||||
def get(segment, side):
|
def get(segment, side):
|
||||||
segment_type = segment.get('type', 'function')
|
segment_type = segment.get('type', 'function')
|
||||||
try:
|
try:
|
||||||
|
@ -265,6 +316,8 @@ def gen_segment_getter(pl, ext, common_config, theme_configs, default_module, ge
|
||||||
get_key(True, segment, module, function_name, name, 'args', {}).items()
|
get_key(True, segment, module, function_name, name, 'args', {}).items()
|
||||||
))
|
))
|
||||||
|
|
||||||
|
display_condition = gen_display_condition(segment)
|
||||||
|
|
||||||
if segment_type == 'segment_list':
|
if segment_type == 'segment_list':
|
||||||
# Handle startup and shutdown of _contents_func?
|
# Handle startup and shutdown of _contents_func?
|
||||||
subsegments = [
|
subsegments = [
|
||||||
|
@ -292,8 +345,7 @@ def gen_segment_getter(pl, ext, common_config, theme_configs, default_module, ge
|
||||||
'draw_hard_divider': None,
|
'draw_hard_divider': None,
|
||||||
'draw_inner_divider': None,
|
'draw_inner_divider': None,
|
||||||
'side': side,
|
'side': side,
|
||||||
'exclude_modes': segment.get('exclude_modes', []),
|
'display_condition': display_condition,
|
||||||
'include_modes': segment.get('include_modes', []),
|
|
||||||
'width': None,
|
'width': None,
|
||||||
'align': None,
|
'align': None,
|
||||||
'expand': None,
|
'expand': None,
|
||||||
|
@ -342,8 +394,7 @@ def gen_segment_getter(pl, ext, common_config, theme_configs, default_module, ge
|
||||||
'draw_soft_divider': segment.get('draw_soft_divider', True),
|
'draw_soft_divider': segment.get('draw_soft_divider', True),
|
||||||
'draw_inner_divider': segment.get('draw_inner_divider', False),
|
'draw_inner_divider': segment.get('draw_inner_divider', False),
|
||||||
'side': side,
|
'side': side,
|
||||||
'exclude_modes': segment.get('exclude_modes', []),
|
'display_condition': display_condition,
|
||||||
'include_modes': segment.get('include_modes', []),
|
|
||||||
'width': segment.get('width'),
|
'width': segment.get('width'),
|
||||||
'align': segment.get('align', 'l'),
|
'align': segment.get('align', 'l'),
|
||||||
'expand': expand_func,
|
'expand': expand_func,
|
||||||
|
|
|
@ -136,9 +136,7 @@ class Theme(object):
|
||||||
parsed_segments = []
|
parsed_segments = []
|
||||||
for segment in self.segments[line][side]:
|
for segment in self.segments[line][side]:
|
||||||
# No segment-local modes at this point
|
# No segment-local modes at this point
|
||||||
if mode not in segment['exclude_modes'] and (
|
if segment['display_condition'](self.pl, segment_info, mode):
|
||||||
not segment['include_modes'] or mode in segment['include_modes']
|
|
||||||
):
|
|
||||||
process_segment(
|
process_segment(
|
||||||
self.pl,
|
self.pl,
|
||||||
side,
|
side,
|
||||||
|
|
|
@ -389,7 +389,7 @@ class TestThemeHierarchy(TestRender):
|
||||||
])
|
])
|
||||||
|
|
||||||
|
|
||||||
class TestModes(TestRender):
|
class TestDisplayCondition(TestRender):
|
||||||
@add_args
|
@add_args
|
||||||
def test_include_modes(self, p, config):
|
def test_include_modes(self, p, config):
|
||||||
config['themes/test/default']['segments'] = {
|
config['themes/test/default']['segments'] = {
|
||||||
|
@ -432,6 +432,87 @@ class TestModes(TestRender):
|
||||||
self.assertRenderEqual(p, '{56} s1{6-}>>{--}', mode='m2')
|
self.assertRenderEqual(p, '{56} s1{6-}>>{--}', mode='m2')
|
||||||
self.assertRenderEqual(p, '{56} s2{6-}>>{--}', mode='m3')
|
self.assertRenderEqual(p, '{56} s2{6-}>>{--}', mode='m3')
|
||||||
|
|
||||||
|
@add_args
|
||||||
|
def test_exinclude_function_nonexistent_module(self, p, config):
|
||||||
|
config['themes/test/default']['segments'] = {
|
||||||
|
'left': [
|
||||||
|
highlighted_string('s1', 'g1', exclude_function='xxx_nonexistent_module.foo'),
|
||||||
|
highlighted_string('s2', 'g1', exclude_function='xxx_nonexistent_module.foo', include_function='xxx_nonexistent_module.bar'),
|
||||||
|
highlighted_string('s3', 'g1', include_function='xxx_nonexistent_module.bar'),
|
||||||
|
]
|
||||||
|
}
|
||||||
|
self.assertRenderEqual(p, '{56} s1{56}>{56}s2{56}>{56}s3{6-}>>{--}')
|
||||||
|
|
||||||
|
@add_args
|
||||||
|
def test_exinclude_function(self, p, config):
|
||||||
|
config['themes/test/default']['segments'] = {
|
||||||
|
'left': [
|
||||||
|
highlighted_string('s1', 'g1', exclude_function='mod.foo'),
|
||||||
|
highlighted_string('s2', 'g1', exclude_function='mod.foo', include_function='mod.bar'),
|
||||||
|
highlighted_string('s3', 'g1', include_function='mod.bar'),
|
||||||
|
]
|
||||||
|
}
|
||||||
|
launched = set()
|
||||||
|
fool = [None]
|
||||||
|
barl = [None]
|
||||||
|
|
||||||
|
def foo(*args, **kwargs):
|
||||||
|
launched.add('foo')
|
||||||
|
self.assertEqual(set(kwargs.keys()), set(('pl', 'segment_info', 'mode')))
|
||||||
|
self.assertEqual(args, ())
|
||||||
|
return fool[0]
|
||||||
|
|
||||||
|
def bar(*args, **kwargs):
|
||||||
|
launched.add('bar')
|
||||||
|
self.assertEqual(set(kwargs.keys()), set(('pl', 'segment_info', 'mode')))
|
||||||
|
self.assertEqual(args, ())
|
||||||
|
return barl[0]
|
||||||
|
|
||||||
|
with replace_item(sys.modules, 'mod', Args(foo=foo, bar=bar)):
|
||||||
|
fool[0] = True
|
||||||
|
barl[0] = True
|
||||||
|
self.assertRenderEqual(p, '{56} s3{6-}>>{--}')
|
||||||
|
self.assertEqual(launched, set(('foo', 'bar')))
|
||||||
|
|
||||||
|
fool[0] = False
|
||||||
|
barl[0] = True
|
||||||
|
self.assertRenderEqual(p, '{56} s1{56}>{56}s2{56}>{56}s3{6-}>>{--}')
|
||||||
|
self.assertEqual(launched, set(('foo', 'bar')))
|
||||||
|
|
||||||
|
fool[0] = False
|
||||||
|
barl[0] = False
|
||||||
|
self.assertRenderEqual(p, '{56} s1{6-}>>{--}')
|
||||||
|
self.assertEqual(launched, set(('foo', 'bar')))
|
||||||
|
|
||||||
|
fool[0] = True
|
||||||
|
barl[0] = False
|
||||||
|
self.assertRenderEqual(p, '{--}')
|
||||||
|
self.assertEqual(launched, set(('foo', 'bar')))
|
||||||
|
|
||||||
|
@add_args
|
||||||
|
def test_exinclude_modes_override_functions(self, p, config):
|
||||||
|
config['themes/test/default']['segments'] = {
|
||||||
|
'left': [
|
||||||
|
highlighted_string('s1', 'g1', exclude_function='mod.foo', exclude_modes=['m2']),
|
||||||
|
highlighted_string('s2', 'g1', exclude_function='mod.foo', include_modes=['m2']),
|
||||||
|
highlighted_string('s3', 'g1', include_function='mod.foo', exclude_modes=['m2']),
|
||||||
|
highlighted_string('s4', 'g1', include_function='mod.foo', include_modes=['m2']),
|
||||||
|
]
|
||||||
|
}
|
||||||
|
fool = [None]
|
||||||
|
|
||||||
|
def foo(*args, **kwargs):
|
||||||
|
return fool[0]
|
||||||
|
|
||||||
|
with replace_item(sys.modules, 'mod', Args(foo=foo)):
|
||||||
|
fool[0] = True
|
||||||
|
self.assertRenderEqual(p, '{56} s4{6-}>>{--}', mode='m2')
|
||||||
|
self.assertRenderEqual(p, '{56} s3{56}>{56}s4{6-}>>{--}', mode='m1')
|
||||||
|
|
||||||
|
fool[0] = False
|
||||||
|
self.assertRenderEqual(p, '{56} s2{56}>{56}s4{6-}>>{--}', mode='m2')
|
||||||
|
self.assertRenderEqual(p, '{56} s1{6-}>>{--}', mode='m1')
|
||||||
|
|
||||||
|
|
||||||
class TestSegmentAttributes(TestRender):
|
class TestSegmentAttributes(TestRender):
|
||||||
@add_args
|
@add_args
|
||||||
|
|
Loading…
Reference in New Issue