-
Notifications
You must be signed in to change notification settings - Fork 226
Remove separate component tag helper discovery #8721
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Closed
Closed
Changes from 4 commits
Commits
Show all changes
6 commits
Select commit
Hold shift + click to select a range
c82595c
Add a test
jjonescz 3a80d78
Remove separate component tag helper discovery
jjonescz c4399eb
Update tests
jjonescz 5d79b44
Add test without base class in C#
jjonescz eab33ed
Improve tests
jjonescz e6ffc6c
Test with `[HtmlTargetElement]`
jjonescz File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
93 changes: 93 additions & 0 deletions
93
...test/Microsoft.NET.Sdk.Razor.SourceGenerators.Tests/RazorSourceGeneratorComponentTests.cs
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,93 @@ | ||
| // Licensed to the .NET Foundation under one or more agreements. | ||
| // The .NET Foundation licenses this file to you under the MIT license. | ||
|
|
||
| using System.Threading.Tasks; | ||
| using Microsoft.AspNetCore.Razor.Test.Common; | ||
| using Xunit; | ||
|
|
||
| namespace Microsoft.NET.Sdk.Razor.SourceGenerators; | ||
|
|
||
| public sealed class RazorSourceGeneratorComponentTests : RazorSourceGeneratorTestsBase | ||
| { | ||
| [Fact, WorkItem("https://github.com/dotnet/razor/issues/8718")] | ||
| public async Task PartialClass() | ||
| { | ||
| // Arrange | ||
| var project = CreateTestProject(new() | ||
| { | ||
| ["Shared/Component1.razor"] = """ | ||
| <Component2 /> | ||
| """, | ||
| ["Shared/Component2.razor"] = """ | ||
| @inherits ComponentBase | ||
|
|
||
| @code { | ||
| [Parameter] | ||
| public RenderFragment? ChildContent { get; set; } | ||
| } | ||
| """ | ||
| }, new() | ||
| { | ||
| ["Component2.razor.cs"] = """ | ||
| using Microsoft.AspNetCore.Components; | ||
|
|
||
| namespace MyApp.Shared; | ||
|
|
||
| public partial class Component2 : ComponentBase | ||
| { | ||
|
|
||
| } | ||
| """ | ||
| }); | ||
| var compilation = await project.GetCompilationAsync(); | ||
| var driver = await GetDriverAsync(project); | ||
|
|
||
| // Act | ||
| var result = RunGenerator(compilation!, ref driver); | ||
|
|
||
| // Assert | ||
| Assert.Empty(result.Diagnostics); | ||
| Assert.Equal(2, result.GeneratedSources.Length); | ||
| } | ||
|
|
||
| [Fact, WorkItem("https://github.com/dotnet/razor/issues/8718")] | ||
| public async Task PartialClass_NoBaseInCSharp() | ||
| { | ||
| // Arrange | ||
| var project = CreateTestProject(new() | ||
| { | ||
| ["Shared/Component1.razor"] = """ | ||
| <Component2 /> | ||
| """, | ||
| ["Shared/Component2.razor"] = """ | ||
| @inherits ComponentBase | ||
|
|
||
| @code { | ||
| [Parameter] | ||
| public RenderFragment? ChildContent { get; set; } | ||
| } | ||
| """ | ||
| }, new() | ||
| { | ||
| ["Component2.razor.cs"] = """ | ||
| using Microsoft.AspNetCore.Components; | ||
|
|
||
| namespace MyApp.Shared; | ||
|
|
||
| public partial class Component2 | ||
| { | ||
|
|
||
| } | ||
| """ | ||
| }); | ||
| var compilation = await project.GetCompilationAsync(); | ||
| var driver = await GetDriverAsync(project); | ||
|
|
||
| // Act | ||
| var result = RunGenerator(compilation!, ref driver); | ||
|
|
||
| // Assert | ||
| Assert.Empty(result.Diagnostics); | ||
| Assert.Equal(2, result.GeneratedSources.Length); | ||
| } | ||
| } |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This is a pretty significant performance de-opt. I don't think I'm understanding why it's necessary; what's actually causing the errors here?
Uh oh!
There was an error while loading. Please reload this page.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Right, forgot to explain, sorry. For example, consider the test added in this PR. The component is discovered both in
tagHelpersFromComponentsstep andtagHelpersFromCompilationstep. In the latter, the descriptor is different than in the former, because the component from the.csfile has a propertyChildContent(appears asBoundAttributeon the descriptor), so both tag helper descriptors remain.Yes, we could deduplicate them somehow, I guess. But I'm not sure if this is such de-opt, since
compilation.AddSyntaxTrees(generatedDeclarationSyntaxTrees);was already present (in thetagHelpersFromComponentsstep). So I did it this way because I think it's safer (more similar to how it worked previously, before the regression was introduced).Uh oh!
There was an error while loading. Please reload this page.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The previous code did not need to do a full discovery on the entire compilation every time a razor file changed. This will do that, and that reduction in generator activity is where the performance savings came from. I think we need to investigate the deduping; separately, we need to decide if #8718 is a regression that needs to be serviced. If it is, then maybe we take this change and immediately work on the dedup problem.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Not sure what you mean by previous code. But before the perf improvements, the code did a full discovery on the entire compilation every time a razor file changed:
razor/src/Compiler/Microsoft.NET.Sdk.Razor.SourceGenerators/RazorSourceGenerator.cs
Lines 94 to 131 in fcae931
Right now in
main, you're right it's better, the discovery still happens for the full compilation (since fixing another regression in #8614) but it's scoped per component (tagHelperFeature.TargetSymbol = targetSymbol;):razor/src/Compiler/Microsoft.NET.Sdk.Razor.SourceGenerators/RazorSourceGenerator.cs
Lines 97 to 128 in 5803c80