##// END OF EJS Templates
templater: wrap get/min/max result so map operation can apply to element...
Yuya Nishihara -
r34535:b3073e17 default
parent child Browse files
Show More
@@ -78,13 +78,18 b' class _mappable(object):'
78 78 value. Use unwrapvalue() or unwraphybrid() to obtain the inner object.
79 79 """
80 80
81 def __init__(self, gen, value, makemap):
82 self.gen = gen
81 def __init__(self, gen, key, value, makemap):
82 if gen is not None:
83 self.gen = gen # generator or function returning generator
84 self._key = key
83 85 self._value = value # may be generator of strings
84 86 self._makemap = makemap
85 87
88 def gen(self):
89 yield pycompat.bytestr(self._value)
90
86 91 def tomap(self):
87 return self._makemap()
92 return self._makemap(self._key)
88 93
89 94 def itermaps(self):
90 95 yield self.tomap()
@@ -114,6 +119,20 b' def unwrapvalue(thing):'
114 119 return thing
115 120 return thing._value
116 121
122 def wraphybridvalue(container, key, value):
123 """Wrap an element of hybrid container to be mappable
124
125 The key is passed to the makemap function of the given container, which
126 should be an item generated by iter(container).
127 """
128 makemap = getattr(container, '_makemap', None)
129 if makemap is None:
130 return value
131 if util.safehasattr(value, '_makemap'):
132 # a nested hybrid list/dict, which has its own way of map operation
133 return value
134 return _mappable(None, key, value, makemap)
135
117 136 def showdict(name, data, mapping, plural=None, key='key', value='value',
118 137 fmt='%s=%s', separator=' '):
119 138 c = [{key: k, value: v} for k, v in data.iteritems()]
@@ -578,7 +597,7 b' def showmanifest(**args):'
578 597 f = templ('manifest', **args)
579 598 # TODO: perhaps 'ctx' should be dropped from mapping because manifest
580 599 # rev and node are completely different from changeset's.
581 return _mappable(f, f, lambda: {'rev': mrev, 'node': mhex})
600 return _mappable(f, None, f, lambda x: {'rev': mrev, 'node': mhex})
582 601
583 602 def shownames(namespace, **args):
584 603 """helper method to generate a template keyword for a namespace"""
@@ -730,7 +730,10 b' def get(context, mapping, args):'
730 730 raise error.ParseError(_("get() expects a dict as first argument"))
731 731
732 732 key = evalfuncarg(context, mapping, args[1])
733 return dictarg.get(key)
733 val = dictarg.get(key)
734 if val is None:
735 return
736 return templatekw.wraphybridvalue(dictarg, key, val)
734 737
735 738 @templatefunc('if(expr, then[, else])')
736 739 def if_(context, mapping, args):
@@ -874,10 +877,11 b' def max_(context, mapping, args, **kwarg'
874 877
875 878 iterable = evalfuncarg(context, mapping, args[0])
876 879 try:
877 return max(iterable)
880 x = max(iterable)
878 881 except (TypeError, ValueError):
879 882 # i18n: "max" is a keyword
880 883 raise error.ParseError(_("max first argument should be an iterable"))
884 return templatekw.wraphybridvalue(iterable, x, x)
881 885
882 886 @templatefunc('min(iterable)')
883 887 def min_(context, mapping, args, **kwargs):
@@ -888,10 +892,11 b' def min_(context, mapping, args, **kwarg'
888 892
889 893 iterable = evalfuncarg(context, mapping, args[0])
890 894 try:
891 return min(iterable)
895 x = min(iterable)
892 896 except (TypeError, ValueError):
893 897 # i18n: "min" is a keyword
894 898 raise error.ParseError(_("min first argument should be an iterable"))
899 return templatekw.wraphybridvalue(iterable, x, x)
895 900
896 901 @templatefunc('mod(a, b)')
897 902 def mod(context, mapping, args):
@@ -3128,10 +3128,24 b' Test new-style inline templating of non-'
3128 3128 $ hg log -R latesttag -r tip -T '{manifest % "{rev}:{node}"}\n'
3129 3129 11:2bc6e9006ce29882383a22d39fd1f4e66dd3e2fc
3130 3130
3131 Test manifest can be join()-ed as before, though it's silly:
3131 $ hg log -R latesttag -r tip -T '{get(extras, "branch") % "{key}: {value}\n"}'
3132 branch: default
3133 $ hg log -R latesttag -r tip -T '{get(extras, "unknown") % "{key}\n"}'
3134 hg: parse error: None is not iterable
3135 [255]
3136 $ hg log -R latesttag -r tip -T '{min(extras) % "{key}: {value}\n"}'
3137 branch: default
3138 $ hg log -R latesttag -l1 -T '{min(revset("0:9")) % "{rev}:{node|short}\n"}'
3139 0:ce3cec86e6c2
3140 $ hg log -R latesttag -l1 -T '{max(revset("0:9")) % "{rev}:{node|short}\n"}'
3141 9:fbc7cd862e9c
3142
3143 Test manifest/get() can be join()-ed as before, though it's silly:
3132 3144
3133 3145 $ hg log -R latesttag -r tip -T '{join(manifest, "")}\n'
3134 3146 11:2bc6e9006ce2
3147 $ hg log -R latesttag -r tip -T '{join(get(extras, "branch"), "")}\n'
3148 default
3135 3149
3136 3150 Test the sub function of templating for expansion:
3137 3151
General Comments 0
You need to be logged in to leave comments. Login now