~bzr-pqm/bzr/bzr.dev

« back to all changes in this revision

Viewing changes to bzrlib/revisionspec.py

  • Committer: Aaron Bentley
  • Date: 2010-08-18 14:39:37 UTC
  • mto: This revision was merged to the branch mainline in revision 5443.
  • Revision ID: aaron@aaronbentley.com-20100818143937-ti9wfm07zuywq6zb
Implement 'annotate' revision-id.

Show diffs side-by-side

added added

removed removed

Lines of Context:
31
31
    revision,
32
32
    symbol_versioning,
33
33
    trace,
 
34
    workingtree,
34
35
    )
35
36
 
36
37
 
900
901
            self._get_submit_location(context_branch))
901
902
 
902
903
 
 
904
class RevisionSpec_annotate(RevisionIDSpec):
 
905
 
 
906
    prefix = 'annotate:'
 
907
 
 
908
    help_txt = """Select the revision that last modified the specified line.
 
909
 
 
910
    Select the revision that last modified the specified line.  Line is
 
911
    specified as path:number.  Path is a relative path to the file.  Numbers
 
912
    start at 1, and are relative to the current version, not the last-
 
913
    committed version of the file.
 
914
    """
 
915
 
 
916
    def _raise_invalid(self, numstring, context_branch):
 
917
        raise errors.InvalidRevisionSpec(self.user_spec, context_branch,
 
918
            'No such line: %s' % numstring)
 
919
 
 
920
    def _as_revision_id(self, context_branch):
 
921
        path, numstring = self.spec.rsplit(':', 1)
 
922
        try:
 
923
            index = int(numstring) - 1
 
924
        except ValueError:
 
925
            self._raise_invalid(numstring, context_branch)
 
926
        tree, file_path = workingtree.WorkingTree.open_containing(path)
 
927
        tree.lock_read()
 
928
        try:
 
929
            file_id = tree.path2id(file_path)
 
930
            if file_id is None:
 
931
                raise errors.InvalidRevisionSpec(self.user_spec,
 
932
                    context_branch, "File '%s' is not versioned." %
 
933
                    file_path)
 
934
            revision_ids = [r for (r, l) in tree.annotate_iter(file_id)]
 
935
        finally:
 
936
            tree.unlock()
 
937
        try:
 
938
            revision_id = revision_ids[index]
 
939
        except IndexError:
 
940
            self._raise_invalid(numstring, context_branch)
 
941
        if revision_id == revision.CURRENT_REVISION:
 
942
            raise errors.InvalidRevisionSpec(self.user_spec, context_branch,
 
943
                'Line %s has not been committed.' % numstring)
 
944
        return revision_id
 
945
 
 
946
 
903
947
class RevisionSpec_mainline(RevisionIDSpec):
904
948
 
905
949
    help_txt = """Select mainline revision that merged the specified revision.
948
992
_register_revspec(RevisionSpec_ancestor)
949
993
_register_revspec(RevisionSpec_branch)
950
994
_register_revspec(RevisionSpec_submit)
 
995
_register_revspec(RevisionSpec_annotate)
951
996
_register_revspec(RevisionSpec_mainline)
952
997
 
953
998
# classes in this list should have a "prefix" attribute, against which