dependabot-nuget 0.321.3 → 0.322.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/helpers/lib/NuGetUpdater/Directory.Packages.props +22 -22
- data/helpers/lib/NuGetUpdater/DotNetPackageCorrelation.Cli/Program.cs +21 -7
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Cli/Commands/AnalyzeCommand.cs +19 -11
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Cli/Commands/CloneCommand.cs +19 -9
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Cli/Commands/DiscoverCommand.cs +21 -14
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Cli/Commands/FrameworkCheckCommand.cs +8 -5
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Cli/Commands/RunCommand.cs +29 -16
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Cli/Commands/UpdateCommand.cs +20 -19
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Cli/Program.cs +2 -1
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Core/Files/GlobalJsonBuildFile.cs +5 -13
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Core/PrivateSourceTimedOutException.cs +12 -0
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Core/Run/ApiModel/JobErrorBase.cs +4 -0
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Core/Run/ApiModel/PrivateSourceTimedOut.cs +10 -0
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Core/Run/PullRequestTextGenerator.cs +1 -1
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Core/Run/UpdateHandlers/CreateSecurityUpdatePullRequestHandler.cs +1 -1
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Core/Run/UpdateHandlers/GroupUpdateAllVersionsHandler.cs +2 -2
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Core/Run/UpdateHandlers/RefreshGroupUpdatePullRequestHandler.cs +1 -1
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Core/Run/UpdateHandlers/RefreshSecurityUpdatePullRequestHandler.cs +1 -1
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Core/Run/UpdateHandlers/RefreshVersionUpdatePullRequestHandler.cs +1 -1
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Core/Updater/FileWriters/FileWriterWorker.cs +84 -34
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Core/Updater/FileWriters/XmlFileWriter.cs +17 -5
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Core/Updater/UpdateOperationBase.cs +18 -7
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Core/Utilities/MSBuildHelper.cs +15 -0
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Core.Test/Discover/DiscoveryWorkerTests.GlobalJson.cs +0 -2
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Core.Test/Discover/DiscoveryWorkerTests.cs +0 -2
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Core.Test/Files/GlobalJsonBuildFileTests.cs +0 -1
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Core.Test/Run/HttpApiHandlerTests.cs +1 -0
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Core.Test/Run/JobErrorBaseTests.cs +7 -0
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Core.Test/Run/MessageReportTests.cs +11 -0
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Core.Test/Run/PullRequestTextTests.cs +21 -22
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Core.Test/Run/RunWorkerTests.cs +1 -1
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Core.Test/Run/SerializationTests.cs +8 -0
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Core.Test/Update/FileWriters/FileWriterWorkerTests.cs +1 -1
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Core.Test/Update/FileWriters/FileWriterWorkerTests_MiscellaneousTests.cs +45 -0
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Core.Test/Update/FileWriters/XmlFileWriterTests.cs +26 -0
- data/helpers/lib/NuGetUpdater/NuGetUpdater.Core.Test/Utilities/MSBuildHelperTests.cs +16 -0
- data/helpers/lib/NuGetUpdater/global.json +1 -1
- metadata +6 -4
@@ -32,13 +32,36 @@ public class FileWriterWorker
|
|
32
32
|
)
|
33
33
|
{
|
34
34
|
var updateOperations = new List<UpdateOperationBase>();
|
35
|
-
var
|
36
|
-
var projectDirectoryRelativeToRepoRoot = Path.GetRelativePath(repoContentsPath.FullName, projectDirectory).FullyNormalizedRootedPath();
|
35
|
+
var initialProjectDirectory = new DirectoryInfo(Path.GetDirectoryName(projectPath.FullName)!);
|
37
36
|
|
38
37
|
// first try non-project updates
|
38
|
+
var nonProjectUpdates = await ProcessNonProjectUpdatesAsync(repoContentsPath, initialProjectDirectory, dependencyName, oldDependencyVersion, newDependencyVersion);
|
39
|
+
updateOperations.AddRange(nonProjectUpdates);
|
40
|
+
|
41
|
+
// then try packages.config updates
|
42
|
+
var packagesConfigUpdates = await ProcessPackagesConfigUpdatesAsync(repoContentsPath, projectPath, dependencyName, oldDependencyVersion, newDependencyVersion);
|
43
|
+
updateOperations.AddRange(packagesConfigUpdates);
|
44
|
+
|
45
|
+
// then try project updates
|
46
|
+
var packageReferenceUpdates = await ProcessPackageReferenceUpdatesAsync(repoContentsPath, initialProjectDirectory, projectPath, dependencyName, newDependencyVersion);
|
47
|
+
updateOperations.AddRange(packageReferenceUpdates);
|
48
|
+
|
49
|
+
var normalizedUpdateOperations = UpdateOperationBase.NormalizeUpdateOperationCollection(repoContentsPath.FullName, updateOperations);
|
50
|
+
return normalizedUpdateOperations;
|
51
|
+
}
|
52
|
+
|
53
|
+
private async Task<ImmutableArray<UpdateOperationBase>> ProcessNonProjectUpdatesAsync(
|
54
|
+
DirectoryInfo repoContentsPath,
|
55
|
+
DirectoryInfo initialProjectDirectory,
|
56
|
+
string dependencyName,
|
57
|
+
NuGetVersion oldDependencyVersion,
|
58
|
+
NuGetVersion newDependencyVersion
|
59
|
+
)
|
60
|
+
{
|
61
|
+
var updateOperations = new List<UpdateOperationBase>();
|
39
62
|
var updatedDotNetToolsPath = await DotNetToolsJsonUpdater.UpdateDependencyAsync(
|
40
63
|
repoContentsPath.FullName,
|
41
|
-
|
64
|
+
initialProjectDirectory.FullName,
|
42
65
|
dependencyName,
|
43
66
|
oldDependencyVersion.ToString(),
|
44
67
|
newDependencyVersion.ToString(),
|
@@ -57,7 +80,7 @@ public class FileWriterWorker
|
|
57
80
|
|
58
81
|
var updatedGlobalJsonPath = await GlobalJsonUpdater.UpdateDependencyAsync(
|
59
82
|
repoContentsPath.FullName,
|
60
|
-
|
83
|
+
initialProjectDirectory.FullName,
|
61
84
|
dependencyName,
|
62
85
|
oldDependencyVersion.ToString(),
|
63
86
|
newDependencyVersion.ToString(),
|
@@ -74,33 +97,54 @@ public class FileWriterWorker
|
|
74
97
|
});
|
75
98
|
}
|
76
99
|
|
77
|
-
|
100
|
+
return [.. updateOperations];
|
101
|
+
}
|
102
|
+
|
103
|
+
private async Task<ImmutableArray<UpdateOperationBase>> ProcessPackagesConfigUpdatesAsync(
|
104
|
+
DirectoryInfo repoContentsPath,
|
105
|
+
FileInfo projectPath,
|
106
|
+
string dependencyName,
|
107
|
+
NuGetVersion oldDependencyVersion,
|
108
|
+
NuGetVersion newDependencyVersion
|
109
|
+
)
|
110
|
+
{
|
78
111
|
var additionalFiles = ProjectHelper.GetAllAdditionalFilesFromProject(projectPath.FullName, ProjectHelper.PathFormat.Full);
|
79
112
|
var packagesConfigFullPath = additionalFiles.Where(p => Path.GetFileName(p).Equals(ProjectHelper.PackagesConfigFileName, StringComparison.OrdinalIgnoreCase)).FirstOrDefault();
|
80
|
-
if (packagesConfigFullPath is
|
113
|
+
if (packagesConfigFullPath is null)
|
81
114
|
{
|
82
|
-
|
83
|
-
repoContentsPath.FullName,
|
84
|
-
projectPath.FullName,
|
85
|
-
dependencyName,
|
86
|
-
oldDependencyVersion.ToString(),
|
87
|
-
newDependencyVersion.ToString(),
|
88
|
-
packagesConfigFullPath,
|
89
|
-
_logger
|
90
|
-
);
|
91
|
-
var packagesConfigOperationsWithNormalizedPaths = packagesConfigOperations
|
92
|
-
.Select(op => op with { UpdatedFiles = [.. op.UpdatedFiles.Select(f => Path.GetRelativePath(repoContentsPath.FullName, f).FullyNormalizedRootedPath())] })
|
93
|
-
.ToArray();
|
94
|
-
updateOperations.AddRange(packagesConfigOperationsWithNormalizedPaths);
|
115
|
+
return [];
|
95
116
|
}
|
96
117
|
|
97
|
-
|
98
|
-
|
118
|
+
var packagesConfigOperations = await PackagesConfigUpdater.UpdateDependencyAsync(
|
119
|
+
repoContentsPath.FullName,
|
120
|
+
projectPath.FullName,
|
121
|
+
dependencyName,
|
122
|
+
oldDependencyVersion.ToString(),
|
123
|
+
newDependencyVersion.ToString(),
|
124
|
+
packagesConfigFullPath,
|
125
|
+
_logger
|
126
|
+
);
|
127
|
+
var packagesConfigOperationsWithNormalizedPaths = packagesConfigOperations
|
128
|
+
.Select(op => op with { UpdatedFiles = [.. op.UpdatedFiles.Select(f => Path.GetRelativePath(repoContentsPath.FullName, f).FullyNormalizedRootedPath())] })
|
129
|
+
.ToImmutableArray();
|
130
|
+
return packagesConfigOperationsWithNormalizedPaths;
|
131
|
+
}
|
132
|
+
|
133
|
+
private async Task<ImmutableArray<UpdateOperationBase>> ProcessPackageReferenceUpdatesAsync(
|
134
|
+
DirectoryInfo repoContentsPath,
|
135
|
+
DirectoryInfo initialProjectDirectory,
|
136
|
+
FileInfo projectPath,
|
137
|
+
string dependencyName,
|
138
|
+
NuGetVersion newDependencyVersion
|
139
|
+
)
|
140
|
+
{
|
141
|
+
var initialProjectDirectoryRelativeToRepoRoot = Path.GetRelativePath(repoContentsPath.FullName, initialProjectDirectory.FullName).FullyNormalizedRootedPath();
|
142
|
+
var initialDiscoveryResult = await _discoveryWorker.RunAsync(repoContentsPath.FullName, initialProjectDirectoryRelativeToRepoRoot);
|
99
143
|
var initialProjectDiscovery = initialDiscoveryResult.GetProjectDiscoveryFromFullPath(repoContentsPath, projectPath);
|
100
144
|
if (initialProjectDiscovery is null)
|
101
145
|
{
|
102
146
|
_logger.Info($"Unable to find project discovery for project {projectPath}.");
|
103
|
-
return [
|
147
|
+
return [];
|
104
148
|
}
|
105
149
|
|
106
150
|
var initialRequestedDependency = initialProjectDiscovery.Dependencies
|
@@ -108,14 +152,14 @@ public class FileWriterWorker
|
|
108
152
|
if (initialRequestedDependency is null || initialRequestedDependency.Version is null)
|
109
153
|
{
|
110
154
|
_logger.Info($"Dependency {dependencyName} not found in initial project discovery.");
|
111
|
-
return [
|
155
|
+
return [];
|
112
156
|
}
|
113
157
|
|
114
158
|
var initialDependencyVersion = NuGetVersion.Parse(initialRequestedDependency.Version);
|
115
159
|
if (initialDependencyVersion >= newDependencyVersion)
|
116
160
|
{
|
117
161
|
_logger.Info($"Dependency {dependencyName} is already at version {initialDependencyVersion}, no update needed.");
|
118
|
-
return [
|
162
|
+
return [];
|
119
163
|
}
|
120
164
|
|
121
165
|
var initialTopLevelDependencies = initialProjectDiscovery.Dependencies
|
@@ -126,6 +170,7 @@ public class FileWriterWorker
|
|
126
170
|
? initialTopLevelDependencies.Select(d => d.Name.Equals(dependencyName, StringComparison.OrdinalIgnoreCase) ? newDependency : d).ToImmutableArray()
|
127
171
|
: initialTopLevelDependencies.Concat([newDependency]).ToImmutableArray();
|
128
172
|
|
173
|
+
var updateOperations = new List<UpdateOperationBase>();
|
129
174
|
foreach (var targetFramework in initialProjectDiscovery.TargetFrameworks)
|
130
175
|
{
|
131
176
|
var resolvedDependencies = await _dependencySolver.SolveAsync(initialTopLevelDependencies, desiredDependencies, targetFramework);
|
@@ -154,13 +199,13 @@ public class FileWriterWorker
|
|
154
199
|
var orderedProjectDiscovery = GetProjectDiscoveryEvaluationOrder(repoContentsPath, initialDiscoveryResult, projectPath, _logger);
|
155
200
|
|
156
201
|
// track original contents
|
157
|
-
var originalFileContents = await GetOriginalFileContentsAsync(repoContentsPath,
|
202
|
+
var originalFileContents = await GetOriginalFileContentsAsync(repoContentsPath, initialProjectDirectory, orderedProjectDiscovery);
|
158
203
|
|
159
204
|
var allUpdatedFiles = new List<string>();
|
160
205
|
foreach (var projectDiscovery in orderedProjectDiscovery)
|
161
206
|
{
|
162
207
|
var projectFullPath = Path.Join(repoContentsPath.FullName, initialDiscoveryResult.Path, projectDiscovery.FilePath).FullyNormalizedRootedPath();
|
163
|
-
var updatedFiles = await TryPerformFileWritesAsync(repoContentsPath,
|
208
|
+
var updatedFiles = await TryPerformFileWritesAsync(_fileWriter, repoContentsPath, initialProjectDirectory, projectDiscovery, resolvedDependencies.Value);
|
164
209
|
allUpdatedFiles.AddRange(updatedFiles);
|
165
210
|
}
|
166
211
|
|
@@ -172,7 +217,7 @@ public class FileWriterWorker
|
|
172
217
|
}
|
173
218
|
|
174
219
|
// this final call to discover has the benefit of also updating the lock file if it exists
|
175
|
-
var finalDiscoveryResult = await _discoveryWorker.RunAsync(repoContentsPath.FullName,
|
220
|
+
var finalDiscoveryResult = await _discoveryWorker.RunAsync(repoContentsPath.FullName, initialProjectDirectoryRelativeToRepoRoot);
|
176
221
|
var finalProjectDiscovery = finalDiscoveryResult.GetProjectDiscoveryFromFullPath(repoContentsPath, projectPath);
|
177
222
|
if (finalProjectDiscovery is null)
|
178
223
|
{
|
@@ -222,8 +267,7 @@ public class FileWriterWorker
|
|
222
267
|
updateOperations.AddRange(computedOperationsWithUpdatedFiles);
|
223
268
|
}
|
224
269
|
|
225
|
-
|
226
|
-
return normalizedUpdateOperations;
|
270
|
+
return [.. updateOperations];
|
227
271
|
}
|
228
272
|
|
229
273
|
internal static async Task<Dictionary<string, string>> GetOriginalFileContentsAsync(DirectoryInfo repoContentsPath, DirectoryInfo initialStartingDirectory, IEnumerable<ProjectDiscoveryResult> projectDiscoveryResults)
|
@@ -292,16 +336,22 @@ public class FileWriterWorker
|
|
292
336
|
return projectDiscoveryOrder;
|
293
337
|
}
|
294
338
|
|
295
|
-
|
339
|
+
internal static async Task<ImmutableArray<string>> TryPerformFileWritesAsync(
|
340
|
+
IFileWriter fileWriter,
|
341
|
+
DirectoryInfo repoContentsPath,
|
342
|
+
DirectoryInfo originalDiscoveryDirectory,
|
343
|
+
ProjectDiscoveryResult projectDiscovery,
|
344
|
+
ImmutableArray<Dependency> requiredPackageVersions
|
345
|
+
)
|
296
346
|
{
|
297
|
-
var originalFileContents = await GetOriginalFileContentsAsync(repoContentsPath,
|
347
|
+
var originalFileContents = await GetOriginalFileContentsAsync(repoContentsPath, originalDiscoveryDirectory, [projectDiscovery]);
|
298
348
|
var relativeFilePaths = originalFileContents.Keys
|
299
349
|
.Select(p => Path.GetRelativePath(repoContentsPath.FullName, p).FullyNormalizedRootedPath())
|
300
350
|
.ToImmutableArray();
|
301
351
|
|
302
352
|
// try update
|
303
353
|
var addPackageReferenceElementForPinnedPackages = !projectDiscovery.CentralPackageTransitivePinningEnabled;
|
304
|
-
var success = await
|
354
|
+
var success = await fileWriter.UpdatePackageVersionsAsync(repoContentsPath, relativeFilePaths, projectDiscovery.Dependencies, requiredPackageVersions, addPackageReferenceElementForPinnedPackages);
|
305
355
|
var updatedFiles = new List<string>();
|
306
356
|
foreach (var (filePath, originalContents) in originalFileContents)
|
307
357
|
{
|
@@ -320,7 +370,7 @@ public class FileWriterWorker
|
|
320
370
|
await RestoreOriginalFileContentsAsync(originalFileContents);
|
321
371
|
}
|
322
372
|
|
323
|
-
var sortedUpdatedFiles = updatedFiles.OrderBy(p => p, StringComparer.Ordinal);
|
324
|
-
return
|
373
|
+
var sortedUpdatedFiles = updatedFiles.OrderBy(p => p, StringComparer.Ordinal).ToImmutableArray();
|
374
|
+
return sortedUpdatedFiles;
|
325
375
|
}
|
326
376
|
}
|
@@ -23,15 +23,20 @@ public class XmlFileWriter : IFileWriter
|
|
23
23
|
|
24
24
|
private readonly ILogger _logger;
|
25
25
|
|
26
|
-
// these file extensions are
|
27
|
-
private static readonly HashSet<string>
|
28
|
-
|
26
|
+
// these file extensions are valid project entrypoints; everything else is ignored
|
27
|
+
private static readonly HashSet<string> SupportedProjectFileExtensions = new(StringComparer.OrdinalIgnoreCase)
|
28
|
+
{
|
29
29
|
".csproj",
|
30
30
|
".vbproj",
|
31
31
|
".fsproj",
|
32
|
+
};
|
33
|
+
|
34
|
+
// these file extensions are valid additional files and can be updated; everything else is ignored
|
35
|
+
private static readonly HashSet<string> SupportedAdditionalFileExtensions = new(StringComparer.OrdinalIgnoreCase)
|
36
|
+
{
|
32
37
|
".props",
|
33
38
|
".targets",
|
34
|
-
|
39
|
+
};
|
35
40
|
|
36
41
|
public XmlFileWriter(ILogger logger)
|
37
42
|
{
|
@@ -54,8 +59,15 @@ public class XmlFileWriter : IFileWriter
|
|
54
59
|
|
55
60
|
var updatesPerformed = requiredPackageVersions.ToDictionary(d => d.Name, _ => false, StringComparer.OrdinalIgnoreCase);
|
56
61
|
var projectRelativePath = relativeFilePaths[0];
|
62
|
+
var projectExtension = Path.GetExtension(projectRelativePath);
|
63
|
+
if (!SupportedProjectFileExtensions.Contains(projectExtension))
|
64
|
+
{
|
65
|
+
_logger.Warn($"Project extension '{projectExtension}' not supported; skipping XML update.");
|
66
|
+
return false;
|
67
|
+
}
|
68
|
+
|
57
69
|
var filesAndContentsTasks = relativeFilePaths
|
58
|
-
.Where(path =>
|
70
|
+
.Where(path => SupportedProjectFileExtensions.Contains(Path.GetExtension(path)) || SupportedAdditionalFileExtensions.Contains(Path.GetExtension(path)))
|
59
71
|
.Select(async path =>
|
60
72
|
{
|
61
73
|
var content = await ReadFileContentsAsync(repoContentsPath, path);
|
@@ -21,7 +21,18 @@ public abstract record UpdateOperationBase
|
|
21
21
|
public required NuGetVersion NewVersion { get; init; }
|
22
22
|
public required ImmutableArray<string> UpdatedFiles { get; init; }
|
23
23
|
|
24
|
-
|
24
|
+
protected abstract string GetReportText();
|
25
|
+
|
26
|
+
public string GetReport(bool includeFileNames)
|
27
|
+
{
|
28
|
+
var report = GetReportText();
|
29
|
+
if (includeFileNames)
|
30
|
+
{
|
31
|
+
report += $" in {string.Join(", ", UpdatedFiles)}";
|
32
|
+
}
|
33
|
+
|
34
|
+
return report;
|
35
|
+
}
|
25
36
|
|
26
37
|
public ReportedDependency ToReportedDependency(string projectPath, IEnumerable<ReportedDependency> previouslyReportedDependencies, IEnumerable<Dependency> updatedDependencies)
|
27
38
|
{
|
@@ -49,9 +60,9 @@ public abstract record UpdateOperationBase
|
|
49
60
|
};
|
50
61
|
}
|
51
62
|
|
52
|
-
internal static string GenerateUpdateOperationReport(IEnumerable<UpdateOperationBase> updateOperations)
|
63
|
+
internal static string GenerateUpdateOperationReport(IEnumerable<UpdateOperationBase> updateOperations, bool includeFileNames = true)
|
53
64
|
{
|
54
|
-
var updateMessages = updateOperations.Select(u => u.GetReport()).ToImmutableArray();
|
65
|
+
var updateMessages = updateOperations.Select(u => u.GetReport(includeFileNames)).Distinct(StringComparer.OrdinalIgnoreCase).ToImmutableArray();
|
55
66
|
if (updateMessages.Length == 0)
|
56
67
|
{
|
57
68
|
return string.Empty;
|
@@ -144,12 +155,12 @@ public abstract record UpdateOperationBase
|
|
144
155
|
public record DirectUpdate : UpdateOperationBase
|
145
156
|
{
|
146
157
|
public override string Type => nameof(DirectUpdate);
|
147
|
-
|
158
|
+
protected override string GetReportText()
|
148
159
|
{
|
149
160
|
var fromText = OldVersion is null
|
150
161
|
? string.Empty
|
151
162
|
: $"from {OldVersion} ";
|
152
|
-
return $"Updated {DependencyName} {fromText}to {NewVersion}
|
163
|
+
return $"Updated {DependencyName} {fromText}to {NewVersion}";
|
153
164
|
}
|
154
165
|
|
155
166
|
public sealed override string ToString() => GetString();
|
@@ -158,7 +169,7 @@ public record DirectUpdate : UpdateOperationBase
|
|
158
169
|
public record PinnedUpdate : UpdateOperationBase
|
159
170
|
{
|
160
171
|
public override string Type => nameof(PinnedUpdate);
|
161
|
-
|
172
|
+
protected override string GetReportText() => $"Pinned {DependencyName} at {NewVersion}";
|
162
173
|
public sealed override string ToString() => GetString();
|
163
174
|
}
|
164
175
|
|
@@ -168,7 +179,7 @@ public record ParentUpdate : UpdateOperationBase, IEquatable<UpdateOperationBase
|
|
168
179
|
public required string ParentDependencyName { get; init; }
|
169
180
|
public required NuGetVersion ParentNewVersion { get; init; }
|
170
181
|
|
171
|
-
|
182
|
+
protected override string GetReportText() => $"Updated {DependencyName} to {NewVersion} indirectly via {ParentDependencyName}/{ParentNewVersion}";
|
172
183
|
|
173
184
|
bool IEquatable<UpdateOperationBase>.Equals(UpdateOperationBase? other)
|
174
185
|
{
|
@@ -976,6 +976,7 @@ internal static partial class MSBuildHelper
|
|
976
976
|
ThrowOnMissingPackages(output);
|
977
977
|
ThrowOnUpdateNotPossible(output);
|
978
978
|
ThrowOnRateLimitExceeded(output);
|
979
|
+
ThrowOnTimeout(output);
|
979
980
|
ThrowOnBadResponse(output);
|
980
981
|
ThrowOnUnparseableFile(output);
|
981
982
|
}
|
@@ -1009,6 +1010,19 @@ internal static partial class MSBuildHelper
|
|
1009
1010
|
}
|
1010
1011
|
}
|
1011
1012
|
|
1013
|
+
private static void ThrowOnTimeout(string stdout)
|
1014
|
+
{
|
1015
|
+
var patterns = new[]
|
1016
|
+
{
|
1017
|
+
new Regex(@"The HTTP request to 'GET (?<Source>[^']+)' has timed out after \d+ms"),
|
1018
|
+
};
|
1019
|
+
var match = patterns.Select(p => p.Match(stdout)).Where(m => m.Success).FirstOrDefault();
|
1020
|
+
if (match is not null)
|
1021
|
+
{
|
1022
|
+
throw new PrivateSourceTimedOutException(match.Groups["Source"].Value);
|
1023
|
+
}
|
1024
|
+
}
|
1025
|
+
|
1012
1026
|
private static void ThrowOnBadResponse(string stdout)
|
1013
1027
|
{
|
1014
1028
|
var patterns = new[]
|
@@ -1043,6 +1057,7 @@ internal static partial class MSBuildHelper
|
|
1043
1057
|
new Regex(@"Unable to find package (?<PackageName>[^ ]+)\. No packages exist with this id in source\(s\): (?<PackageSource>.*)$", RegexOptions.Multiline),
|
1044
1058
|
new Regex(@"Unable to find package (?<PackageName>[^ ]+) with version \((?<PackageVersion>[^)]+)\)"),
|
1045
1059
|
new Regex(@"Unable to find package '(?<PackageName>[^ ]+)'\."),
|
1060
|
+
new Regex(@"Unable to resolve dependency '(?<PackageName>[^']+)'\. Source\(s\) used"),
|
1046
1061
|
new Regex(@"Could not resolve SDK ""(?<PackageName>[^ ]+)""\."),
|
1047
1062
|
new Regex(@"Failed to fetch results from V2 feed at '.*FindPackagesById\(\)\?id='(?<PackageName>[^']+)'&semVerLevel=2\.0\.0' with following message : Response status code does not indicate success: 404\."),
|
1048
1063
|
};
|
data/helpers/lib/NuGetUpdater/NuGetUpdater.Core.Test/Discover/DiscoveryWorkerTests.GlobalJson.cs
CHANGED
@@ -31,7 +31,6 @@ public partial class DiscoveryWorkerTests
|
|
31
31
|
{
|
32
32
|
FilePath = "global.json",
|
33
33
|
Dependencies = [
|
34
|
-
new("Microsoft.NET.Sdk", "2.2.104", DependencyType.MSBuildSdk),
|
35
34
|
new("Microsoft.Build.Traversal", "1.0.45", DependencyType.MSBuildSdk),
|
36
35
|
]
|
37
36
|
},
|
@@ -65,7 +64,6 @@ public partial class DiscoveryWorkerTests
|
|
65
64
|
{
|
66
65
|
FilePath = "global.json",
|
67
66
|
Dependencies = [
|
68
|
-
new("Microsoft.NET.Sdk", "2.2.104", DependencyType.MSBuildSdk),
|
69
67
|
new("Microsoft.Build.Traversal", "1.0.45", DependencyType.MSBuildSdk),
|
70
68
|
]
|
71
69
|
},
|
@@ -690,7 +690,6 @@ public partial class DiscoveryWorkerTests : DiscoveryWorkerTestBase
|
|
690
690
|
{
|
691
691
|
FilePath = "global.json",
|
692
692
|
Dependencies = [
|
693
|
-
new("Microsoft.NET.Sdk", "6.0.405", DependencyType.MSBuildSdk),
|
694
693
|
new("My.Custom.Sdk", "5.0.0", DependencyType.MSBuildSdk),
|
695
694
|
new("My.Other.Sdk", "1.0.0-beta", DependencyType.MSBuildSdk),
|
696
695
|
]
|
@@ -1044,7 +1043,6 @@ public partial class DiscoveryWorkerTests : DiscoveryWorkerTestBase
|
|
1044
1043
|
{
|
1045
1044
|
FilePath = "global.json",
|
1046
1045
|
Dependencies = [
|
1047
|
-
new("Microsoft.NET.Sdk", "6.0.405", DependencyType.MSBuildSdk),
|
1048
1046
|
new("My.Custom.Sdk", "5.0.0", DependencyType.MSBuildSdk),
|
1049
1047
|
new("My.Other.Sdk", "1.0.0-beta", DependencyType.MSBuildSdk),
|
1050
1048
|
]
|
@@ -53,7 +53,6 @@ public class GlobalJsonBuildFileTests
|
|
53
53
|
{
|
54
54
|
var expectedDependencies = new List<Dependency>
|
55
55
|
{
|
56
|
-
new("Microsoft.NET.Sdk", "6.0.405", DependencyType.MSBuildSdk),
|
57
56
|
new("My.Custom.Sdk", "5.0.0", DependencyType.MSBuildSdk),
|
58
57
|
new("My.Other.Sdk", "1.0.0-beta", DependencyType.MSBuildSdk)
|
59
58
|
};
|
@@ -149,6 +149,7 @@ public class HttpApiHandlerTests
|
|
149
149
|
yield return [new JobRepoNotFound("unused"), "record_update_job_error"];
|
150
150
|
yield return [new PrivateSourceAuthenticationFailure(["unused"]), "record_update_job_error"];
|
151
151
|
yield return [new PrivateSourceBadResponse(["unused"]), "record_update_job_error"];
|
152
|
+
yield return [new PrivateSourceTimedOut("unused"), "record_update_job_error"];
|
152
153
|
yield return [new PullRequestExistsForLatestVersion("unused", "unused"), "record_update_job_error"];
|
153
154
|
yield return [new PullRequestExistsForSecurityUpdate([]), "record_update_job_error"];
|
154
155
|
yield return [new SecurityUpdateDependencyNotFound(), "record_update_job_error"];
|
@@ -61,6 +61,13 @@ public class JobErrorBaseTests : TestBase
|
|
61
61
|
new PrivateSourceBadResponse(["http://nuget.example.com/v3/index.json"]),
|
62
62
|
];
|
63
63
|
|
64
|
+
// service returned corrupt package
|
65
|
+
yield return
|
66
|
+
[
|
67
|
+
new InvalidDataException("Central Directory corrupt."),
|
68
|
+
new PrivateSourceBadResponse(["http://nuget.example.com/v3/index.json"]),
|
69
|
+
];
|
70
|
+
|
64
71
|
// top-level exception turns into private_source_authentication_failure
|
65
72
|
yield return
|
66
73
|
[
|
@@ -160,6 +160,17 @@ public class MessageReportTests
|
|
160
160
|
"""
|
161
161
|
];
|
162
162
|
|
163
|
+
yield return
|
164
|
+
[
|
165
|
+
// message
|
166
|
+
new PrivateSourceTimedOut("url"),
|
167
|
+
// expected
|
168
|
+
"""
|
169
|
+
Error type: private_source_timed_out
|
170
|
+
- source: url
|
171
|
+
"""
|
172
|
+
];
|
173
|
+
|
163
174
|
yield return
|
164
175
|
[
|
165
176
|
// message
|
@@ -79,7 +79,7 @@ public class PullRequestTextTests
|
|
79
79
|
// expectedBody
|
80
80
|
"""
|
81
81
|
Performed the following updates:
|
82
|
-
- Updated Some.Package from 1.0.0 to 1.2.3
|
82
|
+
- Updated Some.Package from 1.0.0 to 1.2.3
|
83
83
|
"""
|
84
84
|
];
|
85
85
|
|
@@ -108,7 +108,7 @@ public class PullRequestTextTests
|
|
108
108
|
// expectedBody
|
109
109
|
"""
|
110
110
|
Performed the following updates:
|
111
|
-
- Updated Some.Package from 1.0.0 to 1.2.3
|
111
|
+
- Updated Some.Package from 1.0.0 to 1.2.3
|
112
112
|
"""
|
113
113
|
];
|
114
114
|
|
@@ -137,7 +137,7 @@ public class PullRequestTextTests
|
|
137
137
|
// expectedBody
|
138
138
|
"""
|
139
139
|
Performed the following updates:
|
140
|
-
- Updated Some.Package from 1.0.0 to 1.2.3
|
140
|
+
- Updated Some.Package from 1.0.0 to 1.2.3
|
141
141
|
"""
|
142
142
|
];
|
143
143
|
|
@@ -173,8 +173,8 @@ public class PullRequestTextTests
|
|
173
173
|
// expectedBody
|
174
174
|
"""
|
175
175
|
Performed the following updates:
|
176
|
-
- Updated Some.Package from 1.0.0 to 1.2.3
|
177
|
-
- Updated Some.Package from 4.0.0 to 4.5.6
|
176
|
+
- Updated Some.Package from 1.0.0 to 1.2.3
|
177
|
+
- Updated Some.Package from 4.0.0 to 4.5.6
|
178
178
|
"""
|
179
179
|
];
|
180
180
|
|
@@ -229,10 +229,10 @@ public class PullRequestTextTests
|
|
229
229
|
// expectedBody
|
230
230
|
"""
|
231
231
|
Performed the following updates:
|
232
|
-
- Updated Package.A from 0.1.0 to 1.0.0
|
233
|
-
- Updated Package.A from 0.2.0 to 2.0.0
|
234
|
-
- Updated Package.B from 0.3.0 to 3.0.0
|
235
|
-
- Updated Package.B from 0.4.0 to 4.0.0
|
232
|
+
- Updated Package.A from 0.1.0 to 1.0.0
|
233
|
+
- Updated Package.A from 0.2.0 to 2.0.0
|
234
|
+
- Updated Package.B from 0.3.0 to 3.0.0
|
235
|
+
- Updated Package.B from 0.4.0 to 4.0.0
|
236
236
|
"""
|
237
237
|
];
|
238
238
|
|
@@ -317,14 +317,14 @@ public class PullRequestTextTests
|
|
317
317
|
// expectedBody
|
318
318
|
"""
|
319
319
|
Performed the following updates:
|
320
|
-
- Updated Package.A from 0.1.0 to 1.0.0
|
321
|
-
- Updated Package.A from 0.2.0 to 2.0.0
|
322
|
-
- Updated Package.B from 0.3.0 to 3.0.0
|
323
|
-
- Updated Package.B from 0.4.0 to 4.0.0
|
324
|
-
- Updated Package.C from 0.5.0 to 5.0.0
|
325
|
-
- Updated Package.C from 0.6.0 to 6.0.0
|
326
|
-
- Updated Package.D from 0.7.0 to 7.0.0
|
327
|
-
- Updated Package.D from 0.8.0 to 8.0.0
|
320
|
+
- Updated Package.A from 0.1.0 to 1.0.0
|
321
|
+
- Updated Package.A from 0.2.0 to 2.0.0
|
322
|
+
- Updated Package.B from 0.3.0 to 3.0.0
|
323
|
+
- Updated Package.B from 0.4.0 to 4.0.0
|
324
|
+
- Updated Package.C from 0.5.0 to 5.0.0
|
325
|
+
- Updated Package.C from 0.6.0 to 6.0.0
|
326
|
+
- Updated Package.D from 0.7.0 to 7.0.0
|
327
|
+
- Updated Package.D from 0.8.0 to 8.0.0
|
328
328
|
"""
|
329
329
|
];
|
330
330
|
|
@@ -357,7 +357,7 @@ public class PullRequestTextTests
|
|
357
357
|
// expectedBody
|
358
358
|
"""
|
359
359
|
Performed the following updates:
|
360
|
-
- Updated Some.Package from 1.0.0 to 1.2.3
|
360
|
+
- Updated Some.Package from 1.0.0 to 1.2.3
|
361
361
|
"""
|
362
362
|
];
|
363
363
|
|
@@ -398,8 +398,8 @@ public class PullRequestTextTests
|
|
398
398
|
// expectedBody
|
399
399
|
"""
|
400
400
|
Performed the following updates:
|
401
|
-
- Updated Package.A from 1.0.0 to 1.2.3
|
402
|
-
- Updated Package.B from 4.0.0 to 4.5.6
|
401
|
+
- Updated Package.A from 1.0.0 to 1.2.3
|
402
|
+
- Updated Package.B from 4.0.0 to 4.5.6
|
403
403
|
"""
|
404
404
|
];
|
405
405
|
|
@@ -437,8 +437,7 @@ public class PullRequestTextTests
|
|
437
437
|
// expectedBody
|
438
438
|
"""
|
439
439
|
Performed the following updates:
|
440
|
-
- Updated Some.Package from 1.0.0 to 1.2.3
|
441
|
-
- Updated Some.Package from 1.0.0 to 1.2.3 in b.txt
|
440
|
+
- Updated Some.Package from 1.0.0 to 1.2.3
|
442
441
|
"""
|
443
442
|
];
|
444
443
|
}
|
@@ -3522,7 +3522,7 @@ public class RunWorkerTests
|
|
3522
3522
|
updaterWorker ??= new UpdaterWorker(jobId, experimentsManager, logger);
|
3523
3523
|
|
3524
3524
|
var worker = new RunWorker(jobId, testApiHandler, discoveryWorker, analyzeWorker, updaterWorker, logger);
|
3525
|
-
var repoContentsPathDirectoryInfo = new DirectoryInfo(
|
3525
|
+
var repoContentsPathDirectoryInfo = new DirectoryInfo(repoContentsPath);
|
3526
3526
|
var actualResult = await worker.RunAsync(job, repoContentsPathDirectoryInfo, repoContentsPathDirectoryInfo, "TEST-COMMIT-SHA", experimentsManager);
|
3527
3527
|
var actualApiMessages = testApiHandler.ReceivedMessages
|
3528
3528
|
.Select(m =>
|
@@ -707,6 +707,14 @@ public class SerializationTests : TestBase
|
|
707
707
|
"""
|
708
708
|
];
|
709
709
|
|
710
|
+
yield return
|
711
|
+
[
|
712
|
+
new PrivateSourceTimedOut("url"),
|
713
|
+
"""
|
714
|
+
{"data":{"error-type":"private_source_timed_out","error-details":{"source":"url"}}}
|
715
|
+
"""
|
716
|
+
];
|
717
|
+
|
710
718
|
yield return
|
711
719
|
[
|
712
720
|
new PullRequestExistsForLatestVersion("dep", "ver"),
|
data/helpers/lib/NuGetUpdater/NuGetUpdater.Core.Test/Update/FileWriters/FileWriterWorkerTests.cs
CHANGED
@@ -415,7 +415,7 @@ public class FileWriterWorkerTests : TestBase
|
|
415
415
|
""")
|
416
416
|
],
|
417
417
|
expectedOperations: [
|
418
|
-
new DirectUpdate() { DependencyName = "Some.Dependency", NewVersion = NuGetVersion.Parse("2.0.0"), UpdatedFiles = ["/
|
418
|
+
new DirectUpdate() { DependencyName = "Some.Dependency", NewVersion = NuGetVersion.Parse("2.0.0"), UpdatedFiles = ["/packages.config", "/project.csproj"] }
|
419
419
|
]
|
420
420
|
);
|
421
421
|
}
|
@@ -106,4 +106,49 @@ public class FileWriterWorkerTests_MiscellaneousTests
|
|
106
106
|
Assert.Equal("initial client content", await File.ReadAllTextAsync(Path.Join(repoContentsPath.FullName, "client/client.csproj"), TestContext.Current.CancellationToken));
|
107
107
|
Assert.Equal("initial packages config content", await File.ReadAllTextAsync(Path.Join(repoContentsPath.FullName, "client/packages.config"), TestContext.Current.CancellationToken));
|
108
108
|
}
|
109
|
+
|
110
|
+
[Fact]
|
111
|
+
public async Task TryPerformFileWrites_ReportsAppropriateUpdatedFilePaths_WhenStartingFromDifferentProjectDirectory()
|
112
|
+
{
|
113
|
+
// discovery was initiated from the "tests" directory, but we're now evaluating the "client" project for file writes
|
114
|
+
// arrange
|
115
|
+
using var tempDir = await TemporaryDirectory.CreateWithContentsAsync(
|
116
|
+
("tests/tests.csproj", """
|
117
|
+
<Project>
|
118
|
+
<ItemGroup>
|
119
|
+
<PackageReference Include="Some.Package" Version="1.0.0" />
|
120
|
+
</ItemGroup>
|
121
|
+
</Project>
|
122
|
+
"""),
|
123
|
+
("client/client.csproj", """
|
124
|
+
<Project>
|
125
|
+
<ItemGroup>
|
126
|
+
<PackageReference Include="Some.Package" Version="1.0.0" />
|
127
|
+
</ItemGroup>
|
128
|
+
</Project>
|
129
|
+
""")
|
130
|
+
);
|
131
|
+
var logger = new TestLogger();
|
132
|
+
var fileWriter = new XmlFileWriter(logger);
|
133
|
+
var originalDiscoveryDirectory = new DirectoryInfo(Path.Join(tempDir.DirectoryPath, "tests"));
|
134
|
+
var projectDiscovery = new ProjectDiscoveryResult()
|
135
|
+
{
|
136
|
+
FilePath = "../client/client.csproj",
|
137
|
+
Dependencies = [new("Some.Package", "1.0.0", DependencyType.PackageReference)],
|
138
|
+
ImportedFiles = [],
|
139
|
+
AdditionalFiles = [],
|
140
|
+
};
|
141
|
+
|
142
|
+
// act
|
143
|
+
var updatedFilePaths = await FileWriterWorker.TryPerformFileWritesAsync(
|
144
|
+
fileWriter,
|
145
|
+
new DirectoryInfo(tempDir.DirectoryPath),
|
146
|
+
originalDiscoveryDirectory,
|
147
|
+
projectDiscovery,
|
148
|
+
[new("Some.Package", "1.0.1", DependencyType.PackageReference)]
|
149
|
+
);
|
150
|
+
|
151
|
+
// assert
|
152
|
+
AssertEx.Equal(["/client/client.csproj"], updatedFilePaths);
|
153
|
+
}
|
109
154
|
}
|