# HG changeset patch # User Steve Losh # Date 1254790206 14400 # Node ID 1ef154bb1a4fb54d8612ce4bc257b317dadd788f # Parent 7e437c5261bb9791a9254204456329428b0a0089 Add file-level commenting. diff -r 7e437c5261bb -r 1ef154bb1a4f review/extension_ui.py --- a/review/extension_ui.py Mon Oct 05 19:45:45 2009 -0400 +++ b/review/extension_ui.py Mon Oct 05 20:50:06 2009 -0400 @@ -1,5 +1,6 @@ '''The review extension's UI.''' +import os import messages from api import * from mercurial import util @@ -17,18 +18,27 @@ ui.note(messages.INIT_EXISTS_COMMITTED) else: raise util.Abort(messages.INIT_EXISTS_UNCOMMITTED) - return -def _comment_command(ui, repo, **opts): +def _comment_command(ui, repo, *fnames, **opts): + rev = opts.pop('rev') + filename = fnames[0] if fnames else '' + message = opts.pop('message') + rd = ReviewDatastore(ui, repo) - rcset = rd[opts.pop('rev')] - message = opts.pop('message') + rcset = rd[rev] + + if filename: + filename = os.path.relpath(filename, start=repo.root) + + if filename not in repo[rcset.node].files(): + raise util.Abort( + messages.COMMENT_FILE_DOES_NOT_EXIST % (filename, repo[rev].rev()) + ) if not message: raise util.Abort(messages.COMMENT_REQUIRES_MESSAGE) - rcset.add_comment(message=message) - return + rcset.add_comment(message=message, filename=filename) def _signoff_command(ui, repo, **opts): rd = ReviewDatastore(ui, repo) @@ -48,11 +58,10 @@ force=opts.pop('force')) except SignoffExists: raise util.Abort(messages.SIGNOFF_EXISTS) - - return def _review_command(ui, repo, *fnames, **opts): rev = opts.pop('rev') + rd = ReviewDatastore(ui, repo) cset = repo[rev] rcset = rd[rev] @@ -81,6 +90,13 @@ header = messages.REVIEW_LOG_FILE_HEADER % filename print '\n\n%s %s' % (header, '-'*(80-(len(header)+1))) + file_level_comments = filter(lambda c: filename == c.filename, rcset.comments) + for comment in file_level_comments: + ui.write(messages.REVIEW_LOG_COMMENT_AUTHOR % comment.author) + for line in comment.message.splitlines(): + ui.write(messages.REVIEW_LOG_COMMENT_LINE % line) + + content = diffs[filename].splitlines()[2:] prefix = '%%%dd: ' % len(str(len(content)-1)) @@ -94,7 +110,7 @@ if opts.pop('init'): return _init_command(ui, repo, **opts) elif opts.pop('comment'): - return _comment_command(ui, repo, **opts) + return _comment_command(ui, repo, *fnames, **opts) elif opts.pop('signoff'): return _signoff_command(ui, repo, **opts) else: @@ -103,16 +119,17 @@ cmdtable = { 'review': (review, [ - ('i', 'init', False, 'start code reviewing this repository'), - ('', 'local-path', '', 'the local path to the code review data'), - ('', 'remote-path', '', 'the remote path to code review data'), - ('c', 'comment', False, 'add a comment'), - ('s', 'signoff', False, 'sign off'), - ('', 'yes', False, 'sign off as stating the changeset is good'), - ('', 'no', False, 'sign off as stating the changeset is bad'), - ('m', 'message', '', 'use as the comment or signoff message'), - ('', 'force', False, 'overwrite an existing signoff'), - ('r', 'rev', '.', 'the revision to review'), + ('i', 'init', False, 'start code reviewing this repository'), + ('', 'local-path', '', 'the local path to the code review data'), + ('', 'remote-path', '', 'the remote path to code review data'), + ('c', 'comment', False, 'add a comment'), + ('s', 'signoff', False, 'sign off'), + ('', 'yes', False, 'sign off as stating the changeset is good'), + ('', 'no', False, 'sign off as stating the changeset is bad'), + ('m', 'message', '', 'use as the comment or signoff message'), + ('', 'force', False, 'overwrite an existing signoff'), + ('f', 'file', '', 'comment on '), + ('r', 'rev', '.', 'the revision to review'), ], 'hg review') } \ No newline at end of file diff -r 7e437c5261bb -r 1ef154bb1a4f review/messages.py --- a/review/messages.py Mon Oct 05 19:45:45 2009 -0400 +++ b/review/messages.py Mon Oct 05 20:50:06 2009 -0400 @@ -22,6 +22,10 @@ a message must be provided to add a comment! ''' +COMMENT_FILE_DOES_NOT_EXIST = '''\ +file %s was not changed in revision %s! +''' + SIGNOFF_REQUIRES_MESSAGE = '''\ a message must be provided to sign off! ''' diff -r 7e437c5261bb -r 1ef154bb1a4f review/tests/test_comment.py --- a/review/tests/test_comment.py Mon Oct 05 19:45:45 2009 -0400 +++ b/review/tests/test_comment.py Mon Oct 05 20:50:06 2009 -0400 @@ -78,3 +78,40 @@ assert messages.REVIEW_LOG_COMMENT_LINE % 'Test comment one.' in output assert messages.REVIEW_LOG_COMMENT_LINE % 'Test comment two.' in output + +@with_setup(setup_reviewed_sandbox, teardown_sandbox) +def test_add_comments_to_file(): + sandbox = get_sandbox_repo() + + author_line = messages.REVIEW_LOG_COMMENT_AUTHOR % '|' + a1, _, a2 = author_line.partition('|') + + review(comment=True, message='Test comment one.', rev='1', files=['file_one']) + + output = review(rev='1', files=['file_one']) + assert a1 in output + assert a2 in output + assert messages.REVIEW_LOG_COMMENT_LINE % 'Test comment one.' in output + + output = review(rev='1', files=['file_two']) + assert messages.REVIEW_LOG_COMMENT_LINE % 'Test comment one.' not in output + + output = review(rev='0', files=['file_one']) + assert a1 not in output + assert a2 not in output + assert messages.REVIEW_LOG_COMMENT_LINE % 'Test comment one.' not in output + + +@with_setup(setup_reviewed_sandbox, teardown_sandbox) +def test_add_comments_to_bad_file(): + sandbox = get_sandbox_repo() + + try: + review(comment=True, message='Test comment one.', files=['bad']) + except hgutil.Abort, e: + error = str(e) + assert messages.COMMENT_FILE_DOES_NOT_EXIST % ('bad', '2') in error + else: + assert False, 'The correct error message was not printed.' + + diff -r 7e437c5261bb -r 1ef154bb1a4f review/tests/util.py --- a/review/tests/util.py Mon Oct 05 19:45:45 2009 -0400 +++ b/review/tests/util.py Mon Oct 05 20:50:06 2009 -0400 @@ -6,13 +6,15 @@ _ui = ui.ui() def review(init=False, comment=False, signoff=False, yes=False, no=False, - force=False, message='', rev='.', local_path='', remote_path=''): + force=False, message='', rev='.', local_path='', remote_path='', files=None): + + files = files if files else [] _ui.pushbuffer() - extension_ui.review(_ui, get_sandbox_repo(), + extension_ui.review(_ui, get_sandbox_repo(), *files, init=init, comment=comment, signoff=signoff, yes=yes, no=no, - force=force, message=message, rev=rev, local_path=local_path, - remote_path=remote_path) + force=force, message=message, rev=rev, + local_path=local_path, remote_path=remote_path ) output = _ui.popbuffer() print output