Skip to content

Latest commit

 

History

History
87 lines (52 loc) · 7.11 KB

File metadata and controls

87 lines (52 loc) · 7.11 KB

Was this documentation helpful? Share feedback

Testing

Running Tests

Tests can be executed with the command line (via build.cmd -test), as part of the PR build, or in Visual Studio. Note that because of limited resources in the build pool, tests ran from the command line or in the build pool are serialized. This avoids test failures associated with parallel testing. Visual Studio does not have such restrictions and is best used for individual tests and test investigations. When running from the command line, using the -testgroup parameter can be used to limit the amount of tests executed. For example build.cmd -test -testgroup PR will run the same tests as the PR build.

The framework of the test assemblies is controlled by TestTargetFrameworks. The test itself is attributed with a particular framework based on the TargetFrameworkMonikerTraitAttribute.

Unit Tests

Unit test assemblies directly reference types from various dotnet-monitor assemblies. However, since most of dotnet-monitor heavily relies on code injection, there are utility classes to simplify unit test creation.

Functional Tests

Functional tests are composed of 3 main parts:

  1. The test itself, which sets up and validates the results.
  2. An instance of dotnet-monitor
  3. An instance of an application that is being monitored (from the UnitTestApp assembly)
  • ScenarioRunner is typically used to orchestrate test runs. The class will spawn both an instance of dotnet-monitor and an instance of test application. The app and the test communicate via stdio. The test communicates with dotnet-monitor via its Api surface.
  • The dotnet-monitor Api surface can be accessed through the ApiClient.
  • New scenarios can be added here.
  • The AsyncWaitScenario is sufficient for most tests.
  • Coordination of the scenario and the test is done via message passing (json over stdio) between the test and the app. To send messages to the app from the test, AppRunner's SendCommandAsync is used. In the scenario definition, ScenarioHelpers's WaitForCommandAsync is used. This can be used to synchronize various points of the test application with the execution of the dotnet-monitor Api from the test itself.

Native/Profiler Tests

This test assembly provides a test to make sure the dotnet-monitor profiler can load into a target app.

Schema Generation

Dotnet-monitor generates schema.json using unit tests. If dotnet-monitor's configuration changes, the schema.json file needs to be updated. Note that it is possible to compile option classes directly into the ConfigurationSchema project. This may be necessary in order to attribute properties appropriately for schema generation. See Microsoft.Diagnostics.Monitoring.ConfigurationSchema.csproj. See the Configuration learning path for more details.

OpenAPI generation

These assemblies and tests are used to generate the OpenAPI spec for the dotnet-monitor API. Changes to the dotnet-monitor api surface require updating openapi.json.

If using VSCode or Codespaces, you can also use the Regenerate openapi.json task.

Startup hooks / hosting startup

This assembly is injected into a dotnet-monitor runner (using DOTNET_STARTUP_HOOKS) to facilitate Assembly resolution during test runs.

Uses ASPNETCORE_HOSTINGSTARTUPASSEMBLIES to inject a service into dotnet-monitor during test time. This allows tests to locate files that are not normally part of the test deployment, such as the native profiler.

Unit tests around features that are injected via DOTNET_STARTUP_HOOKS into the target application. This currently includes the Exceptions History feature.

Misc test assemblies

Utility classes that are shared between Unit Tests and Functional Tests.

Utility classes shared between unit test assemblies.