2

An open source project uses CMake to build it's project files.

I don't agree with CMake - it's a 10mb installer to create batch files for a few hundred kb of source and even then it hardcodes the developers path to the output. It does not do relative paths at all, nor does it use the handy macros that Visual Studio provides.

So I decided to look around. Gyp looked promising but again it is placing a reliance on the user having Python installed and that is back to the reason why I dislike CMake. At least it doesn't hard code paths though.

So I thought about using batch files, and simple find and replace but since the project files are xml why not XSLT? So a bit of searching ran across this page here on SO which seemed to show what I want to do at a very simplistic level.

So I edited the answer by Dimitre Novatchev to the following:

<xsl:template match="OutDir/text()">
   <xsl:text>Diferent text</xsl:text>
 </xsl:template>

Hoping that would find the following and change it:

<OutDir Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">U:\unittest-cpp-pj\vs_projects\vs2012_x86\Debug\</OutDir>

However that didn't work - using the VS2010 xslt debugger it doesn't even break on the line. I don't want to spend months learning how to use XSLT correctly for something as seemingly simple as this. All I need is something that I can fire at 28 xml files and be done with it.

Once I have this working I will expand it to replace the fields with the correct values.

Update: This is the entire XSLT:

<xsl:stylesheet version="1.0"
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
  <xsl:output omit-xml-declaration="yes" indent="yes"/>
  <xsl:strip-space elements="*"/>

  <xsl:template match="node()|@*">
    <xsl:copy>
      <xsl:apply-templates select="node()|@*"/>
    </xsl:copy>
  </xsl:template>

  <xsl:template match="OutDir/text()">
    <xsl:text>Diferent text</xsl:text>
  </xsl:template>
</xsl:stylesheet>
5
  • Can you please post more of your input XML and the desired output XML? We need more context. Commented Nov 20, 2013 at 13:42
  • 2
    This is probably due to namespaces. Is there a statement like xmlns="http://schemas.microsoft.com/developer/msbuild/2003" on the root element of the XML? Commented Nov 20, 2013 at 13:49
  • If this is the only template you employ it is not going to work. Therefore, it would be fruitful if you could show all of XSLT code as well - and then we're happy to help. Commented Nov 20, 2013 at 13:50
  • @ThomasW: The entire vcxproj is 14kb in size. I can't post the entireity of it. Commented Nov 20, 2013 at 14:31
  • @TimC: Yes there is. How does that affect it? Commented Nov 20, 2013 at 14:32

1 Answer 1

1

Based on the suggestion of @Tim C, if there is a namespace issue, this is how you can solve it.

Assuming an input file like this (note the namespace declaration on the root):

<?xml version="1.0" encoding="utf-8"?>

 <root xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
  <other/>
  <other/>
  <OutDir Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">U:\unittest-cpp-pj\vs_projects\vs2012_x86\Debug\</OutDir>
  <other/>
</root>

Use this stylesheet (note that I have declared another namespace "ms"):

<?xml version="1.0" encoding="utf-8"?>

<xsl:stylesheet version="1.0"
 xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
 xmlns:ms="http://schemas.microsoft.com/developer/msbuild/2003">
 <xsl:output omit-xml-declaration="yes" indent="yes"/>
 <xsl:strip-space elements="*"/>

 <xsl:template match="node()|@*">
  <xsl:copy>
  <xsl:apply-templates select="node()|@*"/>
  </xsl:copy>
 </xsl:template>

 <xsl:template match="ms:OutDir/text()">
  <xsl:text>Different text</xsl:text>
 </xsl:template>
</xsl:stylesheet>

You did not catch the OutDir element before because it inherits the namespace of the root. An OutDir element without a namespace (which is what you tried) is not the same as ms:OutDir with a namespace - at least for the XSLT processor.

Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.