From 57a4d56491e296be2b59f77a0cf9862f68b8e994 Mon Sep 17 00:00:00 2001 From: Tomas Matousek Date: Wed, 26 Jun 2019 18:31:23 -0700 Subject: [PATCH 1/2] Use environment variabels and non-local configurations conditionally --- .../GitConfigTests.cs | 19 ++- .../GitDataTests.cs | 9 +- .../GitOperationsTests.cs | 42 +++---- .../GitRepositoryTests.cs | 10 +- .../GitDataReader/GitConfig.Reader.cs | 70 ++++++++--- .../GitDataReader/GitEnvironment.cs | 51 ++++++-- .../GitDataReader/GitRepository.cs | 8 +- .../GitOperations.cs | 6 +- .../LocateRepository.cs | 4 +- .../RepositoryTask.cs | 44 +++---- src/Microsoft.Build.Tasks.Git/Resources.resx | 6 + .../build/Microsoft.Build.Tasks.Git.targets | 27 +++- .../xlf/Resources.cs.xlf | 10 ++ .../xlf/Resources.de.xlf | 10 ++ .../xlf/Resources.es.xlf | 10 ++ .../xlf/Resources.fr.xlf | 10 ++ .../xlf/Resources.it.xlf | 10 ++ .../xlf/Resources.ja.xlf | 10 ++ .../xlf/Resources.ko.xlf | 10 ++ .../xlf/Resources.pl.xlf | 10 ++ .../xlf/Resources.pt-BR.xlf | 10 ++ .../xlf/Resources.ru.xlf | 10 ++ .../xlf/Resources.tr.xlf | 10 ++ .../xlf/Resources.zh-Hans.xlf | 10 ++ .../xlf/Resources.zh-Hant.xlf | 10 ++ .../GitHubTests.cs | 116 ++++++++++++++++-- .../DotNetSdk/DotNetSdkTestBase.cs | 2 +- 27 files changed, 446 insertions(+), 98 deletions(-) diff --git a/src/Microsoft.Build.Tasks.Git.UnitTests/GitConfigTests.cs b/src/Microsoft.Build.Tasks.Git.UnitTests/GitConfigTests.cs index 89585b87..7e3da0aa 100644 --- a/src/Microsoft.Build.Tasks.Git.UnitTests/GitConfigTests.cs +++ b/src/Microsoft.Build.Tasks.Git.UnitTests/GitConfigTests.cs @@ -15,7 +15,7 @@ private static IEnumerable Inspect(GitConfig config) => config.EnumerateVariables().Select(kvp => $"{kvp.Key}={string.Join("|", kvp.Value)}"); private static GitConfig LoadFromString(string gitDirectory, string configPath, string configContent) - => new GitConfig.Reader(gitDirectory, gitDirectory, new GitEnvironment(Path.GetTempPath()), _ => new StringReader(configContent)). + => new GitConfig.Reader(gitDirectory, gitDirectory, GitEnvironment.Empty, _ => new StringReader(configContent)). LoadFrom(configPath); [Fact] @@ -160,6 +160,21 @@ TextReader openFile(string path) }, Inspect(config)); } + [Fact] + public void ConditionalInclude_HomeNotSupported() + { + var gitDirectory = PathUtils.ToPosixPath(Path.Combine(Path.GetTempPath(), ".git")) + "/"; + + var config = @" +[includeIf ""gitdir/i:~/**/.GIT/""] + path = xyz +"; + + var reader = new GitConfig.Reader(gitDirectory, gitDirectory, GitEnvironment.Empty, _ => new StringReader(config)); + + Assert.Throws(() => reader.LoadFrom(Path.Combine(gitDirectory, "config"))); + } + [Fact] public void IncludeRecursion() { @@ -189,7 +204,7 @@ TextReader openFile(string path) }); } - Assert.Throws(() => new GitConfig.Reader(gitDirectory, gitDirectory, new GitEnvironment("/home"), openFile).LoadFrom(Path.Combine(gitDirectory, "config"))); + Assert.Throws(() => new GitConfig.Reader(gitDirectory, gitDirectory, GitEnvironment.Empty, openFile).LoadFrom(Path.Combine(gitDirectory, "config"))); } [Theory] diff --git a/src/Microsoft.Build.Tasks.Git.UnitTests/GitDataTests.cs b/src/Microsoft.Build.Tasks.Git.UnitTests/GitDataTests.cs index 0aaf3408..e73c9199 100644 --- a/src/Microsoft.Build.Tasks.Git.UnitTests/GitDataTests.cs +++ b/src/Microsoft.Build.Tasks.Git.UnitTests/GitDataTests.cs @@ -16,7 +16,6 @@ public class GitDataTests [Fact] public void MinimalGitData() { - var environment = new GitEnvironment("/home"); var repoDir = Temp.CreateDirectory(); var gitDir = repoDir.CreateDirectory(".git"); @@ -42,13 +41,13 @@ public void MinimalGitData() gitDirSub.CreateDirectory("objects"); gitDirSub.CreateDirectory("refs"); - var repository = GitRepository.OpenRepository(repoDir.Path, environment); + var repository = GitRepository.OpenRepository(repoDir.Path, GitEnvironment.Empty); - Assert.Equal("http://github.com/test-org/test-repo", GitOperations.GetRepositoryUrl(repository)); + Assert.Equal("http://github.com/test-org/test-repo", GitOperations.GetRepositoryUrl(repository, remoteName: null)); Assert.Equal("1111111111111111111111111111111111111111", repository.GetHeadCommitSha()); var warnings = new List<(string, object[])>(); - var sourceRoots = GitOperations.GetSourceRoots(repository, (message, args) => warnings.Add((message, args))); + var sourceRoots = GitOperations.GetSourceRoots(repository, remoteName: null, (message, args) => warnings.Add((message, args))); AssertEx.Equal(new[] { $@"'{repoDir.Path}{s}' SourceControl='git' RevisionId='1111111111111111111111111111111111111111' ScmRepositoryUrl='http://github.com/test-org/test-repo'", @@ -65,7 +64,7 @@ public void MinimalGitData() new MockItem(@"sub\ignore_in_submodule_d"), }; - var untrackedFiles = GitOperations.GetUntrackedFiles(repository, files, repoDir.Path, path => GitRepository.OpenRepository(path, environment)); + var untrackedFiles = GitOperations.GetUntrackedFiles(repository, files, repoDir.Path, path => GitRepository.OpenRepository(path, GitEnvironment.Empty)); AssertEx.Equal(new[] { diff --git a/src/Microsoft.Build.Tasks.Git.UnitTests/GitOperationsTests.cs b/src/Microsoft.Build.Tasks.Git.UnitTests/GitOperationsTests.cs index 1ab8f7e7..d820032a 100644 --- a/src/Microsoft.Build.Tasks.Git.UnitTests/GitOperationsTests.cs +++ b/src/Microsoft.Build.Tasks.Git.UnitTests/GitOperationsTests.cs @@ -16,8 +16,6 @@ public class GitOperationsTests private static readonly char s = Path.DirectorySeparatorChar; private static readonly string s_root = (s == '/') ? "/usr/src" : @"C:\src"; - private static readonly GitEnvironment s_environment = new GitEnvironment("/home"); - private string _workingDir = s_root; private GitRepository CreateRepository( @@ -30,7 +28,7 @@ public class GitOperationsTests workingDir ??= _workingDir; var gitDir = Path.Combine(workingDir, ".git"); return new GitRepository( - s_environment, + GitEnvironment.Empty, config ?? GitConfig.Empty, gitDir, gitDir, @@ -78,7 +76,7 @@ public void GetRepositoryUrl_NoRemotes() { var repo = CreateRepository(); var warnings = new List<(string, object[])>(); - Assert.Null(GitOperations.GetRepositoryUrl(repo, (message, args) => warnings.Add((message, args)))); + Assert.Null(GitOperations.GetRepositoryUrl(repo, remoteName: null, logWarning: (message, args) => warnings.Add((message, args)))); AssertEx.Equal(new[] { Resources.RepositoryHasNoRemote }, warnings.Select(TestUtilities.InspectDiagnostic)); } @@ -91,7 +89,7 @@ public void GetRepositoryUrl_Origin() var warnings = new List<(string, object[])>(); - Assert.Equal("http://github.com/origin", GitOperations.GetRepositoryUrl(repo, (message, args) => warnings.Add((message, args)))); + Assert.Equal("http://github.com/origin", GitOperations.GetRepositoryUrl(repo, remoteName: null, logWarning: (message, args) => warnings.Add((message, args)))); Assert.Empty(warnings); } @@ -105,7 +103,7 @@ public void GetRepositoryUrl_NoOrigin() var warnings = new List<(string, object[])>(); - Assert.Equal("http://github.com/abc", GitOperations.GetRepositoryUrl(repo, (message, args) => warnings.Add((message, args)))); + Assert.Equal("http://github.com/abc", GitOperations.GetRepositoryUrl(repo, remoteName: null, logWarning: (message, args) => warnings.Add((message, args)))); Assert.Empty(warnings); } @@ -120,8 +118,8 @@ public void GetRepositoryUrl_Specified() var warnings = new List<(string, object[])>(); Assert.Equal("http://github.com/abc", - GitOperations.GetRepositoryUrl(repo, (message, args) => warnings.Add((message, args)), - remoteName: "abc")); + GitOperations.GetRepositoryUrl(repo, remoteName: "abc", + logWarning: (message, args) => warnings.Add((message, args)))); Assert.Empty(warnings); } @@ -136,8 +134,8 @@ public void GetRepositoryUrl_SpecifiedNotFound_OriginFallback() var warnings = new List<(string, object[])>(); Assert.Equal("http://github.com/origin", - GitOperations.GetRepositoryUrl(repo, (message, args) => warnings.Add((message, args)), - remoteName: "myremote")); + GitOperations.GetRepositoryUrl(repo, remoteName: "myremote", + logWarning: (message, args) => warnings.Add((message, args)))); AssertEx.Equal(new[] { @@ -155,8 +153,8 @@ public void GetRepositoryUrl_SpecifiedNotFound_FirstFallback() var warnings = new List<(string, object[])>(); Assert.Equal("http://github.com/abc", - GitOperations.GetRepositoryUrl(repo, (message, args) => warnings.Add((message, args)), - remoteName: "myremote")); + GitOperations.GetRepositoryUrl(repo, remoteName: "myremote", + logWarning: (message, args) => warnings.Add((message, args)))); AssertEx.Equal(new[] { @@ -170,7 +168,7 @@ public void GetRepositoryUrl_BadUrl() var repo = CreateRepository(config: CreateConfig(("remote.origin.url", "http://?"))); var warnings = new List<(string, object[])>(); - Assert.Null(GitOperations.GetRepositoryUrl(repo, (message, args) => warnings.Add((message, args)))); + Assert.Null(GitOperations.GetRepositoryUrl(repo, remoteName: null, logWarning: (message, args) => warnings.Add((message, args)))); AssertEx.Equal(new[] { string.Format(Resources.InvalidRepositoryRemoteUrl, "origin", "http://?") @@ -187,7 +185,7 @@ public void GetRepositoryUrl_InsteadOf() }))); var warnings = new List<(string, object[])>(); - Assert.Equal("ssh://git@github.com/org/repo", GitOperations.GetRepositoryUrl(repo, (message, args) => warnings.Add((message, args)))); + Assert.Equal("ssh://git@github.com/org/repo", GitOperations.GetRepositoryUrl(repo, remoteName: null, logWarning: (message, args) => warnings.Add((message, args)))); Assert.Empty(warnings); } @@ -303,7 +301,7 @@ public void GetSourceRoots_RepoWithoutCommits() var repo = CreateRepository(); var warnings = new List<(string, object[])>(); - var items = GitOperations.GetSourceRoots(repo, (message, args) => warnings.Add((message, args))); + var items = GitOperations.GetSourceRoots(repo, remoteName: null, (message, args) => warnings.Add((message, args))); Assert.Empty(items); AssertEx.Equal(new[] { Resources.RepositoryHasNoCommit }, warnings.Select(TestUtilities.InspectDiagnostic)); @@ -320,7 +318,7 @@ public void GetSourceRoots_RepoWithoutCommitsWithSubmodules() CreateSubmodule("1", "sub/2", "http://2.com", "2222222222222222222222222222222222222222"))); ; var warnings = new List<(string, object[])>(); - var items = GitOperations.GetSourceRoots(repo, (message, args) => warnings.Add((message, args))); + var items = GitOperations.GetSourceRoots(repo, remoteName: null, (message, args) => warnings.Add((message, args))); AssertEx.Equal(new[] { @@ -341,7 +339,7 @@ public void GetSourceRoots_RepoWithCommitsWithSubmodules() CreateSubmodule("1", "sub/2", "http://2.com", "2222222222222222222222222222222222222222"))); var warnings = new List<(string, object[])>(); - var items = GitOperations.GetSourceRoots(repo, (message, args) => warnings.Add((message, args))); + var items = GitOperations.GetSourceRoots(repo, remoteName: null, (message, args) => warnings.Add((message, args))); AssertEx.Equal(new[] { @@ -365,7 +363,7 @@ public void GetSourceRoots_RelativeSubmodulePaths_Windows() CreateSubmodule("2", "sub/2", "../a", "2222222222222222222222222222222222222222"))); var warnings = new List<(string, object[])>(); - var items = GitOperations.GetSourceRoots(repo, (message, args) => warnings.Add((message, args))); + var items = GitOperations.GetSourceRoots(repo, remoteName: null, (message, args) => warnings.Add((message, args))); AssertEx.Equal(new[] { @@ -389,7 +387,7 @@ public void GetSourceRoots_RelativeSubmodulePaths_Windows_UnicodeAndEscapes() CreateSubmodule("%25ለ", "sub/%25ለ", "../a", "2222222222222222222222222222222222222222"))); var warnings = new List<(string, object[])>(); - var items = GitOperations.GetSourceRoots(repo, (message, args) => warnings.Add((message, args))); + var items = GitOperations.GetSourceRoots(repo, remoteName: null, (message, args) => warnings.Add((message, args))); AssertEx.Equal(new[] { @@ -413,7 +411,7 @@ public void GetSourceRoots_RelativeSubmodulePaths_Unix() CreateSubmodule("2", "sub/2", "../a", "2222222222222222222222222222222222222222"))); var warnings = new List<(string, object[])>(); - var items = GitOperations.GetSourceRoots(repo, (message, args) => warnings.Add((message, args))); + var items = GitOperations.GetSourceRoots(repo, remoteName: null, (message, args) => warnings.Add((message, args))); AssertEx.Equal(new[] { @@ -437,7 +435,7 @@ public void GetSourceRoots_RelativeSubmodulePaths_Unix_UnicodeAndEscapes() CreateSubmodule("%25ለ", "sub/%25ለ", "../a", "2222222222222222222222222222222222222222"))); var warnings = new List<(string, object[])>(); - var items = GitOperations.GetSourceRoots(repo, (message, args) => warnings.Add((message, args))); + var items = GitOperations.GetSourceRoots(repo, remoteName: null, (message, args) => warnings.Add((message, args))); AssertEx.Equal(new[] { @@ -459,7 +457,7 @@ public void GetSourceRoots_InvalidSubmoduleUrl() CreateSubmodule("3", "sub/3", "http://3.com", "3333333333333333333333333333333333333333"))); var warnings = new List<(string, object[])>(); - var items = GitOperations.GetSourceRoots(repo, (message, args) => warnings.Add((message, args))); + var items = GitOperations.GetSourceRoots(repo, remoteName: null, (message, args) => warnings.Add((message, args))); AssertEx.Equal(new[] { diff --git a/src/Microsoft.Build.Tasks.Git.UnitTests/GitRepositoryTests.cs b/src/Microsoft.Build.Tasks.Git.UnitTests/GitRepositoryTests.cs index d0f278d9..a80c2a90 100644 --- a/src/Microsoft.Build.Tasks.Git.UnitTests/GitRepositoryTests.cs +++ b/src/Microsoft.Build.Tasks.Git.UnitTests/GitRepositoryTests.cs @@ -143,7 +143,7 @@ public void OpenRepository() } [Fact] - public void OpenReopsitory_VersionNotSupported() + public void OpenRepository_VersionNotSupported() { using var temp = new TempRoot(); @@ -190,7 +190,7 @@ public void Submodules() [submodule ""S5""] # ignore if url unspecified path = s4 "); - var repository = new GitRepository(new GitEnvironment("/home"), GitConfig.Empty, gitDir.Path, gitDir.Path, workingDir.Path); + var repository = new GitRepository(GitEnvironment.Empty, GitConfig.Empty, gitDir.Path, gitDir.Path, workingDir.Path); var submodules = GitRepository.EnumerateSubmoduleConfig(repository.ReadSubmoduleConfig()); AssertEx.Equal(new[] @@ -261,7 +261,7 @@ public void Submodules_Errors() path = sub10 url = http://github.com "); - var repository = new GitRepository(new GitEnvironment("/home"), GitConfig.Empty, gitDir.Path, gitDir.Path, workingDir.Path); + var repository = new GitRepository(GitEnvironment.Empty, GitConfig.Empty, gitDir.Path, gitDir.Path, workingDir.Path); var submodules = repository.GetSubmodules(); AssertEx.Equal(new[] @@ -348,7 +348,7 @@ public void GetHeadCommitSha() var gitDir = temp.CreateDirectory(); gitDir.CreateFile("HEAD").WriteAllText("ref: refs/heads/master \t\v\r\n"); - var repository = new GitRepository(new GitEnvironment("/home"), GitConfig.Empty, gitDir.Path, commonDir.Path, workingDirectory: null); + var repository = new GitRepository(GitEnvironment.Empty, GitConfig.Empty, gitDir.Path, commonDir.Path, workingDirectory: null); Assert.Equal("0000000000000000000000000000000000000000", repository.GetHeadCommitSha()); } @@ -369,7 +369,7 @@ public void GetSubmoduleHeadCommitSha() submoduleRefsHeadsDir.CreateFile("master").WriteAllText("0000000000000000000000000000000000000000"); submoduleGitDir.CreateFile("HEAD").WriteAllText("ref: refs/heads/master"); - var repository = new GitRepository(new GitEnvironment("/home"), GitConfig.Empty, gitDir.Path, gitDir.Path, workingDir.Path); + var repository = new GitRepository(GitEnvironment.Empty, GitConfig.Empty, gitDir.Path, gitDir.Path, workingDir.Path); Assert.Equal("0000000000000000000000000000000000000000", repository.GetSubmoduleHeadCommitSha(submoduleWorkingDir.Path)); } } diff --git a/src/Microsoft.Build.Tasks.Git/GitDataReader/GitConfig.Reader.cs b/src/Microsoft.Build.Tasks.Git/GitDataReader/GitConfig.Reader.cs index 19ec770e..61507b04 100644 --- a/src/Microsoft.Build.Tasks.Git/GitDataReader/GitConfig.Reader.cs +++ b/src/Microsoft.Build.Tasks.Git/GitDataReader/GitConfig.Reader.cs @@ -6,6 +6,7 @@ using System.Diagnostics; using System.IO; using System.Text; +using Microsoft.Build.Tasks.SourceControl; namespace Microsoft.Build.Tasks.Git { @@ -37,6 +38,7 @@ public Reader(string gitDirectory, string commonDirectory, GitEnvironment enviro /// /// + /// internal GitConfig Load() { var variables = new Dictionary>(); @@ -51,6 +53,7 @@ internal GitConfig Load() /// /// + /// internal GitConfig LoadFrom(string path) { var variables = new Dictionary>(); @@ -65,10 +68,13 @@ private string GetXdgDirectory() { return Path.Combine(xdgConfigHome, "git"); } - else + + if (_environment.HomeDirectory != null) { return Path.Combine(_environment.HomeDirectory, ".config", "git"); } + + return null; } internal IEnumerable EnumerateExistingConfigurationFiles() @@ -84,28 +90,35 @@ internal IEnumerable EnumerateExistingConfigurationFiles() } // system - var systemDir = _environment.SystemDirectory; + var systemDir = GetSystemConfigurationDirectory(); if (systemDir != null) { var systemConfig = Path.Combine(systemDir, "gitconfig"); - if (systemConfig != null) + if (File.Exists(systemConfig)) { yield return systemConfig; } } // XDG - var xdgConfig = Path.Combine(GetXdgDirectory(), "config"); - if (File.Exists(xdgConfig)) + var xdgDir = GetXdgDirectory(); + if (xdgDir != null) { - yield return xdgConfig; + var xdgConfig = Path.Combine(xdgDir, "config"); + if (File.Exists(xdgConfig)) + { + yield return xdgConfig; + } } // global (user home) - var globalConfig = Path.Combine(_environment.HomeDirectory, ".gitconfig"); - if (File.Exists(globalConfig)) + if (_environment.HomeDirectory != null) { - yield return globalConfig; + var globalConfig = Path.Combine(_environment.HomeDirectory, ".gitconfig"); + if (File.Exists(globalConfig)) + { + yield return globalConfig; + } } // local @@ -115,7 +128,29 @@ internal IEnumerable EnumerateExistingConfigurationFiles() yield return localConfig; } - // TODO: worktree config + // TODO: https://github.com/dotnet/sourcelink/issues/303 + // worktree config + } + + private string GetSystemConfigurationDirectory() + { + if (_environment.SystemDirectory == null) + { + return null; + } + + if (!PathUtils.IsUnixLikePlatform) + { + // Git for Windows stores gitconfig under [install dir]\mingw64\etc, + // but other Git Windows implementations use [install dir]\etc. + var mingwEtc = Path.Combine(_environment.SystemDirectory, "..", "mingw64", "etc"); + if (Directory.Exists(mingwEtc)) + { + return mingwEtc; + } + } + + return _environment.SystemDirectory; } /// @@ -204,7 +239,7 @@ private string NormalizeRelativePath(string relativePath, string basePath, GitVa string root; if (relativePath.Length >= 2 && relativePath[0] == '~' && PathUtils.IsDirectorySeparator(relativePath[1])) { - root = _environment.HomeDirectory; + root = _environment.GetHomeDirectoryForPathExpansion(relativePath); relativePath = relativePath.Substring(2); } else @@ -222,6 +257,7 @@ private string NormalizeRelativePath(string relativePath, string basePath, GitVa } } + private bool IsIncludePath(GitVariableName key, string configFilePath) { // unconditional: @@ -256,20 +292,22 @@ private bool IsIncludePath(GitVariableName key, string configFilePath) return false; } - if (pattern.Length >= 2 && (pattern[0] == '.' || pattern[0] == '~') && PathUtils.IsDirectorySeparator(pattern[1])) + if (pattern.Length >= 2 && pattern[0] == '.' && pattern[1] == '/') { // leading './' is substituted with the path to the directory containing the current config file. + pattern = PathUtils.CombinePosixPaths(PathUtils.ToPosixPath(Path.GetDirectoryName(configFilePath)), pattern.Substring(2)); + } + else if (pattern.Length >= 2 && pattern[0] == '~' && pattern[1] == '/') + { // leading '~/' is substituted with HOME path - var root = (pattern[0] == '.') ? Path.GetDirectoryName(configFilePath) : _environment.HomeDirectory; - - pattern = PathUtils.CombinePosixPaths(PathUtils.ToPosixPath(root), pattern.Substring(2)); + pattern = PathUtils.CombinePosixPaths(PathUtils.ToPosixPath(_environment.GetHomeDirectoryForPathExpansion(pattern)), pattern.Substring(2)); } else if (!PathUtils.IsAbsolute(pattern)) { pattern = "**/" + pattern; } - if (PathUtils.IsDirectorySeparator(pattern[pattern.Length - 1])) + if (pattern[pattern.Length - 1] == '/') { pattern += "**"; } diff --git a/src/Microsoft.Build.Tasks.Git/GitDataReader/GitEnvironment.cs b/src/Microsoft.Build.Tasks.Git/GitDataReader/GitEnvironment.cs index 129fdf2a..b98f6e17 100644 --- a/src/Microsoft.Build.Tasks.Git/GitDataReader/GitEnvironment.cs +++ b/src/Microsoft.Build.Tasks.Git/GitDataReader/GitEnvironment.cs @@ -4,17 +4,24 @@ using System.Diagnostics; using System.IO; using System.Linq; +using Microsoft.Build.Tasks.SourceControl; namespace Microsoft.Build.Tasks.Git { internal sealed class GitEnvironment { + private const string LocalConfigurationScopeName = "local"; + private const string GitRepositoryConfigurationScopeName = "GitRepositoryConfigurationScope"; + + public static readonly GitEnvironment Empty = new GitEnvironment(); + public string HomeDirectory { get; } public string XdgConfigHomeDirectory { get; } public string ProgramDataDirectory { get; } public string SystemDirectory { get; } - // TODO: consider adding environment variables: GIT_DIR, GIT_DISCOVERY_ACROSS_FILESYSTEM, GIT_CEILING_DIRECTORIES + // TODO: https://github.com/dotnet/sourcelink/issues/301 + // consider adding environment variables: GIT_DIR, GIT_DISCOVERY_ACROSS_FILESYSTEM, GIT_CEILING_DIRECTORIES // https://git-scm.com/docs/git#Documentation/git.txt-codeGITDIRcode // https://git-scm.com/docs/git#Documentation/git.txt-codeGITCEILINGDIRECTORIEScode // https://git-scm.com/docs/git#Documentation/git.txt-codeGITDISCOVERYACROSSFILESYSTEMcode @@ -26,14 +33,15 @@ internal sealed class GitEnvironment // https://git-scm.com/docs/git#Documentation/git.txt-codeGITWORKTREEcode public GitEnvironment( - string homeDirectory, + string homeDirectory = null, string xdgConfigHomeDirectory = null, string programDataDirectory = null, string systemDirectory = null) { - Debug.Assert(!string.IsNullOrEmpty(homeDirectory)); - - HomeDirectory = homeDirectory; + if (!string.IsNullOrWhiteSpace(homeDirectory)) + { + HomeDirectory = homeDirectory; + } if (!string.IsNullOrWhiteSpace(xdgConfigHomeDirectory)) { @@ -51,19 +59,38 @@ internal sealed class GitEnvironment } } - public static GitEnvironment CreateFromProcessEnvironment() + public static GitEnvironment Create(string configurationScope) { - var systemDir = PathUtils.IsUnixLikePlatform ? "/etc" : - Path.Combine(FindWindowsGitInstallation(), "mingw64", "etc"); + if (string.IsNullOrEmpty(configurationScope)) + { + return CreateFromProcessEnvironment(); + } + if (string.Equals(configurationScope, LocalConfigurationScopeName, StringComparison.OrdinalIgnoreCase)) + { + return Empty; + } + + throw new NotSupportedException(string.Format(Resources.ValueOfIsNotValidConfigurationScope, GitRepositoryConfigurationScopeName, configurationScope)); + } + + public static GitEnvironment CreateFromProcessEnvironment() + { return new GitEnvironment( homeDirectory: Environment.GetFolderPath(Environment.SpecialFolder.UserProfile, Environment.SpecialFolderOption.DoNotVerify), xdgConfigHomeDirectory: Environment.GetEnvironmentVariable("XDG_CONFIG_HOME"), programDataDirectory: Environment.GetEnvironmentVariable("PROGRAMDATA"), - systemDirectory: systemDir); + systemDirectory: FindSystemDirectory()); } - public static string FindWindowsGitInstallation() + private static string FindSystemDirectory() + { + return PathUtils.IsUnixLikePlatform ? + (Environment.GetEnvironmentVariable("MICROSOFT_SOURCELINK_TEST_ENVIRONMENT_ETC_DIR") ?? "/etc") : + Path.Combine(FindWindowsGitInstallation(), "etc"); + } + + private static string FindWindowsGitInstallation() { Debug.Assert(!PathUtils.IsUnixLikePlatform); @@ -108,5 +135,9 @@ public static string FindWindowsGitInstallation() #endif return null; } + + internal string GetHomeDirectoryForPathExpansion(string path) + => HomeDirectory ?? throw new NotSupportedException( + string.Format(Resources.HomeRelativePathsAreNotAllowed, GitRepositoryConfigurationScopeName, LocalConfigurationScopeName, path)); } } diff --git a/src/Microsoft.Build.Tasks.Git/GitDataReader/GitRepository.cs b/src/Microsoft.Build.Tasks.Git/GitDataReader/GitRepository.cs index a5d625c7..4648fb0e 100644 --- a/src/Microsoft.Build.Tasks.Git/GitDataReader/GitRepository.cs +++ b/src/Microsoft.Build.Tasks.Git/GitDataReader/GitRepository.cs @@ -332,16 +332,19 @@ private static bool IsObjectId(string reference) /// /// + /// public ImmutableArray GetSubmodules() => _lazySubmodules.Value.Submodules; /// /// + /// public ImmutableArray GetSubmoduleDiagnostics() => _lazySubmodules.Value.Diagnostics; /// /// + /// private (ImmutableArray Submodules, ImmutableArray Diagnostics) ReadSubmodules() { var workingDirectory = GetWorkingDirectory(); @@ -470,8 +473,9 @@ internal static bool LocateRepository(string directory, out string gitDirectory, while (directory != null) { - // TODO: stop on device boundary - + // TODO: https://github.com/dotnet/sourcelink/issues/302 + // stop on device boundary + var dotGitPath = Path.Combine(directory, GitDirName); if (Directory.Exists(dotGitPath)) diff --git a/src/Microsoft.Build.Tasks.Git/GitOperations.cs b/src/Microsoft.Build.Tasks.Git/GitOperations.cs index 600d75bb..12199e5d 100644 --- a/src/Microsoft.Build.Tasks.Git/GitOperations.cs +++ b/src/Microsoft.Build.Tasks.Git/GitOperations.cs @@ -17,7 +17,7 @@ internal static class GitOperations private const string RemoteSectionName = "remote"; private const string UrlSectionName = "url"; - public static string GetRepositoryUrl(GitRepository repository, Action logWarning = null, string remoteName = null) + public static string GetRepositoryUrl(GitRepository repository, string remoteName, Action logWarning = null) { string unknownRemoteName = null; string remoteUrl = null; @@ -177,7 +177,7 @@ private static bool TryParseScp(string value, out Uri uri) return Uri.TryCreate(url, UriKind.Absolute, out uri); } - public static ITaskItem[] GetSourceRoots(GitRepository repository, Action logWarning) + public static ITaskItem[] GetSourceRoots(GitRepository repository, string remoteName, Action logWarning) { var result = new List(); var repoRoot = GetRepositoryRoot(repository); @@ -186,7 +186,7 @@ public static ITaskItem[] GetSourceRoots(GitRepository repository, Action + /// Sets the scope of git repository configuration. By default (no scope specified) configuration is read from environment variables + /// and system and global user git/ssh configuration files. + /// + /// Supported values: + /// If "local" is specified the configuration is only read from the configuration files local to the repository (or work tree). + /// + public string ConfigurationScope { get; set; } + #if NET461 static RepositoryTask() => AssemblyResolver.Initialize(); #endif - private static readonly string s_cacheKeyPrefix = "3AE29AB7-AE6B-48BA-9851-98A15ED51C94:"; public sealed override bool Execute() { @@ -49,15 +60,15 @@ bool logAssemblyLoadingErrors() [MethodImpl(MethodImplOptions.NoInlining)] private void ExecuteImpl() { - var repository = GetOrCreateRepositoryInstance(); - if (repository == null) - { - // error has already been reported - return; - } - try { + var repository = GetOrCreateRepositoryInstance(); + if (repository == null) + { + // error has already been reported + return; + } + Execute(repository); } catch (Exception e) when (e is IOException || e is InvalidDataException || e is NotSupportedException) @@ -84,17 +95,9 @@ private GitRepository GetOrCreateRepositoryInstance() var initialPath = GetInitialPath(); GitRepositoryLocation location; - try + if (!GitRepository.TryFindRepository(initialPath, out location)) { - if (!GitRepository.TryFindRepository(initialPath, out location)) - { - Log.LogWarning(Resources.UnableToLocateRepository, initialPath); - return null; - } - } - catch (Exception e) when (e is IOException || e is InvalidDataException || e is NotSupportedException) - { - Log.LogError(Resources.ErrorReadingGitRepositoryInformation, e.Message); + Log.LogWarning(Resources.UnableToLocateRepository, initialPath); return null; } @@ -106,8 +109,7 @@ private GitRepository GetOrCreateRepositoryInstance() try { - // TODO: configure environment - repository = GitRepository.OpenRepository(location, GitEnvironment.CreateFromProcessEnvironment()); + repository = GitRepository.OpenRepository(location, GitEnvironment.Create(ConfigurationScope)); } catch (Exception e) when (e is IOException || e is InvalidDataException || e is NotSupportedException) { @@ -127,7 +129,7 @@ private GitRepository GetOrCreateRepositoryInstance() } private string GetCacheKey(string repositoryId) - => s_cacheKeyPrefix + repositoryId; + => s_cacheKeyPrefix + (string.IsNullOrEmpty(ConfigurationScope) ? "*" : ConfigurationScope) + ":" + repositoryId; private bool TryGetCachedRepositoryInstance(string cacheKey, bool requireCached, out GitRepository repository) { diff --git a/src/Microsoft.Build.Tasks.Git/Resources.resx b/src/Microsoft.Build.Tasks.Git/Resources.resx index 5d89413d..8bf77b5b 100644 --- a/src/Microsoft.Build.Tasks.Git/Resources.resx +++ b/src/Microsoft.Build.Tasks.Git/Resources.resx @@ -186,4 +186,10 @@ Repository does not have the specified remote '{0}'; using '{1}' instead. + + The value of {0} is not a valid configuration scope: '{1}'. + + + Home relative paths are not allowed when {0} is '{1}': '{2}' + \ No newline at end of file diff --git a/src/Microsoft.Build.Tasks.Git/build/Microsoft.Build.Tasks.Git.targets b/src/Microsoft.Build.Tasks.Git/build/Microsoft.Build.Tasks.Git.targets index 66754274..213daf5e 100644 --- a/src/Microsoft.Build.Tasks.Git/build/Microsoft.Build.Tasks.Git.targets +++ b/src/Microsoft.Build.Tasks.Git/build/Microsoft.Build.Tasks.Git.targets @@ -2,12 +2,30 @@ + + + + local + - + + @@ -26,7 +44,12 @@ - + + diff --git a/src/Microsoft.Build.Tasks.Git/xlf/Resources.cs.xlf b/src/Microsoft.Build.Tasks.Git/xlf/Resources.cs.xlf index e857c51c..143b77e5 100644 --- a/src/Microsoft.Build.Tasks.Git/xlf/Resources.cs.xlf +++ b/src/Microsoft.Build.Tasks.Git/xlf/Resources.cs.xlf @@ -17,6 +17,11 @@ The format of the file '{0}' is invalid. + + Home relative paths are not allowed when {0} is '{1}': '{2}' + Home relative paths are not allowed when {0} is '{1}': '{2}' + + Repository does not have a working directory. Repository does not have a working directory. @@ -112,6 +117,11 @@ Unsupported repository version {0}. Only versions up to {1} are supported. + + The value of {0} is not a valid configuration scope: '{1}'. + The value of {0} is not a valid configuration scope: '{1}'. + + The value of {0} is not a valid path: '{1}'. The value of {0} is not a valid path: '{1}'. diff --git a/src/Microsoft.Build.Tasks.Git/xlf/Resources.de.xlf b/src/Microsoft.Build.Tasks.Git/xlf/Resources.de.xlf index 3a78b141..030259c4 100644 --- a/src/Microsoft.Build.Tasks.Git/xlf/Resources.de.xlf +++ b/src/Microsoft.Build.Tasks.Git/xlf/Resources.de.xlf @@ -17,6 +17,11 @@ The format of the file '{0}' is invalid. + + Home relative paths are not allowed when {0} is '{1}': '{2}' + Home relative paths are not allowed when {0} is '{1}': '{2}' + + Repository does not have a working directory. Repository does not have a working directory. @@ -112,6 +117,11 @@ Unsupported repository version {0}. Only versions up to {1} are supported. + + The value of {0} is not a valid configuration scope: '{1}'. + The value of {0} is not a valid configuration scope: '{1}'. + + The value of {0} is not a valid path: '{1}'. The value of {0} is not a valid path: '{1}'. diff --git a/src/Microsoft.Build.Tasks.Git/xlf/Resources.es.xlf b/src/Microsoft.Build.Tasks.Git/xlf/Resources.es.xlf index c86bcd41..124014b9 100644 --- a/src/Microsoft.Build.Tasks.Git/xlf/Resources.es.xlf +++ b/src/Microsoft.Build.Tasks.Git/xlf/Resources.es.xlf @@ -17,6 +17,11 @@ The format of the file '{0}' is invalid. + + Home relative paths are not allowed when {0} is '{1}': '{2}' + Home relative paths are not allowed when {0} is '{1}': '{2}' + + Repository does not have a working directory. Repository does not have a working directory. @@ -112,6 +117,11 @@ Unsupported repository version {0}. Only versions up to {1} are supported. + + The value of {0} is not a valid configuration scope: '{1}'. + The value of {0} is not a valid configuration scope: '{1}'. + + The value of {0} is not a valid path: '{1}'. The value of {0} is not a valid path: '{1}'. diff --git a/src/Microsoft.Build.Tasks.Git/xlf/Resources.fr.xlf b/src/Microsoft.Build.Tasks.Git/xlf/Resources.fr.xlf index 16acfed9..f683c68a 100644 --- a/src/Microsoft.Build.Tasks.Git/xlf/Resources.fr.xlf +++ b/src/Microsoft.Build.Tasks.Git/xlf/Resources.fr.xlf @@ -17,6 +17,11 @@ The format of the file '{0}' is invalid. + + Home relative paths are not allowed when {0} is '{1}': '{2}' + Home relative paths are not allowed when {0} is '{1}': '{2}' + + Repository does not have a working directory. Repository does not have a working directory. @@ -112,6 +117,11 @@ Unsupported repository version {0}. Only versions up to {1} are supported. + + The value of {0} is not a valid configuration scope: '{1}'. + The value of {0} is not a valid configuration scope: '{1}'. + + The value of {0} is not a valid path: '{1}'. The value of {0} is not a valid path: '{1}'. diff --git a/src/Microsoft.Build.Tasks.Git/xlf/Resources.it.xlf b/src/Microsoft.Build.Tasks.Git/xlf/Resources.it.xlf index 601581cc..0867a28b 100644 --- a/src/Microsoft.Build.Tasks.Git/xlf/Resources.it.xlf +++ b/src/Microsoft.Build.Tasks.Git/xlf/Resources.it.xlf @@ -17,6 +17,11 @@ The format of the file '{0}' is invalid. + + Home relative paths are not allowed when {0} is '{1}': '{2}' + Home relative paths are not allowed when {0} is '{1}': '{2}' + + Repository does not have a working directory. Repository does not have a working directory. @@ -112,6 +117,11 @@ Unsupported repository version {0}. Only versions up to {1} are supported. + + The value of {0} is not a valid configuration scope: '{1}'. + The value of {0} is not a valid configuration scope: '{1}'. + + The value of {0} is not a valid path: '{1}'. The value of {0} is not a valid path: '{1}'. diff --git a/src/Microsoft.Build.Tasks.Git/xlf/Resources.ja.xlf b/src/Microsoft.Build.Tasks.Git/xlf/Resources.ja.xlf index 7fb48af1..b7747a47 100644 --- a/src/Microsoft.Build.Tasks.Git/xlf/Resources.ja.xlf +++ b/src/Microsoft.Build.Tasks.Git/xlf/Resources.ja.xlf @@ -17,6 +17,11 @@ The format of the file '{0}' is invalid. + + Home relative paths are not allowed when {0} is '{1}': '{2}' + Home relative paths are not allowed when {0} is '{1}': '{2}' + + Repository does not have a working directory. Repository does not have a working directory. @@ -112,6 +117,11 @@ Unsupported repository version {0}. Only versions up to {1} are supported. + + The value of {0} is not a valid configuration scope: '{1}'. + The value of {0} is not a valid configuration scope: '{1}'. + + The value of {0} is not a valid path: '{1}'. The value of {0} is not a valid path: '{1}'. diff --git a/src/Microsoft.Build.Tasks.Git/xlf/Resources.ko.xlf b/src/Microsoft.Build.Tasks.Git/xlf/Resources.ko.xlf index 32cc6120..db4ce6d8 100644 --- a/src/Microsoft.Build.Tasks.Git/xlf/Resources.ko.xlf +++ b/src/Microsoft.Build.Tasks.Git/xlf/Resources.ko.xlf @@ -17,6 +17,11 @@ The format of the file '{0}' is invalid. + + Home relative paths are not allowed when {0} is '{1}': '{2}' + Home relative paths are not allowed when {0} is '{1}': '{2}' + + Repository does not have a working directory. Repository does not have a working directory. @@ -112,6 +117,11 @@ Unsupported repository version {0}. Only versions up to {1} are supported. + + The value of {0} is not a valid configuration scope: '{1}'. + The value of {0} is not a valid configuration scope: '{1}'. + + The value of {0} is not a valid path: '{1}'. The value of {0} is not a valid path: '{1}'. diff --git a/src/Microsoft.Build.Tasks.Git/xlf/Resources.pl.xlf b/src/Microsoft.Build.Tasks.Git/xlf/Resources.pl.xlf index 6cd29b81..97e87bb0 100644 --- a/src/Microsoft.Build.Tasks.Git/xlf/Resources.pl.xlf +++ b/src/Microsoft.Build.Tasks.Git/xlf/Resources.pl.xlf @@ -17,6 +17,11 @@ The format of the file '{0}' is invalid. + + Home relative paths are not allowed when {0} is '{1}': '{2}' + Home relative paths are not allowed when {0} is '{1}': '{2}' + + Repository does not have a working directory. Repository does not have a working directory. @@ -112,6 +117,11 @@ Unsupported repository version {0}. Only versions up to {1} are supported. + + The value of {0} is not a valid configuration scope: '{1}'. + The value of {0} is not a valid configuration scope: '{1}'. + + The value of {0} is not a valid path: '{1}'. The value of {0} is not a valid path: '{1}'. diff --git a/src/Microsoft.Build.Tasks.Git/xlf/Resources.pt-BR.xlf b/src/Microsoft.Build.Tasks.Git/xlf/Resources.pt-BR.xlf index 4556ea1e..979ecb5d 100644 --- a/src/Microsoft.Build.Tasks.Git/xlf/Resources.pt-BR.xlf +++ b/src/Microsoft.Build.Tasks.Git/xlf/Resources.pt-BR.xlf @@ -17,6 +17,11 @@ The format of the file '{0}' is invalid. + + Home relative paths are not allowed when {0} is '{1}': '{2}' + Home relative paths are not allowed when {0} is '{1}': '{2}' + + Repository does not have a working directory. Repository does not have a working directory. @@ -112,6 +117,11 @@ Unsupported repository version {0}. Only versions up to {1} are supported. + + The value of {0} is not a valid configuration scope: '{1}'. + The value of {0} is not a valid configuration scope: '{1}'. + + The value of {0} is not a valid path: '{1}'. The value of {0} is not a valid path: '{1}'. diff --git a/src/Microsoft.Build.Tasks.Git/xlf/Resources.ru.xlf b/src/Microsoft.Build.Tasks.Git/xlf/Resources.ru.xlf index d0fd3c5d..08a03856 100644 --- a/src/Microsoft.Build.Tasks.Git/xlf/Resources.ru.xlf +++ b/src/Microsoft.Build.Tasks.Git/xlf/Resources.ru.xlf @@ -17,6 +17,11 @@ The format of the file '{0}' is invalid. + + Home relative paths are not allowed when {0} is '{1}': '{2}' + Home relative paths are not allowed when {0} is '{1}': '{2}' + + Repository does not have a working directory. Repository does not have a working directory. @@ -112,6 +117,11 @@ Unsupported repository version {0}. Only versions up to {1} are supported. + + The value of {0} is not a valid configuration scope: '{1}'. + The value of {0} is not a valid configuration scope: '{1}'. + + The value of {0} is not a valid path: '{1}'. The value of {0} is not a valid path: '{1}'. diff --git a/src/Microsoft.Build.Tasks.Git/xlf/Resources.tr.xlf b/src/Microsoft.Build.Tasks.Git/xlf/Resources.tr.xlf index d31467c9..1dc290e8 100644 --- a/src/Microsoft.Build.Tasks.Git/xlf/Resources.tr.xlf +++ b/src/Microsoft.Build.Tasks.Git/xlf/Resources.tr.xlf @@ -17,6 +17,11 @@ The format of the file '{0}' is invalid. + + Home relative paths are not allowed when {0} is '{1}': '{2}' + Home relative paths are not allowed when {0} is '{1}': '{2}' + + Repository does not have a working directory. Repository does not have a working directory. @@ -112,6 +117,11 @@ Unsupported repository version {0}. Only versions up to {1} are supported. + + The value of {0} is not a valid configuration scope: '{1}'. + The value of {0} is not a valid configuration scope: '{1}'. + + The value of {0} is not a valid path: '{1}'. The value of {0} is not a valid path: '{1}'. diff --git a/src/Microsoft.Build.Tasks.Git/xlf/Resources.zh-Hans.xlf b/src/Microsoft.Build.Tasks.Git/xlf/Resources.zh-Hans.xlf index d74efb6c..fdab6004 100644 --- a/src/Microsoft.Build.Tasks.Git/xlf/Resources.zh-Hans.xlf +++ b/src/Microsoft.Build.Tasks.Git/xlf/Resources.zh-Hans.xlf @@ -17,6 +17,11 @@ The format of the file '{0}' is invalid. + + Home relative paths are not allowed when {0} is '{1}': '{2}' + Home relative paths are not allowed when {0} is '{1}': '{2}' + + Repository does not have a working directory. Repository does not have a working directory. @@ -112,6 +117,11 @@ Unsupported repository version {0}. Only versions up to {1} are supported. + + The value of {0} is not a valid configuration scope: '{1}'. + The value of {0} is not a valid configuration scope: '{1}'. + + The value of {0} is not a valid path: '{1}'. The value of {0} is not a valid path: '{1}'. diff --git a/src/Microsoft.Build.Tasks.Git/xlf/Resources.zh-Hant.xlf b/src/Microsoft.Build.Tasks.Git/xlf/Resources.zh-Hant.xlf index bce63603..d78f74cd 100644 --- a/src/Microsoft.Build.Tasks.Git/xlf/Resources.zh-Hant.xlf +++ b/src/Microsoft.Build.Tasks.Git/xlf/Resources.zh-Hant.xlf @@ -17,6 +17,11 @@ The format of the file '{0}' is invalid. + + Home relative paths are not allowed when {0} is '{1}': '{2}' + Home relative paths are not allowed when {0} is '{1}': '{2}' + + Repository does not have a working directory. Repository does not have a working directory. @@ -112,6 +117,11 @@ Unsupported repository version {0}. Only versions up to {1} are supported. + + The value of {0} is not a valid configuration scope: '{1}'. + The value of {0} is not a valid configuration scope: '{1}'. + + The value of {0} is not a valid path: '{1}'. The value of {0} is not a valid path: '{1}'. diff --git a/src/SourceLink.Git.IntegrationTests/GitHubTests.cs b/src/SourceLink.Git.IntegrationTests/GitHubTests.cs index 681804e2..69d464d4 100644 --- a/src/SourceLink.Git.IntegrationTests/GitHubTests.cs +++ b/src/SourceLink.Git.IntegrationTests/GitHubTests.cs @@ -7,6 +7,7 @@ using System.Reflection; using System.Xml.Linq; using LibGit2Sharp; +using Microsoft.Build.Tasks.Git; using TestUtilities; using Xunit; @@ -55,9 +56,6 @@ public void EmptyRepository() [ConditionalFact(typeof(DotNetSdkAvailable))] public void MutlipleProjects() { - var repoUrl = "http://github.com/test-org/test-repo"; - var repoName = "test-repo"; - var projectName2 = "Project2"; var projectFileName2 = projectName2 + ".csproj"; @@ -71,8 +69,10 @@ public void MutlipleProjects() using var repo = GitUtilities.CreateGitRepositoryWithSingleCommit( RootDir.Path, - new[] { Path.Combine(ProjectName, ProjectFileName), Path.Combine(projectName2, projectFileName2), }, - repoUrl); + new[] { Path.Combine(ProjectName, ProjectFileName), Path.Combine(projectName2, projectFileName2) }, + "http://github.com/test-org/test-repo1"); + + repo.Network.Remotes.Add("origin2", "http://github.com/test-org/test-repo2"); var commitSha = repo.Head.Tip.Sha; @@ -81,6 +81,9 @@ public void MutlipleProjects() + + origin2 + ", customTargets: "", targets: new[] @@ -97,15 +100,114 @@ public void MutlipleProjects() expectedResults: new[] { SourceRoot, - $"https://raw.githubusercontent.com/test-org/{repoName}/{commitSha}/*", + $"https://raw.githubusercontent.com/test-org/test-repo2/{commitSha}/*", s_relativeSourceLinkJsonPath, - $"http://github.com/test-org/{repoName}", + $"http://github.com/test-org/test-repo2", }, // the second project should reuse the repository info cached by the first project: buildVerbosity: "detailed", expectedBuildOutputFilter: line => line.Contains("SourceLink: Reusing cached git repository information.")); } + private void PrepareTestEnvironment() + { + var homeDir = RootDir.CreateDirectory(".home"); + var xdgDir = RootDir.CreateDirectory(".xdg"); + + EnvironmentVariables.Add("XDG_CONFIG_HOME", xdgDir.Path); + EnvironmentVariables.Add("HOME", homeDir.Path); + + if (PathUtils.IsUnixLikePlatform) + { + EnvironmentVariables.Add("MICROSOFT_SOURCELINK_TEST_ENVIRONMENT_ETC_DIR", homeDir.Path); + + xdgDir.CreateFile("config").WriteAllText(@"[remote ""origin2""]url = http://github.com/test-org/test-repo2"); + } + else + { + var gitInstallDir = RootDir.CreateDirectory(".gitinstall"); + var gitExeDir = gitInstallDir.CreateDirectory("bin"); + gitExeDir.CreateFile("git.exe"); + var etcDir = gitInstallDir.CreateDirectory("mingw64").CreateDirectory("etc"); + + etcDir.CreateFile("gitconfig").WriteAllText(@"[remote ""origin2""]url = http://github.com/test-org/test-repo2"); + + var programDataDir = RootDir.CreateDirectory(".programdata"); + + EnvironmentVariables.Add("USERPROFILE", homeDir.Path); + EnvironmentVariables.Add("PATH", gitExeDir.Path); + EnvironmentVariables.Add("PROGRAMDATA", programDataDir.Path); + } + } + + [ConditionalFact(typeof(DotNetSdkAvailable))] + public void Environment_Enabled() + { + var repo = GitUtilities.CreateGitRepositoryWithSingleCommit(ProjectDir.Path, new[] { ProjectFileName }, "http://github.com/test-org/test-repo1"); + var commitSha = repo.Head.Tip.Sha; + + PrepareTestEnvironment(); + + VerifyValues( + customProps: $@" + + false + origin2 + +", + customTargets: "", + targets: new[] + { + "Build" + }, + expressions: new[] + { + "@(SourceRoot->'%(SourceLinkUrl)')", + "$(PrivateRepositoryUrl)", + }, + expectedResults: new[] + { + $"https://raw.githubusercontent.com/test-org/test-repo2/{commitSha}/*", + $"http://github.com/test-org/test-repo2", + }); + } + + [ConditionalFact(typeof(DotNetSdkAvailable))] + public void Environment_Disabled() + { + var repo = GitUtilities.CreateGitRepositoryWithSingleCommit(ProjectDir.Path, new[] { ProjectFileName }, "http://github.com/test-org/test-repo1"); + var commitSha = repo.Head.Tip.Sha; + + PrepareTestEnvironment(); + + VerifyValues( + customProps: $@" + + true + origin2 + +", + customTargets: "", + targets: new[] + { + "Build" + }, + expressions: new[] + { + "@(SourceRoot->'%(SourceLinkUrl)')", + "$(PrivateRepositoryUrl)", + }, + expectedResults: new[] + { + $"https://raw.githubusercontent.com/test-org/test-repo1/{commitSha}/*", + $"http://github.com/test-org/test-repo1", + }, + expectedWarnings: new[] + { + string.Format(Resources.RepositoryDoesNotHaveSpecifiedRemote, "origin2", "origin") + }); + } + [ConditionalFact(typeof(DotNetSdkAvailable))] public void FullValidation_Https() { diff --git a/src/TestUtilities/DotNetSdk/DotNetSdkTestBase.cs b/src/TestUtilities/DotNetSdk/DotNetSdkTestBase.cs index 61577227..6da1c337 100644 --- a/src/TestUtilities/DotNetSdk/DotNetSdkTestBase.cs +++ b/src/TestUtilities/DotNetSdk/DotNetSdkTestBase.cs @@ -68,7 +68,7 @@ public void F() protected readonly string Configuration; protected readonly string TargetFramework; protected readonly string DotNetPath; - protected readonly IReadOnlyDictionary EnvironmentVariables; + protected readonly Dictionary EnvironmentVariables; protected static readonly string s_relativeSourceLinkJsonPath = Path.Combine("obj", "Debug", "netstandard2.0", "test.sourcelink.json"); protected static readonly string s_relativeOutputFilePath = Path.Combine("obj", "Debug", "netstandard2.0", "test.dll"); From 2ba7526e79490fd4b27b72ef6e58b2fbeda5e634 Mon Sep 17 00:00:00 2001 From: Tomas Matousek Date: Wed, 26 Jun 2019 18:40:10 -0700 Subject: [PATCH 2/2] Fix test --- src/SourceLink.Git.IntegrationTests/GitHubTests.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/SourceLink.Git.IntegrationTests/GitHubTests.cs b/src/SourceLink.Git.IntegrationTests/GitHubTests.cs index 69d464d4..6dc32ef7 100644 --- a/src/SourceLink.Git.IntegrationTests/GitHubTests.cs +++ b/src/SourceLink.Git.IntegrationTests/GitHubTests.cs @@ -121,7 +121,7 @@ private void PrepareTestEnvironment() { EnvironmentVariables.Add("MICROSOFT_SOURCELINK_TEST_ENVIRONMENT_ETC_DIR", homeDir.Path); - xdgDir.CreateFile("config").WriteAllText(@"[remote ""origin2""]url = http://github.com/test-org/test-repo2"); + xdgDir.CreateDirectory("git").CreateFile("config").WriteAllText(@"[remote ""origin2""]url = http://github.com/test-org/test-repo2"); } else {