changeset 582:90df078d6418

Delegate cancel to original support, do not implement CancelSupport ourselves
author Artem Tikhomirov <tikhomirov.artem@gmail.com>
date Mon, 22 Apr 2013 19:17:29 +0200
parents 0890628ed51e
children 47dfa0ec7e35
files src/org/tmatesoft/hg/core/HgAnnotateCommand.java src/org/tmatesoft/hg/core/HgStatusCommand.java src/org/tmatesoft/hg/internal/AdapterPlug.java
diffstat 3 files changed, 34 insertions(+), 34 deletions(-) [+]
line wrap: on
line diff
--- a/src/org/tmatesoft/hg/core/HgAnnotateCommand.java	Mon Apr 22 16:02:17 2013 +0200
+++ b/src/org/tmatesoft/hg/core/HgAnnotateCommand.java	Mon Apr 22 19:17:29 2013 +0200
@@ -108,11 +108,13 @@
 			return;
 		}
 		final int changesetStart = followRename ? 0 : df.getChangesetRevisionIndex(0);
-		Collector c = new Collector();
+		Collector c = new Collector(cancellation);
 		FileAnnotation fa = new FileAnnotation(c);
 		HgBlameFacility af = new HgBlameFacility(df);
 		af.annotate(changesetStart, annotateRevision.get(), fa, HgIterateDirection.NewToOld);
 		progress.worked(1);
+		c.throwIfCancelled();
+		cancellation.checkCancelled();
 		ProgressSupport.Sub subProgress = new ProgressSupport.Sub(progress, 1);
 		LineImpl li = new LineImpl();
 		for (int i = 0; i < c.lineRevisions.length; i++) {
@@ -150,11 +152,17 @@
 	private static class Collector implements LineInspector {
 		private int[] lineRevisions;
 		private byte[][] lines;
+		private final CancelSupport cancelSupport;
+		private CancelledException cancelEx;
 		
-		Collector() {
+		Collector(CancelSupport cancellation) {
+			cancelSupport = cancellation;
 		}
 		
 		public void line(int lineNumber, int changesetRevIndex, BlockData lineContent, LineDescriptor ld) {
+			if (cancelEx != null) {
+				return;
+			}
 			if (lineRevisions == null) {
 				lineRevisions = new int [ld.totalLines()];
 				Arrays.fill(lineRevisions, NO_REVISION);
@@ -162,11 +170,22 @@
 			}
 			lineRevisions[lineNumber] = changesetRevIndex;
 			lines[lineNumber] = lineContent.asArray();
+			try {
+				cancelSupport.checkCancelled();
+			} catch (CancelledException ex) {
+				cancelEx = ex;
+			}
 		}
 		
 		public byte[] line(int i) {
 			return lines[i];
 		}
+		
+		public void throwIfCancelled() throws CancelledException {
+			if (cancelEx != null) {
+				throw cancelEx;
+			}
+		}
 	}
 	
 	
--- a/src/org/tmatesoft/hg/core/HgStatusCommand.java	Mon Apr 22 16:02:17 2013 +0200
+++ b/src/org/tmatesoft/hg/core/HgStatusCommand.java	Mon Apr 22 19:17:29 2013 +0200
@@ -23,6 +23,7 @@
 import java.io.IOException;
 import java.util.ConcurrentModificationException;
 
+import org.tmatesoft.hg.internal.AdapterPlug;
 import org.tmatesoft.hg.internal.ChangelogHelper;
 import org.tmatesoft.hg.internal.Internals;
 import org.tmatesoft.hg.repo.HgRepository;
@@ -30,6 +31,7 @@
 import org.tmatesoft.hg.repo.HgStatusCollector;
 import org.tmatesoft.hg.repo.HgStatusInspector;
 import org.tmatesoft.hg.repo.HgWorkingCopyStatusCollector;
+import org.tmatesoft.hg.util.Adaptable;
 import org.tmatesoft.hg.util.CancelSupport;
 import org.tmatesoft.hg.util.CancelledException;
 import org.tmatesoft.hg.util.Path;
@@ -196,9 +198,6 @@
 					sc.walk(startRevision, endRevision, mediator);
 				}
 			}
-		} catch (CancelledException ex) {
-			// this is our exception, thrown from Mediator.
-			// next check shall throw original cause of the stop - either HgCallbackTargetException or original CancelledException
 			mediator.checkFailure();
 		} catch (HgRuntimeException ex) {
 			throw new HgLibraryFailureException(ex);
@@ -207,7 +206,7 @@
 		}
 	}
 
-	private class Mediator implements HgStatusInspector, CancelSupport {
+	private class Mediator extends AdapterPlug implements HgStatusInspector, Adaptable {
 		boolean needModified;
 		boolean needAdded;
 		boolean needRemoved;
@@ -218,63 +217,43 @@
 		boolean needCopies;
 		HgStatusHandler handler;
 		private ChangelogHelper logHelper;
-		private CancelSupport handlerCancelSupport;
 		private HgCallbackTargetException failure;
-		private CancelledException cancellation;
 
 		Mediator() {
 		}
 		
 		public void start(HgStatusHandler h, CancelSupport hcs, ChangelogHelper changelogHelper) {
 			handler = h;
-			handlerCancelSupport = hcs;
+			super.attachAdapter(CancelSupport.class, hcs);
 			logHelper = changelogHelper;
 		}
 
 		public void done() {
 			handler = null;
-			handlerCancelSupport = null;
+			super.detachAdapter(CancelSupport.class);
 			logHelper = null;
 			failure = null;
-			cancellation = null;
 		}
 		
 		public boolean busy() {
 			return handler != null;
 		}
 
-		// XXX copy from ChangesetTransformer. Perhaps, can share the code?
-		public void checkFailure() throws HgCallbackTargetException, CancelledException {
+		// XXX similar code in ChangesetTransformer
+		public void checkFailure() throws HgCallbackTargetException {
 			// do not forget to clear exceptions for reuse of this instance 
 			if (failure != null) {
 				HgCallbackTargetException toThrow = failure;
 				failure = null; 
 				throw toThrow;
 			}
-			if (cancellation != null) {
-				CancelledException toThrow = cancellation;
-				cancellation = null;
-				throw toThrow;
-			}
-		}
-
-		// XXX copy from ChangesetTransformer. code sharing note above applies
-		public void checkCancelled() throws CancelledException {
-			if (failure != null || cancellation != null) {
-				// stop status iteration. Our exception is for the purposes of cancellation only,
-				// the one we have stored (this.cancellation) is for user
-				throw new CancelledException(); 
-			}
 		}
 
 		private void dispatch(HgStatus s) {
 			try {
 				handler.status(s);
-				handlerCancelSupport.checkCancelled();
 			} catch (HgCallbackTargetException ex) {
 				failure = ex;
-			} catch (CancelledException ex) {
-				cancellation = ex;
 			}
 		}
 
@@ -323,11 +302,8 @@
 		public void invalid(Path fname, Exception err) {
 			try {
 				handler.error(fname, new Outcome(Outcome.Kind.Failure, "Failed to get file status", err));
-				handlerCancelSupport.checkCancelled();
 			} catch (HgCallbackTargetException ex) {
 				failure = ex;
-			} catch (CancelledException ex) {
-				cancellation = ex;
 			}
 		}
 	}
--- a/src/org/tmatesoft/hg/internal/AdapterPlug.java	Mon Apr 22 16:02:17 2013 +0200
+++ b/src/org/tmatesoft/hg/internal/AdapterPlug.java	Mon Apr 22 19:17:29 2013 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2012 TMate Software Ltd
+ * Copyright (c) 2012-2013 TMate Software Ltd
  *  
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License as published by
@@ -37,6 +37,11 @@
 	public <T> void attachAdapter(Class<T> adapterClass, T instance) {
 		adapters.put(adapterClass, instance);
 	}
+	
+	@SuppressWarnings("unchecked")
+	public <T> T detachAdapter(Class<T> adapterClass) {
+		return (T) adapters.remove(adapterClass);
+	}
 
 	public <T> T getAdapter(Class<T> adapterClass) {
 		Object instance = adapters.get(adapterClass);