aboutsummaryrefslogtreecommitdiffstats
path: root/org.eclipse.jgit/src/org/eclipse
diff options
context:
space:
mode:
Diffstat (limited to 'org.eclipse.jgit/src/org/eclipse')
-rw-r--r--org.eclipse.jgit/src/org/eclipse/jgit/internal/JGitText.java2
-rw-r--r--org.eclipse.jgit/src/org/eclipse/jgit/lib/Constants.java9
-rw-r--r--org.eclipse.jgit/src/org/eclipse/jgit/util/FS.java22
-rw-r--r--org.eclipse.jgit/src/org/eclipse/jgit/util/SystemReader.java86
4 files changed, 104 insertions, 15 deletions
diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/internal/JGitText.java b/org.eclipse.jgit/src/org/eclipse/jgit/internal/JGitText.java
index 6a7d22df9d..61b145657d 100644
--- a/org.eclipse.jgit/src/org/eclipse/jgit/internal/JGitText.java
+++ b/org.eclipse.jgit/src/org/eclipse/jgit/internal/JGitText.java
@@ -262,8 +262,10 @@ public class JGitText extends TranslationBundle {
/***/ public String countingObjects;
/***/ public String createBranchFailedUnknownReason;
/***/ public String createBranchUnexpectedResult;
+ /***/ public String createJGitConfigFailed;
/***/ public String createNewFileFailed;
/***/ public String createRequiresZeroOldId;
+ /***/ public String createXDGConfigHomeFailed;
/***/ public String credentialPassword;
/***/ public String credentialPassphrase;
/***/ public String credentialUsername;
diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/lib/Constants.java b/org.eclipse.jgit/src/org/eclipse/jgit/lib/Constants.java
index a084c82871..9274fc6777 100644
--- a/org.eclipse.jgit/src/org/eclipse/jgit/lib/Constants.java
+++ b/org.eclipse.jgit/src/org/eclipse/jgit/lib/Constants.java
@@ -343,6 +343,15 @@ public final class Constants {
public static final String GIT_CONFIG_NOSYSTEM_KEY = "GIT_CONFIG_NOSYSTEM";
/**
+ * The key of the XDG_CONFIG_HOME directory defined in the XDG base
+ * directory specification, see
+ * {@link "https://wiki.archlinux.org/index.php/XDG_Base_Directory"}
+ *
+ * @since 5.5.2
+ */
+ public static final String XDG_CONFIG_HOME = "XDG_CONFIG_HOME";
+
+ /**
* The environment variable that limits how close to the root of the file
* systems JGit will traverse when looking for a repository root.
*/
diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/util/FS.java b/org.eclipse.jgit/src/org/eclipse/jgit/util/FS.java
index 29519298c4..b3d01d3b48 100644
--- a/org.eclipse.jgit/src/org/eclipse/jgit/util/FS.java
+++ b/org.eclipse.jgit/src/org/eclipse/jgit/util/FS.java
@@ -545,9 +545,9 @@ public abstract class FS {
private static void saveToConfig(FileStore s,
FileStoreAttributes c) {
- StoredConfig userConfig;
+ StoredConfig jgitConfig;
try {
- userConfig = SystemReader.getInstance().getUserConfig();
+ jgitConfig = SystemReader.getInstance().getJGitConfig();
} catch (IOException | ConfigInvalidException e) {
LOG.error(JGitText.get().saveFileStoreAttributesFailed, e);
return;
@@ -568,20 +568,19 @@ public abstract class FS {
String key = getConfigKey(s);
while (!succeeded && retries < max_retries) {
try {
- userConfig.load();
- userConfig.setString(
+ jgitConfig.setString(
ConfigConstants.CONFIG_FILESYSTEM_SECTION, key,
ConfigConstants.CONFIG_KEY_TIMESTAMP_RESOLUTION,
String.format("%d %s", //$NON-NLS-1$
Long.valueOf(resolutionValue),
resolutionUnit.name().toLowerCase()));
- userConfig.setString(
+ jgitConfig.setString(
ConfigConstants.CONFIG_FILESYSTEM_SECTION, key,
ConfigConstants.CONFIG_KEY_MIN_RACY_THRESHOLD,
String.format("%d %s", //$NON-NLS-1$
Long.valueOf(minRacyThresholdValue),
minRacyThresholdUnit.name().toLowerCase()));
- userConfig.save();
+ jgitConfig.save();
succeeded = true;
} catch (LockFailedException e) {
// race with another thread, wait a bit and try again
@@ -590,11 +589,11 @@ public abstract class FS {
if (retries < max_retries) {
Thread.sleep(100);
LOG.debug("locking {} failed, retries {}/{}", //$NON-NLS-1$
- userConfig, Integer.valueOf(retries),
+ jgitConfig, Integer.valueOf(retries),
Integer.valueOf(max_retries));
} else {
LOG.warn(MessageFormat.format(
- JGitText.get().lockFailedRetry, userConfig,
+ JGitText.get().lockFailedRetry, jgitConfig,
Integer.valueOf(retries)));
}
} catch (InterruptedException e1) {
@@ -603,12 +602,7 @@ public abstract class FS {
}
} catch (IOException e) {
LOG.error(MessageFormat.format(
- JGitText.get().cannotSaveConfig, userConfig), e);
- break;
- } catch (ConfigInvalidException e) {
- LOG.error(MessageFormat.format(
- JGitText.get().repositoryConfigFileInvalid,
- userConfig, e.getMessage()));
+ JGitText.get().cannotSaveConfig, jgitConfig), e);
break;
}
}
diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/util/SystemReader.java b/org.eclipse.jgit/src/org/eclipse/jgit/util/SystemReader.java
index a2253bc118..59184ffda2 100644
--- a/org.eclipse.jgit/src/org/eclipse/jgit/util/SystemReader.java
+++ b/org.eclipse.jgit/src/org/eclipse/jgit/util/SystemReader.java
@@ -50,6 +50,10 @@ import java.io.File;
import java.io.IOException;
import java.net.InetAddress;
import java.net.UnknownHostException;
+import java.nio.file.Files;
+import java.nio.file.InvalidPathException;
+import java.nio.file.Path;
+import java.nio.file.Paths;
import java.security.AccessController;
import java.security.PrivilegedAction;
import java.text.DateFormat;
@@ -60,6 +64,7 @@ import java.util.concurrent.atomic.AtomicReference;
import org.eclipse.jgit.errors.ConfigInvalidException;
import org.eclipse.jgit.errors.CorruptObjectException;
+import org.eclipse.jgit.internal.JGitText;
import org.eclipse.jgit.lib.Config;
import org.eclipse.jgit.lib.Constants;
import org.eclipse.jgit.lib.ObjectChecker;
@@ -137,6 +142,42 @@ public abstract class SystemReader {
fs);
}
+ private Path getXDGConfigHome(FS fs) {
+ String configHomePath = getenv(Constants.XDG_CONFIG_HOME);
+ if (StringUtils.isEmptyOrNull(configHomePath)) {
+ configHomePath = new File(fs.userHome(), ".config") //$NON-NLS-1$
+ .getAbsolutePath();
+ }
+ try {
+ Path xdgHomePath = Paths.get(configHomePath);
+ Files.createDirectories(xdgHomePath);
+ return xdgHomePath;
+ } catch (IOException | InvalidPathException e) {
+ LOG.error(JGitText.get().createXDGConfigHomeFailed,
+ configHomePath, e);
+ }
+ return null;
+ }
+
+ @Override
+ public FileBasedConfig openJGitConfig(Config parent, FS fs) {
+ Path xdgPath = getXDGConfigHome(fs);
+ if (xdgPath != null) {
+ Path configPath = null;
+ try {
+ configPath = xdgPath.resolve("jgit"); //$NON-NLS-1$
+ Files.createDirectories(configPath);
+ configPath = configPath.resolve(Constants.CONFIG);
+ return new FileBasedConfig(parent, configPath.toFile(), fs);
+ } catch (IOException e) {
+ LOG.error(JGitText.get().createJGitConfigFailed, configPath,
+ e);
+ }
+ }
+ return new FileBasedConfig(parent,
+ new File(fs.userHome(), ".jgitconfig"), fs); //$NON-NLS-1$
+ }
+
@Override
public String getHostname() {
if (hostname == null) {
@@ -198,6 +239,8 @@ public abstract class SystemReader {
private AtomicReference<FileBasedConfig> userConfig = new AtomicReference<>();
+ private AtomicReference<FileBasedConfig> jgitConfig = new AtomicReference<>();
+
private void init() {
// Creating ObjectChecker must be deferred. Unit tests change
// behavior of is{Windows,MacOS} in constructor of subclass.
@@ -275,6 +318,22 @@ public abstract class SystemReader {
public abstract FileBasedConfig openSystemConfig(Config parent, FS fs);
/**
+ * Open the jgit configuration located at $XDG_CONFIG_HOME/jgit/config. Use
+ * {@link #getJGitConfig()} to get the current jgit configuration in the
+ * user home since it manages automatic reloading when the jgit config file
+ * was modified and avoids unnecessary reloads.
+ *
+ * @param parent
+ * a config with values not found directly in the returned config
+ * @param fs
+ * the file system abstraction which will be necessary to perform
+ * certain file system operations.
+ * @return the jgit configuration located at $XDG_CONFIG_HOME/jgit/config
+ * @since 5.5.2
+ */
+ public abstract FileBasedConfig openJGitConfig(Config parent, FS fs);
+
+ /**
* Get the git configuration found in the user home. The configuration will
* be reloaded automatically if the configuration file was modified. Also
* reloads the system config if the system config file was modified. If the
@@ -302,6 +361,31 @@ public abstract class SystemReader {
}
/**
+ * Get the jgit configuration located at $XDG_CONFIG_HOME/jgit/config. The
+ * configuration will be reloaded automatically if the configuration file
+ * was modified. If the configuration file wasn't modified returns the
+ * cached configuration.
+ *
+ * @return the jgit configuration located at $XDG_CONFIG_HOME/jgit/config
+ * @throws ConfigInvalidException
+ * if configuration is invalid
+ * @throws IOException
+ * if something went wrong when reading files
+ * @since 5.5.2
+ */
+ public StoredConfig getJGitConfig()
+ throws ConfigInvalidException, IOException {
+ FileBasedConfig c = jgitConfig.get();
+ if (c == null) {
+ jgitConfig.compareAndSet(null,
+ openJGitConfig(null, FS.DETECTED));
+ c = jgitConfig.get();
+ }
+ updateAll(c);
+ return c;
+ }
+
+ /**
* Get the gitconfig configuration found in the system-wide "etc" directory.
* The configuration will be reloaded automatically if the configuration
* file was modified otherwise returns the cached system level config.
@@ -319,7 +403,7 @@ public abstract class SystemReader {
FileBasedConfig c = systemConfig.get();
if (c == null) {
systemConfig.compareAndSet(null,
- openSystemConfig(null, FS.DETECTED));
+ openSystemConfig(getJGitConfig(), FS.DETECTED));
c = systemConfig.get();
}
updateAll(c);