From 1bb088839b42211e689a55c9d9b3cd3fd6fccff1 Mon Sep 17 00:00:00 2001 From: Safia Abdalla Date: Wed, 17 Mar 2021 16:38:34 -0700 Subject: [PATCH 1/2] Respect consolidated views in all document classifiers --- ...nsolidatedMvcViewDocumentClassifierPass.cs | 90 ------------------- .../src/MvcViewDocumentClassifierPass.cs | 21 ++++- .../src/PublicAPI.Unshipped.txt | 7 +- .../src/RazorExtensions.cs | 10 +-- .../src/RazorPageDocumentClassifierPass.cs | 21 ++++- ...idatedMvcViewDocumentClassifierPassTest.cs | 12 +-- 6 files changed, 48 insertions(+), 113 deletions(-) delete mode 100644 src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/ConsolidatedMvcViewDocumentClassifierPass.cs diff --git a/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/ConsolidatedMvcViewDocumentClassifierPass.cs b/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/ConsolidatedMvcViewDocumentClassifierPass.cs deleted file mode 100644 index 715ae3496e89..000000000000 --- a/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/ConsolidatedMvcViewDocumentClassifierPass.cs +++ /dev/null @@ -1,90 +0,0 @@ -// Copyright (c) .NET Foundation. All rights reserved. -// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. - -using System; -using Microsoft.AspNetCore.Razor.Language; -using Microsoft.AspNetCore.Razor.Language.Intermediate; - -namespace Microsoft.AspNetCore.Mvc.Razor.Extensions -{ - public sealed class ConsolidatedMvcViewDocumentClassifierPass : DocumentClassifierPassBase - { - public static readonly string MvcViewDocumentKind = "mvc.1.0.view"; - - protected override string DocumentKind => MvcViewDocumentKind; - - protected override bool IsMatch(RazorCodeDocument codeDocument, DocumentIntermediateNode documentNode) => true; - - protected override void OnDocumentStructureCreated( - RazorCodeDocument codeDocument, - NamespaceDeclarationIntermediateNode @namespace, - ClassDeclarationIntermediateNode @class, - MethodDeclarationIntermediateNode method) - { - base.OnDocumentStructureCreated(codeDocument, @namespace, @class, method); - - if (!codeDocument.TryComputeNamespace(fallbackToRootNamespace: false, out var namespaceName)) - { - @namespace.Content = "AspNetCoreGeneratedDocument"; - } - else - { - @namespace.Content = namespaceName; - } - - if (!TryComputeClassName(codeDocument, out var className)) - { - // It's possible for a Razor document to not have a file path. - // Eg. When we try to generate code for an in memory document like default imports. - var checksum = Checksum.BytesToString(codeDocument.Source.GetChecksum()); - @class.ClassName = $"AspNetCore_{checksum}"; - } - else - { - @class.ClassName = className; - } - - @class.BaseType = "global::Microsoft.AspNetCore.Mvc.Razor.RazorPage"; - @class.Modifiers.Clear(); - @class.Modifiers.Add("internal"); - @class.Modifiers.Add("sealed"); - - method.MethodName = "ExecuteAsync"; - method.Modifiers.Clear(); - method.Modifiers.Add("public"); - method.Modifiers.Add("async"); - method.Modifiers.Add("override"); - method.ReturnType = $"global::{typeof(System.Threading.Tasks.Task).FullName}"; - } - - private bool TryComputeClassName(RazorCodeDocument codeDocument, out string className) - { - var filePath = codeDocument.Source.RelativePath ?? codeDocument.Source.FilePath; - if (string.IsNullOrEmpty(filePath)) - { - className = null; - return false; - } - - className = GetClassNameFromPath(filePath); - return true; - } - - private static string GetClassNameFromPath(string path) - { - const string cshtmlExtension = ".cshtml"; - - if (string.IsNullOrEmpty(path)) - { - return path; - } - - if (path.EndsWith(cshtmlExtension, StringComparison.OrdinalIgnoreCase)) - { - path = path.Substring(0, path.Length - cshtmlExtension.Length); - } - - return CSharpIdentifier.SanitizeIdentifier(path); - } - } -} \ No newline at end of file diff --git a/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/MvcViewDocumentClassifierPass.cs b/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/MvcViewDocumentClassifierPass.cs index 7ab07afc8ba2..b30e372ee746 100644 --- a/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/MvcViewDocumentClassifierPass.cs +++ b/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/MvcViewDocumentClassifierPass.cs @@ -9,12 +9,19 @@ namespace Microsoft.AspNetCore.Mvc.Razor.Extensions { public class MvcViewDocumentClassifierPass : DocumentClassifierPassBase { + private bool _useConsolidatedMvcViews = false; + public static readonly string MvcViewDocumentKind = "mvc.1.0.view"; protected override string DocumentKind => MvcViewDocumentKind; protected override bool IsMatch(RazorCodeDocument codeDocument, DocumentIntermediateNode documentNode) => true; + public MvcViewDocumentClassifierPass(bool useConsolidatedMvcViews = false) + { + _useConsolidatedMvcViews = useConsolidatedMvcViews; + } + protected override void OnDocumentStructureCreated( RazorCodeDocument codeDocument, NamespaceDeclarationIntermediateNode @namespace, @@ -25,7 +32,7 @@ protected override void OnDocumentStructureCreated( if (!codeDocument.TryComputeNamespace(fallbackToRootNamespace: false, out var namespaceName)) { - @namespace.Content = "AspNetCore"; + @namespace.Content = _useConsolidatedMvcViews ? "AspNetCoreGeneratedDocument" : "AspNetCore"; } else { @@ -47,7 +54,15 @@ protected override void OnDocumentStructureCreated( @class.BaseType = "global::Microsoft.AspNetCore.Mvc.Razor.RazorPage"; @class.Modifiers.Clear(); - @class.Modifiers.Add("public"); + if (_useConsolidatedMvcViews) + { + @class.Modifiers.Add("internal"); + @class.Modifiers.Add("sealed"); + } + else + { + @class.Modifiers.Add("public"); + } method.MethodName = "ExecuteAsync"; method.Modifiers.Clear(); @@ -87,4 +102,4 @@ private static string GetClassNameFromPath(string path) return CSharpIdentifier.SanitizeIdentifier(path); } } -} +} \ No newline at end of file diff --git a/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/PublicAPI.Unshipped.txt b/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/PublicAPI.Unshipped.txt index e4a5fa72ae36..4e70623e7865 100644 --- a/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/PublicAPI.Unshipped.txt +++ b/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/PublicAPI.Unshipped.txt @@ -1,4 +1,5 @@ #nullable enable -Microsoft.AspNetCore.Mvc.Razor.Extensions.ConsolidatedMvcViewDocumentClassifierPass -Microsoft.AspNetCore.Mvc.Razor.Extensions.ConsolidatedMvcViewDocumentClassifierPass.ConsolidatedMvcViewDocumentClassifierPass() -> void -~static readonly Microsoft.AspNetCore.Mvc.Razor.Extensions.ConsolidatedMvcViewDocumentClassifierPass.MvcViewDocumentKind -> string \ No newline at end of file +*REMOVED*Microsoft.AspNetCore.Mvc.Razor.Extensions.MvcViewDocumentClassifierPass.MvcViewDocumentClassifierPass() -> void +*REMOVED*Microsoft.AspNetCore.Mvc.Razor.Extensions.RazorPageDocumentClassifierPass.RazorPageDocumentClassifierPass() -> void +Microsoft.AspNetCore.Mvc.Razor.Extensions.MvcViewDocumentClassifierPass.MvcViewDocumentClassifierPass(bool useConsolidatedMvcViews = false) -> void +Microsoft.AspNetCore.Mvc.Razor.Extensions.RazorPageDocumentClassifierPass.RazorPageDocumentClassifierPass(bool useConsolidatedMvcViews = false) -> void \ No newline at end of file diff --git a/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/RazorExtensions.cs b/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/RazorExtensions.cs index 0c7b298aa738..8825e8d8484e 100644 --- a/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/RazorExtensions.cs +++ b/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/RazorExtensions.cs @@ -38,14 +38,8 @@ public static void Register(RazorProjectEngineBuilder builder) builder.Features.Add(new ViewComponentTagHelperPass()); builder.Features.Add(new RazorPageDocumentClassifierPass()); - if (builder.Configuration.UseConsolidatedMvcViews) - { - builder.Features.Add(new ConsolidatedMvcViewDocumentClassifierPass()); - } - else - { - builder.Features.Add(new MvcViewDocumentClassifierPass()); - } + builder.Features.Add(new RazorPageDocumentClassifierPass(builder.Configuration.UseConsolidatedMvcViews)); + builder.Features.Add(new MvcViewDocumentClassifierPass(builder.Configuration.UseConsolidatedMvcViews)); builder.Features.Add(new MvcImportProjectFeature()); diff --git a/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/RazorPageDocumentClassifierPass.cs b/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/RazorPageDocumentClassifierPass.cs index 567754cd663a..7ab9d98b59a7 100644 --- a/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/RazorPageDocumentClassifierPass.cs +++ b/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/RazorPageDocumentClassifierPass.cs @@ -11,9 +11,16 @@ namespace Microsoft.AspNetCore.Mvc.Razor.Extensions { public class RazorPageDocumentClassifierPass : DocumentClassifierPassBase { + private bool _useConsolidatedMvcViews = false; + public static readonly string RazorPageDocumentKind = "mvc.1.0.razor-page"; public static readonly string RouteTemplateKey = "RouteTemplate"; + public RazorPageDocumentClassifierPass(bool useConsolidatedMvcViews = false) + { + _useConsolidatedMvcViews = useConsolidatedMvcViews; + } + private static readonly RazorProjectEngine LeadingDirectiveParsingEngine = RazorProjectEngine.Create( RazorConfiguration.Create(RazorLanguageVersion.Version_3_0, "leading-directive-parser", Array.Empty()), RazorProjectFileSystem.Create("/"), @@ -50,7 +57,7 @@ protected override void OnDocumentStructureCreated( if (!codeDocument.TryComputeNamespace(fallbackToRootNamespace: false, out var namespaceName)) { - @namespace.Content = "AspNetCore"; + @namespace.Content = _useConsolidatedMvcViews ? "AspNetCoreGeneratedDocument" : "AspNetCore"; } else { @@ -71,7 +78,15 @@ protected override void OnDocumentStructureCreated( @class.BaseType = "global::Microsoft.AspNetCore.Mvc.RazorPages.Page"; @class.Modifiers.Clear(); - @class.Modifiers.Add("public"); + if (_useConsolidatedMvcViews) + { + @class.Modifiers.Add("internal"); + @class.Modifiers.Add("sealed"); + } + else + { + @class.Modifiers.Add("public"); + } method.MethodName = "ExecuteAsync"; method.Modifiers.Clear(); @@ -178,4 +193,4 @@ private static string GetClassNameFromPath(string path) return CSharpIdentifier.SanitizeIdentifier(path); } } -} +} \ No newline at end of file diff --git a/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/test/ConsolidatedMvcViewDocumentClassifierPassTest.cs b/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/test/ConsolidatedMvcViewDocumentClassifierPassTest.cs index b4c6ed145ed7..d8d5751f60b9 100644 --- a/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/test/ConsolidatedMvcViewDocumentClassifierPassTest.cs +++ b/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/test/ConsolidatedMvcViewDocumentClassifierPassTest.cs @@ -19,7 +19,7 @@ public void ConsolidatedMvcViewDocumentClassifierPass_SetsDifferentNamespace() var projectEngine = CreateProjectEngine(); var irDocument = CreateIRDocument(projectEngine, codeDocument); - var pass = new ConsolidatedMvcViewDocumentClassifierPass + var pass = new MvcViewDocumentClassifierPass(useConsolidatedMvcViews: true) { Engine = projectEngine.Engine }; @@ -42,7 +42,7 @@ public void ConsolidatedMvcViewDocumentClassifierPass_SetsClass() var projectEngine = CreateProjectEngine(); var irDocument = CreateIRDocument(projectEngine, codeDocument); - var pass = new ConsolidatedMvcViewDocumentClassifierPass + var pass = new MvcViewDocumentClassifierPass(useConsolidatedMvcViews: true) { Engine = projectEngine.Engine }; @@ -67,7 +67,7 @@ public void MvcViewDocumentClassifierPass_NullFilePath_SetsClass() var projectEngine = CreateProjectEngine(); var irDocument = CreateIRDocument(projectEngine, codeDocument); - var pass = new ConsolidatedMvcViewDocumentClassifierPass + var pass = new MvcViewDocumentClassifierPass(useConsolidatedMvcViews: true) { Engine = projectEngine.Engine }; @@ -86,7 +86,7 @@ public void MvcViewDocumentClassifierPass_NullFilePath_SetsClass() [Theory] [InlineData("/Views/Home/Index.cshtml", "_Views_Home_Index")] [InlineData("/Areas/MyArea/Views/Home/About.cshtml", "_Areas_MyArea_Views_Home_About")] - public void MvcViewDocumentClassifierPass_UsesRelativePathToGenerateTypeName(string relativePath, string expected) + public void ConsolidatedMvcViewDocumentClassifierPass_UsesRelativePathToGenerateTypeName(string relativePath, string expected) { // Arrange var properties = new RazorSourceDocumentProperties(filePath: "ignored", relativePath: relativePath); @@ -94,7 +94,7 @@ public void MvcViewDocumentClassifierPass_UsesRelativePathToGenerateTypeName(str var projectEngine = CreateProjectEngine(); var irDocument = CreateIRDocument(projectEngine, codeDocument); - var pass = new ConsolidatedMvcViewDocumentClassifierPass + var pass = new MvcViewDocumentClassifierPass(useConsolidatedMvcViews: true) { Engine = projectEngine.Engine }; @@ -117,7 +117,7 @@ public void ConsolidatedMvcViewDocumentClassifierPass_SetsUpExecuteAsyncMethod() var projectEngine = CreateProjectEngine(); var irDocument = CreateIRDocument(projectEngine, codeDocument); - var pass = new ConsolidatedMvcViewDocumentClassifierPass + var pass = new MvcViewDocumentClassifierPass(useConsolidatedMvcViews: true) { Engine = projectEngine.Engine }; From f74e400fceeda5b4f48df71cff0a486d13bbd355 Mon Sep 17 00:00:00 2001 From: Safia Abdalla Date: Wed, 17 Mar 2021 16:49:11 -0700 Subject: [PATCH 2/2] Address feedback from peer review --- .../src/MvcViewDocumentClassifierPass.cs | 4 +++- .../src/PublicAPI.Unshipped.txt | 6 ++---- .../src/RazorExtensions.cs | 4 ++-- .../src/RazorPageDocumentClassifierPass.cs | 4 +++- 4 files changed, 10 insertions(+), 8 deletions(-) diff --git a/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/MvcViewDocumentClassifierPass.cs b/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/MvcViewDocumentClassifierPass.cs index b30e372ee746..7f0a09f729e7 100644 --- a/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/MvcViewDocumentClassifierPass.cs +++ b/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/MvcViewDocumentClassifierPass.cs @@ -17,7 +17,9 @@ public class MvcViewDocumentClassifierPass : DocumentClassifierPassBase protected override bool IsMatch(RazorCodeDocument codeDocument, DocumentIntermediateNode documentNode) => true; - public MvcViewDocumentClassifierPass(bool useConsolidatedMvcViews = false) + public MvcViewDocumentClassifierPass() : this(false) { } + + public MvcViewDocumentClassifierPass(bool useConsolidatedMvcViews) { _useConsolidatedMvcViews = useConsolidatedMvcViews; } diff --git a/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/PublicAPI.Unshipped.txt b/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/PublicAPI.Unshipped.txt index 4e70623e7865..84adfeccba4f 100644 --- a/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/PublicAPI.Unshipped.txt +++ b/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/PublicAPI.Unshipped.txt @@ -1,5 +1,3 @@ #nullable enable -*REMOVED*Microsoft.AspNetCore.Mvc.Razor.Extensions.MvcViewDocumentClassifierPass.MvcViewDocumentClassifierPass() -> void -*REMOVED*Microsoft.AspNetCore.Mvc.Razor.Extensions.RazorPageDocumentClassifierPass.RazorPageDocumentClassifierPass() -> void -Microsoft.AspNetCore.Mvc.Razor.Extensions.MvcViewDocumentClassifierPass.MvcViewDocumentClassifierPass(bool useConsolidatedMvcViews = false) -> void -Microsoft.AspNetCore.Mvc.Razor.Extensions.RazorPageDocumentClassifierPass.RazorPageDocumentClassifierPass(bool useConsolidatedMvcViews = false) -> void \ No newline at end of file +Microsoft.AspNetCore.Mvc.Razor.Extensions.MvcViewDocumentClassifierPass.MvcViewDocumentClassifierPass(bool useConsolidatedMvcViews) -> void +Microsoft.AspNetCore.Mvc.Razor.Extensions.RazorPageDocumentClassifierPass.RazorPageDocumentClassifierPass(bool useConsolidatedMvcViews) -> void \ No newline at end of file diff --git a/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/RazorExtensions.cs b/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/RazorExtensions.cs index 8825e8d8484e..48b31377c439 100644 --- a/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/RazorExtensions.cs +++ b/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/RazorExtensions.cs @@ -37,9 +37,9 @@ public static void Register(RazorProjectEngineBuilder builder) builder.Features.Add(new PagesPropertyInjectionPass()); builder.Features.Add(new ViewComponentTagHelperPass()); builder.Features.Add(new RazorPageDocumentClassifierPass()); - + builder.Features.Add(new RazorPageDocumentClassifierPass(builder.Configuration.UseConsolidatedMvcViews)); - builder.Features.Add(new MvcViewDocumentClassifierPass(builder.Configuration.UseConsolidatedMvcViews)); + builder.Features.Add(new MvcViewDocumentClassifierPass(builder.Configuration.UseConsolidatedMvcViews)); builder.Features.Add(new MvcImportProjectFeature()); diff --git a/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/RazorPageDocumentClassifierPass.cs b/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/RazorPageDocumentClassifierPass.cs index 7ab9d98b59a7..c2889be5f66e 100644 --- a/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/RazorPageDocumentClassifierPass.cs +++ b/src/Razor/Microsoft.AspNetCore.Mvc.Razor.Extensions/src/RazorPageDocumentClassifierPass.cs @@ -16,7 +16,9 @@ public class RazorPageDocumentClassifierPass : DocumentClassifierPassBase public static readonly string RazorPageDocumentKind = "mvc.1.0.razor-page"; public static readonly string RouteTemplateKey = "RouteTemplate"; - public RazorPageDocumentClassifierPass(bool useConsolidatedMvcViews = false) + public RazorPageDocumentClassifierPass() : this(false) { } + + public RazorPageDocumentClassifierPass(bool useConsolidatedMvcViews) { _useConsolidatedMvcViews = useConsolidatedMvcViews; }