| File: SdkRazorGenerate.cs | Web Access |
| Project: src\sdk\src\RazorSdk\Tasks\Microsoft.NET.Sdk.Razor.Tasks.csproj (Microsoft.NET.Sdk.Razor.Tasks) |
// Licensed to the .NET Foundation under one or more agreements. // The .NET Foundation licenses this file to you under the MIT license. #nullable disable using Microsoft.Build.Framework; namespace Microsoft.AspNetCore.Razor.Tasks { public class SdkRazorGenerate : DotNetToolTask { private static readonly string[] SourceRequiredMetadata = new string[] { FullPath, GeneratedOutput, TargetPath, }; private const string GeneratedOutput = "GeneratedOutput"; private const string DocumentKind = "DocumentKind"; private const string TargetPath = "TargetPath"; private const string FullPath = "FullPath"; private const string Identity = "Identity"; private const string AssemblyName = "AssemblyName"; private const string AssemblyFilePath = "AssemblyFilePath"; private const string CssScope = "CssScope"; public string RootNamespace { get; set; } public string CSharpLanguageVersion { get; set; } [Required] public string Version { get; set; } [Required] public ITaskItem[] Configuration { get; set; } [Required] public ITaskItem[] Extensions { get; set; } [Required] public ITaskItem[] Sources { get; set; } [Required] public string ProjectRoot { get; set; } [Required] public string TagHelperManifest { get; set; } public bool GenerateDeclaration { get; set; } public bool SupportLocalizedComponentNames { get; set; } internal override string Command => "generate"; protected override bool ValidateParameters() { if (!Directory.Exists(ProjectRoot)) { Log.LogError("The specified project root directory {0} doesn't exist.", ProjectRoot); return false; } if (Configuration.Length == 0) { Log.LogError("The project {0} must provide a value for {1}.", ProjectRoot, nameof(Configuration)); return false; } for (var i = 0; i < Sources.Length; i++) { if (!EnsureRequiredMetadata(Sources[i], FullPath) || !EnsureRequiredMetadata(Sources[i], GeneratedOutput) || !EnsureRequiredMetadata(Sources[i], TargetPath)) { Log.LogError("The Razor source item '{0}' is missing a required metadata entry. Required metadata are: '{1}'", Sources[i], SourceRequiredMetadata); return false; } } for (var i = 0; i < Extensions.Length; i++) { if (!EnsureRequiredMetadata(Extensions[i], Identity) || !EnsureRequiredMetadata(Extensions[i], AssemblyName) || !EnsureRequiredMetadata(Extensions[i], AssemblyFilePath)) { return false; } } return base.ValidateParameters(); } protected override string GenerateResponseFileCommands() { var builder = new StringBuilder(); builder.AppendLine(Command); // We might be talking to a downlevel version of the command line tool, which doesn't // understand certain parameters. Assume 2.1 if we can't parse the version because 2.1 // 2.2 are the releases that have command line tool delivered by a package. if (!System.Version.TryParse(Version, out var parsedVersion)) { parsedVersion = new System.Version(2, 1); } for (var i = 0; i < Sources.Length; i++) { var input = Sources[i]; builder.AppendLine("-s"); builder.AppendLine(input.GetMetadata(FullPath)); builder.AppendLine("-r"); builder.AppendLine(input.GetMetadata(TargetPath)); builder.AppendLine("-o"); var outputPath = Path.Combine(ProjectRoot, input.GetMetadata(GeneratedOutput)); builder.AppendLine(outputPath); // Added in 3.0 if (parsedVersion.Major >= 3) { var kind = input.GetMetadata(DocumentKind); if (!string.IsNullOrEmpty(kind)) { builder.AppendLine("-k"); builder.AppendLine(kind); } } } // Added in 5.0: CSS scopes if (parsedVersion.Major >= 5) { for (var i = 0; i < Sources.Length; i++) { // Most inputs won't have an associated CSS scope, so we only want to generate // a scope parameter for those that do. Hence we need to specify in the parameter // which one we're talking about. var input = Sources[i]; var cssScope = input.GetMetadata(CssScope); if (!string.IsNullOrEmpty(cssScope)) { builder.AppendLine("-cssscopedinput"); builder.AppendLine(input.GetMetadata(FullPath)); builder.AppendLine("-cssscopevalue"); builder.AppendLine(cssScope); } } } builder.AppendLine("-p"); builder.AppendLine(ProjectRoot); builder.AppendLine("-t"); builder.AppendLine(TagHelperManifest); builder.AppendLine("-v"); builder.AppendLine(Version); builder.AppendLine("-c"); builder.AppendLine(Configuration[0].GetMetadata(Identity)); // Added in 3.0 if (parsedVersion.Major >= 3) { if (!string.IsNullOrEmpty(RootNamespace)) { builder.AppendLine("--root-namespace"); builder.AppendLine(RootNamespace); } if (GenerateDeclaration) { builder.AppendLine("--generate-declaration"); } } if (SupportLocalizedComponentNames) { builder.AppendLine("--support-localized-component-names"); } if (!string.IsNullOrEmpty(CSharpLanguageVersion)) { builder.AppendLine("--csharp-language-version"); builder.AppendLine(CSharpLanguageVersion); } for (var i = 0; i < Extensions.Length; i++) { builder.AppendLine("-n"); builder.AppendLine(Extensions[i].GetMetadata(Identity)); builder.AppendLine("-e"); builder.AppendLine(Path.GetFullPath(Extensions[i].GetMetadata(AssemblyFilePath))); } return builder.ToString(); } private bool EnsureRequiredMetadata(ITaskItem item, string metadataName) { var value = item.GetMetadata(metadataName); if (string.IsNullOrEmpty(value)) { Log.LogError($"Missing required metadata '{metadataName}' for '{item.ItemSpec}."); return false; } return true; } } }