Mercurial > hg4j
comparison src/org/tmatesoft/hg/core/HgCheckoutCommand.java @ 563:ca56a36c2eea
HgCheckoutCommand: clean parameter, discard changes in WD, test for clean checkout
author | Artem Tikhomirov <tikhomirov.artem@gmail.com> |
---|---|
date | Thu, 28 Feb 2013 16:34:33 +0100 |
parents | 47b7bedf0569 |
children | 78a9e26e670d |
comparison
equal
deleted
inserted
replaced
562:6fbca6506bb5 | 563:ca56a36c2eea |
---|---|
29 import org.tmatesoft.hg.internal.EncodingHelper; | 29 import org.tmatesoft.hg.internal.EncodingHelper; |
30 import org.tmatesoft.hg.internal.Experimental; | 30 import org.tmatesoft.hg.internal.Experimental; |
31 import org.tmatesoft.hg.internal.Internals; | 31 import org.tmatesoft.hg.internal.Internals; |
32 import org.tmatesoft.hg.internal.WorkingDirFileWriter; | 32 import org.tmatesoft.hg.internal.WorkingDirFileWriter; |
33 import org.tmatesoft.hg.repo.HgDataFile; | 33 import org.tmatesoft.hg.repo.HgDataFile; |
34 import org.tmatesoft.hg.repo.HgDirstate; | |
35 import org.tmatesoft.hg.repo.HgInternals; | |
34 import org.tmatesoft.hg.repo.HgInvalidRevisionException; | 36 import org.tmatesoft.hg.repo.HgInvalidRevisionException; |
35 import org.tmatesoft.hg.repo.HgManifest; | 37 import org.tmatesoft.hg.repo.HgManifest; |
38 import org.tmatesoft.hg.repo.HgDirstate.EntryKind; | |
39 import org.tmatesoft.hg.repo.HgDirstate.Record; | |
36 import org.tmatesoft.hg.repo.HgManifest.Flags; | 40 import org.tmatesoft.hg.repo.HgManifest.Flags; |
37 import org.tmatesoft.hg.repo.HgRepository; | 41 import org.tmatesoft.hg.repo.HgRepository; |
38 import org.tmatesoft.hg.repo.HgRuntimeException; | 42 import org.tmatesoft.hg.repo.HgRuntimeException; |
39 import org.tmatesoft.hg.util.CancelledException; | 43 import org.tmatesoft.hg.util.CancelledException; |
40 import org.tmatesoft.hg.util.Path; | 44 import org.tmatesoft.hg.util.Path; |
52 @Experimental(reason="Work in progress") | 56 @Experimental(reason="Work in progress") |
53 public class HgCheckoutCommand extends HgAbstractCommand<HgCheckoutCommand>{ | 57 public class HgCheckoutCommand extends HgAbstractCommand<HgCheckoutCommand>{ |
54 | 58 |
55 private final HgRepository repo; | 59 private final HgRepository repo; |
56 private int revisionToCheckout = HgRepository.BAD_REVISION; | 60 private int revisionToCheckout = HgRepository.BAD_REVISION; |
61 private boolean cleanCheckout; | |
57 | 62 |
58 public HgCheckoutCommand(HgRepository hgRepo) { | 63 public HgCheckoutCommand(HgRepository hgRepo) { |
59 repo = hgRepo; | 64 repo = hgRepo; |
65 } | |
66 | |
67 /** | |
68 * Whether to discard all uncommited changes prior to check-out. | |
69 * | |
70 * NOTE, at the moment, only clean checkout is supported! | |
71 * | |
72 * @param clean <code>true</code> to discard any change | |
73 * @return <code>this</code> for convenience | |
74 */ | |
75 public HgCheckoutCommand clean(boolean clean) { | |
76 cleanCheckout = clean; | |
77 return this; | |
60 } | 78 } |
61 | 79 |
62 /** | 80 /** |
63 * Select revision to check out | 81 * Select revision to check out |
64 * | 82 * |
75 } | 93 } |
76 | 94 |
77 /** | 95 /** |
78 * Select revision to check out using local revision index | 96 * Select revision to check out using local revision index |
79 * | 97 * |
80 * @param changesetIndex local revision index | 98 * @param changesetIndex local revision index, or {@link HgRepository#TIP} |
81 * @return <code>this</code> for convenience | 99 * @return <code>this</code> for convenience |
82 * @throws HgBadArgumentException if failed to find supplied changeset | 100 * @throws HgBadArgumentException if failed to find supplied changeset |
83 */ | 101 */ |
84 public HgCheckoutCommand changeset(int changesetIndex) throws HgBadArgumentException { | 102 public HgCheckoutCommand changeset(int changesetIndex) throws HgBadArgumentException { |
85 int lastCsetIndex = repo.getChangelog().getLastRevision(); | 103 int lastCsetIndex = repo.getChangelog().getLastRevision(); |
104 if (changesetIndex == HgRepository.TIP) { | |
105 changesetIndex = lastCsetIndex; | |
106 } | |
86 if (changesetIndex < 0 || changesetIndex > lastCsetIndex) { | 107 if (changesetIndex < 0 || changesetIndex > lastCsetIndex) { |
87 throw new HgBadArgumentException(String.format("Bad revision index %d, value from [0..%d] expected", changesetIndex, lastCsetIndex), null).setRevisionIndex(changesetIndex); | 108 throw new HgBadArgumentException(String.format("Bad revision index %d, value from [0..%d] expected", changesetIndex, lastCsetIndex), null).setRevisionIndex(changesetIndex); |
88 } | 109 } |
89 revisionToCheckout = changesetIndex; | 110 revisionToCheckout = changesetIndex; |
90 return this; | 111 return this; |
97 * @throws CancelledException | 118 * @throws CancelledException |
98 */ | 119 */ |
99 public void execute() throws HgException, CancelledException { | 120 public void execute() throws HgException, CancelledException { |
100 try { | 121 try { |
101 Internals internalRepo = Internals.getInstance(repo); | 122 Internals internalRepo = Internals.getInstance(repo); |
102 // FIXME remove tracked files from wd (perhaps, just forget 'Added'?) | 123 if (cleanCheckout) { |
103 // TODO | 124 // remove tracked files from wd (perhaps, just forget 'Added'?) |
125 // for now, just delete each and every tracked file | |
126 // TODO WorkingCopy container with getFile(HgDataFile/Path) to access files in WD | |
127 HgDirstate dirstate = new HgInternals(repo).getDirstate(); | |
128 dirstate.walk(new HgDirstate.Inspector() { | |
129 | |
130 public boolean next(EntryKind kind, Record entry) { | |
131 File f = new File(repo.getWorkingDir(), entry.name().toString()); | |
132 if (f.exists()) { | |
133 f.delete(); | |
134 } | |
135 return true; | |
136 } | |
137 }); | |
138 } else { | |
139 throw new HgBadArgumentException("Sorry, only clean checkout is supported now, use #clean(true)", null); | |
140 } | |
104 final DirstateBuilder dirstateBuilder = new DirstateBuilder(internalRepo); | 141 final DirstateBuilder dirstateBuilder = new DirstateBuilder(internalRepo); |
105 final CheckoutWorker worker = new CheckoutWorker(internalRepo); | 142 final CheckoutWorker worker = new CheckoutWorker(internalRepo); |
106 HgManifest.Inspector insp = new HgManifest.Inspector() { | 143 HgManifest.Inspector insp = new HgManifest.Inspector() { |
107 | 144 |
108 public boolean next(Nodeid nid, Path fname, Flags flags) { | 145 public boolean next(Nodeid nid, Path fname, Flags flags) { |
125 dirstateBuilder.parents(repo.getChangelog().getRevision(revisionToCheckout), null); | 162 dirstateBuilder.parents(repo.getChangelog().getRevision(revisionToCheckout), null); |
126 repo.getManifest().walk(revisionToCheckout, revisionToCheckout, insp); | 163 repo.getManifest().walk(revisionToCheckout, revisionToCheckout, insp); |
127 worker.checkFailed(); | 164 worker.checkFailed(); |
128 File dirstateFile = internalRepo.getRepositoryFile(Dirstate); | 165 File dirstateFile = internalRepo.getRepositoryFile(Dirstate); |
129 try { | 166 try { |
130 FileChannel dirstate = new FileOutputStream(dirstateFile).getChannel(); | 167 FileChannel dirstateFileChannel = new FileOutputStream(dirstateFile).getChannel(); |
131 dirstateBuilder.serialize(dirstate); | 168 dirstateBuilder.serialize(dirstateFileChannel); |
132 dirstate.close(); | 169 dirstateFileChannel.close(); |
133 } catch (IOException ex) { | 170 } catch (IOException ex) { |
134 throw new HgIOException("Can't write down new directory state", ex, dirstateFile); | 171 throw new HgIOException("Can't write down new directory state", ex, dirstateFile); |
135 } | 172 } |
136 String branchName = repo.getChangelog().range(revisionToCheckout, revisionToCheckout).get(0).branch(); | 173 String branchName = repo.getChangelog().range(revisionToCheckout, revisionToCheckout).get(0).branch(); |
137 assert branchName != null; | 174 assert branchName != null; |