一、前言
本篇主要討論.NET Core應用程序項目結構的主題,重點探索.NET Core應用程序的多平台編譯問題,這里指的多平台是指.NET Framework、.NET Core App、.NET Standard、Mono、UWP等多平台的條件編譯、項目(包)引用、編譯符號等問題。
.NET Core已經將新的項目管理配置過渡回MSBuild編譯系統中。雖然現在可以從無到有的使用VS2017來創建一個新的MSBuild項目,但是還是有好多遺留程序使用着以JSON格式存儲的項目配置文件為基礎的項目。Scott Hanselman也在博客中發文教大家怎么使用新的.NET SDK RC4工具將project.json轉換到MSBuild的.csproj項目系統。當然這篇文章也解釋了MS為什么要這么做。
MSBuild 是一種基於 XML 的項目文件格式的項目配置文件。這種格式容易理解、易於擴展並且完全受 Microsoft 支持。MSBuild 項目文件的格式使開發人員能夠充分描述哪些項需要生成,以及如何利用不同的平台和配置生成這些項。另外,項目文件的格式還使開發人員能夠創作可重用的生成規則,這些規則可以分解到不同的文件中,以便可以在產品內的不同項目之間一致地執行生成。
當時ASP.NET Core的第一個版本為了使開源平台對開發者更具吸引力,ASP.NET Core采用了一種基於JSON的項目系統project.json文件定義,這是一種與Node.js類似的定義,這對於吸引Web開發者來說是個明智的選擇。但是隨着.NET Core的整體開源,非Web開發者如UWP和Xamarin,對這種JSON項目結構並不熟悉。這些開發者和社區都希望繼續使用MSBuild的XML項目系統。因些微軟宣布他們將為.NET Core重新啟用和規范MSBuild構建系統。在最新的.NET Core SDK 1.0 RC4 版本中,dotnet cli(命令行接口,dotnet cli 1.0.0-preview3-004056及以后版本)已經包含了”dotnet migrate”命令,這個命令為了將JSON為基礎的配置項目轉換為.csproj項目配置文件。
本文不再談論如何使用新dotnet cli命令行,而卓重討論多平台編譯問題。
二、定義多平台
project.json
在project.json項目配置中定義多平台,使用的是”frameworks”節點來配置的,並且在每個平台節點下也配置了對應的項目引用或依賴。
下面的實例使用project.json定義的多平台和依賴如下:
"frameworks": { "net451": { "frameworkAssemblies": { "System.Xml": "4.0.0.0", } }, "netstandard1.6": { "dependencies": { "System.Runtime":"4.1.0", "System.Xml.XmlSerializer": "4.0.11" }, } }
MSBuild
在.csproj項目配置中定義多平台,要使用”TargetFrameworks”的XML節點來配置:
<TargetFrameworks>netstandard1.6;net45;</TargetFrameworks>
如果要定義某個平台下的依賴引用的話需要如下定義:
<ItemGroup Condition=" '$(TargetFramework)' == 'net45' "> <Reference Include="System.Xml" /> </ItemGroup> <ItemGroup Condition=" '$(TargetFramework)' == 'netstandard1.6' "> <PackageReference Include="System.Xml.XmlSerializer" Version="4.0.11"/> </ItemGroup>
當然有時候我們還需要對某個平台定義,定義編譯符號常量:
<PropertyGroup Condition="'$(TargetFramework)' == 'netstandard1.6'"> <DefineConstants>$(DefineConstants);NETSTANDARD</DefineConstants> </PropertyGroup>
這些代碼中就可以針對平台特性來編寫代碼了:
#if NETSTANDARD //netstandard1.*平台代碼 #endif
如果我們想在某個平台下,只編譯某些文件,也是可以實現的:
<ItemGroup Condition=" '$(TargetFramework)' == 'net45' ">
<Reference Include="System" />
<Reference Include="Microsoft.CSharp" />
<Compile Include="Platforms\net45\*.cs" />
</ItemGroup>
三、結語
說實話MSBuild的項目配置系統還是比較靈活的,以后整個dotnet體系的構建過程也都得到了統一。在dotnet cli中也集成了msbuild,即dotnet build。
GitHub:https://github.com/maxzhang1985/YOYOFx 如果覺還可以請Star下, 歡迎一起交流。
.NET Core 開源學習群:214741894