git/list[1] front-page[2] threads[3] people[4] search[5] about
 

Re: [JGIT PATCH v2 07/24] Added findWorkTree method to Repository class.

From
Shawn O. Pearce <spearce@spearce.org>
Date
May 13, 2008, 00:24 UTC
Message-ID
<20080513002409.GC29038@spearce.org>
In-Reply-To
<1210623222-24908-8-git-send-email-florianskarten@web.de>
Florian Koeberle <florianskarten@web.de> wrote:
Show 18 quoted lines
> @@ -1242,4 +1247,89 @@ public class Repository {
>  		}
>  	}
>  
> +	/**
> +	 * Find the git repository for the current working directory.
> +	 * 
> +	 * @return a {@link Repository}.
> +	 * @throws IOException
> +	 *             if the system property user.dir isn't set or if it is
> +	 *             invalid.
> +	 */
> +	public static WorkTree findWorkTree() throws IOException {
> +		final String workingDirectoryPath = System.getProperty("user.dir");
> +		if (workingDirectoryPath == null) {
> +			throw new IOException("unable to get working directory");
> +		}
> +		final File workingDirectoryFile = new File(workingDirectoryPath);
Isn't `final File workingDirectoryFile = new File(".")` easier to write?

And if we are going to throw a checked exception because we cannot find a repository in ".", maybe that should be a new checked exception, like NoGitRepositoryFoundException?

> +	/**
> +	 * Checks if a path is a valid git repository. Works similar like the method
> +	 * is_git_directory from the original setup.c file.

References to C Git aren't common in jgit source code. We aren't a reference implementation, but that hasn't stopped people from finding out code a sane description of "how things work". I'd rather not describe our code in terms of C Git's code; especially what happens if C Git refactors one day, this reference might no longer make sense. Anyone coming back here to improve jgit or use this method will be confused about what we are doing.

Show 9 quoted lines
> +	 * 
> +	 * @param directory
> +	 *            the path which should be checked.
> +	 * @return true if the path is a valid git repository.
> +	 */
> +	private static boolean isRepository(File directory) {
> +		if (!directory.isDirectory()) {
> +			return false;
> +		}

We usually omit { and } on simple conditions like this. Its a coding pattern we stole from C Git, which stole it from the Linux kernel.

Show 18 quoted lines
> +	private static WorkTree findWorkTree(File directory) throws IOException {
> +		File currentDirectory = directory.getAbsoluteFile();
> +		while (true) {
> +			final File commonGitDirectory = new File(directory,
> +					REPOSITORY_DIRECTORY_NAME);
> +			if (isRepository(commonGitDirectory)) {
> +				return new WorkTree(currentDirectory, new Repository(
> +						commonGitDirectory));
> +			}
> +
> +			if (isRepository(currentDirectory)) {
> +				return new WorkTree(null, new Repository(currentDirectory));
> +			}
> +			currentDirectory = currentDirectory.getParentFile();
> +			if (currentDirectory == null) {
> +				throw new IOException("Can't find git repository");
> +			}
> +		}

Would this perhaps be a shorter, easier to follow variant of the same algorithm?

	directory = directory.getAbsoluteFile();
	File workdir = directory;
	while (workdir != null) {
		final File gitdir = new File(workdir, REPOSITORY_DIRECTORY_NAME);
		if (isRepository(gitdir))
			return new WorkTree(workdir, new Repository(gitdir));
		if (isRepository(workdir))
			return new WorkTree(null, new Repository(workdir));
		workdir = workdir.getParentFile();
	}
	throw new NoGitRepositoryFoundException("No repository for " + directory);

I often do write infinite loops with "for (;;) {", but usually its because the loop condition is based on an iterator-style method returning null at the end and I want to store the result in a local variable scoped to only the body of the loop:

	for (;;) {
		final RevCommit next = walk.next();
		if (next == null)
			break;
		// use next somehow
	}

Otherwise I try to avoid infinite loops in my final version of something. Though on a recent job interview the interviewer noticed I tend to start writing code with an infinite loop, then go back and correct the loop condition before saying "done". ;-)

-- 
Shawn.
Previous: Florian KoeberleNext: Florian Köberle
Message 14 of 46 in “Implementation of a file tree iteration using ignore rules.”
  1. 0/24 Implementation of a file tree iteration using ignore rules.Florian Koeberle, May 12, 2008
  2. 01/24 Start of an implementation of a git like command line tool.Florian Koeberle, May 12, 2008
  3. 02/24 Formatted Repository class.Florian Koeberle, May 12, 2008
  4. 03/24 Formatted Constats class.Florian Koeberle, May 12, 2008
  5. 04/24 Added path related constats to Constats class.Florian Koeberle, May 12, 2008
  6. Shawn O. PearceMay 12, 2008
  7. Florian KöberleMay 23, 2008
  8. 05/24 Added WorkTree class which can be constructed over Repository.Florian Koeberle, May 12, 2008
  9. Shawn O. PearceMay 13, 2008
  10. Robin RosenbergMay 13, 2008
  11. Shawn O. PearceMay 14, 2008
  12. 06/24 Added a "init" command to the git like command line tool.Florian Koeberle, May 12, 2008
  13. 07/24 Added findWorkTree method to Repository class.Florian Koeberle, May 12, 2008
  14. Shawn O. PearceMay 13, 2008
  15. Florian KöberleMay 23, 2008
  16. Miklos VajnaMay 23, 2008
  17. Shawn O. PearceMay 23, 2008
  18. Robin RosenbergMay 23, 2008
  19. 08/24 Added the interface FilePattern.Florian Koeberle, May 12, 2008
  20. 09/24 Added the class Rule.Florian Koeberle, May 12, 2008
  21. 10/24 Added the iterface Rules.Florian Koeberle, May 12, 2008
  22. 11/24 Added the class FNMatchPattern.Florian Koeberle, May 12, 2008
  23. Shawn O. PearceMay 13, 2008
  24. 12/24 Added the class GlobalFilePatternFlorian Koeberle, May 12, 2008
  25. 13/24 Added the class ComplexFilePattern.Florian Koeberle, May 12, 2008
  26. 14/24 Added the class IgnoreRuleListFactory.Florian Koeberle, May 12, 2008
  27. Shawn O. PearceMay 13, 2008
  28. Florian KöberleMay 13, 2008
  29. Shawn O. PearceMay 14, 2008
  30. 15/24 Added a Rules interface implementation and a factory for it.Florian Koeberle, May 12, 2008
  31. 16/24 Added test class OverallIgnoreRulestest.Florian Koeberle, May 12, 2008
  32. 17/24 Added the class TreeFilePattern.Florian Koeberle, May 12, 2008
  33. Shawn O. PearceMay 13, 2008
  34. 18/24 Added InvalidPatternException and PathNotInProjectDirectoryExceptionFlorian Koeberle, May 12, 2008
  35. 19/24 Added the class AddRuleListFactory.Florian Koeberle, May 12, 2008
  36. Shawn O. PearceMay 13, 2008
  37. Florian KöberleMay 13, 2008
  38. Robin RosenbergMay 13, 2008
  39. Shawn O. PearceMay 14, 2008
  40. 20/24 Added class AddRulesFactory.Florian Koeberle, May 12, 2008
  41. 21/24 Added the class LightFileTreeIterator and a test for it.Florian Koeberle, May 12, 2008
  42. Paolo BonziniMay 14, 2008
  43. 22/24 Added class LightFileTreeIterable.Florian Koeberle, May 12, 2008
  44. 23/24 Added the test class AddCommandIterationTest.Florian Koeberle, May 12, 2008
  45. 24/24 Added a "add" command to the git like command line tool.Florian Koeberle, May 12, 2008
  46. Miklos VajnaMay 12, 2008

Read the whole thread, see it on lore, or plain text.

$ cat FOOTERMessages come from the public archive at lore.kernel.org/git, fetched every hour. The front page is chosen and written each morning by an AI editor and can be wrong; the threads themselves are the record. About and API. For agents: an MCP server at https://gitlist.dev/mcp, and any thread, story or person page as Markdown by adding .md to its URL (or sending Accept: text/markdown). Details in /llms.txt.