Core Tools Version: 96 Commit hash: c54cdc36323e9543ba11fb61dd107616e9022bba
Function Runtime Version: 3.0.14916.0
C#
I'm trying to use xUnit to test an Azure Function. After setting up my test environment using the following logic, the test runs; however, the Values in local.settings.json are not loaded into environment variables, as they would be if I ran the function using func start.
What is the recommended way to load those values to environment variables when writing tests like the following?
````
var startup = new Startup();
var host = new HostBuilder()
.ConfigureWebJobs(startup.Configure)
.Build();
var sut = new Function1(....);
Assert.Equal(....);
````
Thank you,
Ben
Greetings @bgribaudo,
The function app settings values can also be read in your code as environment variables depending on the language you choose, for in this case its C#.
Please find the link to include Environment variables in your code here - functions-reference-csharp#environment-variables
This issue has been automatically marked as stale because it has been marked as requiring author feedback but has not had any activity for 4 days. It will be closed if no further activity occurs within 3 days of this comment.
Hi @v-anvari,
Thanks! The challenge is that when running automated (unit/integration) tests, the function app settings are not automatically getting loaded into environment variables, so I can't read them out using System.Environment.GetEnvironmentVariable (e.g. the example you linked to).
I ended up creating a helper method that the appropriate test class(es) call which emulates what func start does (reading each key-value pair local.settings.json's Values element into an environment variable):
````
static void ConfigureEnvironmentVariablesFromLocalSettings()
{
var path = Path.GetDirectoryName(typeof(MyClass).Assembly.Location);
var json = File.ReadAllText(Path.Join(path, "local.settings.json"));
var parsed = Newtonsoft.Json.Linq.JObject.Parse(json).Value
foreach (var item in parsed)
{
Environment.SetEnvironmentVariable(item.Key, item.Value.ToString());
}
}
````
Usage Example:
````
ConfigureEnvironmentVariablesFromLocalSettings();
var startup = new Startup();
var host = new HostBuilder()
.ConfigureWebJobs(startup.Configure)
.Build();
````
Is something like this the recommended way to make function app settings available during integration testing or is there a better alternative?
Note: The above has some catches, such as potential variable value conflicts due to parallel test execution. Also, depending on the use case, it may be desirable to ensure that environment variables are reset to their original values at test class teardown (code to do this not shown above).
Thanks,
Ben
It's indeed confusing that one can exectute the same:
new ConfigurationBuilder()
.AddJsonFile("local.settings.json", optional: true, reloadOnChange: true)
.AddEnvironmentVariables()
.Build();
in a unit test and get a completely unusable configuration object (everything is prefixed with Values:).
I too am looking for a recommended way to set up for integration tests that excercise components within the function project (not the function entry points).
The local.settings.json values are configuration appsettings which are loaded into the environment by the host runtime. Since Xunit is using its own testrunner, it doesn't know about the environments. Here's some suggestions on getting the environment variables setup with xunit.
https://stackoverflow.com/questions/57359147/how-to-use-environment-variables-in-unit-tests-net-core
https://stackoverflow.com/questions/48307861/read-values-from-local-setting-json-while-debugging-test
For the secret portions of local settings json, some options.
https://docs.microsoft.com/en-us/aspnet/core/security/app-secrets?view=aspnetcore-5.0&tabs=windows
Some implementation here.
https://damienbod.com/2020/07/12/azure-functions-configuration-and-secrets-management/
Hi @bgribaudo , Kindly let us know if the above settings has resolved the issue for you.
Thank you, @asears, for those links.
Most helpful comment
Hi @v-anvari,
Thanks! The challenge is that when running automated (unit/integration) tests, the function app settings are not automatically getting loaded into environment variables, so I can't read them out using System.Environment.GetEnvironmentVariable (e.g. the example you linked to).
I ended up creating a helper method that the appropriate test class(es) call which emulates what
func startdoes (reading each key-value pair local.settings.json'sValueselement into an environment variable):````("Values");
static void ConfigureEnvironmentVariablesFromLocalSettings()
{
var path = Path.GetDirectoryName(typeof(MyClass).Assembly.Location);
var json = File.ReadAllText(Path.Join(path, "local.settings.json"));
var parsed = Newtonsoft.Json.Linq.JObject.Parse(json).Value
}
````
Usage Example:
````
ConfigureEnvironmentVariablesFromLocalSettings();
var startup = new Startup();
var host = new HostBuilder()
.ConfigureWebJobs(startup.Configure)
.Build();
````
Is something like this the recommended way to make function app settings available during integration testing or is there a better alternative?
Note: The above has some catches, such as potential variable value conflicts due to parallel test execution. Also, depending on the use case, it may be desirable to ensure that environment variables are reset to their original values at test class teardown (code to do this not shown above).
Thanks,
Ben