1 /*******************************************************************************
2 * Copyright (C) 2007, Robin Rosenberg <robin.rosenberg@dewire.com>
3 * Copyright (C) 2007, Shawn O. Pearce <spearce@spearce.org>
4 * Copyright (C) 2008, Google Inc.
6 * All rights reserved. This program and the accompanying materials
7 * are made available under the terms of the Eclipse Public License v1.0
8 * See LICENSE for the full license text, also available.
9 *******************************************************************************/
10 package org
.spearce
.egit
.core
.project
;
13 import java
.io
.IOException
;
14 import java
.util
.ArrayList
;
15 import java
.util
.Collection
;
17 import org
.eclipse
.core
.resources
.IContainer
;
18 import org
.eclipse
.core
.resources
.IProject
;
19 import org
.eclipse
.core
.resources
.IResource
;
20 import org
.eclipse
.core
.runtime
.CoreException
;
21 import org
.eclipse
.core
.runtime
.IPath
;
22 import org
.eclipse
.core
.runtime
.IProgressMonitor
;
23 import org
.eclipse
.core
.runtime
.NullProgressMonitor
;
24 import org
.eclipse
.core
.runtime
.SubProgressMonitor
;
25 import org
.spearce
.egit
.core
.CoreText
;
28 * Searches for existing Git repositories associated with a project's files.
30 * This finder algorithm searches a project's contained files to see if any of
31 * them are located within the working directory of an existing Git repository.
32 * The finder searches through linked resources, as the EGit core is capable of
33 * dealing with linked directories spanning multiple repositories in the same
37 * The search algorithm is exhaustive, it will find all matching repositories.
38 * For the project itself as well as for each linked container within the
39 * project it scans down the local filesystem trees to locate any Git
40 * repositories which may be found there. It also scans up the local filesystem
41 * tree to locate any Git repository which may be outside of Eclipse's
42 * workspace-view of the world, but which contains the project or a linked
43 * resource within the project. In short, if there is a Git repository
44 * associated, it finds it.
47 public class RepositoryFinder
{
48 private final IProject proj
;
50 private final Collection
<RepositoryMapping
> results
= new ArrayList
<RepositoryMapping
>();
53 * Create a new finder to locate Git repositories for a project.
56 * the project this new finder should locate the existing Git
59 public RepositoryFinder(final IProject p
) {
64 * Run the search algorithm.
67 * a progress monitor to report feedback to; may be null.
68 * @return all found {@link RepositoryMapping} instances associated with the
69 * project supplied to this instance's constructor.
70 * @throws CoreException
71 * Eclipse was unable to access its workspace, and threw up on
72 * us. We're throwing it back at the caller.
74 public Collection
<RepositoryMapping
> find(IProgressMonitor m
) throws CoreException
{
76 m
= new NullProgressMonitor();
82 private void find(final IProgressMonitor m
, final IContainer c
)
83 throws CoreException
{
84 final IPath loc
= c
.getLocation();
87 m
.subTask(CoreText
.RepositoryFinder_finding
);
90 final File fsLoc
= loc
.toFile();
91 final File ownCfg
= configFor(fsLoc
);
92 final IResource
[] children
;
94 if (ownCfg
.isFile()) {
95 register(c
, ownCfg
.getParentFile());
96 } else if (c
.isLinked() || c
instanceof IProject
) {
97 File p
= fsLoc
.getParentFile();
99 final File pCfg
= configFor(p
);
101 register(c
, pCfg
.getParentFile());
104 p
= p
.getParentFile();
109 children
= c
.members();
110 if (children
!= null && children
.length
> 0) {
111 final int scale
= 100 / children
.length
;
112 for (int k
= 0; k
< children
.length
; k
++) {
113 final IResource o
= children
[k
];
114 if (o
instanceof IContainer
115 && !o
.getName().equals(".git")) {
116 find(new SubProgressMonitor(m
, scale
),
129 private File
configFor(final File fsLoc
) {
130 return new File(new File(fsLoc
, ".git"), "config");
133 private void register(final IContainer c
, final File gitdir
) {
136 f
= gitdir
.getCanonicalFile();
137 } catch (IOException ioe
) {
138 f
= gitdir
.getAbsoluteFile();
140 results
.add(new RepositoryMapping(c
, f
));