##// END OF EJS Templates
comments: allow commenting on empty files without content.
marcink -
r3081:0fdc01e5 default
parent child Browse files
Show More
@@ -20,6 +20,7 b''
20
20
21 import logging
21 import logging
22 import difflib
22 import difflib
23 import string
23 from itertools import groupby
24 from itertools import groupby
24
25
25 from pygments import lex
26 from pygments import lex
@@ -28,11 +29,11 b' from pygments.lexers.special import Text'
28
29
29 from rhodecode.lib.helpers import (
30 from rhodecode.lib.helpers import (
30 get_lexer_for_filenode, html_escape, get_custom_lexer)
31 get_lexer_for_filenode, html_escape, get_custom_lexer)
31 from rhodecode.lib.utils2 import AttributeDict, StrictAttributeDict
32 from rhodecode.lib.utils2 import AttributeDict, StrictAttributeDict, safe_unicode
32 from rhodecode.lib.vcs.nodes import FileNode
33 from rhodecode.lib.vcs.nodes import FileNode
33 from rhodecode.lib.vcs.exceptions import VCSError, NodeDoesNotExistError
34 from rhodecode.lib.vcs.exceptions import VCSError, NodeDoesNotExistError
34 from rhodecode.lib.diff_match_patch import diff_match_patch
35 from rhodecode.lib.diff_match_patch import diff_match_patch
35 from rhodecode.lib.diffs import LimitedDiffContainer
36 from rhodecode.lib.diffs import LimitedDiffContainer, DEL_FILENODE, BIN_FILENODE
36 from pygments.lexers import get_lexer_by_name
37 from pygments.lexers import get_lexer_by_name
37
38
38 plain_text_lexer = get_lexer_by_name(
39 plain_text_lexer = get_lexer_by_name(
@@ -506,6 +507,7 b' class DiffSet(object):'
506 'target_mode': patch['stats']['new_mode'],
507 'target_mode': patch['stats']['new_mode'],
507 'limited_diff': isinstance(patch, LimitedDiffContainer),
508 'limited_diff': isinstance(patch, LimitedDiffContainer),
508 'hunks': [],
509 'hunks': [],
510 'hunk_ops': None,
509 'diffset': self,
511 'diffset': self,
510 })
512 })
511
513
@@ -515,6 +517,30 b' class DiffSet(object):'
515 hunkbit.target_file_path = target_file_path
517 hunkbit.target_file_path = target_file_path
516 filediff.hunks.append(hunkbit)
518 filediff.hunks.append(hunkbit)
517
519
520 # Simulate hunk on OPS type line which doesn't really contain any diff
521 # this allows commenting on those
522 actions = []
523 for op_id, op_text in filediff.patch['stats']['ops'].items():
524 if op_id == DEL_FILENODE:
525 actions.append(u'file was deleted')
526 elif op_id == BIN_FILENODE:
527 actions.append(u'binary diff hidden')
528 else:
529 actions.append(safe_unicode(op_text))
530 action_line = u'FILE WITHOUT CONTENT: ' + \
531 u', '.join(map(string.upper, actions)) or u'UNDEFINED_ACTION'
532
533 hunk_ops = {'source_length': 0, 'source_start': 0,
534 'lines': [
535 {'new_lineno': 0, 'old_lineno': 1,
536 'action': 'unmod', 'line': action_line}
537 ],
538 'section_header': u'', 'target_start': 1, 'target_length': 1}
539
540 hunkbit = self.parse_hunk(hunk_ops, source_file, target_file)
541 hunkbit.source_file_path = source_file_path
542 hunkbit.target_file_path = target_file_path
543 filediff.hunk_ops = hunkbit
518 return filediff
544 return filediff
519
545
520 def parse_hunk(self, hunk, source_file, target_file):
546 def parse_hunk(self, hunk, source_file, target_file):
@@ -149,42 +149,37 b' collapse_all = len(diffset.files) > coll'
149 lines_changed = filediff.patch['stats']['added'] + filediff.patch['stats']['deleted']
149 lines_changed = filediff.patch['stats']['added'] + filediff.patch['stats']['deleted']
150 over_lines_changed_limit = lines_changed > lines_changed_limit
150 over_lines_changed_limit = lines_changed > lines_changed_limit
151 %>
151 %>
152 <input ${collapse_all and 'checked' or ''} class="filediff-collapse-state" id="filediff-collapse-${id(filediff)}" type="checkbox">
152
153 <input ${(collapse_all and 'checked' or '')} class="filediff-collapse-state" id="filediff-collapse-${id(filediff)}" type="checkbox">
153 <div
154 <div
154 class="filediff"
155 class="filediff"
155 data-f-path="${filediff.patch['filename']}"
156 data-f-path="${filediff.patch['filename']}"
156 id="a_${h.FID('', filediff.patch['filename'])}">
157 id="a_${h.FID('', filediff.patch['filename'])}"
158 >
159
157 <label for="filediff-collapse-${id(filediff)}" class="filediff-heading">
160 <label for="filediff-collapse-${id(filediff)}" class="filediff-heading">
158 <div class="filediff-collapse-indicator"></div>
161 <div class="filediff-collapse-indicator"></div>
159 ${diff_ops(filediff)}
162 ${diff_ops(filediff)}
160 </label>
163 </label>
161 ${diff_menu(filediff, use_comments=use_comments)}
164 ${diff_menu(filediff, use_comments=use_comments)}
162 <table class="cb cb-diff-${c.diffmode} code-highlight ${over_lines_changed_limit and 'cb-collapsed' or ''}">
165 <table class="cb cb-diff-${c.diffmode} code-highlight ${(over_lines_changed_limit and 'cb-collapsed' or '')}">
166
167 ## new/deleted/empty content case
163 %if not filediff.hunks:
168 % if not filediff.hunks:
164 %for op_id, op_text in filediff.patch['stats']['ops'].items():
169 ## Comment container, on "fakes" hunk that contains all data to render comments
165 <tr>
170 ${render_hunk_lines(c.diffmode, filediff.hunk_ops, use_comments=use_comments, inline_comments=inline_comments)}
166 <td class="cb-text cb-${op_class(op_id)}" ${c.diffmode == 'unified' and 'colspan=4' or 'colspan=6'}>
167 %if op_id == DEL_FILENODE:
168 ${_('File was deleted')}
169 %elif op_id == BIN_FILENODE:
170 ${_('Binary file hidden')}
171 %else:
172 ${op_text}
173 %endif
171 % endif
174 </td>
172
175 </tr>
176 %endfor
177 %endif
178 %if filediff.limited_diff:
173 %if filediff.limited_diff:
179 <tr class="cb-warning cb-collapser">
174 <tr class="cb-warning cb-collapser">
180 <td class="cb-text" ${c.diffmode == 'unified' and 'colspan=4' or 'colspan=6'}>
175 <td class="cb-text" ${(c.diffmode == 'unified' and 'colspan=4' or 'colspan=6')}>
181 ${_('The requested commit is too big and content was truncated.')} <a href="${h.current_route_path(request, fulldiff=1)}" onclick="return confirm('${_("Showing a big diff might take some time and resources, continue?")}')">${_('Show full diff')}</a>
176 ${_('The requested commit is too big and content was truncated.')} <a href="${h.current_route_path(request, fulldiff=1)}" onclick="return confirm('${_("Showing a big diff might take some time and resources, continue?")}')">${_('Show full diff')}</a>
182 </td>
177 </td>
183 </tr>
178 </tr>
184 %else:
179 %else:
185 %if over_lines_changed_limit:
180 %if over_lines_changed_limit:
186 <tr class="cb-warning cb-collapser">
181 <tr class="cb-warning cb-collapser">
187 <td class="cb-text" ${c.diffmode == 'unified' and 'colspan=4' or 'colspan=6'}>
182 <td class="cb-text" ${(c.diffmode == 'unified' and 'colspan=4' or 'colspan=6')}>
188 ${_('This diff has been collapsed as it changes many lines, (%i lines changed)' % lines_changed)}
183 ${_('This diff has been collapsed as it changes many lines, (%i lines changed)' % lines_changed)}
189 <a href="#" class="cb-expand"
184 <a href="#" class="cb-expand"
190 onclick="$(this).closest('table').removeClass('cb-collapsed'); return false;">${_('Show them')}
185 onclick="$(this).closest('table').removeClass('cb-collapsed'); return false;">${_('Show them')}
@@ -199,28 +194,20 b' collapse_all = len(diffset.files) > coll'
199
194
200 %for hunk in filediff.hunks:
195 % for hunk in filediff.hunks:
201 <tr class="cb-hunk">
196 <tr class="cb-hunk">
202 <td ${c.diffmode == 'unified' and 'colspan=3' or ''}>
197 <td ${(c.diffmode == 'unified' and 'colspan=3' or '')}>
203 ## TODO: dan: add ajax loading of more context here
198 ## TODO: dan: add ajax loading of more context here
204 ## <a href="#">
199 ## <a href="#">
205 <i class="icon-more"></i>
200 <i class="icon-more"></i>
206 ## </a>
201 ## </a>
207 </td>
202 </td>
208 <td ${c.diffmode == 'sideside' and 'colspan=5' or ''}>
203 <td ${(c.diffmode == 'sideside' and 'colspan=5' or '')}>
209 @@
204 @@
210 -${hunk.source_start},${hunk.source_length}
205 -${hunk.source_start},${hunk.source_length}
211 +${hunk.target_start},${hunk.target_length}
206 +${hunk.target_start},${hunk.target_length}
212 ${hunk.section_header}
207 ${hunk.section_header}
213 </td>
208 </td>
214 </tr>
209 </tr>
215 %if c.diffmode == 'unified':
210 ${render_hunk_lines(c.diffmode, hunk, use_comments=use_comments, inline_comments=inline_comments)}
216 ${render_hunk_lines_unified(hunk, use_comments=use_comments, inline_comments=inline_comments)}
217 %elif c.diffmode == 'sideside':
218 ${render_hunk_lines_sideside(hunk, use_comments=use_comments, inline_comments=inline_comments)}
219 %else:
220 <tr class="cb-line">
221 <td>unknown diff mode</td>
222 </tr>
223 %endif
224 %endfor
211 % endfor
225
212
226 <% unmatched_comments = (inline_comments or {}).get(filediff.patch['filename'], {}) %>
213 <% unmatched_comments = (inline_comments or {}).get(filediff.patch['filename'], {}) %>
@@ -292,7 +279,7 b' collapse_all = len(diffset.files) > coll'
292 display_state = ''
279 display_state = ''
293 %>
280 %>
294 <div class="filediffs filediff-outdated" style="${display_state}">
281 <div class="filediffs filediff-outdated" style="${display_state}">
295 <input ${collapse_all and 'checked' or ''} class="filediff-collapse-state" id="filediff-collapse-${id(filename)}" type="checkbox">
282 <input ${(collapse_all and 'checked' or '')} class="filediff-collapse-state" id="filediff-collapse-${id(filename)}" type="checkbox">
296 <div class="filediff" data-f-path="${filename}" id="a_${h.FID('', filename)}">
283 <div class="filediff" data-f-path="${filename}" id="a_${h.FID('', filename)}">
297 <label for="filediff-collapse-${id(filename)}" class="filediff-heading">
284 <label for="filediff-collapse-${id(filename)}" class="filediff-heading">
298 <div class="filediff-collapse-indicator"></div>
285 <div class="filediff-collapse-indicator"></div>
@@ -714,6 +701,20 b' def get_comments_for(diff_type, comments'
714 %endfor
701 %endfor
715 </%def>
702 </%def>
716
703
704
705 <%def name="render_hunk_lines(diff_mode, hunk, use_comments, inline_comments)">
706 % if diff_mode == 'unified':
707 ${render_hunk_lines_unified(hunk, use_comments=use_comments, inline_comments=inline_comments)}
708 % elif diff_mode == 'sideside':
709 ${render_hunk_lines_sideside(hunk, use_comments=use_comments, inline_comments=inline_comments)}
710 % else:
711 <tr class="cb-line">
712 <td>unknown diff mode</td>
713 </tr>
714 % endif
715 </%def>
716
717
717 <%def name="render_add_comment_button()">
718 <%def name="render_add_comment_button()">
718 <button class="btn btn-small btn-primary cb-comment-box-opener" onclick="return Rhodecode.comments.createComment(this)">
719 <button class="btn btn-small btn-primary cb-comment-box-opener" onclick="return Rhodecode.comments.createComment(this)">
719 <span><i class="icon-comment"></i></span>
720 <span><i class="icon-comment"></i></span>
General Comments 0
You need to be logged in to leave comments. Login now