Skip to content

[Proposal]: MTP Command-line aliasesΒ #7249

@Youssef1313

Description

@Youssef1313

Summary

This is a proposal to allow easier migration from VSTest to MTP, by introducing a systematic way of mapping command-line options. The detailed proposal below is more technical, but the less technical summary is that this feature allows us to get back VSTest options such as --logger and --collect, but only when we know that logger or datacollector can be handled in MTP. External owners of VSTest loggers and data collectors can decide to maintain the VSTest syntax, but they definitely will need to implement the extension for MTP. The amount of VSTest extension owners is definitely much less than the whole user space of testing, so this can be manageable.

Background and Motivation

Today, we still have many users on VSTest, and we want to make the migration to MTP as smooth as possible. This proposal will serve the purpose of letting --logger trx, --collect CodeCoverage, etc to remain working, while still producing meaningful errors for unsupported loggers and data collectors.

Proposed Feature

In MTP command-line extensibility, we have the concept of CommandLineOption. Extensions (including test frameworks) can define their own command-line options, and it's an error to define the same command-line option by multiple extensions as it results in an ambiguity.

The proposal here is to have a different concept, CommandLineOptionAlias.

  • A command-line option alias, in the initial design, will be forced to be single-arity.
  • Multiple extensions can register the same command-line option alias (e.g, --logger`).
  • A command-line option alias will have a CanHandle method. Only one of the registered aliases can return true. Otherwise, it's an error.
  • If none of the registered alises can handle the given argument, that is also an error.
  • It's an error to have a command-line option with the same name as any registered alias.
  • An alias will have a Handle method that returns a list of option/value which represents the transformation of that alias.
  • Command line aliases are likely needed to be evaluated very early. Hence they won't have access to any services. They will be for the purpose of systematic syntactic transformations.

An example usage for that can be as follows:

testApplicationBuilder.CommandLineAliases.AddProvider(new TrxLoggerProvider());

internal sealed class TrxLoggerProvider : ICommandLineAlias
{
    public override string AliasName => "logger";

    public bool CanHandle(string[] arguments)
    {
        return arguments[0] == "trx" || arguments[0].StartsWith("trx;");
    }

    public IEnumerable<CommandLineAliasTransformation> Handle(string[] arguments)
    {
        if (arguments[0] == "trx") return [new CommandLineAliasTransformation("report-trx", Array.Empty<string>())];

        // Handle cases like trx;LogFileName=...
        // which will map to multiple transformations.
    }

    // Consider: Maybe it's better to combine CanHandle and Handle as a single TryHandle method.
}
  • CommandLineParseResult will remain merely the parse result of the command-line. It won't contain the transformations. However, CommandLineManager should consider the transformations. The effect of that is that ICommandLineOptions.IsOptionSet and ICommandLineOptions.TryGetOptionArgumentList will know about the transformations, and is what will set the whole thing to be working correctly together.

Drawbacks

  • This will allow doing stuff in two different ways in MTP. Users can be confused why both --logger trx and --report-trx are allowed.
  • Extra complexity in MTP extensibility that shouldn't ideally exist, but is existing only to ease migration.
  • Before going that way, I would like us to be sure that the change in command-line options is a source of pain for migrations for users. We need to prevent the additional complexity unless it's really really needed.

Metadata

Metadata

Assignees

No one assigned

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions