Java Code Examples for org.eclipse.jgit.revwalk.RevWalk#parseCommit()

The following examples show how to use org.eclipse.jgit.revwalk.RevWalk#parseCommit() . You can vote up the ones you like or vote down the ones you don't like, and go to the original project or source file by following the links above each example. You may check out the related API usage on the sidebar.
Example 1
Source File: Git.java    From OpenSZZ-Cloud-Native with GNU General Public License v3.0 6 votes vote down vote up
/**
 * It gets commit object starting from a specific sha
 *
 */
public RevCommit getCommit(String sha, PrintWriter l){
 File  localRepo1 = new File(workingDirectory+"");
 //Repository repository = git.getRepository();
 RevCommit commit = null;
 try{
  org.eclipse.jgit.api.Git git = org.eclipse.jgit.api.Git.open(localRepo1);
  Repository repository = git.getRepository();
  RevWalk walk = new RevWalk( repository);
  ObjectId commitId = ObjectId.fromString( sha);
   commit = walk.parseCommit( commitId );
  //System.out.println(commit.getCommitTime());
} catch (Exception e) {
	e.printStackTrace();
	l.println((e));
	return null;
}
 return commit;
}
 
Example 2
Source File: GitManager.java    From scava with Eclipse Public License 2.0 6 votes vote down vote up
@Override
public Date getDateForRevision(VcsRepository repository, String revision) throws Exception {
	Git git = getGit((GitRepository)repository);
	
	Repository repo = git.getRepository();
	RevWalk walk = new RevWalk(repo);
	
	Iterator<RevCommit> iterator = git.log().call().iterator();
	walk.parseCommit(iterator.next());
	
	Date date = null;
	while (iterator.hasNext()) {
		RevCommit commit = iterator.next();
		if (commit.getId().getName().equals(revision)) {
			date = new Date(Long.valueOf(commit.getCommitTime())*1000); 
		}
	}
	
	repo.close();
	git.close();

	return date;
}
 
Example 3
Source File: JGitOperator.java    From verigreen with Apache License 2.0 6 votes vote down vote up
boolean isRefBehind( Ref behind, Ref tracking ) throws IOException {
  RevWalk walk = new RevWalk( _git.getRepository() );
  try {
    RevCommit behindCommit = walk.parseCommit( behind.getObjectId() );
    RevCommit trackingCommit = walk.parseCommit( tracking.getObjectId() );
    walk.setRevFilter( RevFilter.MERGE_BASE );
    walk.markStart( behindCommit );
    walk.markStart( trackingCommit );
    RevCommit mergeBase = walk.next();
    walk.reset();
    walk.setRevFilter( RevFilter.ALL );
    int aheadCount = RevWalkUtils.count( walk, behindCommit, mergeBase );
    int behindCount = RevWalkUtils.count( walk, trackingCommit, mergeBase );
    
    return behindCount > aheadCount ? true:false;
  } catch (Throwable e) {
         throw new RuntimeException(String.format(
                 "Failed to check if [%s] behind [%s]",
                 behind,
                 tracking), e);
     } 
  finally {
    walk.dispose();
  }
}
 
Example 4
Source File: GitUtils.java    From blueocean-plugin with MIT License 6 votes vote down vote up
@SuppressFBWarnings(value={"RCN_REDUNDANT_NULLCHECK_WOULD_HAVE_BEEN_A_NPE"}, justification="JDK11 produces different bytecode - https://github.com/spotbugs/spotbugs/issues/756")
static byte[] readFile(Repository repository, String ref, String filePath) {
    try (ObjectReader reader = repository.newObjectReader()) {
        ObjectId branchRef = repository.resolve(ref); // repository.exactRef(ref);
        if (branchRef != null) { // for empty repositories, branchRef may be null
            RevWalk revWalk = new RevWalk(repository);
            RevCommit commit = revWalk.parseCommit(branchRef);
            // and using commit's tree find the path
            RevTree tree = commit.getTree();
            TreeWalk treewalk = TreeWalk.forPath(reader, filePath, tree);
            if (treewalk != null) {
                // use the blob id to read the file's data
                return reader.open(treewalk.getObjectId(0)).getBytes();
            }
        }
    } catch (IOException ex) {
        throw new RuntimeException(ex);
    }
    return null;
}
 
Example 5
Source File: JGitOperator.java    From verigreen with Apache License 2.0 6 votes vote down vote up
@Override
public boolean isBranchContainsCommit(String branchName, String commitId) {
    
    boolean ans = false;
    RevWalk walk = new RevWalk(_repo);
    RevCommit commit;
    Ref ref;
    try {
        commit = walk.parseCommit(_repo.resolve(commitId + "^0"));
        ref = _repo.getRef(branchName);
        if (walk.isMergedInto(commit, walk.parseCommit(ref.getObjectId()))) {
            ans = true;
        }
        walk.dispose();
    } catch (Throwable e) {
        throw new RuntimeException(String.format(
                "Failed to check if commit [%s] is part of branch[%s]",
                commitId,
                branchName), e);
    }
    
    return ans;
}
 
Example 6
Source File: GitHistoryRefactoringMinerImpl.java    From RefactoringMiner with MIT License 6 votes vote down vote up
@Override
public Churn churnAtCommit(Repository repository, String commitId, RefactoringHandler handler) {
	GitService gitService = new GitServiceImpl();
	RevWalk walk = new RevWalk(repository);
	try {
		RevCommit commit = walk.parseCommit(repository.resolve(commitId));
		if (commit.getParentCount() > 0) {
			walk.parseCommit(commit.getParent(0));
			return gitService.churn(repository, commit);
		}
		else {
			logger.warn(String.format("Ignored revision %s because it has no parent", commitId));
		}
	} catch (MissingObjectException moe) {
		logger.warn(String.format("Ignored revision %s due to missing commit", commitId), moe);
	} catch (Exception e) {
		logger.warn(String.format("Ignored revision %s due to error", commitId), e);
		handler.handleException(commitId, e);
	} finally {
		walk.close();
		walk.dispose();
	}
	return null;
}
 
Example 7
Source File: JGitAPIImpl.java    From git-client-plugin with MIT License 5 votes vote down vote up
/**
 * Adds all matching refs as start commits.
 */
private void markRefs(RevWalk walk, Predicate<Ref> filter) throws IOException {
    try (Repository repo = getRepository()) {
        for (Ref r : repo.getAllRefs().values()) {
            if (filter.apply(r)) {
                RevCommit c = walk.parseCommit(r.getObjectId());
                walk.markStart(c);
            }
        }
    }
}
 
Example 8
Source File: GitRepoMetaData.java    From GitFx with Apache License 2.0 5 votes vote down vote up
private static AbstractTreeIterator prepareTreeParser(Repository repository, String objectId) throws IOException,
        MissingObjectException,
        IncorrectObjectTypeException {
    RevWalk walk = new RevWalk(repository) ;
    RevCommit commit = walk.parseCommit(ObjectId.fromString(objectId));
    RevTree tree = walk.parseTree(commit.getTree().getId());
    CanonicalTreeParser oldTreeParser = new CanonicalTreeParser();
    ObjectReader oldReader = repository.newObjectReader();
    oldTreeParser.reset(oldReader, tree.getId());
    walk.dispose();
    return oldTreeParser;
}
 
Example 9
Source File: SMAGit.java    From salesforce-migration-assistant with MIT License 5 votes vote down vote up
/**
 * Returns the blob information for the file at the specified path and commit
 *
 * @param repoItem
 * @param commit
 * @return
 * @throws Exception
 */
public byte[] getBlob(String repoItem, String commit) throws Exception
{
    byte[] data;

    String parentPath = repository.getDirectory().getParent();

    ObjectId commitId = repository.resolve(commit);

    ObjectReader reader = repository.newObjectReader();
    RevWalk revWalk = new RevWalk(reader);
    RevCommit revCommit = revWalk.parseCommit(commitId);
    RevTree tree = revCommit.getTree();
    TreeWalk treeWalk = TreeWalk.forPath(reader, repoItem, tree);

    if (treeWalk != null)
    {
        data = reader.open(treeWalk.getObjectId(0)).getBytes();
    }
    else
    {
        throw new IllegalStateException("Did not find expected file '" + repoItem + "'");
    }

    reader.release();

    return data;
}
 
Example 10
Source File: ListBranchesJob.java    From orion.server with Eclipse Public License 1.0 5 votes vote down vote up
private ObjectId getCommitObjectId(Repository db, ObjectId oid) throws MissingObjectException, IncorrectObjectTypeException, IOException {
	RevWalk walk = new RevWalk(db);
	try {
		return walk.parseCommit(oid);
	} finally {
		walk.close();
	}
}
 
Example 11
Source File: ListTagsJob.java    From orion.server with Eclipse Public License 1.0 5 votes vote down vote up
private ObjectId getCommitObjectId(Repository db, ObjectId oid) throws MissingObjectException, IncorrectObjectTypeException, IOException {
	RevWalk walk = new RevWalk(db);
	try {
		return walk.parseCommit(oid);
	} finally {
		walk.close();
	}
}
 
Example 12
Source File: Tags.java    From gradle-gitsemver with Apache License 2.0 5 votes vote down vote up
private static int getCountBetweenCommits(Repository repo,
                                          ObjectId headObjectId,
                                          ObjectId lastTagObjectId)
        throws MissingObjectException, IncorrectObjectTypeException, IOException {
    RevWalk walk = new RevWalk(repo);
    RevCommit startingPoint = walk.parseCommit(headObjectId);
    walk.markStart(startingPoint);
    RevCommit end = walk.lookupCommit(lastTagObjectId);
    walk.sort(RevSort.TOPO);
    int commitCount = 0;
    for (RevCommit c = walk.next(); nonNullOrEnd(end, c); c = walk.next()) {
        commitCount++;
    }
    return commitCount;
}
 
Example 13
Source File: GitManager.java    From scava with Eclipse Public License 2.0 5 votes vote down vote up
@Override
	public int compareVersions(VcsRepository repository, String versionOne, String versionTwo) throws Exception {
		Git git = getGit((GitRepository)repository);
		
		Repository repo = git.getRepository();
		RevWalk walk = new RevWalk(repo);
		
		Iterator<RevCommit> iterator = git.log().call().iterator();
		walk.parseCommit(iterator.next());
		
		List<String> revisions = new ArrayList<String>();
		
		// The commits are ordered latest first, so we want the last one.
		while(iterator.hasNext()) { 
			RevCommit commit = iterator.next();
			revisions.add(commit.getId().getName());
		}
		Integer oneIndex = revisions.indexOf(versionOne);
		Integer twoIndex = revisions.indexOf(versionTwo);
		
//		System.out.println(oneIndex);
//		System.out.println(twoIndex);
//		System.out.println(revisions);
		
		repo.close();
		git.close();
		
		// Because the revision list is reversed, we compare two to one instead of the other way around
		return twoIndex.compareTo(oneIndex);
	}
 
Example 14
Source File: GITStatusCrawler.java    From celerio with Apache License 2.0 5 votes vote down vote up
private static RevTree getTree(Repository repository) throws IOException {
    ObjectId lastCommitId = repository.resolve(Constants.HEAD);

    // a RevWalk allows to walk over commits based on some filtering
    RevWalk revWalk = new RevWalk(repository);
    RevCommit commit = revWalk.parseCommit(lastCommitId);

    // and using commit's tree find the path
    RevTree tree = commit.getTree();
    return tree;
}
 
Example 15
Source File: GitClient.java    From steady with Apache License 2.0 4 votes vote down vote up
/** {@inheritDoc} */
public Map<String, String> getCommitLogEntries( Set<String> _revs ) {
	final Map<String, String> hits = new HashMap<String, String>();
	if (!_revs.isEmpty() ) {
		try {
			Repository repository = this.getRepositoryFromPath( null );

			RevWalk walk = new RevWalk( repository );
			//walk.setRevFilter(RevFilter);
			RevCommit commit = null;

			Git git = new Git( repository );
			Iterable<RevCommit> logs = git.log().call();
			Iterator<RevCommit> i = logs.iterator();

			String commitId = null;
			String commitMsg = null;

			// iterate over all commits
			while ( i.hasNext() ) {
				commit = walk.parseCommit( i.next() );

				commitId = commit.getName();
				commitMsg = commit.getFullMessage();

				// iterate over all revisions to search for
				for ( String sid : _revs ) {
					if(sid.contains(":")){
						sid= sid.substring(0,sid.indexOf(":")-1);
					}
					if ( !sid.equals( "" ) && sid.equals( commitId ) ) {
						hits.put( commitId , commitMsg );
						continue;
					}
				}

			}
		}
		catch ( UnknownHostException e ) {
			GitClient.log.error( "Proxy issues?" );
			e.printStackTrace();
		}
		catch ( IOException ioe ) {
			GitClient.log.error( "Something went wrong with the I/O" );
			ioe.printStackTrace();
		}
		catch ( GitAPIException ge ) {
			GitClient.log.error( "Something went wrong with the GIT API" );
			ge.printStackTrace();
		}
	}
	return hits;
}
 
Example 16
Source File: ThemeServiceImpl.java    From halo with GNU General Public License v3.0 4 votes vote down vote up
private void pullFromGit(@NonNull ThemeProperty themeProperty) throws
    IOException, GitAPIException, URISyntaxException {
    Assert.notNull(themeProperty, "Theme property must not be null");

    // Get branch
    String branch = StringUtils.isBlank(themeProperty.getBranch()) ?
        DEFAULT_REMOTE_BRANCH : themeProperty.getBranch();

    Git git = null;

    try {
        git = GitUtils.openOrInit(Paths.get(themeProperty.getThemePath()));

        Repository repository = git.getRepository();

        RevWalk revWalk = new RevWalk(repository);

        Ref ref = repository.findRef(Constants.HEAD);

        Assert.notNull(ref, Constants.HEAD + " ref was not found!");

        RevCommit lastCommit = revWalk.parseCommit(ref.getObjectId());

        // Force to set remote name
        git.remoteRemove().setRemoteName(THEME_PROVIDER_REMOTE_NAME).call();
        RemoteConfig remoteConfig = git.remoteAdd()
            .setName(THEME_PROVIDER_REMOTE_NAME)
            .setUri(new URIish(themeProperty.getRepo()))
            .call();

        // Add all changes
        git.add()
            .addFilepattern(".")
            .call();
        // Commit the changes
        git.commit().setMessage("Commit by halo automatically").call();

        // Check out to specified branch
        if (!StringUtils.equalsIgnoreCase(branch, git.getRepository().getBranch())) {
            boolean present = git.branchList()
                .call()
                .stream()
                .map(Ref::getName)
                .anyMatch(name -> StringUtils.equalsIgnoreCase(name, branch));

            git.checkout()
                .setCreateBranch(true)
                .setForced(!present)
                .setName(branch)
                .call();
        }

        // Pull with rebasing
        PullResult pullResult = git.pull()
            .setRemote(remoteConfig.getName())
            .setRemoteBranchName(branch)
            .setRebase(true)
            .call();

        if (!pullResult.isSuccessful()) {
            log.debug("Rebase result: [{}]", pullResult.getRebaseResult());
            log.debug("Merge result: [{}]", pullResult.getMergeResult());

            throw new ThemeUpdateException("拉取失败!您与主题作者可能同时更改了同一个文件");
        }

        // updated successfully.
        ThemeProperty updatedThemeProperty = getProperty(Paths.get(themeProperty.getThemePath()));

        // Not support current halo version.
        if (StringUtils.isNotEmpty(updatedThemeProperty.getRequire()) && !VersionUtil.compareVersion(HaloConst.HALO_VERSION, updatedThemeProperty.getRequire())) {
            // reset theme version
            git.reset()
                .setMode(ResetCommand.ResetType.HARD)
                .setRef(lastCommit.getName())
                .call();
            throw new ThemeNotSupportException("新版本主题仅支持 Halo " + updatedThemeProperty.getRequire() + " 以上的版本");
        }
    } finally {
        GitUtils.closeQuietly(git);
    }

}
 
Example 17
Source File: CommitTest.java    From netbeans with Apache License 2.0 4 votes vote down vote up
public void testAmendCommit () throws Exception {
    repository.getConfig().setString("user", null, "name", "John");
    repository.getConfig().setString("user", null, "email", "[email protected]");
    repository.getConfig().save();

    File dir = new File(workDir, "testdir");
    File newOne = new File(dir, "test.txt");
    File another = new File(dir, "test2.txt");
    dir.mkdirs();
    write(newOne, "content1");
    write(another, "content2");

    GitClient client = getClient(workDir);
    client.add(new File[] { newOne, another }, NULL_PROGRESS_MONITOR);
    GitRevisionInfo info = client.commit(new File[] { newOne, another }, "initial commit", null, null, NULL_PROGRESS_MONITOR);
    Map<File, GitStatus> statuses = client.getStatus(new File[] { newOne, another }, NULL_PROGRESS_MONITOR);
    assertStatus(statuses, workDir, newOne, true, GitStatus.Status.STATUS_NORMAL, GitStatus.Status.STATUS_NORMAL, GitStatus.Status.STATUS_NORMAL, false);
    assertStatus(statuses, workDir, another, true, GitStatus.Status.STATUS_NORMAL, GitStatus.Status.STATUS_NORMAL, GitStatus.Status.STATUS_NORMAL, false);
    
    write(newOne, "modification1");
    write(another, "modification2");

    client.add(new File[] { newOne, another }, NULL_PROGRESS_MONITOR);
    GitRevisionInfo lastCommit = client.commit(new File[] { newOne }, "second commit", null, null, false, NULL_PROGRESS_MONITOR);
    statuses = client.getStatus(new File[] { workDir }, NULL_PROGRESS_MONITOR);
    assertStatus(statuses, workDir, newOne, true, GitStatus.Status.STATUS_NORMAL, GitStatus.Status.STATUS_NORMAL, GitStatus.Status.STATUS_NORMAL, false);
    assertStatus(statuses, workDir, another, true, GitStatus.Status.STATUS_MODIFIED, GitStatus.Status.STATUS_NORMAL, GitStatus.Status.STATUS_MODIFIED, false);
    Map<File, GitFileInfo> modifiedFiles = lastCommit.getModifiedFiles();
    assertTrue(modifiedFiles.get(newOne).getStatus().equals(Status.MODIFIED));
    assertNull(modifiedFiles.get(another));

    assertEquals(1, lastCommit.getParents().length);
    assertEquals(info.getRevision(), lastCommit.getParents()[0]);
    assertEquals(lastCommit.getRevision(), client.getBranches(false, NULL_PROGRESS_MONITOR).get("master").getId());
    
    Thread.sleep(1100);
    
    long time = lastCommit.getCommitTime();
    RevWalk walk = new RevWalk(repository);
    RevCommit originalCommit = walk.parseCommit(repository.resolve(lastCommit.getRevision()));
    lastCommit = client.commit(new File[] { newOne, another }, "second commit, modified message",
            new GitUser("user2", "user2.email"), new GitUser("committer2", "committer2.email"), true, NULL_PROGRESS_MONITOR);
    RevCommit amendedCommit = walk.parseCommit(repository.resolve(lastCommit.getRevision()));
    assertEquals("Commit time should not change after amend", time, lastCommit.getCommitTime());
    assertEquals(originalCommit.getAuthorIdent().getWhen(), amendedCommit.getAuthorIdent().getWhen());
    // commit time should not equal.
    assertFalse(originalCommit.getCommitterIdent().getWhen().equals(amendedCommit.getCommitterIdent().getWhen()));
    statuses = client.getStatus(new File[] { workDir }, NULL_PROGRESS_MONITOR);
    assertStatus(statuses, workDir, newOne, true, GitStatus.Status.STATUS_NORMAL, GitStatus.Status.STATUS_NORMAL, GitStatus.Status.STATUS_NORMAL, false);
    assertStatus(statuses, workDir, another, true, GitStatus.Status.STATUS_NORMAL, GitStatus.Status.STATUS_NORMAL, GitStatus.Status.STATUS_NORMAL, false);
    modifiedFiles = lastCommit.getModifiedFiles();
    assertTrue(modifiedFiles.get(newOne).getStatus().equals(Status.MODIFIED));
    assertTrue(modifiedFiles.get(another).getStatus().equals(Status.MODIFIED));

    assertEquals(1, lastCommit.getParents().length);
    assertEquals(info.getRevision(), lastCommit.getParents()[0]);
    assertEquals(lastCommit.getRevision(), client.getBranches(false, NULL_PROGRESS_MONITOR).get("master").getId());
}
 
Example 18
Source File: GitProctorCore.java    From proctor with Apache License 2.0 4 votes vote down vote up
@Override
public TestVersionResult determineVersions(final String fetchRevision) throws StoreException.ReadException {
    try {
        final RevWalk walk = new RevWalk(git.getRepository());
        final ObjectId commitId = ObjectId.fromString(fetchRevision);
        final RevCommit headTree = walk.parseCommit(commitId);
        final RevTree tree = headTree.getTree();

        // now use a TreeWalk to iterate over all files in the Tree recursively
        // you can set Filters to narrow down the results if needed
        final TreeWalk treeWalk = new TreeWalk(git.getRepository());
        treeWalk.addTree(tree);
        treeWalk.setFilter(AndTreeFilter
            .create(PathFilter.create(testDefinitionsDirectory), PathSuffixFilter.create("definition.json")));
        treeWalk.setRecursive(true);

        final List<TestVersionResult.Test> tests = Lists.newArrayList();
        while (treeWalk.next()) {
            final ObjectId id = treeWalk.getObjectId(0);
            // final RevTree revTree = walk.lookupTree(id);

            final String path = treeWalk.getPathString();
            final String[] pieces = path.split("/");
            final String testname = pieces[pieces.length - 2]; // tree / parent directory name

            // testname, blobid pair
            // note this is the blobid hash - not a commit hash
            // RevTree.id and RevBlob.id
            tests.add(new TestVersionResult.Test(testname, id.name()));
        }

        walk.dispose();
        return new TestVersionResult(
                tests,
                new Date(Long.valueOf(headTree.getCommitTime()) * 1000 /* convert seconds to milliseconds */),
                determineAuthorId(headTree),
                headTree.toObjectId().getName(),
                headTree.getFullMessage()
        );
    } catch (final IOException e) {
        throw new StoreException.ReadException(e);
    }
}
 
Example 19
Source File: CommitPatch.java    From repairnator with MIT License 4 votes vote down vote up
@Override
protected StepStatus businessExecute() {
    if (this.getConfig().isPush()) {
        if (this.commitType == CommitType.COMMIT_HUMAN_PATCH) {
            this.getLogger().info("Commit human patch...");
        } else {
            this.getLogger().info("Commit info from repair tools...");
        }

        super.setCommitType(this.commitType);

        try {
            Git git = Git.open(new File(this.getInspector().getRepoToPushLocalPath()));
            Ref oldHeadRef = git.getRepository().exactRef("HEAD");

            RevWalk revWalk = new RevWalk(git.getRepository());
            RevCommit headRev = revWalk.parseCommit(oldHeadRef.getObjectId());
            revWalk.dispose();

            StepStatus stepStatus = super.businessExecute();

            if (stepStatus.isSuccess()) {
                RevCommit commit = super.getCommit();
                this.getInspector().getGitHelper().computePatchStats(this.getInspector().getJobStatus(), git, headRev, commit);

                if (this.commitType == CommitType.COMMIT_HUMAN_PATCH) {
                    this.setPushState(PushState.PATCH_COMMITTED);
                } else {
                    this.setPushState(PushState.REPAIR_INFO_COMMITTED);
                }
            } else {
                if (this.commitType == CommitType.COMMIT_HUMAN_PATCH) {
                    this.setPushState(PushState.PATCH_NOT_COMMITTED);
                } else {
                    this.setPushState(PushState.REPAIR_INFO_NOT_COMMITTED);
                }
            }
            return stepStatus;
        } catch (IOException e) {
            this.addStepError("Error while opening the local git repository, maybe it has not been initialized.", e);
        }
        if (this.commitType == CommitType.COMMIT_HUMAN_PATCH) {
            this.setPushState(PushState.PATCH_NOT_COMMITTED);
        } else {
            this.setPushState(PushState.REPAIR_INFO_NOT_COMMITTED);
        }
        return StepStatus.buildSkipped(this,"Error while committing.");
    } else {
        this.getLogger().info("Repairnator is configured NOT to push. Step bypassed.");
        return StepStatus.buildSkipped(this);
    }
}
 
Example 20
Source File: LayoutHelper.java    From git-as-svn with GNU General Public License v2.0 4 votes vote down vote up
/**
 * Get new revisions list.
 *
 * @param repository    Repository.
 * @param loaded        Already loaded commits.
 * @param targetCommits Target commits.
 * @return Return new commits ordered by creation time. Parent revision always are before child.
 */
public static List<RevCommit> getNewRevisions(@NotNull Repository repository, @NotNull Set<? extends ObjectId> loaded, @NotNull Collection<? extends ObjectId> targetCommits) throws IOException {
  final Map<RevCommit, RevisionNode> revisionChilds = new HashMap<>();
  final Deque<RevCommit> revisionFirst = new ArrayDeque<>();
  final Deque<RevCommit> revisionQueue = new ArrayDeque<>();
  final RevWalk revWalk = new RevWalk(repository);
  for (ObjectId target : targetCommits) {
    if (!loaded.contains(target)) {
      final RevCommit revCommit = revWalk.parseCommit(target);
      revisionQueue.add(revCommit);
      revisionChilds.put(revCommit, new RevisionNode());
    }
  }
  while (!revisionQueue.isEmpty()) {
    final RevCommit commit = revWalk.parseCommit(revisionQueue.remove());
    if (commit == null || loaded.contains(commit.getId())) {
      revisionFirst.add(commit);
      continue;
    }
    if (commit.getParentCount() > 0) {
      final RevisionNode commitNode = revisionChilds.get(commit);
      for (RevCommit parent : commit.getParents()) {
        commitNode.parents.add(parent);
        revisionChilds.computeIfAbsent(parent, (id) -> {
          revisionQueue.add(parent);
          return new RevisionNode();
        }).childs.add(commit);
      }
    } else {
      revisionFirst.add(commit);
    }
  }
  final List<RevCommit> result = new ArrayList<>(revisionChilds.size());
  while (!revisionChilds.isEmpty()) {
    RevCommit firstCommit = null;
    RevisionNode firstNode = null;
    final Iterator<RevCommit> iterator = revisionFirst.iterator();
    while (iterator.hasNext()) {
      final RevCommit iterCommit = iterator.next();
      final RevisionNode iterNode = revisionChilds.get(iterCommit);
      if (iterNode == null) {
        iterator.remove();
        continue;
      }
      if (!iterNode.parents.isEmpty()) {
        iterator.remove();
      } else if (firstCommit == null || firstCommit.getCommitTime() > iterCommit.getCommitTime()) {
        firstNode = iterNode;
        firstCommit = iterCommit;
      }
    }
    if (firstNode == null || firstCommit == null) {
      throw new IllegalStateException();
    }
    revisionChilds.remove(firstCommit);
    result.add(firstCommit);
    for (RevCommit childId : firstNode.childs) {
      final RevisionNode childNode = revisionChilds.get(childId);
      if (childNode != null) {
        childNode.parents.remove(firstCommit);
        if (childNode.parents.isEmpty()) {
          revisionFirst.add(childId);
        }
      }
    }
  }
  return result;
}