136 lines
6.4 KiB
C#
136 lines
6.4 KiB
C#
// Copyright (c) Microsoft Open Technologies, Inc. All rights reserved. See License.txt in the project root for license information.
|
|
|
|
namespace System.Data.Entity
|
|
{
|
|
using System.Diagnostics;
|
|
using System.Diagnostics.CodeAnalysis;
|
|
using System.IO;
|
|
using System.IO.Compression;
|
|
using System.Linq;
|
|
using System.Reflection;
|
|
using System.Resources;
|
|
using System.Security;
|
|
using System.Security.Permissions;
|
|
|
|
#if !SILVERLIGHT
|
|
#endif
|
|
|
|
/// <summary>
|
|
/// Various utilities for dealing with embedded resources
|
|
/// </summary>
|
|
public static class ResourceUtilities
|
|
{
|
|
#if !SILVERLIGHT
|
|
/// <summary>
|
|
/// Extracts the specified compressed resource to a given directory
|
|
/// </summary>
|
|
/// <param name="outputDirectory"> Output directory </param>
|
|
/// <param name="assembly"> Assembly that contains the resource </param>
|
|
/// <param name="resourceName"> Partial resource name </param>
|
|
/// <remarks>
|
|
/// The method prefixes the actual resource with unqualified assembly name + '.Resources.' (
|
|
/// so you should put all your resources under 'Resources' directory within a project)
|
|
/// and appends '.gz' to it. You should use gzip to produce compressed files.
|
|
/// </remarks>
|
|
[SecuritySafeCritical]
|
|
// Calling File.Create demands FileIOPermission (Write flag) for the file path to which the resource is extracted.
|
|
[PermissionSet(SecurityAction.Assert, Unrestricted = true)]
|
|
[SuppressMessage("Microsoft.Naming", "CA2204:Literals should be spelled correctly", MessageId = "gz",
|
|
Justification = ".gz is GZIP file extension")]
|
|
[SuppressMessage("Microsoft.Usage", "CA2202:Do not dispose objects multiple times",
|
|
Justification = "Bogus warning, object will be disposed once.")]
|
|
public static void ExtractCompressedResourceToDirectory(string outputDirectory, Assembly assembly, string resourceName)
|
|
{
|
|
ValidateCommonArguments(outputDirectory, assembly, resourceName);
|
|
|
|
var fullResourceName = new AssemblyName(assembly.FullName).Name + ".Resources." + resourceName + ".gz";
|
|
using (var compressedInputStream = assembly.GetManifestResourceStream(fullResourceName))
|
|
{
|
|
if (compressedInputStream == null)
|
|
{
|
|
throw new IOException("Embedded resource " + fullResourceName + " not found in " + assembly.FullName);
|
|
}
|
|
|
|
using (var decompressedInputStream = new GZipStream(compressedInputStream, CompressionMode.Decompress))
|
|
{
|
|
using (Stream outputStream = File.Create(Path.Combine(outputDirectory, resourceName)))
|
|
{
|
|
IOHelpers.CopyStream(decompressedInputStream, outputStream);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
#endif
|
|
|
|
/// <summary>
|
|
/// Copies the named embedded resources from given assembly into the current directory.
|
|
/// </summary>
|
|
/// <param name="assembly"> The assembly. </param>
|
|
/// <param name="prefix"> The prefix to use for each name. </param>
|
|
/// <param name="overwrite"> if set to <c>true</c> then an existing file of the same name name will be overwritten. </param>
|
|
/// <param name="names"> The resource names, which will become the file names. </param>
|
|
public static void CopyEmbeddedResourcesToCurrentDir(
|
|
Assembly assembly, string prefix, bool overwrite,
|
|
params string[] names)
|
|
{
|
|
foreach (var name in names)
|
|
{
|
|
using (var sourceStream = assembly.GetManifestResourceStream(prefix + name))
|
|
{
|
|
Debug.Assert(sourceStream != null, "Could not create stream for embedded resource " + prefix + name);
|
|
|
|
var destinationPath = Path.Combine(@".\", name);
|
|
if (!File.Exists(destinationPath) || overwrite)
|
|
{
|
|
using (
|
|
var destinationStream = new FileStream(destinationPath, FileMode.Create, FileAccess.Write))
|
|
{
|
|
var sourceBuffer = new byte[sourceStream.Length];
|
|
sourceStream.Read(sourceBuffer, 0, sourceBuffer.Length);
|
|
destinationStream.Write(sourceBuffer, 0, sourceBuffer.Length);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// Builds a resource manager for the given assembly.
|
|
/// </summary>
|
|
/// <param name="assembly"> The assembly to build the resource manager for. </param>
|
|
/// <returns> The resource manager. </returns>
|
|
public static ResourceManager BuildResourceManager(Assembly assembly)
|
|
{
|
|
ExceptionHelpers.CheckArgumentNotNull(assembly, "assembly");
|
|
return new ResourceManager(FindSingleResourceTable(assembly), assembly);
|
|
}
|
|
|
|
private static void ValidateCommonArguments(string outputDirectory, Assembly assembly, string resourceName)
|
|
{
|
|
ExceptionHelpers.CheckArgumentNotNull(outputDirectory, "outputDirectory");
|
|
ExceptionHelpers.CheckArgumentNotNull(assembly, "assembly");
|
|
ExceptionHelpers.CheckArgumentNotNull(resourceName, "resourceName");
|
|
|
|
if (!Directory.Exists(outputDirectory))
|
|
{
|
|
throw new IOException("Output directory '" + outputDirectory + "' does not exist.");
|
|
}
|
|
}
|
|
|
|
private static string FindSingleResourceTable(Assembly assembly)
|
|
{
|
|
var resources = assembly.GetManifestResourceNames().Where(r => r.EndsWith(".resources", StringComparison.Ordinal));
|
|
if (resources.Count() != 1)
|
|
{
|
|
throw new NotSupportedException(
|
|
"The supplied assembly does not contain exactly one resource table, if the assembly contains multiple tables call the overload that specifies which table to use.");
|
|
}
|
|
|
|
var resource = resources.Single();
|
|
|
|
// Need to trim the ".resources" off the end
|
|
return resource.Substring(0, resource.Length - 10);
|
|
}
|
|
}
|
|
}
|