summaryrefslogtreecommitdiffstats
path: root/org.eclipse.jgit
diff options
context:
space:
mode:
authorPreben Ingvaldsen <preben@puppetlabs.com>2016-03-01 11:37:54 -0800
committerChristian Halstrick <christian.halstrick@sap.com>2016-04-05 10:43:40 +0200
commit403f04d8dd744a6cc1c2a61540c34483b94c06b5 (patch)
tree09caf267b9c0808b9c93c1217b5dfebadde322be /org.eclipse.jgit
parentbf32c9102fb1b5fdfa7a26a120b5d9a6b428dd2f (diff)
downloadjgit-403f04d8dd744a6cc1c2a61540c34483b94c06b5.tar.gz
jgit-403f04d8dd744a6cc1c2a61540c34483b94c06b5.zip
Implement DIR_NO_GITLINKS
Implement the DIR_NO_GITLINKS setting with the same functionality it provides in cGit. Bug: 436200 Change-Id: I8304e42df2d7e8d7925f515805e075a92ff6ce28 Signed-off-by: Preben Ingvaldsen <preben@puppetlabs.com>
Diffstat (limited to 'org.eclipse.jgit')
-rw-r--r--org.eclipse.jgit/src/org/eclipse/jgit/api/AddCommand.java6
-rw-r--r--org.eclipse.jgit/src/org/eclipse/jgit/lib/ConfigConstants.java6
-rw-r--r--org.eclipse.jgit/src/org/eclipse/jgit/treewalk/AbstractTreeIterator.java9
-rw-r--r--org.eclipse.jgit/src/org/eclipse/jgit/treewalk/FileTreeIterator.java34
-rw-r--r--org.eclipse.jgit/src/org/eclipse/jgit/treewalk/TreeWalk.java7
-rw-r--r--org.eclipse.jgit/src/org/eclipse/jgit/treewalk/WorkingTreeIterator.java35
-rw-r--r--org.eclipse.jgit/src/org/eclipse/jgit/treewalk/WorkingTreeOptions.java13
7 files changed, 99 insertions, 11 deletions
diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/api/AddCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/api/AddCommand.java
index 3b94f16f1a..1f37833a41 100644
--- a/org.eclipse.jgit/src/org/eclipse/jgit/api/AddCommand.java
+++ b/org.eclipse.jgit/src/org/eclipse/jgit/api/AddCommand.java
@@ -45,6 +45,7 @@ package org.eclipse.jgit.api;
import static org.eclipse.jgit.lib.Constants.OBJ_BLOB;
import static org.eclipse.jgit.lib.FileMode.GITLINK;
+import static org.eclipse.jgit.lib.FileMode.TYPE_GITLINK;
import static org.eclipse.jgit.lib.FileMode.TYPE_TREE;
import java.io.IOException;
@@ -201,7 +202,10 @@ public class AddCommand extends GitCommand<DirCache> {
continue;
}
- if (f.getEntryRawMode() == TYPE_TREE) {
+ if ((f.getEntryRawMode() == TYPE_TREE
+ && f.getIndexFileMode(c) != FileMode.GITLINK) ||
+ (f.getEntryRawMode() == TYPE_GITLINK
+ && f.getIndexFileMode(c) == FileMode.TREE)) {
// Index entry exists and is symlink, gitlink or file,
// otherwise the tree would have been entered above.
// Replace the index entry by diving into tree of files.
diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/lib/ConfigConstants.java b/org.eclipse.jgit/src/org/eclipse/jgit/lib/ConfigConstants.java
index 054d193017..abc8c269ff 100644
--- a/org.eclipse.jgit/src/org/eclipse/jgit/lib/ConfigConstants.java
+++ b/org.eclipse.jgit/src/org/eclipse/jgit/lib/ConfigConstants.java
@@ -235,6 +235,12 @@ public class ConfigConstants {
*/
public static final String CONFIG_KEY_HIDEDOTFILES = "hidedotfiles";
+ /**
+ * The "dirnogitlinks" key
+ * @since 4.3
+ */
+ public static final String CONFIG_KEY_DIRNOGITLINKS = "dirNoGitLinks";
+
/** The "precomposeunicode" key */
public static final String CONFIG_KEY_PRECOMPOSEUNICODE = "precomposeunicode";
diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/treewalk/AbstractTreeIterator.java b/org.eclipse.jgit/src/org/eclipse/jgit/treewalk/AbstractTreeIterator.java
index dc835e4f36..07fc829db4 100644
--- a/org.eclipse.jgit/src/org/eclipse/jgit/treewalk/AbstractTreeIterator.java
+++ b/org.eclipse.jgit/src/org/eclipse/jgit/treewalk/AbstractTreeIterator.java
@@ -729,4 +729,13 @@ public abstract class AbstractTreeIterator {
public String toString() {
return getClass().getSimpleName() + "[" + getEntryPathString() + "]"; //$NON-NLS-1$
}
+
+ /**
+ * @return whether or not this Iterator is iterating through the Work Tree
+ *
+ * @since 4.3
+ */
+ public boolean isWorkTree() {
+ return false;
+ }
}
diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/treewalk/FileTreeIterator.java b/org.eclipse.jgit/src/org/eclipse/jgit/treewalk/FileTreeIterator.java
index eb4f1a87d0..db81e1af9b 100644
--- a/org.eclipse.jgit/src/org/eclipse/jgit/treewalk/FileTreeIterator.java
+++ b/org.eclipse.jgit/src/org/eclipse/jgit/treewalk/FileTreeIterator.java
@@ -94,7 +94,10 @@ public class FileTreeIterator extends WorkingTreeIterator {
* the repository whose working tree will be scanned.
*/
public FileTreeIterator(Repository repo) {
- this(repo, DefaultFileModeStrategy.INSTANCE);
+ this(repo,
+ repo.getConfig().get(WorkingTreeOptions.KEY).isDirNoGitLinks() ?
+ NoGitlinksStrategy.INSTANCE :
+ DefaultFileModeStrategy.INSTANCE);
}
/**
@@ -291,6 +294,35 @@ public class FileTreeIterator extends WorkingTreeIterator {
}
}
+ /**
+ * A FileModeStrategy that implements native git's DIR_NO_GITLINKS
+ * behavior. This is the same as the default FileModeStrategy, except
+ * all directories will be treated as directories regardless of whether
+ * or not they contain a .git directory or file.
+ *
+ * @since 4.3
+ */
+ static public class NoGitlinksStrategy implements FileModeStrategy {
+
+ /**
+ * a singleton instance of the default FileModeStrategy
+ */
+ public final static NoGitlinksStrategy INSTANCE = new NoGitlinksStrategy();
+
+ @Override
+ public FileMode getMode(File f, FS.Attributes attributes) {
+ if (attributes.isSymbolicLink()) {
+ return FileMode.SYMLINK;
+ } else if (attributes.isDirectory()) {
+ return FileMode.TREE;
+ } else if (attributes.isExecutable()) {
+ return FileMode.EXECUTABLE_FILE;
+ } else {
+ return FileMode.REGULAR_FILE;
+ }
+ }
+ }
+
/**
* Wrapper for a standard Java IO file
diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/treewalk/TreeWalk.java b/org.eclipse.jgit/src/org/eclipse/jgit/treewalk/TreeWalk.java
index aecbac11ea..501d676735 100644
--- a/org.eclipse.jgit/src/org/eclipse/jgit/treewalk/TreeWalk.java
+++ b/org.eclipse.jgit/src/org/eclipse/jgit/treewalk/TreeWalk.java
@@ -1187,7 +1187,12 @@ public class TreeWalk implements AutoCloseable, AttributesProvider {
for (int i = 0; i < trees.length; i++) {
final AbstractTreeIterator t = trees[i];
final AbstractTreeIterator n;
- if (t.matches == ch && !t.eof() && FileMode.TREE.equals(t.mode))
+ // If we find a GITLINK when attempting to enter a subtree, then the
+ // GITLINK must exist as a TREE in the index, meaning the working tree
+ // entry should be treated as a TREE
+ if (t.matches == ch && !t.eof() &&
+ (FileMode.TREE.equals(t.mode)
+ || (FileMode.GITLINK.equals(t.mode) && t.isWorkTree())))
n = t.createSubtreeIterator(reader, idBuffer);
else
n = t.createEmptyTreeIterator();
diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/treewalk/WorkingTreeIterator.java b/org.eclipse.jgit/src/org/eclipse/jgit/treewalk/WorkingTreeIterator.java
index ca8f9aa373..39176c621e 100644
--- a/org.eclipse.jgit/src/org/eclipse/jgit/treewalk/WorkingTreeIterator.java
+++ b/org.eclipse.jgit/src/org/eclipse/jgit/treewalk/WorkingTreeIterator.java
@@ -264,7 +264,7 @@ public abstract class WorkingTreeIterator extends AbstractTreeIterator {
// the cached index information for the path.
//
DirCacheIterator i = state.walk.getTree(state.dirCacheTree,
- DirCacheIterator.class);
+ DirCacheIterator.class);
if (i != null) {
DirCacheEntry ent = i.getDirCacheEntry();
if (ent != null && compareMetadata(ent) == MetadataDiff.EQUAL) {
@@ -289,6 +289,11 @@ public abstract class WorkingTreeIterator extends AbstractTreeIterator {
return zeroid;
}
+ @Override
+ public boolean isWorkTree() {
+ return true;
+ }
+
/**
* Get submodule id for given entry.
*
@@ -916,17 +921,31 @@ public abstract class WorkingTreeIterator extends AbstractTreeIterator {
*/
public FileMode getIndexFileMode(final DirCacheIterator indexIter) {
final FileMode wtMode = getEntryFileMode();
- if (indexIter == null)
- return wtMode;
- if (getOptions().isFileMode())
+ if (indexIter == null) {
return wtMode;
+ }
final FileMode iMode = indexIter.getEntryFileMode();
- if (FileMode.REGULAR_FILE == wtMode
- && FileMode.EXECUTABLE_FILE == iMode)
+ if (getOptions().isFileMode() && iMode != FileMode.GITLINK && iMode != FileMode.TREE) {
+ return wtMode;
+ }
+ if (!getOptions().isFileMode()) {
+ if (FileMode.REGULAR_FILE == wtMode
+ && FileMode.EXECUTABLE_FILE == iMode) {
+ return iMode;
+ }
+ if (FileMode.EXECUTABLE_FILE == wtMode
+ && FileMode.REGULAR_FILE == iMode) {
+ return iMode;
+ }
+ }
+ if (FileMode.GITLINK == iMode
+ && FileMode.TREE == wtMode) {
return iMode;
- if (FileMode.EXECUTABLE_FILE == wtMode
- && FileMode.REGULAR_FILE == iMode)
+ }
+ if (FileMode.TREE == iMode
+ && FileMode.GITLINK == wtMode) {
return iMode;
+ }
return wtMode;
}
diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/treewalk/WorkingTreeOptions.java b/org.eclipse.jgit/src/org/eclipse/jgit/treewalk/WorkingTreeOptions.java
index a8990b1e95..dea07c1973 100644
--- a/org.eclipse.jgit/src/org/eclipse/jgit/treewalk/WorkingTreeOptions.java
+++ b/org.eclipse.jgit/src/org/eclipse/jgit/treewalk/WorkingTreeOptions.java
@@ -73,6 +73,8 @@ public class WorkingTreeOptions {
private final HideDotFiles hideDotFiles;
+ private final boolean dirNoGitLinks;
+
private WorkingTreeOptions(final Config rc) {
fileMode = rc.getBoolean(ConfigConstants.CONFIG_CORE_SECTION,
ConfigConstants.CONFIG_KEY_FILEMODE, true);
@@ -87,6 +89,9 @@ public class WorkingTreeOptions {
hideDotFiles = rc.getEnum(ConfigConstants.CONFIG_CORE_SECTION, null,
ConfigConstants.CONFIG_KEY_HIDEDOTFILES,
HideDotFiles.DOTGITONLY);
+ dirNoGitLinks = rc.getBoolean(ConfigConstants.CONFIG_CORE_SECTION, null,
+ ConfigConstants.CONFIG_KEY_DIRNOGITLINKS,
+ false);
}
/** @return true if the execute bit on working files should be trusted. */
@@ -131,4 +136,12 @@ public class WorkingTreeOptions {
public HideDotFiles getHideDotFiles() {
return hideDotFiles;
}
+
+ /**
+ * @return whether or not we treat nested repos as directories.
+ * If true, folders containing .git entries will not be
+ * treated as gitlinks.
+ * @since 4.3
+ */
+ public boolean isDirNoGitLinks() { return dirNoGitLinks; }
}