comparison mercurial/cmdutil.py @ 34856:890afefa7296

diff: pass a diff hunks filter function from changeset_printer to patch.diff() We add a 'hunksfilterfn' keyword argument in all functions of the call stack from changeset_printer.show() to patch.diff(). This is a callable that will be used to filter out hunks by line range and will be used in the "-L/--line-range" option of "hg log" command introduced in the following changesets.
author Denis Laxalde <denis.laxalde@logilab.fr>
date Fri, 06 Oct 2017 14:45:17 +0200
parents d45236f3d38e
children 84c6b9384d6a
comparison
equal deleted inserted replaced
34855:35c6a54ec1ff 34856:890afefa7296
1492 if fo is not None: 1492 if fo is not None:
1493 fo.close() 1493 fo.close()
1494 1494
1495 def diffordiffstat(ui, repo, diffopts, node1, node2, match, 1495 def diffordiffstat(ui, repo, diffopts, node1, node2, match,
1496 changes=None, stat=False, fp=None, prefix='', 1496 changes=None, stat=False, fp=None, prefix='',
1497 root='', listsubrepos=False): 1497 root='', listsubrepos=False, hunksfilterfn=None):
1498 '''show diff or diffstat.''' 1498 '''show diff or diffstat.'''
1499 if fp is None: 1499 if fp is None:
1500 write = ui.write 1500 write = ui.write
1501 else: 1501 else:
1502 def write(s, **kw): 1502 def write(s, **kw):
1520 diffopts = diffopts.copy(context=0) 1520 diffopts = diffopts.copy(context=0)
1521 width = 80 1521 width = 80
1522 if not ui.plain(): 1522 if not ui.plain():
1523 width = ui.termwidth() 1523 width = ui.termwidth()
1524 chunks = patch.diff(repo, node1, node2, match, changes, diffopts, 1524 chunks = patch.diff(repo, node1, node2, match, changes, diffopts,
1525 prefix=prefix, relroot=relroot) 1525 prefix=prefix, relroot=relroot,
1526 hunksfilterfn=hunksfilterfn)
1526 for chunk, label in patch.diffstatui(util.iterlines(chunks), 1527 for chunk, label in patch.diffstatui(util.iterlines(chunks),
1527 width=width): 1528 width=width):
1528 write(chunk, label=label) 1529 write(chunk, label=label)
1529 else: 1530 else:
1530 for chunk, label in patch.diffui(repo, node1, node2, match, 1531 for chunk, label in patch.diffui(repo, node1, node2, match,
1531 changes, diffopts, prefix=prefix, 1532 changes, diffopts, prefix=prefix,
1532 relroot=relroot): 1533 relroot=relroot,
1534 hunksfilterfn=hunksfilterfn):
1533 write(chunk, label=label) 1535 write(chunk, label=label)
1534 1536
1535 if listsubrepos: 1537 if listsubrepos:
1536 ctx1 = repo[node1] 1538 ctx1 = repo[node1]
1537 ctx2 = repo[node2] 1539 ctx2 = repo[node2]
1589 1591
1590 def close(self): 1592 def close(self):
1591 if self.footer: 1593 if self.footer:
1592 self.ui.write(self.footer) 1594 self.ui.write(self.footer)
1593 1595
1594 def show(self, ctx, copies=None, matchfn=None, **props): 1596 def show(self, ctx, copies=None, matchfn=None, hunksfilterfn=None,
1597 **props):
1595 props = pycompat.byteskwargs(props) 1598 props = pycompat.byteskwargs(props)
1596 if self.buffered: 1599 if self.buffered:
1597 self.ui.pushbuffer(labeled=True) 1600 self.ui.pushbuffer(labeled=True)
1598 self._show(ctx, copies, matchfn, props) 1601 self._show(ctx, copies, matchfn, hunksfilterfn, props)
1599 self.hunk[ctx.rev()] = self.ui.popbuffer() 1602 self.hunk[ctx.rev()] = self.ui.popbuffer()
1600 else: 1603 else:
1601 self._show(ctx, copies, matchfn, props) 1604 self._show(ctx, copies, matchfn, hunksfilterfn, props)
1602 1605
1603 def _show(self, ctx, copies, matchfn, props): 1606 def _show(self, ctx, copies, matchfn, hunksfilterfn, props):
1604 '''show a single changeset or file revision''' 1607 '''show a single changeset or file revision'''
1605 changenode = ctx.node() 1608 changenode = ctx.node()
1606 rev = ctx.rev() 1609 rev = ctx.rev()
1607 1610
1608 if self.ui.quiet: 1611 if self.ui.quiet:
1712 self.ui.write(_("summary: %s\n") % 1715 self.ui.write(_("summary: %s\n") %
1713 description.splitlines()[0], 1716 description.splitlines()[0],
1714 label='log.summary') 1717 label='log.summary')
1715 self.ui.write("\n") 1718 self.ui.write("\n")
1716 1719
1717 self.showpatch(ctx, matchfn) 1720 self.showpatch(ctx, matchfn, hunksfilterfn=hunksfilterfn)
1718 1721
1719 def _showobsfate(self, ctx): 1722 def _showobsfate(self, ctx):
1720 obsfate = templatekw.showobsfate(repo=self.repo, ctx=ctx, ui=self.ui) 1723 obsfate = templatekw.showobsfate(repo=self.repo, ctx=ctx, ui=self.ui)
1721 1724
1722 if obsfate: 1725 if obsfate:
1727 1730
1728 def _exthook(self, ctx): 1731 def _exthook(self, ctx):
1729 '''empty method used by extension as a hook point 1732 '''empty method used by extension as a hook point
1730 ''' 1733 '''
1731 1734
1732 def showpatch(self, ctx, matchfn): 1735 def showpatch(self, ctx, matchfn, hunksfilterfn=None):
1733 if not matchfn: 1736 if not matchfn:
1734 matchfn = self.matchfn 1737 matchfn = self.matchfn
1735 if matchfn: 1738 if matchfn:
1736 stat = self.diffopts.get('stat') 1739 stat = self.diffopts.get('stat')
1737 diff = self.diffopts.get('patch') 1740 diff = self.diffopts.get('patch')
1738 diffopts = patch.diffallopts(self.ui, self.diffopts) 1741 diffopts = patch.diffallopts(self.ui, self.diffopts)
1739 node = ctx.node() 1742 node = ctx.node()
1740 prev = ctx.p1().node() 1743 prev = ctx.p1().node()
1741 if stat: 1744 if stat:
1742 diffordiffstat(self.ui, self.repo, diffopts, prev, node, 1745 diffordiffstat(self.ui, self.repo, diffopts, prev, node,
1743 match=matchfn, stat=True) 1746 match=matchfn, stat=True,
1747 hunksfilterfn=hunksfilterfn)
1744 if diff: 1748 if diff:
1745 if stat: 1749 if stat:
1746 self.ui.write("\n") 1750 self.ui.write("\n")
1747 diffordiffstat(self.ui, self.repo, diffopts, prev, node, 1751 diffordiffstat(self.ui, self.repo, diffopts, prev, node,
1748 match=matchfn, stat=False) 1752 match=matchfn, stat=False,
1753 hunksfilterfn=hunksfilterfn)
1749 self.ui.write("\n") 1754 self.ui.write("\n")
1750 1755
1751 class jsonchangeset(changeset_printer): 1756 class jsonchangeset(changeset_printer):
1752 '''format changeset information.''' 1757 '''format changeset information.'''
1753 1758
1760 if not self._first: 1765 if not self._first:
1761 self.ui.write("\n]\n") 1766 self.ui.write("\n]\n")
1762 else: 1767 else:
1763 self.ui.write("[]\n") 1768 self.ui.write("[]\n")
1764 1769
1765 def _show(self, ctx, copies, matchfn, props): 1770 def _show(self, ctx, copies, matchfn, hunksfilterfn, props):
1766 '''show a single changeset or file revision''' 1771 '''show a single changeset or file revision'''
1767 rev = ctx.rev() 1772 rev = ctx.rev()
1768 if rev is None: 1773 if rev is None:
1769 jrev = jnode = 'null' 1774 jrev = jnode = 'null'
1770 else: 1775 else:
1894 if not self.footer: 1899 if not self.footer:
1895 self.footer = "" 1900 self.footer = ""
1896 self.footer += templater.stringify(self.t(self._parts['docfooter'])) 1901 self.footer += templater.stringify(self.t(self._parts['docfooter']))
1897 return super(changeset_templater, self).close() 1902 return super(changeset_templater, self).close()
1898 1903
1899 def _show(self, ctx, copies, matchfn, props): 1904 def _show(self, ctx, copies, matchfn, hunksfilterfn, props):
1900 '''show a single changeset or file revision''' 1905 '''show a single changeset or file revision'''
1901 props = props.copy() 1906 props = props.copy()
1902 props.update(templatekw.keywords) 1907 props.update(templatekw.keywords)
1903 props['templ'] = self.t 1908 props['templ'] = self.t
1904 props['ctx'] = ctx 1909 props['ctx'] = ctx
1926 self.ui.write(h) 1931 self.ui.write(h)
1927 1932
1928 # write changeset metadata, then patch if requested 1933 # write changeset metadata, then patch if requested
1929 key = self._parts[self._tref] 1934 key = self._parts[self._tref]
1930 self.ui.write(templater.stringify(self.t(key, **props))) 1935 self.ui.write(templater.stringify(self.t(key, **props)))
1931 self.showpatch(ctx, matchfn) 1936 self.showpatch(ctx, matchfn, hunksfilterfn=hunksfilterfn)
1932 1937
1933 if self._parts['footer']: 1938 if self._parts['footer']:
1934 if not self.footer: 1939 if not self.footer:
1935 self.footer = templater.stringify( 1940 self.footer = templater.stringify(
1936 self.t(self._parts['footer'], **props)) 1941 self.t(self._parts['footer'], **props))