mercurial/templatefilters.py
changeset 38201 56dd15178190
parent 38024 f5a1aa8c6987
child 38287 0fe65bb7e160
equal deleted inserted replaced
38200:c019db5ccfa1 38201:56dd15178190
    96     """Any text. Treats the text as a path, and returns the last
    96     """Any text. Treats the text as a path, and returns the last
    97     component of the path after splitting by the path separator.
    97     component of the path after splitting by the path separator.
    98     For example, "foo/bar/baz" becomes "baz" and "foo/bar//" becomes "".
    98     For example, "foo/bar/baz" becomes "baz" and "foo/bar//" becomes "".
    99     """
    99     """
   100     return os.path.basename(path)
   100     return os.path.basename(path)
       
   101 
       
   102 @templatefilter('commonprefix')
       
   103 def commonprefix(filelist):
       
   104     """List of text. Treats each list item as file name with /
       
   105     as path separator and returns the longest common directory
       
   106     prefix shared by all list items.
       
   107     Returns the empty string if no common prefix exists.
       
   108 
       
   109     The list items are not normalized, i.e. "foo/../bar" is handled as
       
   110     file "bar" in the directory "foo/..". Leading slashes are ignored.
       
   111 
       
   112     For example, ["foo/bar/baz", "foo/baz/bar"] becomes "foo" and
       
   113     ["foo/bar", "baz"] becomes "".
       
   114     """
       
   115     def common(a, b):
       
   116         if len(a) > len(b):
       
   117             a = b[:len(a)]
       
   118         elif len(b) > len(a):
       
   119             b = b[:len(a)]
       
   120         if a == b:
       
   121             return a
       
   122         for i in xrange(len(a)):
       
   123             if a[i] != b[i]:
       
   124                 return a[:i]
       
   125         return a
       
   126     try:
       
   127         if not filelist:
       
   128             return ""
       
   129         dirlist = [f.lstrip('/').split('/')[:-1] for f in filelist]
       
   130         if len(dirlist) == 1:
       
   131             return '/'.join(dirlist[0])
       
   132         a = min(dirlist)
       
   133         b = max(dirlist)
       
   134         # The common prefix of a and b is shared with all
       
   135         # elements of the list since Python sorts lexicographical
       
   136         # and [1, x] after [1].
       
   137         return '/'.join(common(a, b))
       
   138     except TypeError:
       
   139         raise error.ParseError(_('argument is not a list of text'))
   101 
   140 
   102 @templatefilter('count')
   141 @templatefilter('count')
   103 def count(i):
   142 def count(i):
   104     """List or text. Returns the length as an integer."""
   143     """List or text. Returns the length as an integer."""
   105     try:
   144     try: