title: XSLT: Move node one level up
body: <p>I would like to know how to move nodes up one level using XSLT if certain conditions are complied. To give you an example have a look at the following XML source:</p>
  
  <pre><code>&lt;Settings&gt;
    &lt;String [...]&gt;
      &lt;Boolean [...]/&gt;
    &lt;/String&gt;
  &lt;/Settings&gt;
  </code></pre>
  
  <p>That is the XML I have as starting situation. To be clear, the node names "Settings", "String", "Boolean" are special nodes we defined.</p>
  
  <p>The problem is that "Boolean" nodes are not allowed inside of "String" nodes. That's why I have to move those "Boolean" nodes on level up. The desired XML would look like this:</p>
  
  <pre><code>&lt;Settings&gt;
    &lt;String [...]&gt;&lt;/String&gt;
    &lt;Boolean [...]/&gt;
  &lt;/Settings&gt;
  </code></pre>
  
  <p>The XSLT also has to work with every String node which has a sibling Boolean node, regardless of the position in the XML-tree.</p>
  
  <p>So far I learned that you have to first copy all of your XML using a "identity rule" and then apply some special rules for the desired transformations: </p>
  
  <pre><code>&lt;?xml version="1.0" encoding="UTF-8"?&gt;
  &lt;xsl:stylesheet version="2.0" 
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform"        
    xmlns:fo="http://www.w3.org/1999/XSL/Format" 
    xmlns:xs="http://www.w3.org/2001/XMLSchema" 
    xmlns:fn="http://www.w3.org/2005/xpath-functions"&gt;
  
    &lt;!-- Identity rule --&gt;
    &lt;xsl:template match="node() | @*"&gt;
      &lt;xsl:copy&gt;
        &lt;xsl:apply-templates select="node() | @*"/&gt;
      &lt;/xsl:copy&gt;
    &lt;/xsl:template&gt;
  
    &lt;!-- special rules ... --&gt;
  
  &lt;/xsl:stylesheet&gt;
  </code></pre>
  
  <p>The thing I am struggling with is the rule to move all "Boolean" nodes which are siblings of "String" nodes one level up. How can I do that?!?</p>