<?xml version="1.0" encoding="UTF-8" ?>
<xsl:stylesheet version="1.0" 
                xmlns:xsl="http://www.w3.org/1999/XSL/Transform" 
                xmlns="urn:nhibernate-mapping-2.2"
                xmlns:a="http://cygnets.co.uk/schemas/adl-1.2"
                exclude-result-prefixes="a">

  <!--
      Application Description Framework
      adl2hibernate.xsl
      
      (c) 2007 Cygnet Solutions Ltd
      
      Transform ADL to Verbose (or canonical) ADL
      Most defaults are replaced with their actual values.
      
      $Author: af $
      $Revision: 1.2 $
  -->

  <xsl:output indent="no" method="xml" encoding="utf-8"/>

  <xsl:template match="a:application">
      <hibernate-mapping>
        <xsl:apply-templates select="@namespace|@assembly|@schema" />
        <xsl:comment>
          ***************************************************************************
          *
          *	©2007 Cygnet Solutions Ltd
          *
          *	THIS FILE IS AUTOMATICALLY GENERATED AND SHOULD NOT
          *	BE MANUALLY EDITED. 
          *
          *	Generated using adl2hibernate-mapping.xsl revision <xsl:value-of select="substring('$Revision: 1.2 $', 12)"/>
          *
          ***************************************************************************
        </xsl:comment>
        <xsl:apply-templates select="a:entity|comment()"/>
      </hibernate-mapping>
  </xsl:template>

  <xsl:template match="a:entity">
    <class>
      <xsl:apply-templates select="@name|@table" />
      <xsl:apply-templates select="a:key" />
      <xsl:apply-templates select="a:property|a:set|a:bag|a:subclass|a:component|a:discriminator|a:one-to-one" />
    </class>
  </xsl:template>

  <xsl:template match="a:key">
    <xsl:choose>
      <xsl:when test="count(a:property)=0">
        <xsl:message terminate="yes">
          Class '<xsl:value-of select="ancestor::a:entity/@name"/>' has no properties in its key
        </xsl:message>
      </xsl:when>
      <xsl:when test="count(a:property)=1">
        <id>
          <xsl:apply-templates select="a:property/@*|a:property/node()" />
        </id>
      </xsl:when>
      <xsl:otherwise>
        <composite-id>
          <xsl:apply-templates select="a:property" mode="key" />
        </composite-id>
      </xsl:otherwise>
    </xsl:choose>
  </xsl:template>

  <xsl:template match="a:property" mode="key">
    <xsl:choose>
      <xsl:when test="@type='entity'">
        <key-many-to-one>
          <xsl:apply-templates select="@name|@column|@entity|node()"/>
        </key-many-to-one>
      </xsl:when>
      <xsl:when test="true()">
        <key-property>
          <xsl:apply-templates select="@*|node()"/>
        </key-property>
      </xsl:when>
    </xsl:choose>
  </xsl:template>

  <xsl:template match="a:property">
    <xsl:choose>
      <xsl:when test="@type='entity'">
        <many-to-one>
          <xsl:apply-templates select="@name|@column|@entity|node()"/>
        </many-to-one>
      </xsl:when>
      <xsl:when test="true()">
        <property><xsl:apply-templates select="@*|node()"/></property>
      </xsl:when>
    </xsl:choose>
  </xsl:template>

  <xsl:template match="a:property/@type">
    <xsl:attribute name="type">
      <xsl:call-template name="type-spec">
        <xsl:with-param name="typename" select="../@type"/>
      </xsl:call-template>
      <xsl:if test="../@size">(<xsl:value-of select="../@size"/>)</xsl:if>
    </xsl:attribute>
  </xsl:template>

  <xsl:template match="a:property/@size"><!--Remove--></xsl:template>

  <xsl:template match="a:property/@required">
    <xsl:if test="string(.)='true'">
      <xsl:attribute name="not-null">true</xsl:attribute>
    </xsl:if>
  </xsl:template>

  <xsl:template match="@entity">
    <xsl:attribute name="class">
      <xsl:value-of select="."/></xsl:attribute>
  </xsl:template>

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

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

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

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

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

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

  <xsl:template match="a:one-to-many">
    <one-to-many>
      <xsl:apply-templates select="@*|node()" />
    </one-to-many>
  </xsl:template>

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

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

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

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

  <xsl:template name="type-spec">
    <xsl:param name="typename"/>
    <xsl:param name="nullable" select="false()"/>
    <xsl:variable name="type0" select="/a:application/a:type[@name=$typename]|document('types.xml')/types/type[@name=$typename]"/>
    <xsl:variable name="type" select="$type0[1]"/>
    <xsl:choose>
      <xsl:when test="$type/@hibernate">
        <xsl:value-of select="$type/@hibernate" />
      </xsl:when>
      <xsl:when test="$type/@dotnet">
        <xsl:value-of select="$type/@dotnet" />
      </xsl:when>
      <xsl:when test="$type">
        <xsl:message terminate="yes">Error! Found type "<xsl:value-of select="$typename"/>" but cannot find 'dotnet' or 'hibernate' attributes.</xsl:message>
      </xsl:when>
      <xsl:otherwise>
        <xsl:message terminate="yes">Error! Type "<xsl:value-of select="$typename"/>" not found.</xsl:message>
      </xsl:otherwise>
    </xsl:choose>
  </xsl:template>


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


</xsl:stylesheet>