Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

T4 referenced assembly blocks build

In Visual Studio 2010 I have the following project layout:

  • Solution
    • project A
      • class C
      • class D
    • project B
      • T4 template

The T4 template contains a assembly reference like this:

<#@ assembly name="$(SolutionDir)\A\bin\Debug\A.dll" #>

The template instantiates an instance of class C. When I run the T4 template the processor loads the project A's dll and correctly creates the output. The error arises when I want to change something in project A, say modify either class C or D.

Unable to copy file "obj\Debug\A.dll" to "bin\Debug\A.dll". The process cannot access the file 'bin\Debug\A.dll' because it is being used by another process.

The only way I found to get rid of this error is to restart Visual Studio. Is there any other way to force the unloading of the A.dll assembly from VS?

like image 620
m0sa Avatar asked Jan 12 '11 17:01

m0sa


1 Answers

Im using VS2010 SP1 and was still getting blocked during build after first build when running a custom T4 template during the POST-BUILD events which accessed instances of classes of the same project.

How I got it to work was to use Reflection to access classes from the Project dll.

I still got the blocking issue when loading the dll directly from the file.

NOTE: The trick was to load the .dll into memory as a byte array and then load the assembly from the raw byte array. DONT load from the file using the Assembly.LoadFrom

This code is from my T4 template file and is accessing a static class "Information" and calling a static Method "Version" to return a string value.

string assemblyPath = Path.Combine(projectPath, @"bin\SampleProject.dll");
byte[] data;

using (var fs = File.OpenRead(assemblyPath))
{
    data = new byte[fs.Length];
    fs.Read(data, 0, Convert.ToInt32(fs.Length));
}

if (data == null || data.Length == 0)
{
    throw new ApplicationException("Failed to load " + assemblyPath);
}

var asm = Assembly.Load(data);
appVersion = (string) asm.GetType("SampleProject.Information").GetField("Version").GetValue(null);
like image 159
Adam Avatar answered Sep 20 '22 19:09

Adam