Skip to content

Commit

Permalink
WIP: Agent updated, unit tests pass
Browse files Browse the repository at this point in the history
  • Loading branch information
tippmar-nr committed Oct 7, 2024
1 parent 709ddb6 commit 3bd7c28
Show file tree
Hide file tree
Showing 19 changed files with 268 additions and 157 deletions.
19 changes: 13 additions & 6 deletions src/Agent/NewRelic/Agent/Core/AgentInstallConfiguration.cs
Original file line number Diff line number Diff line change
Expand Up @@ -20,14 +20,21 @@ namespace NewRelic.Agent.Core
{
public static partial class AgentInstallConfiguration
{
// This field exists only for testing purposes. It allows bootstrap logic and regular
// configuration logic to use the same environment variable logic.
public static IEnvironment EnvironmentVariableProxy = new SharedInterfaces.Environment();

#if NETSTANDARD2_0
private const string NewRelicHomeEnvironmentVariable = "CORECLR_NEWRELIC_HOME";
// TODO: remove legacy env var name in v11
private static readonly string[] NewRelicHomeEnvironmentVariables = ["CORECLR_NEW_RELIC_HOME", "CORECLR_NEWRELIC_HOME"];
private const string RuntimeDirectoryName = "netcore";
#else
private const string NewRelicHomeEnvironmentVariable = "NEWRELIC_HOME";
// TODO: remove legacy env var name in v11
private static readonly string[] NewRelicHomeEnvironmentVariables = ["NEW_RELIC_HOME", "NEWRELIC_HOME"];
private const string RuntimeDirectoryName = "netframework";
#endif
private const string NewRelicInstallPathEnvironmentVariable = "NEWRELIC_INSTALL_PATH";
// TODO: remove legacy env var name in v11
private static readonly string[] NewRelicInstallPathEnvironmentVariables = ["NEW_RELIC_INSTALL_PATH", "NEWRELIC_INSTALL_PATH"];

public static bool IsWindows { get; }
#if NETFRAMEWORK
Expand Down Expand Up @@ -158,7 +165,7 @@ private static bool GetIsNetCore30OrAbove()

private static string GetNewRelicHome()
{
var newRelicHome = System.Environment.GetEnvironmentVariable(NewRelicHomeEnvironmentVariable);
var newRelicHome = EnvironmentVariableProxy.GetEnvironmentVariableFromList(NewRelicHomeEnvironmentVariables);
if (newRelicHome != null && Directory.Exists(newRelicHome)) return Path.GetFullPath(newRelicHome);
#if NETFRAMEWORK
var key = Registry.LocalMachine.OpenSubKey(@"Software\New Relic\.NET Agent");
Expand All @@ -169,14 +176,14 @@ private static string GetNewRelicHome()

private static string GetNewRelicInstallPath()
{
var newRelicInstallPath = System.Environment.GetEnvironmentVariable(NewRelicInstallPathEnvironmentVariable);
var newRelicInstallPath = EnvironmentVariableProxy.GetEnvironmentVariableFromList(NewRelicInstallPathEnvironmentVariables);
if (newRelicInstallPath != null)
{
newRelicInstallPath = Path.Combine(newRelicInstallPath, RuntimeDirectoryName);
if (Directory.Exists(newRelicInstallPath)) return newRelicInstallPath;
}

newRelicInstallPath = System.Environment.GetEnvironmentVariable(NewRelicHomeEnvironmentVariable);
newRelicInstallPath = EnvironmentVariableProxy.GetEnvironmentVariableFromList(NewRelicHomeEnvironmentVariables);
return newRelicInstallPath;
}

Expand Down
18 changes: 12 additions & 6 deletions src/Agent/NewRelic/Agent/Core/AgentManager.cs
Original file line number Diff line number Diff line change
Expand Up @@ -217,7 +217,7 @@ private void LogInitialized()
List<string> environmentVariables = new List<string> {
"CORECLR_ENABLE_PROFILING",
"CORECLR_PROFILER",
"CORECLR_NEWRELIC_HOME",
"CORECLR_NEW_RELIC_HOME",
"CORECLR_PROFILER_PATH",
"CORECLR_PROFILER_PATH_32",
"CORECLR_PROFILER_PATH_64",
Expand All @@ -226,8 +226,8 @@ private void LogInitialized()
"COR_PROFILER_PATH",
"COR_PROFILER_PATH_32",
"COR_PROFILER_PATH_64",
"NEWRELIC_HOME",
"NEWRELIC_INSTALL_PATH",
"NEW_RELIC_HOME",
"NEW_RELIC_INSTALL_PATH",
"NEW_RELIC_APP_NAME",
"RoleName",
"IISEXPRESS_SITENAME",
Expand All @@ -246,8 +246,8 @@ private void LogInitialized()
"NEW_RELIC_PROCESS_HOST_DISPLAY_NAME",
"NEW_RELIC_IGNORE_SERVER_SIDE_CONFIG",
"NEW_RELIC_LOG",
"NEWRELIC_PROFILER_LOG_DIRECTORY",
"NEWRELIC_LOG_LEVEL",
"NEW_RELIC_PROFILER_LOG_DIRECTORY",
"NEW_RELIC_LOG_LEVEL",
"NEW_RELIC_LOG_ENABLED",
"NEW_RELIC_LOG_CONSOLE",
"NEW_RELIC_LABELS",
Expand Down Expand Up @@ -285,7 +285,13 @@ private void LogInitialized()
"NEW_RELIC_CODE_LEVEL_METRICS_ENABLED",
"NEW_RELIC_SEND_DATA_ON_EXIT",
"NEW_RELIC_SEND_DATA_ON_EXIT_THRESHOLD_MS",
"NEW_RELIC_AZURE_FUNCTION_MODE_ENABLED"
"NEW_RELIC_AZURE_FUNCTION_MODE_ENABLED",
// TODO: remove in v11
"CORECLR_NEWRELIC_HOME",
"NEWRELIC_HOME",
"NEWRELIC_INSTALL_PATH",
"NEWRELIC_PROFILER_LOG_DIRECTORY",
"NEWRELIC_LOG_LEVEL",
};

List<string> environmentVariablesSensitive = new List<string> {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -284,7 +284,8 @@ public string GetFullLogFileName()

private string GetNewRelicLogDirectory()
{
var newRelicLogDirectory = ConfigLoaderHelpers.GetEnvironmentVar("NEWRELIC_LOG_DIRECTORY");
// TODO: remove legacy env var name in v11
var newRelicLogDirectory = ConfigLoaderHelpers.GetEnvironmentVar("NEW_RELIC_LOG_DIRECTORY", "NEWRELIC_LOG_DIRECTORY");
if (newRelicLogDirectory != null && _checkDirectoryExists(newRelicLogDirectory)) return _getFullPath(newRelicLogDirectory);

return newRelicLogDirectory;
Expand Down
10 changes: 8 additions & 2 deletions src/Agent/NewRelic/Agent/Core/Config/ConfigurationLoader.cs
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@
using NewRelic.Agent.Core.SharedInterfaces;
using System;
using System.IO;
using System.Linq;
using System.Xml;
using System.Xml.Schema;
using System.Xml.Serialization;
Expand Down Expand Up @@ -569,9 +570,14 @@ public static class ConfigLoaderHelpers
// configuration logic to use the same environment variable logic.
public static IEnvironment EnvironmentVariableProxy = new SharedInterfaces.Environment();

public static string GetEnvironmentVar(string name)
public static string GetEnvironmentVar(params string[] environmentVariableNames)
{
return EnvironmentVariableProxy.GetEnvironmentVariable(name);
var result = (environmentVariableNames ?? Enumerable.Empty<string>())
.Select(EnvironmentVariableProxy.GetEnvironmentVariable)
.FirstOrDefault(value => value != null);

// needs to return null instead of empty string
return result == string.Empty ? null : result;
}

public static string GetOverride(string name, string fallback)
Expand Down
32 changes: 10 additions & 22 deletions src/Agent/NewRelic/Agent/Core/Configuration/DefaultConfiguration.cs
Original file line number Diff line number Diff line change
Expand Up @@ -211,8 +211,9 @@ public virtual string AgentLicenseKey
if (_agentLicenseKey != null)
return _agentLicenseKey;

// TODO: remove legacy env var name in v11
_agentLicenseKey = _configurationManagerStatic.GetAppSetting(Constants.AppSettingsLicenseKey)
?? EnvironmentOverrides(_localConfiguration.service.licenseKey, "NEW_RELIC_LICENSE_KEY", "NEWRELIC_LICENSEKEY");
?? EnvironmentOverrides(_localConfiguration.service.licenseKey, "NEW_RELIC_LICENSE_KEY", "NEWRELIC_LICENSEKEY");

if (_agentLicenseKey != null)
_agentLicenseKey = _agentLicenseKey.Trim();
Expand Down Expand Up @@ -2509,10 +2510,7 @@ private static T ServerOverrides<T>(T server, T local) where T : class

private IEnumerable<string> EnvironmentOverrides(IEnumerable<string> local, params string[] environmentVariableNames)
{
var envValue = (environmentVariableNames ?? Enumerable.Empty<string>())
.Select(_environment.GetEnvironmentVariable)
.Where(value => value != null)
.FirstOrDefault();
var envValue = _environment.GetEnvironmentVariableFromList(environmentVariableNames ?? []);

// took this approach to eliminate a null object issue when combining the different calls together. Also a bit easier to read.
if (string.IsNullOrWhiteSpace(envValue))
Expand All @@ -2533,10 +2531,7 @@ private string EnvironmentOverrides(string local, params string[] environmentVar

public static string EnvironmentOverrides(IEnvironment environment, string local, params string[] environmentVariableNames)
{
var envValue = (environmentVariableNames ?? Enumerable.Empty<string>())
.Select(environment.GetEnvironmentVariable)
.Where(value => !string.IsNullOrWhiteSpace(value))
.FirstOrDefault(); // returns null if no env var found or if enumerable<string> is empty
var envValue = environment.GetEnvironmentVariableFromList(environmentVariableNames ?? []);

// if we get a null, we use local - should not get whitespace
if (string.IsNullOrWhiteSpace(envValue))
Expand All @@ -2549,9 +2544,7 @@ public static string EnvironmentOverrides(IEnvironment environment, string local

private uint? EnvironmentOverrides(uint? local, params string[] environmentVariableNames)
{
var env = environmentVariableNames
.Select(_environment.GetEnvironmentVariable)
.FirstOrDefault(value => value != null);
var env = _environment.GetEnvironmentVariableFromList(environmentVariableNames ?? []);

return uint.TryParse(env, out uint parsedValue) ? parsedValue : local;
}
Expand All @@ -2563,18 +2556,14 @@ public static string EnvironmentOverrides(IEnvironment environment, string local

public static int? EnvironmentOverrides(IEnvironment environment, int? local, params string[] environmentVariableNames)
{
var env = environmentVariableNames
.Select(environment.GetEnvironmentVariable)
.FirstOrDefault(value => value != null);
var env = environment.GetEnvironmentVariableFromList(environmentVariableNames ?? []);

return int.TryParse(env, out int parsedValue) ? parsedValue : local;
}

private double? EnvironmentOverrides(double? local, params string[] environmentVariableNames)
{
var env = environmentVariableNames
.Select(_environment.GetEnvironmentVariable)
.FirstOrDefault(value => value != null);
var env = _environment.GetEnvironmentVariableFromList(environmentVariableNames ?? []);

return double.TryParse(env, out double parsedValue) ? parsedValue : local;
}
Expand All @@ -2586,9 +2575,7 @@ private bool EnvironmentOverrides(bool local, params string[] environmentVariabl

public static bool EnvironmentOverrides(IEnvironment environment, bool local, params string[] environmentVariableNames)
{
var env = environmentVariableNames
.Select(environment.GetEnvironmentVariable)
.FirstOrDefault(value => value != null);
var env = environment.GetEnvironmentVariableFromList(environmentVariableNames ?? []);

if (env != null)
{
Expand Down Expand Up @@ -3003,7 +2990,8 @@ public static string GetLoggingLevelValue(IEnvironment environment, configuratio
var logLevel = "off";
if (isLoggingEnabled)
{
logLevel = EnvironmentOverrides(environment, localLogConfiguration.level, "NEWRELIC_LOG_LEVEL").ToUpper();
// TODO: remove legacy env var name in v11
logLevel = EnvironmentOverrides(environment, localLogConfiguration.level, "NEW_RELIC_LOG_LEVEL", "NEWRELIC_LOG_LEVEL").ToUpper();
}

return logLevel;
Expand Down
25 changes: 25 additions & 0 deletions src/Agent/NewRelic/Agent/Core/SharedInterfaces/Environment.cs
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,8 @@
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using NewRelic.Agent.Extensions.Logging;

namespace NewRelic.Agent.Core.SharedInterfaces
{
Expand All @@ -19,11 +21,34 @@ public string GetEnvironmentVariable(string variable)
return System.Environment.GetEnvironmentVariable(variable);
}

public string GetEnvironmentVariableFromList(params string[] variables)
{
var envValue = (variables ?? Enumerable.Empty<string>())
.Select(v => GetEnvironmentVariableInternal(v))
.FirstOrDefault(value => value != null);

return envValue == string.Empty ? null : envValue;
}

public string GetEnvironmentVariable(string variable, EnvironmentVariableTarget environmentVariableTarget)
{
return System.Environment.GetEnvironmentVariable(variable, environmentVariableTarget);
}

private string GetEnvironmentVariableInternal(string variable, EnvironmentVariableTarget environmentVariableTarget = EnvironmentVariableTarget.Process)
{
var value = System.Environment.GetEnvironmentVariable(variable, environmentVariableTarget);

// TODO: remove in v11
if (value != null && variable.StartsWith("NEWRELIC_", StringComparison.OrdinalIgnoreCase))
{
var preferredVariableName = variable.ToUpper().Replace("NEWRELIC_", "NEW_RELIC_");
Log.Warn($"The environment variable {variable} is deprecated and will be removed in version 11. Please use {preferredVariableName} instead.");
}

return value;
}

public Dictionary<string, string> GetEnvironmentVariablesWithPrefix(string prefix)
{
var environmentVariables = System.Environment.GetEnvironmentVariables();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -30,5 +30,10 @@ public Dictionary<string, string> GetEnvironmentVariablesWithPrefix(string prefi
{
return _emptyEnvVarDictionary;
}

public string GetEnvironmentVariableFromList(params string[] variables)
{
return null;
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -43,5 +43,11 @@ public interface IEnvironment
/// <exception cref="SecurityException">The caller does not have the required permission to perform this operation.</exception>
Dictionary<string, string> GetEnvironmentVariablesWithPrefix(string prefix);

/// <summary>
/// Retrieves the value of an environment variable, searching the provided list of variables in order. The first variable found is returned.
/// </summary>
/// <param name="variables">A list of one or more environment variable names to search, in order of preference</param>
/// <returns>The value of the first matching environment variable, if found, otherwise <c>null</c></returns>
string GetEnvironmentVariableFromList(params string[] variables);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -58,19 +58,19 @@ public override void Start(string commandLineArguments, Dictionary<string, strin
startInfo.EnvironmentVariables.Remove("COR_ENABLE_PROFILING");
startInfo.EnvironmentVariables.Remove("COR_PROFILER");
startInfo.EnvironmentVariables.Remove("COR_PROFILER_PATH");
startInfo.EnvironmentVariables.Remove("NEWRELIC_HOME");
startInfo.EnvironmentVariables.Remove("NEWRELIC_PROFILER_LOG_DIRECTORY");
startInfo.EnvironmentVariables.Remove("NEWRELIC_LOG_DIRECTORY");
startInfo.EnvironmentVariables.Remove("NEWRELIC_LOG_LEVEL");
startInfo.EnvironmentVariables.Remove("NEWRELIC_LICENSEKEY");
startInfo.EnvironmentVariables.Remove("NEW_RELIC_HOME");
startInfo.EnvironmentVariables.Remove("NEW_RELIC_PROFILER_LOG_DIRECTORY");
startInfo.EnvironmentVariables.Remove("NEW_RELIC_LOG_DIRECTORY");
startInfo.EnvironmentVariables.Remove("NEW_RELIC_LOG_LEVEL");
startInfo.EnvironmentVariables.Remove("NEW_RELIC_LICENSEKEY");
startInfo.EnvironmentVariables.Remove("NEW_RELIC_LICENSE_KEY");
startInfo.EnvironmentVariables.Remove("NEW_RELIC_HOST");
startInfo.EnvironmentVariables.Remove("NEWRELIC_INSTALL_PATH");
startInfo.EnvironmentVariables.Remove("NEW_RELIC_INSTALL_PATH");

startInfo.EnvironmentVariables.Remove("CORECLR_ENABLE_PROFILING");
startInfo.EnvironmentVariables.Remove("CORECLR_PROFILER");
startInfo.EnvironmentVariables.Remove("CORECLR_PROFILER_PATH");
startInfo.EnvironmentVariables.Remove("CORECLR_NEWRELIC_HOME");
startInfo.EnvironmentVariables.Remove("CORECLR_NEW_RELIC_HOME");

// configure env vars as needed for testing environment overrides
foreach (var envVar in environmentVariables)
Expand All @@ -87,7 +87,7 @@ public override void Start(string commandLineArguments, Dictionary<string, strin
startInfo.EnvironmentVariables.Add("CORECLR_ENABLE_PROFILING", "1");
startInfo.EnvironmentVariables.Add("CORECLR_PROFILER", this.ProfilerGuidOverride ?? "{36032161-FFC0-4B61-B559-F6C5D41BAE5A}");
startInfo.EnvironmentVariables.Add("CORECLR_PROFILER_PATH", profilerFilePath);
startInfo.EnvironmentVariables.Add("CORECLR_NEWRELIC_HOME", newRelicHomeDirectoryPath);
startInfo.EnvironmentVariables.Add("CORECLR_NEW_RELIC_HOME", newRelicHomeDirectoryPath);

if (UseTieredCompilation)
{
Expand All @@ -99,10 +99,10 @@ public override void Start(string commandLineArguments, Dictionary<string, strin
startInfo.EnvironmentVariables.Add("COR_ENABLE_PROFILING", "1");
startInfo.EnvironmentVariables.Add("COR_PROFILER", this.ProfilerGuidOverride ?? "{71DA0A04-7777-4EC6-9643-7D28B46A8A41}");
startInfo.EnvironmentVariables.Add("COR_PROFILER_PATH", profilerFilePath);
startInfo.EnvironmentVariables.Add("NEWRELIC_HOME", newRelicHomeDirectoryPath);
startInfo.EnvironmentVariables.Add("NEW_RELIC_HOME", newRelicHomeDirectoryPath);
}

startInfo.EnvironmentVariables.Add("NEWRELIC_PROFILER_LOG_DIRECTORY", profilerLogDirectoryPath);
startInfo.EnvironmentVariables.Add("NEW_RELIC_PROFILER_LOG_DIRECTORY", profilerLogDirectoryPath);

startInfo.Environment.Add("NEW_RELIC_AZURE_FUNCTION_MODE_ENABLED", _enableAzureFunctionMode.ToString());

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -119,19 +119,19 @@ public override void Start(string commandLineArguments, Dictionary<string, strin
startInfo.EnvironmentVariables.Remove("COR_ENABLE_PROFILING");
startInfo.EnvironmentVariables.Remove("COR_PROFILER");
startInfo.EnvironmentVariables.Remove("COR_PROFILER_PATH");
startInfo.EnvironmentVariables.Remove("NEWRELIC_HOME");
startInfo.EnvironmentVariables.Remove("NEWRELIC_PROFILER_LOG_DIRECTORY");
startInfo.EnvironmentVariables.Remove("NEWRELIC_LOG_DIRECTORY");
startInfo.EnvironmentVariables.Remove("NEWRELIC_LOG_LEVEL");
startInfo.EnvironmentVariables.Remove("NEWRELIC_LICENSEKEY");
startInfo.EnvironmentVariables.Remove("NEW_RELIC_HOME");
startInfo.EnvironmentVariables.Remove("NEW_RELIC_PROFILER_LOG_DIRECTORY");
startInfo.EnvironmentVariables.Remove("NEW_RELIC_LOG_DIRECTORY");
startInfo.EnvironmentVariables.Remove("NEW_RELIC_LOG_LEVEL");
startInfo.EnvironmentVariables.Remove("NEW_RELIC_LICENSEKEY");
startInfo.EnvironmentVariables.Remove("NEW_RELIC_LICENSE_KEY");
startInfo.EnvironmentVariables.Remove("NEW_RELIC_HOST");
startInfo.EnvironmentVariables.Remove("NEWRELIC_INSTALL_PATH");
startInfo.EnvironmentVariables.Remove("NEW_RELIC_INSTALL_PATH");

startInfo.EnvironmentVariables.Remove("CORECLR_ENABLE_PROFILING");
startInfo.EnvironmentVariables.Remove("CORECLR_PROFILER");
startInfo.EnvironmentVariables.Remove("CORECLR_PROFILER_PATH");
startInfo.EnvironmentVariables.Remove("CORECLR_NEWRELIC_HOME");
startInfo.EnvironmentVariables.Remove("CORECLR_NEW_RELIC_HOME");

// configure env vars as needed for testing environment overrides
foreach (var envVar in environmentVariables)
Expand Down
Loading

0 comments on commit 3bd7c28

Please sign in to comment.