Follow

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use
Contact

XSL: change attribute value of an element whose parent element attribute has a specific value

I want to modify an XML file created by Tableau using an XSL transformation.

What I need is to change the formula value of the calculation element only if the parent element has the value "ifShow" in the caption attribute.

my XML is of the form:

MEDevel.com: Open-source for Healthcare and Education

Collecting and validating open-source software for healthcare, education, enterprise, development, medical imaging, medical records, and digital pathology.

Visit Medevel

<?xml version='1.0' encoding='utf-8' ?>
<!-- build 20212.21.1112.1433 -->
<workbook source-build='2021.2.5 (20212.21.1112.1433)' source-platform='win' version='18.1' xml:base='https://tableau.company.com' xmlns:user='http://www.tableausoftware.com/xml/user'>
  <datasources>
    <datasource caption='V_Tableau_CommercialLayer' inline='true' name='sqlproxy' version='18.1'>
      <column caption='Month' datatype='string' name='[Calculation_36]' role='dimension' type='nominal'>
        <calculation class='tableau' formula='no change' />
      </column>
      <column caption='ifShow' datatype='string' name='[Calculation_40]' role='dimension' type='nominal'>
        <calculation class='tableau' formula='old code' />
      </column>
     </datasource>
  </datasources>
</workbook>

Desired output:

<?xml version='1.0' encoding='utf-8' ?>
<!-- build 20212.21.1112.1433 -->
<workbook source-build='2021.2.5 (20212.21.1112.1433)' source-platform='win' version='18.1' xml:base='https://tableau.company.com' xmlns:user='http://www.tableausoftware.com/xml/user'>
  <datasources>
    <datasource caption='V_Tableau_CommercialLayer' inline='true' name='sqlproxy' version='18.1'>
      <column caption='Month' datatype='string' name='[Calculation_36]' role='dimension' type='nominal'>
        <calculation class='tableau' formula='no change' />
      </column>
      <column caption='ifShow' datatype='string' name='[Calculation_40]' role='dimension' type='nominal'>
        <calculation class='tableau' formula='new code' />
      </column>
     </datasource>
  </datasources>
</workbook>

The XSL I am using is:

<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet version="1.0" 
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="xml" version="1.0" encoding="UTF-8" indent="yes"/>
    <xsl:param name="pNewFormula" select="'new code'"/>
    <xsl:template match="node()|@*">
        <xsl:copy>
            <xsl:apply-templates select="node()|@*"/>
        </xsl:copy>
    </xsl:template>
    <xsl:template match="column/@caption[. ='ifShow']/calculation">
        <xsl:attribute name="formula">
            <xsl:value-of select="$pNewFormula"/>
        </xsl:attribute>    
    </xsl:template>
</xsl:stylesheet>

However, this doesn’t work and I do not know how to access the child node of the element column

Thank you very much for your support!

>Solution :

How about:

XSLT 1.0

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

<xsl:param name="pNewFormula" select="'new code'"/>

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

<xsl:template match="column[@caption='ifShow']/calculation/@formula">
    <xsl:attribute name="formula">
        <xsl:value-of select="$pNewFormula"/>
    </xsl:attribute>    
</xsl:template>

</xsl:stylesheet>
Add a comment

Leave a Reply

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use

Discover more from Dev solutions

Subscribe now to keep reading and get access to the full archive.

Continue reading