将Postbuild事件添加到项目中
当我生成C#项目(csproj
文件)并编译它时,msbuild
以某种方式无法识别前和后生成事件中的变量$(ConfigurationName)
和$(ProjectDir)
(和其他)。将Postbuild事件添加到项目中
当我手动将生成的.csproj
文件中的前置和后置事件配置向下移动时,则msbuild会正确识别这些变量。
在项目中添加buildevent是我在保存项目之前做的最后一件事。
这是我如何添加:
using Microsoft.Build.Construction;
using Microsoft.Build.Evaluation;
private const string PreBuildEventFixture = "PreBuildEvent";
private const string PostBuildEventFixture = "PostBuildEvent";
private const string PreBuildEvent = "attrib -R \"$(ProjectDir)app.config\"";
private const string PostBuildEvent = "copy \"$(ProjectDir)app.config.$(ConfigurationName)\" \"$(TargetDir)\\$(ProjectName).dll.config\" \r\n attrib -R \"$(ProjectPath)\"";
public void AddBuildEvents(Project project)
{
ProjectPropertyGroupElement propertyGroupElement = project.Xml.AddPropertyGroup();
propertyGroupElement.AddProperty(PreBuildEventFixture, PreBuildEvent);
propertyGroupElement.AddProperty(PostBuildEventFixture, PostBuildEvent);
}
贯穿的MSBuild生成的项目时,我得到的错误是这样的:
The command "copy "app.config." "\.dll.config"" exited with code 1
当我再手动编辑.csproj
文件(用记事本或其他文本编辑器),剪切前和后生成事件,并将其粘贴到<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
元素下,然后msbuild将生成的.csproj
文件正常生成。
将生成事件添加到.csproj
文件的最佳方法是什么,以便在生成的XML
中的Import
元素之后结束?
很显然,我目前使用从Microsoft.Build.Evaluation.Project的的Xml财产AddPropertyGroup请求它的方式是不是。
示例项目:
using System.IO;
using Microsoft.Build.Construction;
using Microsoft.Build.Evaluation;
class Program
{
private const string PreBuildEventFixture = "PreBuildEvent";
private const string PostBuildEventFixture = "PostBuildEvent";
private const string PreBuildEvent = "attrib -R \"$(ProjectDir)app.config\"";
private const string PostBuildEvent = "copy \"$(ProjectDir)app.config.$(ConfigurationName)\" \"$(TargetDir)\\$(ProjectName).exe.config\" \r\n attrib -R \"$(ProjectPath)\"";
private const string ProjectFile = @"C:\test\TestProject\TestProject.csproj";
static void Main(string[] args)
{
if (!File.Exists(ProjectFile))
throw new FileNotFoundException("ProjectFile not found");
ProjectCollection collection = new ProjectCollection();
Project project = collection.LoadProject(ProjectFile);
ProjectPropertyGroupElement propertyGroupElement = project.Xml.AddPropertyGroup();
propertyGroupElement.AddProperty(PreBuildEventFixture, PreBuildEvent);
propertyGroupElement.AddProperty(PostBuildEventFixture, PostBuildEvent);
project.Save();
collection.UnloadAllProjects();
}
}
步骤来重现
- 创建一个新项目
- 手动添加这应该是应用不同app.config.debug文件。调试文件
- 添加postbuildevent:
copy "$(ProjectDir)app.config.$(ConfigurationName)" "$(TargetDir)\$(ProjectName).exe.config
- 看到项目的建立和正确的配置文件被应用
- 使用记事本(这样不会留下任何痕迹)
- 运行示例项目
- 刷新和删除建设前和postbuild事件您创建的项目。
- 输出窗口会说,如果加入他们
The system cannot find the file specified.
var propertyGroupElement = project.Xml.CreatePropertyGroupElement();
project.Xml.AppendChild(propertyGroupElement);
propertyGroupElement.AddProperty(PreBuildEventFixture, PreBuildEvent);
propertyGroupElement.AddProperty(PostBuildEventFixture, PostBuildEvent);
谢谢!完美的作品。 – Alfons 2014-09-04 14:05:19
项目相关的宏不被解析项目实际建造之前(构建项目包括添加引用)。除了使用$(ProjectName)
的,路径可以使用解变量(已经存在)这样构成:
copy "$(SolutionDir)ProjectName\app.config.$(Configuration)" "$(SolutionDir)ProjectName\bin\$(Configuration)\ProjectName.dll.config"
注意,项目名是项目硬编码的实际名称,但因为你生成一个项目这应该很容易添加。
这可能是一个有用的解决方法。 – Alfons 2014-09-01 12:54:04
似乎文件'app.config.'不存在(它缺少'ConfigurationName')。什么是您的手动构建事件? – 2014-08-29 12:09:21
不分析$(ConfigurationName)。如果我将项目文件中的buildevents移动到其中, – Alfons 2014-08-29 12:12:10
猜测其中一个Imports负责设置变量,我搞砸了一个项目文件。在此之后,我必须拥有后期构建事件: 或变量为空。你可以添加构建事件的方式让他们在底部? –
Adam47
2014-08-29 12:46:08