Generate binding redirects for all executable package dependencies.

Binding redirects are already generated for the current project. This
change is to add these same binding redirects to all executable package
dependencies.

Fixes - #2505

TODO: Add tests.
This commit is contained in:
Sridhar Periyasamy 2016-04-19 13:26:46 -07:00
parent 91fb67835d
commit 4ccd88d00e
2 changed files with 44 additions and 21 deletions

View file

@ -34,27 +34,46 @@ namespace Microsoft.DotNet.Cli.Compiler.Common
private static SHA1 Sha1 { get; } = SHA1.Create();
public static XDocument GenerateBindingRedirects(this IEnumerable<LibraryExport> dependencies, XDocument document)
public static void GenerateBindingRedirects(this IEnumerable<LibraryExport> dependencies, IEnumerable<string> configFiles)
{
var redirects = CollectRedirects(dependencies);
if (!redirects.Any())
{
// No redirects required
return document;
return;
}
document = document ?? new XDocument();
var configuration = GetOrAddElement(document, ConfigurationElementName);
foreach (var configFile in configFiles)
{
GenerateBindingRedirects(configFile, redirects);
}
}
internal static void GenerateBindingRedirects(string configFile, AssemblyRedirect[] bindingRedirects)
{
XDocument configRoot = null;
if (File.Exists(configFile))
{
configRoot = XDocument.Load(configFile);
}
configRoot = configRoot ?? new XDocument();
var configuration = GetOrAddElement(configRoot, ConfigurationElementName);
var runtime = GetOrAddElement(configuration, RuntimeElementName);
var assemblyBindings = GetOrAddElement(runtime, AssemblyBindingElementName);
foreach (var redirect in redirects)
foreach (var redirect in bindingRedirects)
{
AddDependentAssembly(redirect, assemblyBindings);
}
return document;
using (var fileStream = File.Open(configFile, FileMode.OpenOrCreate, FileAccess.ReadWrite))
{
configRoot.Save(fileStream);
}
}
private static void AddDependentAssembly(AssemblyRedirect redirect, XElement assemblyBindings)

View file

@ -98,10 +98,10 @@ namespace Microsoft.DotNet.Cli.Compiler.Common
libraryExport.RuntimeAssemblyGroups.GetDefaultAssets().CopyTo(_runtimeOutputPath);
libraryExport.NativeLibraryGroups.GetDefaultAssets().CopyTo(_runtimeOutputPath);
foreach(var group in libraryExport.ResourceAssemblies.GroupBy(r => r.Locale))
foreach (var group in libraryExport.ResourceAssemblies.GroupBy(r => r.Locale))
{
var localeSpecificDir = Path.Combine(_runtimeOutputPath, group.Key);
if(!Directory.Exists(localeSpecificDir))
if (!Directory.Exists(localeSpecificDir))
{
Directory.CreateDirectory(localeSpecificDir);
}
@ -254,30 +254,34 @@ namespace Microsoft.DotNet.Cli.Compiler.Common
public void GenerateBindingRedirects(LibraryExporter exporter)
{
var outputName = _outputPaths.RuntimeFiles.Assembly;
var configFile = outputName + ".config";
var existingConfig = new DirectoryInfo(_context.ProjectDirectory)
.EnumerateFiles()
.FirstOrDefault(f => f.Name.Equals("app.config", StringComparison.OrdinalIgnoreCase));
XDocument baseAppConfig = null;
if (existingConfig != null)
{
using (var fileStream = File.OpenRead(existingConfig.FullName))
File.Copy(existingConfig.FullName, configFile, true);
}
List<string> configFiles = new List<string>();
configFiles.Add(configFile);
foreach (var export in exporter.GetDependencies())
{
var dependencyExecutables = export.RuntimeAssemblyGroups.GetDefaultAssets()
.Where(asset => asset.FileName.ToLower().EndsWith(".exe"))
.Select(asset => Path.Combine(_runtimeOutputPath, asset.FileName));
foreach (var executable in dependencyExecutables)
{
baseAppConfig = XDocument.Load(fileStream);
configFile = executable + ".config";
configFiles.Add(configFile);
}
}
var appConfig = exporter.GetAllExports().GenerateBindingRedirects(baseAppConfig);
if (appConfig == null) { return; }
var path = outputName + ".config";
using (var stream = File.Create(path))
{
appConfig.Save(stream);
}
exporter.GetAllExports().GenerateBindingRedirects(configFiles);
}
}
}