Back to index

moin  1.9.0~rc2
Functions
MoinMoin.util.diff_html Namespace Reference

Functions

def indent
def diff

Function Documentation

def MoinMoin.util.diff_html.diff (   request,
  old,
  new 
)
Find changes between old and new and return
    HTML markup visualising them.

Definition at line 26 of file diff_html.py.

00026 
00027 def diff(request, old, new):
00028     """ Find changes between old and new and return
00029         HTML markup visualising them.
00030     """
00031     _ = request.getText
00032     t_line = _("Line") + " %d"
00033 
00034     seq1 = old.splitlines()
00035     seq2 = new.splitlines()
00036 
00037     seqobj = difflib.SequenceMatcher(None, seq1, seq2)
00038     linematch = seqobj.get_matching_blocks()
00039 
00040     if len(seq1) == len(seq2) and linematch[0] == (0, 0, len(seq1)):
00041         # No differences.
00042         return " - " + _("No differences found!")
00043 
00044     lastmatch = (0, 0)
00045 
00046     result = """
00047 <table class="diff">
00048 <tr>
00049 <td class="diff-removed">
00050 <span>
00051 %s
00052 </span>
00053 </td>
00054 <td class="diff-added">
00055 <span>
00056 %s
00057 </span>
00058 </td>
00059 </tr>
00060 """ % (_('Deletions are marked like this.'), _('Additions are marked like this.'), )
00061 
00062     # Print all differences
00063     for match in linematch:
00064         # Starts of pages identical?
00065         if lastmatch == match[0:2]:
00066             lastmatch = (match[0] + match[2], match[1] + match[2])
00067             continue
00068         llineno, rlineno = lastmatch[0]+1, lastmatch[1]+1
00069         result += """
00070 <tr class="diff-title">
00071 <td>
00072 %s:
00073 </td>
00074 <td>
00075 %s:
00076 </td>
00077 </tr>
00078 """ % (request.formatter.line_anchorlink(1, llineno) + request.formatter.text(t_line % llineno) + request.formatter.line_anchorlink(0),
00079        request.formatter.line_anchorlink(1, rlineno) + request.formatter.text(t_line % rlineno) + request.formatter.line_anchorlink(0))
00080 
00081         leftpane = ''
00082         rightpane = ''
00083         linecount = max(match[0] - lastmatch[0], match[1] - lastmatch[1])
00084         for line in range(linecount):
00085             if line < match[0] - lastmatch[0]:
00086                 if line > 0:
00087                     leftpane += '\n'
00088                 leftpane += seq1[lastmatch[0] + line]
00089             if line < match[1] - lastmatch[1]:
00090                 if line > 0:
00091                     rightpane += '\n'
00092                 rightpane += seq2[lastmatch[1] + line]
00093 
00094         charobj = difflib.SequenceMatcher(None, leftpane, rightpane)
00095         charmatch = charobj.get_matching_blocks()
00096 
00097         if charobj.ratio() < 0.5:
00098             # Insufficient similarity.
00099             if leftpane:
00100                 leftresult = """<span>%s</span>""" % indent(escape(leftpane))
00101             else:
00102                 leftresult = ''
00103 
00104             if rightpane:
00105                 rightresult = """<span>%s</span>""" % indent(escape(rightpane))
00106             else:
00107                 rightresult = ''
00108         else:
00109             # Some similarities; markup changes.
00110             charlast = (0, 0)
00111 
00112             leftresult = ''
00113             rightresult = ''
00114             for thismatch in charmatch:
00115                 if thismatch[0] - charlast[0] != 0:
00116                     leftresult += """<span>%s</span>""" % indent(
00117                         escape(leftpane[charlast[0]:thismatch[0]]))
00118                 if thismatch[1] - charlast[1] != 0:
00119                     rightresult += """<span>%s</span>""" % indent(
00120                         escape(rightpane[charlast[1]:thismatch[1]]))
00121                 leftresult += escape(leftpane[thismatch[0]:thismatch[0] + thismatch[2]])
00122                 rightresult += escape(rightpane[thismatch[1]:thismatch[1] + thismatch[2]])
00123                 charlast = (thismatch[0] + thismatch[2], thismatch[1] + thismatch[2])
00124 
00125         leftpane = '<br>\n'.join([indent(x) for x in leftresult.splitlines()])
00126         rightpane = '<br>\n'.join([indent(x) for x in rightresult.splitlines()])
00127 
00128         # removed width="50%%"
00129         result += """
00130 <tr>
00131 <td class="diff-removed">
00132 %s
00133 </td>
00134 <td class="diff-added">
00135 %s
00136 </td>
00137 </tr>
00138 """ % (leftpane, rightpane)
00139 
00140         lastmatch = (match[0] + match[2], match[1] + match[2])
00141 
00142     result += '</table>\n'
00143     return result
00144 

Here is the call graph for this function:

Definition at line 13 of file diff_html.py.

00013 
00014 def indent(line):
00015     eol = ''
00016     while line and line[0] == '\n':
00017         eol += '\n'
00018         line = line[1:]
00019     stripped = line.lstrip()
00020     if len(line) - len(stripped):
00021         line = "&nbsp;" * (len(line) - len(stripped)) + stripped
00022     #return "%d / %d / %s" % (len(line), len(stripped), line)
00023     return eol + line
00024 
00025 
# This code originally by Scott Moonen, used with permission.

Here is the caller graph for this function: