Публикация проекта .NET 6 с неявным использованием C# 10 через Visual Studio 2022
При публикации веб-приложения ASP.NET Core 6 с C# 10
<ImplicitUsings />
включен в службу приложений Azure из профиля публикации Visual Studio 2022, сборка публикации завершается ошибкой из-за отсутствия операторов.
Фон
В C# 10 представлена новая функция неявного использования , в которой определенные директивы рассматриваются как глобальные директивы на основе SDK. Это можно включить с помощью следующих
csproj
конфигурация:
<PropertyGroup>
<ImplicitUsings>enable</ImplicitUsings>
</PropertyGroup>
Это работает точно так, как ожидалось, с локальной сборкой. Например, при нацеливании на
Microsoft.NET.Sdk.Web
SDK, я могу удалить
using
директивы для
System
,
System.Collections.Generic
,
System.Linq
и т. д.
Ошибка публикации
Однако при публикации в службу приложений Azure из профиля публикации Visual Studio 2022 в выходных данных сборки отображаются следующие ошибки:
C:\Code\MyWebApp\MyClass.cs(41,25): Error CS0246: The type or namespace name 'IEnumerable<>' could not be found (are you missing a using directive or an assembly reference?)
Это можно увидеть ниже как часть расширенного контекста:
Build started...
1>------ Build started: Project: MyWebApp, Configuration: Release Any CPU ------
1>Done building project "MyWebApp.csproj".
2>------ Publish started: Project: MyWebApp, Configuration: Release Any CPU ------
Determining projects to restore...
All projects are up-to-date for restore.
C:\Program Files\Microsoft Visual Studio\2022\Professional\MSBuild\Current\Bin\Roslyn\csc.exe /noconfig /unsafe- /checked- /nowarn:1701,1702,1701,1702,2008 /fullpaths /nostdlib+ /platform:x64 /errorreport:prompt /warn:6 /define:TRACE;RELEASE;NET;NET6_0;NETCOREAPP;NET5_0_OR_GREATER;NET6_0_OR_GREATER;NETCOREAPP1_0_OR_GREATER;NETCOREAPP1_1_OR_GREATER;NETCOREAPP2_0_OR_GREATER;NETCOREAPP2_1_OR_GREATER;NETCOREAPP2_2_OR_GREATER;NETCOREAPP3_0_OR_GREATER;NETCOREAPP3_1_OR_GREATER /errorendlocation /preferreduilang:en-US /highentropyva+ /reference: /debug+ /debug:portable /filealign:512 /optimize+ /out:obj\Release\net6.0\win-x64\MyWebApp.dll /refout:obj\Release\net6.0\win-x64\ref\MyWebApp.dll /target:exe /warnaserror- /utf8output /deterministic+ /langversion:10.0 /analyzerconfig:… /analyzer:"C:\Program Files\dotnet\sdk\6.0.100\Sdks\Microsoft.NET.Sdk.Web\analyzers\cs\Microsoft.AspNetCore.Analyzers.dll" /additionalfile:Areas\MyArea\Index.cshtml … /warnaserror+:NU1605
C:\Code\MyWebApp\MyClass.cs(41,25): Error CS0246: The type or namespace name 'IEnumerable<>' could not be found (are you missing a using directive or an assembly reference?)
2>Build failed. Check the Output window for more details.
========== Build: 1 succeeded, 0 failed, 0 up-to-date, 0 skipped ==========
========== Publish: 0 succeeded, 1 failed, 0 skipped ==========
Я предполагаю, что это как-то связано с
csc.exe
команда, созданная профилем публикации.
Профиль публикации
К сожалению, мне не сразу понятно, как исправить это в моем файле, что довольно просто:
<?xml version="1.0" encoding="utf-8"?>
<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<PropertyGroup>
<WebPublishMethod>MSDeploy</WebPublishMethod>
<ResourceId>/subscriptions/77e95f68-ed69-4bfe-9bbe-0b4d3910722e/resourceGroups/ResourceGroup/providers/Microsoft.Web/sites/MyWebApp</ResourceId>
<PublishProvider>AzureWebSite</PublishProvider>
<LastUsedBuildConfiguration>Release</LastUsedBuildConfiguration>
<LastUsedPlatform>Any CPU</LastUsedPlatform>
<LaunchSiteAfterPublish>True</LaunchSiteAfterPublish>
<ExcludeApp_Data>False</ExcludeApp_Data>
<ProjectGuid>77e95f68-ed69-4bfe-9bbe-0b4d3910722e</ProjectGuid>
<MSDeployServiceURL>mywebapp.scm.azurewebsites.net:443</MSDeployServiceURL>
<DeployIisAppPath>MyWebApp</DeployIisAppPath>
<RemoteSitePhysicalPath />
<SkipExtraFilesOnServer>False</SkipExtraFilesOnServer>
<MSDeployPublishMethod>WMSVC</MSDeployPublishMethod>
<EnableMSDeployBackup>True</EnableMSDeployBackup>
<UserName>$MyWebApp</UserName>
<_SavePWD>True</_SavePWD>
<_DestinationType>AzureWebSite</_DestinationType>
<TargetFramework>net6.0</TargetFramework>
<RuntimeIdentifier>win-x64</RuntimeIdentifier>
<SelfContained>false</SelfContained>
<InstallAspNetCoreSiteExtension>False</InstallAspNetCoreSiteExtension>
<EnableMsDeployAppOffline>True</EnableMsDeployAppOffline>
</PropertyGroup>
</Project>
(Примечание:
ResourceId
,
ProjectGuid
и т. д. анонимизированы и не относятся к реальной собственности.)
Вопрос
Признавая, что это новая функция в новой версии Visual Studio, это может быть ошибкой. Тем не менее, есть ли
pubxml
свойства, необходимые для включения
<ImplicitUsing />
характерная черта? Или есть что-то еще, что необходимо для включения этой функции с профилями публикации Visual Studio?
1 ответ
Во-первых, похоже, что это была ложная тревога. Очевидно, я забыл завершить перезагрузку своей рабочей станции после установки окончательной версии Visual Studio 2022. После перезапуска я теперь могу публиковать с полной поддержкой неявного использования. Упс.
Тем не менее, это дает хорошую возможность дать некоторое представление о том, что я обнаружил постфактум, что может помочь будущим читателям с подобными проблемами и, безусловно, помогло мне лучше понять интеграцию между различными инструментами командной строки.
Аргументы командной строки
Примечательно, что нет никаких параметров командной строки для обработки неявного использования, встроенного в любой из следующих инструментов:
- Пакет SDK для .NET 6.0 ()
- Визуальный компилятор C# ()
- Механизм сборки Майкрософт ()
Поддержка сборки Майкрософт
Вместо этого это обрабатывается с помощью Microsoft Build Engine () при работе с файлом проекта C# (), после чего он генерирует следующий промежуточный файл по адресу:
/{BaseIntermediateOutputPath}/{Configuration}/net6.0/{MyWebApp}.GlobalUsings.g.cs
например, по умолчанию:
/obj/Release/net6.0/MyWebApp.GlobalUsings.g.cs
Этот файл содержит глобальные директивы, относящиеся к настроенному SDK:
// <auto-generated/>
global using global::Microsoft.AspNetCore.Builder;
global using global::Microsoft.AspNetCore.Hosting;
…
В свою очередь, этот файл добавляется к базовому вызову компилятора C#().
Примечание. Пакет SDK для .NET 6.0, т. е.
dotnet.exe
— обеспечивает обертку как частьbuild
илиpublish
команд и, таким образом, предлагает ту же функциональность. Кроме того, по умолчанию .NET SDK сохраняет промежуточные файлы в/obj
папку, тогда как сразу удаляет их.
Поддержка С# 10
Учитывая это, функция неявного использования на самом деле не является частью C# 10 как таковой , несмотря на то, что рекламируется как таковая , а представляет собой небольшой инструментарий, встроенный в Microsoft Build Engine (
msbuild.exe
). Компилятор C# 10 ( поддерживает глобальные)using
директивы , но не знает о неявном использовании.
В конечном счете, это не так уж удивительно, поскольку компилятор C# () на самом деле не знает о файлах проекта C# (
*.csproj
) — это артефакт Microsoft Build Engine с сквозной поддержкой через .NET SDK.
Вывод
Непонятно, почему локальные сборки успешно работали с этим до полной перезагрузки, а вызовы с использованием профилей публикации Visual Studio 2022 завершились неудачно. Я предполагаю, что это как-то связано с тем, как Visual Studio собирает аргументы для компилятора C# (
csc.exe
) как часть процесса публикации. Несмотря на это, проще всего просто перезагрузить рабочую станцию после установки. В противном случае, этот пост, мы надеемся, поможет демистифицировать весь процесс.