diff options
Diffstat (limited to 'org.eclipse.jgit/src/org/eclipse')
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); |