comparison src/org/tmatesoft/hg/repo/HgManifest.java @ 367:2fadf8695f8a

Use 'revision index' instead of the vague 'local revision number' concept in the API
author Artem Tikhomirov <tikhomirov.artem@gmail.com>
date Fri, 16 Dec 2011 15:37:27 +0100
parents 189dc6dc1c3e
children 8107b95f4280
comparison
equal deleted inserted replaced
366:189dc6dc1c3e 367:2fadf8695f8a
119 119
120 /** 120 /**
121 * "Sparse" iteration of the manifest 121 * "Sparse" iteration of the manifest
122 * 122 *
123 * @param inspector 123 * @param inspector
124 * @param localRevisions local changeset revisions to visit 124 * @param revisionIndexes local indexes of changesets to visit
125 */ 125 */
126 public void walk(final Inspector inspector, int... localRevisions) throws HgInvalidControlFileException{ 126 public void walk(final Inspector inspector, int... revisionIndexes) throws HgInvalidControlFileException{
127 if (inspector == null || localRevisions == null) { 127 if (inspector == null || revisionIndexes == null) {
128 throw new IllegalArgumentException(); 128 throw new IllegalArgumentException();
129 } 129 }
130 int[] localManifestRevs = toLocalManifestRevisions(localRevisions); 130 int[] localManifestRevs = toManifestRevisionIndexes(revisionIndexes);
131 content.iterate(localManifestRevs, true, new ManifestParser(inspector)); 131 content.iterate(localManifestRevs, true, new ManifestParser(inspector));
132 } 132 }
133 133
134 // manifest revision number that corresponds to the given changeset 134 // manifest revision number that corresponds to the given changeset
135 /*package-local*/ int fromChangelog(int revisionNumber) throws HgInvalidControlFileException { 135 /*package-local*/ int fromChangelog(int revisionNumber) throws HgInvalidControlFileException {
136 if (HgInternals.wrongLocalRevision(revisionNumber)) { 136 if (HgInternals.wrongRevisionIndex(revisionNumber)) {
137 throw new IllegalArgumentException(String.valueOf(revisionNumber)); 137 throw new IllegalArgumentException(String.valueOf(revisionNumber));
138 } 138 }
139 if (revisionNumber == HgRepository.WORKING_COPY || revisionNumber == HgRepository.BAD_REVISION) { 139 if (revisionNumber == HgRepository.WORKING_COPY || revisionNumber == HgRepository.BAD_REVISION) {
140 throw new IllegalArgumentException("Can't use constants like WORKING_COPY or BAD_REVISION"); 140 throw new IllegalArgumentException("Can't use constants like WORKING_COPY or BAD_REVISION");
141 } 141 }
148 } 148 }
149 149
150 /** 150 /**
151 * Extracts file revision as it was known at the time of given changeset. 151 * Extracts file revision as it was known at the time of given changeset.
152 * 152 *
153 * @param localChangelogRevision local changeset index 153 * @param changelogRevisionIndex local changeset index
154 * @param file path to file in question 154 * @param file path to file in question
155 * @return file revision or <code>null</code> if manifest at specified revision doesn't list such file 155 * @return file revision or <code>null</code> if manifest at specified revision doesn't list such file
156 */ 156 */
157 @Experimental(reason="Perhaps, HgDataFile shall own this method, or get a delegate?") 157 @Experimental(reason="Perhaps, HgDataFile shall own this method, or get a delegate?")
158 public Nodeid getFileRevision(int localChangelogRevision, final Path file) throws HgInvalidControlFileException{ 158 public Nodeid getFileRevision(int changelogRevisionIndex, final Path file) throws HgInvalidControlFileException{
159 return getFileRevisions(file, localChangelogRevision).get(localChangelogRevision); 159 return getFileRevisions(file, changelogRevisionIndex).get(changelogRevisionIndex);
160 } 160 }
161 161
162 // XXX package-local, IntMap, and HgDataFile getFileRevisionAt(int... localChangelogRevisions) 162 // XXX package-local, IntMap, and HgDataFile getFileRevisionAt(int... localChangelogRevisions)
163 @Experimental(reason="@see #getFileRevision") 163 @Experimental(reason="@see #getFileRevision")
164 public Map<Integer, Nodeid> getFileRevisions(final Path file, int... localChangelogRevisions) throws HgInvalidControlFileException{ 164 public Map<Integer, Nodeid> getFileRevisions(final Path file, int... changelogRevisionIndexes) throws HgInvalidControlFileException{
165 // FIXME need tests 165 // FIXME need tests
166 int[] localManifestRevisions = toLocalManifestRevisions(localChangelogRevisions); 166 int[] manifestRevisionIndexes = toManifestRevisionIndexes(changelogRevisionIndexes);
167 final HashMap<Integer,Nodeid> rv = new HashMap<Integer, Nodeid>(localChangelogRevisions.length); 167 final HashMap<Integer,Nodeid> rv = new HashMap<Integer, Nodeid>(changelogRevisionIndexes.length);
168 content.iterate(localManifestRevisions, true, new RevlogStream.Inspector() { 168 content.iterate(manifestRevisionIndexes, true, new RevlogStream.Inspector() {
169 169
170 public void next(int revisionNumber, int actualLen, int baseRevision, int linkRevision, int parent1Revision, int parent2Revision, byte[] nodeid, DataAccess data) throws HgException { 170 public void next(int revisionNumber, int actualLen, int baseRevision, int linkRevision, int parent1Revision, int parent2Revision, byte[] nodeid, DataAccess data) throws HgException {
171 ByteArrayOutputStream bos = new ByteArrayOutputStream(); 171 ByteArrayOutputStream bos = new ByteArrayOutputStream();
172 try { 172 try {
173 byte b; 173 byte b;
197 }); 197 });
198 return rv; 198 return rv;
199 } 199 }
200 200
201 201
202 private int[] toLocalManifestRevisions(int[] localChangelogRevisions) throws HgInvalidControlFileException { 202 private int[] toManifestRevisionIndexes(int[] changelogRevisionIndexes) throws HgInvalidControlFileException {
203 int[] localManifestRevs = new int[localChangelogRevisions.length]; 203 int[] localManifestRevs = new int[changelogRevisionIndexes.length];
204 boolean needsSort = false; 204 boolean needsSort = false;
205 for (int i = 0; i < localChangelogRevisions.length; i++) { 205 for (int i = 0; i < changelogRevisionIndexes.length; i++) {
206 final int manifestLocalRev = fromChangelog(localChangelogRevisions[i]); 206 final int manifestRevisionIndex = fromChangelog(changelogRevisionIndexes[i]);
207 localManifestRevs[i] = manifestLocalRev; 207 localManifestRevs[i] = manifestRevisionIndex;
208 if (i > 0 && localManifestRevs[i-1] > manifestLocalRev) { 208 if (i > 0 && localManifestRevs[i-1] > manifestRevisionIndex) {
209 needsSort = true; 209 needsSort = true;
210 } 210 }
211 } 211 }
212 if (needsSort) { 212 if (needsSort) {
213 Arrays.sort(localManifestRevs); 213 Arrays.sort(localManifestRevs);
474 for (int u : undefinedChangelogRevision) { 474 for (int u : undefinedChangelogRevision) {
475 try { 475 try {
476 Nodeid manifest = repo.getChangelog().range(u, u).get(0).manifest(); 476 Nodeid manifest = repo.getChangelog().range(u, u).get(0).manifest();
477 // FIXME calculate those missing effectively (e.g. cache and sort nodeids to speed lookup 477 // FIXME calculate those missing effectively (e.g. cache and sort nodeids to speed lookup
478 // right away in the #next (may refactor ParentWalker's sequential and sorted into dedicated helper and reuse here) 478 // right away in the #next (may refactor ParentWalker's sequential and sorted into dedicated helper and reuse here)
479 changelog2manifest[u] = repo.getManifest().getLocalRevision(manifest); 479 changelog2manifest[u] = repo.getManifest().getRevisionIndex(manifest);
480 } catch (HgInvalidControlFileException ex) { 480 } catch (HgInvalidControlFileException ex) {
481 // FIXME need to propagate the error up to client 481 // FIXME need to propagate the error up to client
482 repo.getContext().getLog().error(getClass(), ex, null); 482 repo.getContext().getLog().error(getClass(), ex, null);
483 } 483 }
484 } 484 }