如何替换存储在MSBuild属性中的文件路径的扩展名? [英] How can one replace the extension of a file path stored in an MSBuild property?
问题描述
我的MSBuild项目文件中包含以下几行:
I have the following lines in my MSBuild project file:
<PropertyGroup>
<TestResultsFileName Condition=" '$(TestResultsFileName)' == '' ">
TestResults.trx
</TestResultsFileName>
<TestResultsFilePath>$(OutDir)\$(TestResultsFileName)</TestResultsFilePath>
</PropertyGroup>
我需要创建另一个文件,其文件名与TestResultsFilePath相同,只是扩展名为.xml.所以我想有一个属性来保存其他文件的文件路径.
I need to create another file, having the same name as TestResultsFilePath only with the .xml extension. So I want to have a property to hold the file path of the other file.
起初,我以为这样的事情会起作用:
At first, I thought that something like this would work:
<PropertyGroup>
<NUnitResultsFilePath>
$(OutDir)\$(TestResultsFileName->'%(Filename).xml')
</NUnitResultsFilePath>
</PropertyGroup>
当然不是,因为TestResultsFileName不是项集合.不幸的是,事实并非如此,因为它是某些需要简单值而不是集合的任务的参数.
And, of course, it did not, because TestResultsFileName is not an item collection. Unfortunately, it cannot be such, because it is a parameter to some task that expects a simple value, not a collection.
所以,我的问题是如何用.xml替换TestResultsFileName属性值的扩展名?
So, my question is how can I replace the extension of the TestResultsFileName property value with .xml?
谢谢.
推荐答案
没关系.我已经写了一个自定义任务来完成这项工作:
Never mind. I have written a custom task to do the job:
public class ReplaceExtension : Task
{
[Required]
public string FilePath { get; set; }
public string NewExtension { get; set; }
[Output]
public string Result { get; set; }
public override bool Execute()
{
if (string.IsNullOrEmpty(FilePath))
{
Log.LogError("FilePath cannot be empty!");
return false;
}
try
{
int length = FilePath.Length;
int startIndex = length;
int oldExtensionLength = 0;
while (--startIndex >= 0)
{
char ch = FilePath[startIndex];
if (ch == '.')
{
oldExtensionLength = length - startIndex;
break;
}
if (ch == Path.DirectorySeparatorChar ||
ch == Path.AltDirectorySeparatorChar ||
ch == Path.VolumeSeparatorChar)
{
break;
}
}
bool isNewExtensionEmpty = string.IsNullOrEmpty(NewExtension) ||
(NewExtension.Length == 1 && NewExtension[0] == '.');
if (isNewExtensionEmpty)
{
// The new extension is empty - remove the old extension.
if (oldExtensionLength > 0)
{
Result = FilePath.Remove(startIndex, oldExtensionLength);
}
else
{
Result = FilePath;
}
}
else
{
// Replace the old extension with the new one.
StringBuilder sb = new StringBuilder(FilePath.Length - oldExtensionLength +
NewExtension.Length + (NewExtension[0] == '.' ? 0 : 1));
sb.Append(FilePath, 0, FilePath.Length - oldExtensionLength);
if (NewExtension[0] != '.')
{
sb.Append('.');
}
sb.Append(NewExtension);
Result = sb.ToString();
}
}
catch (Exception ex)
{
Log.LogErrorFromException(ex);
}
return !Log.HasLoggedErrors;
}
}
我正在这样使用它:
<Target Name="CreateProperties">
<ReplaceExtension FilePath="$(TestResultsFilePath)" NewExtension="xml">
<Output TaskParameter="Result" PropertyName="NUnitResultsFilePath"/>
</ReplaceExtension>
</Target>
这篇关于如何替换存储在MSBuild属性中的文件路径的扩展名?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!