Skip to content

Instantly share code, notes, and snippets.

@SlyNet
Created May 30, 2013 07:25
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save SlyNet/5676242 to your computer and use it in GitHub Desktop.
Save SlyNet/5676242 to your computer and use it in GitHub Desktop.
XSLT to transfrom hbm.xml mappings to code
<?xml version="1.0" encoding="utf-8"?>
<xsl:stylesheet version="2.0"
xmlns:string="http://symphony-cms.com/functions"
xmlns:func="http://exslt.org/functions"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
extension-element-prefixes="func">
<xsl:output method="text"/>
<xsl:variable name="accessDict">
<accesses>
<access key="property" value="Accessor.Property"/>
<access key="nosetter.camelcase-underscore" value="Accessor.NoSetter"/>
<access key="field.camelcase-underscore" value="Accessor.Field"/>
</accesses>
</xsl:variable>
<xsl:key name="accessByName" match="access" use="string(@key)"/>
<xsl:variable name="cascadeDict">
<cascades>
<cascade key="all-delete-orphan" value="Cascade.All | Cascade.DeleteOrphans" />
<cascade key="all,delete-orphan" value="Cascade.All | Cascade.DeleteOrphans"/>
<cascade key="all" value="Cascade.All" />
<cascade key="save-update" value="Cascade.Persist" />
</cascades>
</xsl:variable>
<xsl:key name="cascadeByName" match="cascade" use="@key"/>
<xsl:template match="map">
using NHibernate.Mapping.ByCode;
using NHibernate.Mapping.ByCode.Conformist;
namespace Mappings
{
<xsl:apply-templates />
}
</xsl:template>
<xsl:template match="class">
<xsl:variable name="fullClassName" select="tokenize(@name, ',')[1]"/>
<xsl:variable name="className" select="tokenize($fullClassName, '\.')[last()]"/>
public class <xsl:value-of select="$className"/>Map : ClassMapping&lt;<xsl:value-of select="$fullClassName"/>&gt;
{
public <xsl:value-of select="$className"/>Map()
{
Table(&quot;<xsl:value-of select="@table"/>&quot;);
<xsl:if test="@dynamic-update">
DynamicUpdate(<xsl:value-of select="@dynamic-update"/>);
</xsl:if>
<xsl:if test="@discriminator-value">
DiscriminatorValue(<xsl:value-of select="@discriminator-value"/>);
</xsl:if>
<xsl:if test="@lazy">
Lazy(<xsl:value-of select="@lazy"/>);
</xsl:if>
<xsl:apply-templates select="*[not(local-name() = 'subclass')]"/>
}
}
<xsl:apply-templates select="subclass"/>
</xsl:template>
<xsl:template match="subclass">
<xsl:variable name="fullClassName" select="tokenize(@name, ',')[1]"/>
<xsl:variable name="className" select="tokenize($fullClassName, '\.')[last()]"/>
public class <xsl:value-of select="$className"/>Map : SubclassMapping&lt;<xsl:value-of select="$fullClassName"/>&gt;
{
public <xsl:value-of select="$className"/>Map()
{
<xsl:if test="@dynamic-update">
DynamicUpdate(<xsl:value-of select="@dynamic-update"/>);
</xsl:if>
<xsl:if test="@discriminator-value">
DiscriminatorValue(<xsl:value-of select="@discriminator-value"/>);
</xsl:if>
<xsl:apply-templates />
}
}
</xsl:template>
<xsl:template match="id">
Id(x => x.<xsl:value-of select="@name"/>, idmap => {
idmap.Column(&quot;<xsl:value-of select="@column"/>&quot;);
idmap.UnsavedValue(<xsl:value-of select="@unsaved-value"/>);
idmap.Generator(Generators.Identity);
});
</xsl:template>
<xsl:template match="discriminator">
Discriminator(dm => dm.Column(&quot;<xsl:value-of select="@column"/>&quot;));
</xsl:template>
<xsl:template match="property">
<xsl:param name="prefix"></xsl:param>
<xsl:value-of select="$prefix"/>Property(x => x.<xsl:value-of select="@name"/>, pm => {
pm.Column(&quot;<xsl:value-of select="column/@name"/>&quot;);
<xsl:if test="column/@not-null">
pm.NotNullable(<xsl:value-of select="column/@not-null"/>);
</xsl:if>
<xsl:if test="@update">
pm.Update(<xsl:value-of select="@update"/>);
</xsl:if>
<xsl:if test="@insert">
pm.Insert(<xsl:value-of select="@insert"/>);
</xsl:if>
<xsl:if test="@access">
mto.Access(<xsl:value-of select="key('accessByName', ./@access ,$accessDict)/@value"/>);
</xsl:if>
});
</xsl:template>
<xsl:template match="component">
<xsl:param name="prefix"></xsl:param>
<xsl:variable name="uniqeId" select="generate-id(.)"/>
<xsl:variable name="componentVar">
<xsl:choose>
<xsl:when test="name(parent::node())='component'">
<xsl:value-of select="concat('cm', substring($uniqeId, string-length($uniqeId)))"/>
</xsl:when>
<xsl:otherwise>
<xsl:value-of select="'cm'"/>
</xsl:otherwise>
</xsl:choose>
</xsl:variable>
<xsl:value-of select="$prefix"/>Component(c => c.<xsl:value-of select="@name"/>, <xsl:value-of select="$componentVar"/> => {
<xsl:apply-templates>
<xsl:with-param name="prefix"><xsl:value-of select="$componentVar"/>.</xsl:with-param>
</xsl:apply-templates>
});
</xsl:template>
<xsl:template match="many-to-one">
<xsl:param name="prefix"></xsl:param>
<xsl:value-of select="$prefix"/>ManyToOne(x => x.<xsl:value-of select="@name"/>, mto => {
mto.Column(&quot;<xsl:value-of select="@column"/>&quot;);
<xsl:if test="@not-null">
mto.NotNullable(<xsl:value-of select="@not-null"/>);
</xsl:if>
<xsl:if test="@unique-key">
mto.UniqueKey(&quot;<xsl:value-of select="@unique-key"/>&quot;);
</xsl:if>
<xsl:if test="@update">
mto.Update(<xsl:value-of select="@update"/>);
</xsl:if>
<xsl:if test="@insert">
mto.Insert(<xsl:value-of select="@insert"/>);
</xsl:if>
<xsl:if test="@access">
mto.Access(<xsl:value-of select="key('accessByName', ./@access ,$accessDict)/@value"/>);
</xsl:if>
});
</xsl:template>
<xsl:template match="set">
Set(x => x.<xsl:value-of select="@name"/>, set => {
set.Table(&quot;<xsl:value-of select="@table"/>&quot;);
<xsl:if test="@lazy">
set.Lazy(CollectionLazy.Lazy);
</xsl:if>
<xsl:if test="key/@column">
set.Key(km => km.Column(&quot;<xsl:value-of select="key/@column"/>&quot;));
</xsl:if>
<xsl:if test="@inverse">
set.Inverse(<xsl:value-of select="@inverse"/>);
</xsl:if>
<xsl:if test="@cascade">
set.Cascade(<xsl:value-of select="key('cascadeByName', ./@cascade ,$cascadeDict)/@value"/>);
</xsl:if>
set.Access(<xsl:value-of select="key('accessByName', ./@access ,$accessDict)/@value"/>);
}, colMap => {
<xsl:choose>
<xsl:when test="count(./many-to-many) &gt; 0">
colMap.ManyToMany(mtm => {
mtm.Column(&quot;<xsl:value-of select="many-to-many/@column"/>&quot;);
});
</xsl:when>
<xsl:when test="count(./one-to-many) &gt; 0">
colMap.OneToMany();
</xsl:when>
<xsl:when test="count(./composite-element) &gt; 0">
colMap.Component(cm => {
<xsl:apply-templates>
<xsl:with-param name="prefix">cm.</xsl:with-param>
</xsl:apply-templates>
});
</xsl:when>
</xsl:choose>
});
</xsl:template>
<xsl:template match="bag">
Bag(x => x.<xsl:value-of select="@name"/>, bm => {
bm.Table(&quot;<xsl:value-of select="@table"/>&quot;);
<xsl:if test="@lazy">
bm.Lazy(CollectionLazy.Lazy);
</xsl:if>
<xsl:if test="key/@column">
bm.Key(km => km.Column(&quot;<xsl:value-of select="key/@column"/>&quot;));
</xsl:if>
<xsl:if test="@inverse">
bm.Inverse(<xsl:value-of select="@inverse"/>);
</xsl:if>
<xsl:if test="@cascade">
bm.Cascade(<xsl:value-of select="key('cascadeByName', ./@cascade ,$cascadeDict)/@value"/>);
</xsl:if>
bm.Access(<xsl:value-of select="key('accessByName', ./@access ,$accessDict)/@value"/>);
}, colMap => {
<xsl:choose>
<xsl:when test="count(./many-to-many) &gt; 0">
colMap.ManyToMany(mtm => {
mtm.Column(&quot;<xsl:value-of select="many-to-many/@column"/>&quot;);
});
</xsl:when>
<xsl:when test="count(./one-to-many) &gt; 0">
colMap.OneToMany();
</xsl:when>
<xsl:when test="count(./composite-element) &gt; 0">
colMap.Component(cm => {
<xsl:apply-templates>
<xsl:with-param name="prefix">cm.</xsl:with-param>
</xsl:apply-templates>
});
</xsl:when>
</xsl:choose>
});
</xsl:template>
</xsl:stylesheet>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment