Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

(#1310) List remembered arguments #2619

Merged
merged 2 commits into from
May 20, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions src/chocolatey.tests.integration/scenarios/ListScenarios.cs
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@
using NuGet.Configuration;
using FluentAssertions;
using FluentAssertions.Execution;
using NUnit.Framework;

namespace chocolatey.tests.integration.scenarios
{
Expand Down Expand Up @@ -140,7 +141,10 @@ public void Should_contain_packages_and_versions_with_a_pipe_between_them()
MockLogger.ContainsMessage("upgradepackage|1.0.0").Should().BeTrue();
}

// Windows only because decryption fallback on Mac/Linux logs a message
[Fact]
[WindowsOnly]
[Platform(Exclude = "Mono")]
public void Should_only_have_messages_related_to_package_information()
{
MockLogger.Messages.Should()
Expand Down
12 changes: 10 additions & 2 deletions src/chocolatey/infrastructure.app/services/NugetService.cs
Original file line number Diff line number Diff line change
Expand Up @@ -192,6 +192,7 @@ it is possible that incomplete package lists are returned from a command
foreach (var pkg in NugetList.GetPackages(config, _nugetLogger, _fileSystem))
{
var package = pkg; // for lamda access
string packageArgumentsUnencrypted = null;

ChocolateyPackageMetadata packageLocalMetadata;
string packageInstallLocation = null;
Expand All @@ -218,6 +219,12 @@ it is possible that incomplete package lists are returned from a command
}

deploymentLocation = packageInfo.DeploymentLocation;
if (!string.IsNullOrWhiteSpace(packageInfo.Arguments))
{
var decryptedArguments = ArgumentsUtility.DecryptPackageArgumentsFile(_fileSystem, packageInfo.Package.Id, packageInfo.Package.Version.ToNormalizedStringChecked());

packageArgumentsUnencrypted = "\n Remembered Package Arguments: \n {0}".FormatWith(string.Join(Environment.NewLine + " ", decryptedArguments));
}
}

if (!config.QuietOutput)
Expand All @@ -244,7 +251,7 @@ Package url{6}
Tags: {9}
Software Site: {10}
Software License: {11}{12}{13}{14}{15}{16}
Description: {17}{18}{19}
Description: {17}{18}{19}{20}
".FormatWith(
package.Title.EscapeCurlyBraces(),
package.Published.GetValueOrDefault().UtcDateTime.ToShortDateString(),
Expand Down Expand Up @@ -279,7 +286,8 @@ Package url{6}
package.Summary != null && !string.IsNullOrWhiteSpace(package.Summary.ToStringSafe()) ? "\r\n Summary: {0}".FormatWith(package.Summary.EscapeCurlyBraces().ToStringSafe()) : string.Empty,
package.Description.EscapeCurlyBraces().Replace("\n ", "\n").Replace("\n", "\n "),
!string.IsNullOrWhiteSpace(package.ReleaseNotes.ToStringSafe()) ? "{0} Release Notes: {1}".FormatWith(Environment.NewLine, package.ReleaseNotes.EscapeCurlyBraces().Replace("\n ", "\n").Replace("\n", "\n ")) : string.Empty,
!string.IsNullOrWhiteSpace(deploymentLocation) ? "{0} Deployed to: '{1}'".FormatWith(Environment.NewLine, deploymentLocation) : string.Empty
!string.IsNullOrWhiteSpace(deploymentLocation) ? "{0} Deployed to: '{1}'".FormatWith(Environment.NewLine, deploymentLocation) : string.Empty,
packageArgumentsUnencrypted != null ? packageArgumentsUnencrypted : string.Empty
));
}
}
Expand Down
69 changes: 69 additions & 0 deletions src/chocolatey/infrastructure.app/utility/ArgumentsUtility.cs
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,9 @@
// limitations under the License.

using System;
using System.Collections.Generic;
using chocolatey.infrastructure.app.nuget;
using chocolatey.infrastructure.filesystem;

namespace chocolatey.infrastructure.app.utility
{
Expand Down Expand Up @@ -50,6 +53,72 @@ public static bool SensitiveArgumentsProvided(string commandArguments)
;
}

public static IEnumerable<string> DecryptPackageArgumentsFile(IFileSystem fileSystem, string id, string version)
{
var argumentsPath = fileSystem.CombinePaths(ApplicationParameters.InstallLocation, ".chocolatey", "{0}.{1}".FormatWith(id, version));
var argumentsFile = fileSystem.CombinePaths(argumentsPath, ".arguments");

var arguments = string.Empty;

// Get the arguments decrypted in here and return them
try
{
if (fileSystem.FileExists(argumentsFile))
{
arguments = fileSystem.ReadFile(argumentsFile);
}
}
catch (Exception ex)
{
"chocolatey".Log().Error("There was an error attempting to read the contents of the .arguments file for version '{0}' of package '{1}'. See log file for more information.".FormatWith(version, id));
}

if (string.IsNullOrEmpty(arguments))
{
"chocolatey".Log().Debug("Unable to locate .arguments file for version '{0}' of package '{1}'.".FormatWith(version, id));
yield break;
}

// The following code is borrowed from the Chocolatey codebase, should
// be extracted to a separate location in choco executable so we can re-use it.
var packageArgumentsUnencrypted = arguments.Contains(" --") && arguments.ToStringSafe().Length > 4
? arguments
: NugetEncryptionUtility.DecryptString(arguments);

// Lets do a global check first to see if there are any sensitive arguments
// before we filter out the values used later.
var sensitiveArgs = SensitiveArgumentsProvided(packageArgumentsUnencrypted);

var packageArgumentsSplit =
packageArgumentsUnencrypted.Split(new[] { " --" }, StringSplitOptions.RemoveEmptyEntries);

foreach (var packageArgument in packageArgumentsSplit.OrEmpty())
{
var isSensitiveArgument = sensitiveArgs && SensitiveArgumentsProvided(string.Concat("--", packageArgument));

var packageArgumentSplit =
packageArgument.Split(new[] { '=' }, 2, StringSplitOptions.RemoveEmptyEntries);

var optionName = packageArgumentSplit[0].ToStringSafe();
var optionValue = string.Empty;

if (packageArgumentSplit.Length == 2 && isSensitiveArgument)
{
optionValue = "[REDACTED ARGUMENT]";
}
else if (packageArgumentSplit.Length == 2)
{
optionValue = packageArgumentSplit[1].ToStringSafe().UnquoteSafe();
if (optionValue.StartsWith("'"))
{
optionValue.UnquoteSafe();
}
}

yield return "--{0}{1}".FormatWith(optionName, string.IsNullOrWhiteSpace(optionValue) ? string.Empty : "=" + optionValue);
}
}

#pragma warning disable IDE0022, IDE1006
[Obsolete("This overload is deprecated and will be removed in v3.")]
public static bool arguments_contain_sensitive_information(string commandArguments)
Expand Down
Loading