comparison src/org/tmatesoft/hg/core/HgAnnotateCommand.java @ 569:c4fd1037bc6f

Support for copy/rename follow/no-follow for annotate
author Artem Tikhomirov <tikhomirov.artem@gmail.com>
date Wed, 10 Apr 2013 20:04:54 +0200
parents 32453f30de07
children 0890628ed51e
comparison
equal deleted inserted replaced
568:8ed4f4f4f0a6 569:c4fd1037bc6f
25 import org.tmatesoft.hg.internal.Experimental; 25 import org.tmatesoft.hg.internal.Experimental;
26 import org.tmatesoft.hg.internal.FileAnnotation; 26 import org.tmatesoft.hg.internal.FileAnnotation;
27 import org.tmatesoft.hg.internal.FileAnnotation.LineDescriptor; 27 import org.tmatesoft.hg.internal.FileAnnotation.LineDescriptor;
28 import org.tmatesoft.hg.internal.FileAnnotation.LineInspector; 28 import org.tmatesoft.hg.internal.FileAnnotation.LineInspector;
29 import org.tmatesoft.hg.repo.HgBlameFacility.BlockData; 29 import org.tmatesoft.hg.repo.HgBlameFacility.BlockData;
30 import org.tmatesoft.hg.repo.HgBlameFacility;
30 import org.tmatesoft.hg.repo.HgDataFile; 31 import org.tmatesoft.hg.repo.HgDataFile;
31 import org.tmatesoft.hg.repo.HgRepository; 32 import org.tmatesoft.hg.repo.HgRepository;
32 import org.tmatesoft.hg.util.CancelledException; 33 import org.tmatesoft.hg.util.CancelledException;
34 import org.tmatesoft.hg.util.Path;
33 35
34 /** 36 /**
35 * WORK IN PROGRESS. UNSTABLE API 37 * WORK IN PROGRESS. UNSTABLE API
36 * 38 *
37 * 'hg annotate' counterpart, report origin revision and file line-by-line 39 * 'hg annotate' counterpart, report origin revision and file line-by-line
42 @Experimental(reason="Work in progress. Unstable API") 44 @Experimental(reason="Work in progress. Unstable API")
43 public class HgAnnotateCommand extends HgAbstractCommand<HgAnnotateCommand> { 45 public class HgAnnotateCommand extends HgAbstractCommand<HgAnnotateCommand> {
44 46
45 private final HgRepository repo; 47 private final HgRepository repo;
46 private final CsetParamKeeper annotateRevision; 48 private final CsetParamKeeper annotateRevision;
47 private HgDataFile file; 49 private Path file;
50 private boolean followRename;
48 51
49 public HgAnnotateCommand(HgRepository hgRepo) { 52 public HgAnnotateCommand(HgRepository hgRepo) {
50 repo = hgRepo; 53 repo = hgRepo;
51 annotateRevision = new CsetParamKeeper(repo); 54 annotateRevision = new CsetParamKeeper(repo);
52 annotateRevision.doSet(HgRepository.TIP); 55 annotateRevision.doSet(HgRepository.TIP);
60 public HgAnnotateCommand changeset(int changelogRevIndex) throws HgBadArgumentException { 63 public HgAnnotateCommand changeset(int changelogRevIndex) throws HgBadArgumentException {
61 annotateRevision.set(changelogRevIndex); 64 annotateRevision.set(changelogRevIndex);
62 return this; 65 return this;
63 } 66 }
64 67
65 public HgAnnotateCommand file(HgDataFile fileNode) { 68 /**
66 file = fileNode; 69 * Select file to annotate, origin of renamed/copied file would be followed, too.
70 *
71 * @param filePath path relative to repository root
72 * @return <code>this</code> for convenience
73 */
74 public HgAnnotateCommand file(Path filePath) {
75 return file(filePath, true);
76 }
77
78 /**
79 * Select file to annotate.
80 *
81 * @param filePath path relative to repository root
82 * @param followCopyRename true to follow copies/renames.
83 * @return <code>this</code> for convenience
84 */
85 public HgAnnotateCommand file(Path filePath, boolean followCopyRename) {
86 file = filePath;
87 followRename = followCopyRename;
67 return this; 88 return this;
68 } 89 }
69 90
70 // TODO [1.1] set encoding and provide String line content from LineInfo 91 // TODO [1.1] set encoding and provide String line content from LineInfo
71 92
72 // FIXME [1.1] follow and no-follow parameters
73
74 public void execute(Inspector inspector) throws HgException, HgCallbackTargetException, CancelledException { 93 public void execute(Inspector inspector) throws HgException, HgCallbackTargetException, CancelledException {
75 if (inspector == null) { 94 if (inspector == null) {
76 throw new IllegalArgumentException(); 95 throw new IllegalArgumentException();
77 } 96 }
78 if (file == null) { 97 if (file == null) {
79 throw new HgBadArgumentException("Command needs file argument", null); 98 throw new HgBadArgumentException("Command needs file argument", null);
80 } 99 }
100 HgDataFile df = repo.getFileNode(file);
101 if (!df.exists()) {
102 return;
103 }
104 final int changesetStart = followRename ? 0 : df.getChangesetRevisionIndex(0);
81 Collector c = new Collector(); 105 Collector c = new Collector();
82 FileAnnotation.annotate(file, annotateRevision.get(), c); 106 FileAnnotation fa = new FileAnnotation(c);
107 HgBlameFacility af = new HgBlameFacility(df);
108 af.annotate(changesetStart, annotateRevision.get(), fa, HgIterateDirection.NewToOld);
83 LineImpl li = new LineImpl(); 109 LineImpl li = new LineImpl();
84 for (int i = 0; i < c.lineRevisions.length; i++) { 110 for (int i = 0; i < c.lineRevisions.length; i++) {
85 li.init(i+1, c.lineRevisions[i], c.line(i)); 111 li.init(i+1, c.lineRevisions[i], c.line(i));
86 inspector.next(li); 112 inspector.next(li);
87 } 113 }
90 /** 116 /**
91 * Callback to receive annotated lines 117 * Callback to receive annotated lines
92 */ 118 */
93 @Callback 119 @Callback
94 public interface Inspector { 120 public interface Inspector {
95 // start(FileDescriptor); 121 // start(FileDescriptor) throws HgCallbackTargetException;
96 void next(LineInfo lineInfo); 122 void next(LineInfo lineInfo) throws HgCallbackTargetException;
97 // end(FileDescriptor); 123 // end(FileDescriptor) throws HgCallbackTargetException;
98 } 124 }
99 125
100 /** 126 /**
101 * Describes a line reported through {@link Inspector#next(LineInfo)} 127 * Describes a line reported through {@link Inspector#next(LineInfo)}
102 * 128 *