How to access a binary resource in a C# applicatio

2019-02-16 23:23发布

I'm trying to store an empty Access database (.mdb) as a resource in my application. I then want to write it out the file system and populate it with table definitions, etc. The problem I'm having in Visual Studio 2005 and my C# application is with not being able to access the resource stored in the same assembly (which I would have thought would be accessible by default). Here's my code:

byte[] abytResource;
System.Reflection.Assembly objAssembly = System.Reflection.Assembly.GetExecutingAssembly();
objStream = objAssembly.GetManifestResourceStream("empty.mdb");
abytResource = new Byte[objStream.Length];
objStream.Read(abytResource, 0, (int)objStream.Length);
objFileStream = new FileStream(newDatabasePathWithName, FileMode.Create);
objFileStream.Write(abytResource, 0, (int)objStream.Length);
objFileStream.Close();

GetManifestResourceStream returns NULL and according to the documentation that's because the resource must be private (because even if it doesn't exist a non-NULL value is returned). So my question is this:

How do i make my resource accessible to my own application? I already added it to the project and marked it as "Embedded Resource", by the way.

Thanks!

3条回答
我想做一个坏孩纸
2楼-- · 2019-02-16 23:44

This will extract a binary embedded resource file ...

    /// <summary>
    /// Extracts an embedded file to local file system.
    /// </summary>
    /// <param name="resName">Resource name of embedded file. NameSpace.FileName.Extension</param>
    /// <param name="fileName">Extracted file name</param>
    public void ExtractEmbeddedFile(string resName, string fileName)
    {
        if (File.Exists(fileName)) File.Delete(fileName);

        Assembly assembly = Assembly.GetExecutingAssembly();

        using (var input = assembly.GetManifestResourceStream(resName))
        using (var output = File.Open(fileName, FileMode.CreateNew))
        {
            if (input == null) throw new FileNotFoundException(resName + ": Embedded resoure file not found");

            var buffer = new byte[32768];
            int read;
            while ((read = input.Read(buffer, 0, buffer.Length)) > 0)
            {
                output.Write(buffer, 0, read);
            }
            output.Flush();
        }
    }

It's very useful for C# Unit tests that require data files where your DLLs typically run without any content files present (they may run in temporary folders created by the unit test framework).

This has another code snippet for text files (not binary files) though it may have memory leaks as it failed to use the using statement.

查看更多
家丑人穷心不美
3楼-- · 2019-02-16 23:57

You need to prefix the "empty.mdb" with the default namespace of the assembly. Something like:

objStream = objAssembly.GetManifestResourceStream("My.Namespace.empty.mdb");
查看更多
ゆ 、 Hurt°
4楼-- · 2019-02-16 23:57

You can also check the names of your resources by invoking

string[] myResources = objAssembly.GetManifestResourceNames();
foreach(string reso in myResources) {
   Console.WriteLine(reso);
}

Also, make sure your empty.mdb file is marked with Embedded Resource on compilation action

alt text http://img520.imageshack.us/img520/6649/sinttuloo.png

查看更多
登录 后发表回答