GetManifestResourceStream返回NULL

问题描述 投票:65回答:10

这是一个C#.NET 4.0应用程序:

我将文本文件嵌入为资源,然后尝试在对话框中显示它:

    var assembly = Assembly.GetExecutingAssembly();
    var resourceName = "MyProj.Help.txt";

        using (Stream stream = assembly.GetManifestResourceStream(resourceName))
        {
            using (StreamReader reader = new StreamReader(stream))
            {
                string result = reader.ReadToEnd();
                System.Windows.Forms.MessageBox.Show(result, "MyProj", MessageBoxButtons.OK);
            }
        }

解决方案是MyProjSolution,可执行文件是MyProj.exe。 Help.txt是一个嵌入式资源。但是,流为空。我已经尝试了MyProjSolution.Help.txt和MyProjSolution.MyProj.Help.txt,但似乎没有任何效果。

c# embedded-resource
10个回答
146
投票

您可以使用以检查资源是否已正确嵌入

//From the assembly where this code lives!
this.GetType().Assembly.GetManifestResourceNames()

//or from the entry point to the application - there is a difference!
Assembly.GetExecutingAssembly().GetManifestResourceNames()

调试时这将列出编写代码的程序集中嵌入的所有资源的所有(完全限定名称)。

请参阅MSDN上的Assembly.GetManifestResourceNames()

只需复制相关名称,然后使用它代替您在变量'resourceName'中定义的任何名称。

注意 - 资源名称区分大小写,如果您错误地嵌入了资源文件,它将不会显示在对GetManifestResourceNames()的调用返回的列表中。另外 - 确保从正确的程序集中读取资源(如果使用了多个程序集) - 从当前正在执行的程序集而不是从引用的程序集中获取资源都很容易。

编辑 - .NET核心 有关如何使用.NET Core嵌入的详细信息,请参阅此SO post

检索清单信息看起来很相似 - 只需使用this.GetType().GetTypeInfo().Assembly.GetManifestResourceNames()从执行代码的程序集中获取清单。

我还没想出如何在.NET Core中完成相当于Assembly.GetExecutingAssembly()的工作!如果有人知道 - 请告诉我,我会更新这个答案。


-2
投票

您可能需要在GetManifestResourceStream参数中指定txt文件的路径,或者您可以尝试将txt文件与可执行文件放在同一目录中。希望有所帮助!


52
投票

我有一个类似的问题,首先检查文件是否包含在项目中,然后转到属性并将该文件的构建操作设置为Embedded Resource。这对我有用。


9
投票

这是我的null值的原因。

http://adrianmejia.com/blog/2011/07/18/cs-getmanifestresourcestream-gotcha/

如果资源“构建操作”属性未设置为“嵌入资源”,则GetManifestResourceStream方法将始终返回NULL

使用所有需要的文件设置此属性后,Assembly.GetManifestResourceStream开始返回当前流而不是NULL


6
投票

只是一个警告。

我无法访问我的文件作为嵌入式资源,即使我指定它是,即使它具有该Build Action属性。浪费了很多时间敲打我的脑袋。我嵌入了一个csharp代码文件,其名称后附加了.txt(xxx.cs.txt)。由于某种原因,GetManifestResourceNames()和GetManifestResourceStream()方法将不会在其名称中看到带.cs的文件。

我简单地将它重命名为xxx.txt,一切都很好。

奇怪的。


3
投票

嵌入文件的“Build Action”属性应设置为“Embedded Resource”以运行该行,如下所示:

Stream stream = assembly.GetManifestResourceStream(resourceName)

右键单击该文件,单击该属性,然后将“Build Action”属性设置为“Embedded Resource”:

enter image description here


1
投票

我有同样的问题,感谢杰伊,我发现它是目录名称中的连字符。

当您引用资源流时,ProjectName.ResourceFolder.Sub-Directory变为ProjectName.ResourceFolder.Sub_Directory


0
投票

在我的例子中,问题是寻找资源的代码与资源本身处于不同的项目中。

您只能访问代码所在的同一项目中的资源。我以为我可以将所有资源都放在网页项目中,但我也需要邮件项目中的图像。

希望这可以帮助处于同样情况的人。

我发现调用Assembly.GetExecutingAssembly().GetManifestResourceNames();非常有用。


0
投票
    First Unload the project and click on edit the project file. 

    Inside the project file make sure that the item you are fetching from the assembly is included inside <EmbeddedResource> tag.

    Eg: 

         <ItemGroup>
          <EmbeddedResource Include="Template\ForExampleFile.html" />
         </ItemGroup>


    The files I added into the project were just in Content tag but not in the EmbeddedResource as shown below by default. Hence the stream was returning null.
    <ItemGroup>
        <Content Include="Template\ForExampleFile.html" />
  </ItemGroup>

0
投票

你需要卸载你的解决方案。然后编辑project.Afterfind你的文件夹,并改变如下:

<EmbeddedResource Include="yourpath" />
© www.soinside.com 2019 - 2024. All rights reserved.