20

我有一个简单的 .net 核心应用程序并通过以下命令发布它:

 dotnet publish -c Release -r win10-x64

SqlLocalDbStarter.csproj

<Project Sdk="Microsoft.NET.Sdk">

  <PropertyGroup>
    <OutputType>Exe</OutputType>
    <TargetFramework>netcoreapp2.1</TargetFramework>
  </PropertyGroup>

  <ItemGroup>
    <PackageReference Include="Microsoft.Win32.Registry" Version="4.5.0" />
  </ItemGroup>

</Project>

当发布过程完成 dotnet在文件夹win10-x64中创建文件bin\Release夹然后打开它后,该文件夹包含publish文件夹以及一些 dll 和 exe 文件。

对我来说有一些问题:

  • exe我需要PE应用程序中的哪个文件(内部/外部发布文件夹)?
  • 为什么当我剪切exe文件并将其移动到其他地方时它不运行(没有消息)?
  • 如果我需要所有dll文件来运行应用程序,那么我有两个选项(内部/外部发布文件夹),内部发布文件夹大小为 66 MB,但外部发布文件夹为 1 MB。
  • 我想要一个exe文件来运行我的程序而无需 dll 文件。

文件夹大小图像

4

3 回答 3

24

.NET 核心 3.0

.NET Core 3.0 开箱即用地支持它。它将所有内容打包在一个.exe文件中(基本控制台应用程序约为 68 MB)。通过分析静态代码引用并从最终构建中排除未使用的框架程序集,有一个PublishTrimmed=true选项可以将大小减小到 ~28 MB。

要配置single exe构建编辑您的csproj文件:

<PropertyGroup>
  <RuntimeIdentifier>win-x64</RuntimeIdentifier>
  <PublishSingleFile>true</PublishSingleFile>
</PropertyGroup>

在带有csproj文件的文件夹中的命令行上:

dotnet publish -r win-x64 -p:PublishSingleFile=true

有关更多详细信息,请参阅 Gopi 给出的一个很好的答案。

独立工具

Warp(感谢 Darien Shannon 在评论中提到它)和dotnet CoreRT。两者都可以与以前版本的 .Net Core 一起使用

它是一个类似于ILMerge的经典工具.NET Framework。这是非常容易使用。对于基本的控制台应用程序,它可以在.exe没有摇树器的情况下产生约 35 MB 和大约 10-15 MB 的摇树器。

点网核心RT

截至 2022 年 1 月,该项目已被dotnet/runtimelab 存储库中的NativeAOT实验所取代。感谢@tj

现在,您可以尝试使用 project.xml 将应用程序预编译为本机单文件可执行文件dotnet CoreRT。我说“尝试”是因为文档

该项目处于开发的早期阶段。

尽管如此,它至少适用于简单的应用程序。请参阅此处的示例。根据其描述,您需要在项目文件夹中运行以下命令:

dotnet new nuget 

这会将 nuget.config 文件添加到您的应用程序。打开文件并在下面的元素中添加以下内容:

<add key="dotnet-core" value="https://dotnet.myget.org/F/dotnet-core/api/v3/index.json" />
<add key="nuget.org" value="https://api.nuget.org/v3/index.json" protocolVersion="3" />

然后运行这个:

dotnet add package Microsoft.DotNet.ILCompiler -v 1.0.0-alpha-* 

然后运行这个:

dotnet publish -r win-x64 -c release

完成后,您可以在 /bin/x64//netcoreapp2.0/publish/ 下项目的根文件夹中找到本机可执行文件

于 2018-06-05T17:59:27.517 回答
15

.NET Core 3.0 之前

dotnet publish -r win-x64 -c Release --self-contained

非常不言自明:

  • 从当前目录发布项目。
  • 构建项目以在 Windows 64 位机器上运行。
  • 以发布配置模式构建
  • 将所有内容发布为“独立”,以便运行应用程序所需的所有内容都与我们的可执行文件打包在一起

所以这很好用,我们最终得到一个文件夹,其中包含我们的 exe 和运行它所需的一切,但问题是即使运行 HelloWorld 控制台应用程序也需要大量的资源。

发布文件夹

.NET Core 3.0 之后

dotnet publish -r win-x64 -c Release /p:PublishSingleFile=true

所有这一切都是运行我们的发布命令,但告诉它把它打包到一个文件中。您会注意到我们不再指定自包含标志。这是因为假设如果您将打包为单个 exe,您将需要它的所有依赖项。说得通。

发布文件夹

一个整洁的 exe!执行此操作时,将依赖项提取到临时目录,然后从那里运行所有内容。它本质上是我们之前发布文件夹的压缩包!我已经玩了一些游戏,老实说,它确实有效。没有什么可说的了。它只是工作。

文件大小和启动成本

  • 敏锐的眼睛会注意到上面的截图。文件大小。超过70MB!这对于一个只在屏幕上打印 Hello World 的应用程序来说太疯狂了!这在 .NET Core 3.0 的 Preview 6 中得到了解决,它具有称为 IL Linker 或 Publish trimmer 的功能,它省略了未使用的 DLL。
  • 您可能会发现的另一个问题是,第一次运行自包含可执行文件时会产生轻微的启动成本。因为它需要在第一次运行时将所有依赖项解压缩到一个临时目录,所以这需要一些时间才能完成。这并不疯狂(5 秒左右),但很明显。幸运的是,在随后的运行中,它使用了这个已经解压缩的临时文件夹,因此可以立即启动。

修改 csproj 并添加 PublishTrimmed = true。

<Project Sdk="Microsoft.NET.Sdk">

  <PropertyGroup>

    <OutputType>Exe</OutputType>

    <TargetFramework>netcoreapp3.0</TargetFramework>

    <PublishTrimmed>true</PublishTrimmed>

  </PropertyGroup>

</Project>

现在运行以下命令:

dotnet publish -r win-x64 -c Release /p:PublishSingleFile=true

参考

  1. https://dotnetcoretutorials.com/2019/06/20/publishing-a-single-exe-file-in-net-core-3-0/
  2. https://www.hanselman.com/blog/MakingATinyNETCore30EntirelySelfcontainedSingleExecutable.aspx
于 2019-06-21T22:09:09.117 回答
2

Microsoft 的此文档dotnet publish -c Release -r win10-x64使用与您使用的相同的文档,并将其记录如下(强调添加):

这将为每个目标平台创建应用程序的发布(而不是调试)版本。生成的文件放置在名为 publish的子目录中,该子目录位于项目的 .\bin\Release\netcoreapp1.1 子目录的子目录中。请注意,每个子目录都包含启动应用所需的完整文件集(包括应用文件和所有 .NET Core 文件)。

与您的应用程序文件一起,发布过程会发出一个程序数据库 (.pdb) 文件,其中包含有关您的应用程序的调试信息。该文件主要用于调试异常。您可以选择不将其与应用程序的文件打包。但是,如果您想调试应用程序的发布版本,您应该保存它。

因此,要部署的正确文件是publish子目录中的文件。该目录超过 60 MB,因为它包含独立部署所需的 .NET 核心库。

于 2018-06-05T16:45:55.587 回答