Thread the project's C# LangVersion through the source-generator-hosted rzc discover path
- Dominant language
- C#
- Stars
- 3.2k
- Forks
- 1.3k
- PR merge metrics
- PR metrics pending
Description
### Background
[#55422](https://github.com/dotnet/sdk/pull/55422) adds an opt-in mode (behind the `_RazorToolUseSourceGenerator` MSBuild property) where the Razor tool (`rzc`) hosts the Razor source generator in-process instead of calling `RazorProjectEngine` directly, for both `generate` and `discover`. A review thread on that PR surfaced a gap in the `discover` path.
### Problem
`DiscoverCommand.ExecuteWithSourceGenerator` builds the C# parse options for the hosted generator with a hardcoded default:
```csharp
// src/RazorSdk/Tool/DiscoverCommand.cs:206
var parseOptions = RazorSourceGeneratorHost.CreateParseOptions(LanguageVersion.Default);
```
Unlike `generate` -- which exposes a `--csharp-language-version` option, has it forwarded by the `SdkRazorGenerate` task from `$(LangVersion)`, and threads it into the parse options -- `discover` has no way to receive the project's actual C# `LangVersion`. The `SdkRazorTagHelper` task doesn't forward it, and `DiscoverCommand` has no corresponding option. The synthetic compilation the generator runs over during discovery is therefore always parsed at the compiler's default C# language version.
### Impact
Two scenarios where the default diverges from the project's real C# version:
1. **Newer compiler, older TFM.** When the Roslyn assemblies backing the tool come from a newer SDK than the project's target framework, `LanguageVersion.Default` can resolve to a newer C# version than the project compiles with (e.g. C# 14 vs C# 12).
2. **`LangVersion=preview`.** A project opting into preview C# features would have discovery run at the (non-preview) default. Any preview-only construct reachable by the discovery compilation would fail to parse, so tag-helper discovery through the hosted generator could fail or diverge from the real build.
Because this path is opt-in (only active when `_RazorToolUseSourceGenerator=true`), it is **not a shipping regression** today. It should be resolved before the SG-hosted path is considered as a default.
### Proposed fix
Thread the project's C# `LangVersion` through to `discover`, mirroring `generate`:
- Add a `--csharp-language-version` option to `DiscoverCommand` (sharing the parse helper with `GenerateCommand`).
- Add a `CSharpLanguageVersion` property to the `SdkRazorTagHelper` task and forward it as `--csharp-language-version`.
- Set `CSharpLanguageVersion="$(LangVersion)"` on the `SdkRazorTagHelper` invocation in the discover targets (mirroring `CodeGeneration.targets:167` / `Component.targets:117` for generate).
- Use that value in `CreateParseOptions` instead of the hardcoded `LanguageVersion.Default`.
### Links
- PR: #55422
- Review thread: https://github.com/dotnet/sdk/pull/55422#discussion_r3643307543
/cc @davidwengier
Contributor guide
No contributing guide indexed for this repository
Assessment
This issue has not been assessed yet.