Mercurial > jhg
diff src/org/tmatesoft/hg/core/HgLogCommand.java @ 215:41a778e3fd31
Issue 5: Facilities for progress and cancellation. More specific exceptions. Exceptions from callbacks as RuntimeException
author | Artem Tikhomirov <tikhomirov.artem@gmail.com> |
---|---|
date | Tue, 17 May 2011 00:56:54 +0200 |
parents | ffc5f6d59f7e |
children | 1792b37650f2 |
line wrap: on
line diff
--- a/src/org/tmatesoft/hg/core/HgLogCommand.java Mon May 16 21:10:36 2011 +0200 +++ b/src/org/tmatesoft/hg/core/HgLogCommand.java Tue May 17 00:56:54 2011 +0200 @@ -27,13 +27,14 @@ import java.util.Set; import java.util.TreeSet; +import org.tmatesoft.hg.repo.HgChangelog; import org.tmatesoft.hg.repo.HgChangelog.RawChangeset; -import org.tmatesoft.hg.repo.HgChangelog; import org.tmatesoft.hg.repo.HgDataFile; import org.tmatesoft.hg.repo.HgRepository; import org.tmatesoft.hg.util.ByteChannel; import org.tmatesoft.hg.util.CancelledException; import org.tmatesoft.hg.util.Path; +import org.tmatesoft.hg.util.ProgressSupport; /** @@ -48,7 +49,7 @@ * @author Artem Tikhomirov * @author TMate Software Ltd. */ -public class HgLogCommand implements HgChangelog.Inspector { +public class HgLogCommand extends HgAbstractCommand<HgLogCommand> implements HgChangelog.Inspector { private final HgRepository repo; private Set<String> users; @@ -164,9 +165,17 @@ /** * Similar to {@link #execute(org.tmatesoft.hg.repo.RawChangeset.Inspector)}, collects and return result as a list. */ - public List<HgChangeset> execute() throws HgException { + public List<HgChangeset> execute() throws HgDataStreamException { CollectHandler collector = new CollectHandler(); - execute(collector); + try { + execute(collector); + } catch (HgCallbackTargetException ex) { + // can't happen as long as our CollectHandler doesn't throw any exception + throw new HgBadStateException(ex.getCause()); + } catch (CancelledException ex) { + // can't happen, see above + throw new HgBadStateException(ex); + } return collector.getChanges(); } @@ -176,13 +185,14 @@ * @throws IllegalArgumentException when inspector argument is null * @throws ConcurrentModificationException if this log command instance is already running */ - public void execute(HgChangesetHandler handler) throws HgException { + public void execute(HgChangesetHandler handler) throws HgDataStreamException, HgCallbackTargetException, CancelledException { if (handler == null) { throw new IllegalArgumentException(); } if (csetTransform != null) { throw new ConcurrentModificationException(); } + final ProgressSupport progressHelper = getProgressSupport(handler); try { count = 0; HgChangelog.ParentWalker pw = parentHelper; // leave it uninitialized unless we iterate whole repo @@ -191,19 +201,27 @@ } // ChangesetTransfrom creates a blank PathPool, and #file(String, boolean) above // may utilize it as well. CommandContext? How about StatusCollector there as well? - csetTransform = new ChangesetTransformer(repo, handler, pw); + csetTransform = new ChangesetTransformer(repo, handler, pw, progressHelper, getCancelSupport(handler)); if (file == null) { + progressHelper.start(endRev - startRev + 1); repo.getChangelog().range(startRev, endRev, this); + csetTransform.checkFailure(); } else { + progressHelper.start(-1/*XXX enum const, or a dedicated method startUnspecified(). How about startAtLeast(int)?*/); HgDataFile fileNode = repo.getFileNode(file); fileNode.history(startRev, endRev, this); + csetTransform.checkFailure(); if (fileNode.isCopy()) { // even if we do not follow history, report file rename do { if (handler instanceof FileHistoryHandler) { FileRevision src = new FileRevision(repo, fileNode.getCopySourceRevision(), fileNode.getCopySourceName()); FileRevision dst = new FileRevision(repo, fileNode.getRevision(0), fileNode.getPath()); - ((FileHistoryHandler) handler).copy(src, dst); + try { + ((FileHistoryHandler) handler).copy(src, dst); + } catch (RuntimeException ex) { + throw new HgCallbackTargetException(ex).setRevision(fileNode.getCopySourceRevision()).setFileName(fileNode.getCopySourceName()); + } } if (limit > 0 && count >= limit) { // if limit reach, follow is useless. @@ -212,12 +230,14 @@ if (followHistory) { fileNode = repo.getFileNode(fileNode.getCopySourceName()); fileNode.history(this); + csetTransform.checkFailure(); } } while (followHistory && fileNode.isCopy()); } } } finally { csetTransform = null; + progressHelper.done(); } }