You can subscribe to this list here.
2004 |
Jan
|
Feb
|
Mar
|
Apr
(248) |
May
(82) |
Jun
(90) |
Jul
(177) |
Aug
(253) |
Sep
(157) |
Oct
(151) |
Nov
(143) |
Dec
(278) |
---|---|---|---|---|---|---|---|---|---|---|---|---|
2005 |
Jan
(152) |
Feb
(107) |
Mar
(177) |
Apr
(133) |
May
(259) |
Jun
(81) |
Jul
(119) |
Aug
(306) |
Sep
(416) |
Oct
(240) |
Nov
(329) |
Dec
(206) |
2006 |
Jan
(466) |
Feb
(382) |
Mar
(153) |
Apr
(162) |
May
(133) |
Jun
(21) |
Jul
(18) |
Aug
(37) |
Sep
(97) |
Oct
(114) |
Nov
(110) |
Dec
(28) |
2007 |
Jan
(74) |
Feb
(65) |
Mar
(49) |
Apr
(76) |
May
(43) |
Jun
(15) |
Jul
(68) |
Aug
(55) |
Sep
(63) |
Oct
(59) |
Nov
(70) |
Dec
(66) |
2008 |
Jan
(71) |
Feb
(60) |
Mar
(120) |
Apr
(31) |
May
(48) |
Jun
(81) |
Jul
(107) |
Aug
(51) |
Sep
(80) |
Oct
(83) |
Nov
(83) |
Dec
(79) |
2009 |
Jan
(83) |
Feb
(110) |
Mar
(97) |
Apr
(91) |
May
(291) |
Jun
(250) |
Jul
(197) |
Aug
(58) |
Sep
(54) |
Oct
(122) |
Nov
(68) |
Dec
(34) |
2010 |
Jan
(50) |
Feb
(17) |
Mar
(63) |
Apr
(61) |
May
(84) |
Jun
(81) |
Jul
(138) |
Aug
(144) |
Sep
(78) |
Oct
(26) |
Nov
(30) |
Dec
(61) |
2011 |
Jan
(33) |
Feb
(35) |
Mar
(166) |
Apr
(221) |
May
(109) |
Jun
(76) |
Jul
(27) |
Aug
(37) |
Sep
(1) |
Oct
(4) |
Nov
(2) |
Dec
(1) |
2012 |
Jan
|
Feb
|
Mar
(2) |
Apr
(2) |
May
|
Jun
|
Jul
(1) |
Aug
|
Sep
(1) |
Oct
|
Nov
(1) |
Dec
|
2013 |
Jan
|
Feb
(1) |
Mar
|
Apr
|
May
|
Jun
|
Jul
(1) |
Aug
(1) |
Sep
(3) |
Oct
(2) |
Nov
|
Dec
(1) |
2014 |
Jan
(1) |
Feb
(1) |
Mar
(3) |
Apr
|
May
|
Jun
|
Jul
|
Aug
|
Sep
|
Oct
|
Nov
|
Dec
|
From: Michael D. <mik...@us...> - 2005-04-12 02:44:36
|
Update of /cvsroot/nhibernate/nhibernate/src/NHibernate/Impl In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv12761/nhibernate/src/NHibernate/Impl Modified Files: SessionImpl.cs Log Message: added comments to a method. Index: SessionImpl.cs =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/src/NHibernate/Impl/SessionImpl.cs,v retrieving revision 1.80 retrieving revision 1.81 diff -C2 -d -r1.80 -r1.81 *** SessionImpl.cs 30 Mar 2005 16:28:54 -0000 1.80 --- SessionImpl.cs 12 Apr 2005 02:44:26 -0000 1.81 *************** *** 1466,1469 **** --- 1466,1480 ---- } + /// <summary> + /// Checks to see if there are any Properties that should not be null + /// are references to null or to a transient object. + /// </summary> + /// <param name="values">An object array of values that should be validated.</param> + /// <param name="persister">The <see cref="IClassPersister"/> that describes which values can be null.</param> + /// <param name="isUpdate">A <see cref="Boolean"/> indicating if this is an Update operation.</param> + /// <exception cref="HibernateException"> + /// Thrown when a non-nullable property contains a value that would + /// persist the value of null to the database. + /// </exception> private static void CheckNullability( object[] values, IClassPersister persister, bool isUpdate ) { |
From: Michael D. <mik...@us...> - 2005-04-11 03:45:48
|
Update of /cvsroot/nhibernate/nhibernate/doc/reference/en In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv6045 Modified Files: master.xml Log Message: work on collections documentation Index: master.xml =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/doc/reference/en/master.xml,v retrieving revision 1.6 retrieving revision 1.7 diff -C2 -d -r1.6 -r1.7 *** master.xml 10 Apr 2005 14:37:18 -0000 1.6 --- master.xml 11 Apr 2005 03:45:38 -0000 1.7 *************** *** 18,22 **** <!ENTITY performance SYSTEM "modules/performance.xml"> <!ENTITY toolset-guide SYSTEM "modules/toolset_guide.xml"> ! <!ENTITY example-parentchild SYSTEM "modules/example-parentchild.xml"> <!ENTITY example-weblog SYSTEM "modules/example_weblog.xml"> <!ENTITY example-mappings SYSTEM "modules/example_mappings.xml"> --- 18,22 ---- <!ENTITY performance SYSTEM "modules/performance.xml"> <!ENTITY toolset-guide SYSTEM "modules/toolset_guide.xml"> ! <!ENTITY example-parentchild SYSTEM "modules/example_parentchild.xml"> <!ENTITY example-weblog SYSTEM "modules/example_weblog.xml"> <!ENTITY example-mappings SYSTEM "modules/example_mappings.xml"> *************** *** 113,116 **** --- 113,117 ---- &collection-mapping; &association-mapping; + &example-parentchild; <index id="index"/> </book> \ No newline at end of file |
From: Michael D. <mik...@us...> - 2005-04-11 03:45:48
|
Update of /cvsroot/nhibernate/nhibernate/doc/reference/en/modules In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv6045/modules Modified Files: association_mapping.xml collection_mapping.xml example_parentchild.xml Log Message: work on collections documentation Index: association_mapping.xml =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/doc/reference/en/modules/association_mapping.xml,v retrieving revision 1.1 retrieving revision 1.2 diff -C2 -d -r1.1 -r1.2 *** association_mapping.xml 10 Apr 2005 14:37:17 -0000 1.1 --- association_mapping.xml 11 Apr 2005 03:45:37 -0000 1.2 *************** *** 13,16 **** --- 13,32 ---- <title>Introduction</title> <para> + Association mappings are often the most difficult thing to get right. In + this section we'll go through the canonical cases one by one, starting + with unidirectional mappings, and then considering the bidirectional cases. + We'll use <literal>Person</literal> and <literal>Address</literal> in all + the examples. The namespace and assembly are not included in the example + mappings to keep the mappings focused on the important aspects. + </para> + <para> + We'll classify associations by wheter or not they map to an intervening + join table, and by multiplicity. + </para> + <para> + Nullable foreign keys are not considered good practive in traditional data + modeling, so all our examples use not null foreign keys. This is not a + requirement of NHibernate, and the mappings will all work if you drop the + nullability constraints. </para> </sect1> *************** *** 58,62 **** <sect2 id="assoc-bidirectional-m21"> <title>one to many / many to one</title> ! <para></para> </sect2> <sect2 id="assoc-bidirectional-121"> --- 74,115 ---- <sect2 id="assoc-bidirectional-m21"> <title>one to many / many to one</title> ! <para> ! A <emphasis>bidirectional one-to-many association</emphasis> is the ! most common kind of association. (This is the standard parent/child ! relationship.) ! </para> ! <programlisting><![CDATA[<class name="Person"> ! <id name="Id" column="personId"> ! <generator class="native" /> ! </id> ! <many-to-one name="Address" ! column="addressId" ! not-null="true" ! /> ! </class> ! ! <class name="Address"> ! <id name="Id" column="addressId"> ! <generator class="native" /> ! </id> ! <set name="People" inverse="true"> ! <key column="addressId" /> ! <one-to-many class="Person" /> ! </set> ! </class>]]></programlisting> ! ! <programlisting><![CDATA[ ! create table Person ! ( ! personId bigint not null primary key, ! addressId bigint not null ! ) ! ! create table Address ! ( ! addressId bigint not null primary key ! ) ! ! ]]></programlisting> </sect2> <sect2 id="assoc-bidirectional-121"> *************** *** 70,74 **** <sect2 id="assoc-bidirectional-join-12m"> <title>one to many / many to one</title> ! <para></para> </sect2> <sect2 id="assoc-bidirectional-join-121"> --- 123,128 ---- <sect2 id="assoc-bidirectional-join-12m"> <title>one to many / many to one</title> ! <para> ! </para> </sect2> <sect2 id="assoc-bidirectional-join-121"> Index: example_parentchild.xml =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/doc/reference/en/modules/example_parentchild.xml,v retrieving revision 1.1 retrieving revision 1.2 diff -C2 -d -r1.1 -r1.2 *** example_parentchild.xml 8 Apr 2005 19:23:35 -0000 1.1 --- example_parentchild.xml 11 Apr 2005 03:45:37 -0000 1.2 *************** *** 0 **** --- 1,274 ---- + <!-- + before committing make sure to comment out the DOCTYPE + It is in here to get intellisense with XMLSpy. The + HomeEdition is a free download. + + <!DOCTYPE chapter PUBLIC "-//OASIS//DTD DocBook XML V4.2//EN" + "../../support/docbook-dtd/docbookx.dtd"> + --> + <chapter id="example-parentchild"> + <title>Example: Parent/Child</title> + + <para> + One of the very first things that new users try to do with NHibernate is to model a parent / child type + relationship. There are two different approaches to this. For various reasons the most convenient + approach, especially for new users, is to model both <literal>Parent</literal> and <literal>Child</literal> + as entity classes with a <literal><one-to-many></literal> association from <literal>Parent</literal> + to <literal>Child</literal>. (The alternative approach is to declare the <literal>Child</literal> as a + <literal><composite-element></literal>.) Now, it turns out that default semantics of a one to many + association (in NHibernate) are much less close to the usual semantics of a parent / child relationship than + those of a composite element mapping. We will explain how to use a <emphasis>bidirectional one to many + association with cascades</emphasis> to model a parent / child relationship efficiently and elegantly. It's + not at all difficult! + </para> + + <sect1 id="example-parentchild-collections"> + <title>A note about collections</title> + <para> + NHibernate collections are considered to be a logical part of the their owning entity; never of the + contained entities. This is a crucial distinction! It has the following consequences: + </para> + + <itemizedlist> + <listitem> + <para> + When we remove/add an object from/to a collection, the version number of the collection owner + is incremented. + </para> + </listitem> + <listitem> + <para> + If an object that was removed from a collection is an instance of a value type (eg, a composite + element), that object will cease to be persistent and its state will be completely removed from + the database. Likewise, adding a value type instance to the collection will cause its state to + be immediately persistent. + </para> + </listitem> + <listitem> + <para> + On the other hand, if an entity is removed from a collection (a one-to-many or many-to-many + association), it will not be deleted, by default. This behavior is completely consistent - a + change to the internal state of another entity should not cause the associated entity to vanish! + Likewise, adding an entity to a collection does not cause that entity to become persistent, by + default. + </para> + </listitem> + </itemizedlist> + + <para> + Instead, the default behavior is that adding an entity to a collection merely creates a link between + the two entities, while removing it removes the link. This is very appropriate for all sorts of cases. + Where it is not appropriate at all is the case of a parent/child relationship, where the life of the + child is bound to the lifecycle of the parent. + </para> + </sect1> + + <sect1 id="example-parentchild-bidir"> + <title>Bidirectional one-to-many</title> + <para> + Suppose we start with a simple <literal><one-to-many></literal> association from + <literal>Parent</literal> to <literal>Child</literal>. + </para> + + <programlisting><![CDATA[<set name="Children"> + <key column="parent_id" /> + <one-to-many class="Child" /> + </set>]]></programlisting> + + <para> + If we were to execute the following code + </para> + + <programlisting><![CDATA[Parent p = session.Load( typeof( Parent ), pid ) as Parent; + Child c = new Child(); + p.Children.Add( c ); + session.Save( c ); + session.Flush(); + ]]></programlisting> + + <para> + NHibernate would issue two SQL statements: + </para> + + <itemizedlist> + <listitem> + <para>an <literal>INSERT</literal> to create the record for <literal>c</literal></para> + </listitem> + <listitem> + <para> + an <literal>UPDATE</literal> to create the link from <literal>p</literal> to + <literal>c</literal> + </para> + </listitem> + </itemizedlist> + + <para> + This is not only inefficient, but also violates any <literal>NOT NULL</literal> constraint on the + <literal>parent_id</literal> column. + </para> + + <para> + The underlying cause is that the link (the foreign key <literal>parent_id</literal>) from + <literal>p</literal> to <literal>c</literal> is not considered part of the state of the <literal>Child</literal> + object and is therefore not created in the <literal>INSERT</literal>. So the solution is to make the link part + of the <literal>Child</literal> mapping. + </para> + + <programlisting><![CDATA[<many-to-one name="Parent" column="parent_id" not-null="true"]]></programlisting> + + <para> + (We also need to add the <literal>Parent</literal> property to the <literal>Child</literal> class.) + </para> + + <para> + Now that the <literal>Child</literal> entity is managing the state of the link, we tell the collection not + to update the link. We use the <literal>inverse</literal> attribute. + </para> + + <programlisting><![CDATA[<set name="Children" inverse="true"> + <key column="parent_id" /> + <one-to-many class="Child" /> + </set>]]></programlisting> + + <para> + The following code would be used to add a new <literal>Child</literal>. + </para> + + <programlisting><![CDATA[Parent p = session.Load( typeof( Parent ), pid ) as Parent; + Child c = new Child(); + c.Parent = p; + p.Children.Add( c ); + session.Save( c ); + session.Flush(); + ]]></programlisting> + + <para> + An now, only one SQL <literal>INSERT</literal> would be issued! + </para> + + <para> + To tighten things up a bit, we could create an <literal>AddChild()</literal> method in + <literal>Parent</literal>. + </para> + + <programlisting><![CDATA[public void AddChild( Child c ) + { + this.Children.Add( c ); + c.Parent = this; + } + ]]></programlisting> + + <para> + The <literal>AddChild</literal> method would simplify the code to + </para> + + <programlisting><![CDATA[Parent p = session.Load( typeof( Parent ), pid ) as Parent; + Child c = new Child(); + p.AddChild( c ); // + session.Save( c ); + session.Flush(); + ]]></programlisting> + + </sect1> + + <sect1 id="example-parentchild-cascades"> + <title>Cascading lifecycle</title> + + <para> + The explicit call to <literal>Save()</literal> is still annoying. We will address this by + using cascades. + </para> + + <programlisting><![CDATA[<set name="Children" inverse="true" cascade="all"> + <key column="parent_id" /> + <one-to-many class="Child" /> + </set>]]></programlisting> + + <para> + This simplifies the code above to + </para> + + <programlisting><![CDATA[Parent p = session.Load( typeof( Parent ), pid ) as Parent; + Child c = new Child(); + p.AddChild( c ); + session.Flush(); + ]]></programlisting> + + <note> + <para> + Cascades depend heavily upon the <literal>unsaved-value</literal> attribute. Please ensure that + the default value of the <literal><id></literal> property is the same as + the <literal>unsaved-value</literal>. + </para> + </note> + + <para> + Similarily, we don't need to iterate over the children when saving or deleting a <literal>Parent</literal>. + The following removes <literal>p</literal> and all its children from the database. + </para> + + <programlisting><![CDATA[Parent p = session.Load( typeof( Parent ), pid ) as Parent; + session.Delete( p ); + session.Flush(); + ]]></programlisting> + + <para> + However, this code + </para> + + <programlisting><![CDATA[Parent p = session.Load( typeof( Parent ), pid ) as Parent; + Child c = null; + foreach( Child child in p.Children ) + { + c = child; // only care about first Child + break; + } + + p.Children.Remove( c ); + c.Parent = null; + + session.Flush();]]></programlisting> + + <para> + will not remove <literal>c</literal> from the database; it will only remove the link to <literal>p</literal> + (and cause a <literal>NOT NULL</literal> constraint violation, in this case). You need to explicitly + <literal>Delete()</literal> the <literal>Child</literal>. + </para> + + <programlisting><![CDATA[Parent p = session.Load( typeof( Parent ), pid ) as Parent; + Child c = null; + foreach( Child child in p.Children ) + { + c = child; // only care about first Child + break; + } + + p.Children.Remove( c ); + c.Parent = null; + + session.Delete( c ); + session.Flush();]]></programlisting> + + <para> + Now, in our case, a <literal>Child</literal> can't really exist without its parent. So if we remove + a <literal>Child</literal> from the collection, we really want it to be deleted. For this, we must + use <literal>cascade="all-delete-orphan"</literal>. + </para> + + <programlisting><![CDATA[<set name="Children" inverse="true" cascade="all-delete-orphan"> + <key column="parent_id" /> + <one-to-many class="Child" /> + </set>]]></programlisting> + + <para> + Note: even though the collection mapping specifies <literal>inverse="true"</literal>, cascades are still + processed by iterating the collection elements. So if you require that an object be saved, deleted or + updated by cascade, you must add it to the collection. It is not enough to simply call the + <literal>Child.Parent</literal> setter. + </para> + </sect1> + <sect1 id="example-parentchild-update"> + <title>Using cascading <literal>update()</literal></title> + <para></para> + </sect1> + </chapter> \ No newline at end of file Index: collection_mapping.xml =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/doc/reference/en/modules/collection_mapping.xml,v retrieving revision 1.3 retrieving revision 1.4 diff -C2 -d -r1.3 -r1.4 *** collection_mapping.xml 10 Apr 2005 14:41:51 -0000 1.3 --- collection_mapping.xml 11 Apr 2005 03:45:37 -0000 1.4 *************** *** 13,19 **** <para> This section does not contain much example .NET code. We assume you already know ! how to use .NET's collections framework. If so, there's not really anything more ! to know - with a single caveat, you may use .NET collections the same way you ! always have. </para> <para> --- 13,19 ---- <para> This section does not contain much example .NET code. We assume you already know ! how to use .NET's collections framework and the concepts behind a Set collection. ! If so, there's not really anything more to know - with a single caveat, you may ! use collections the same way you always have. </para> <para> *************** *** 30,39 **** implementing the collection interface (eg. iteration order of a <literal>Iesi.Collections.ListSet</literal>. The persistent collections actually behave like ! <literal>System.Collections.Dictionary</literal>, <literal>System.Collections.ArrayList</literal>, ! <literal>Iesi.Collections.Set</literal> respectively. Furthermore, the .NET type of a property holding a collection must be the interface type (ie. <literal>IDictionary</literal>, <literal>IList</literal>, or ! <literal>IList</literal>). This restriction exists because NHibernate replaces your instances of <literal>IDictionary</literal>, <literal>IList</literal>, and <literal>ISet</literal> with instances of its own persistent implemetations of those --- 30,39 ---- implementing the collection interface (eg. iteration order of a <literal>Iesi.Collections.ListSet</literal>. The persistent collections actually behave like ! <literal>System.Collections.Hashtable</literal>, <literal>System.Collections.ArrayList</literal>, ! <literal>Iesi.Collections.HashedSet</literal> respectively. Furthermore, the .NET type of a property holding a collection must be the interface type (ie. <literal>IDictionary</literal>, <literal>IList</literal>, or ! <literal>ISet</literal>). This restriction exists because NHibernate replaces your instances of <literal>IDictionary</literal>, <literal>IList</literal>, and <literal>ISet</literal> with instances of its own persistent implemetations of those |
From: Michael D. <mik...@us...> - 2005-04-10 14:42:17
|
Update of /cvsroot/nhibernate/nhibernate/doc/reference/en/modules In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv16016/modules Modified Files: collection_mapping.xml Log Message: fixed typo in name of chapter Index: collection_mapping.xml =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/doc/reference/en/modules/collection_mapping.xml,v retrieving revision 1.2 retrieving revision 1.3 diff -C2 -d -r1.2 -r1.3 *** collection_mapping.xml 10 Apr 2005 14:37:17 -0000 1.2 --- collection_mapping.xml 10 Apr 2005 14:41:51 -0000 1.3 *************** *** 8,12 **** --> <chapter id="collections"> ! <title>Basic O/R Mapping</title> <sect1 id="collections-persistent"> <title>Persistent Collections</title> --- 8,12 ---- --> <chapter id="collections"> ! <title>Collection Mapping</title> <sect1 id="collections-persistent"> <title>Persistent Collections</title> |
From: Michael D. <mik...@us...> - 2005-04-10 14:37:46
|
Update of /cvsroot/nhibernate/nhibernate/doc/reference/en In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv14027 Modified Files: master.xml Log Message: started the shell on collections documentation Index: master.xml =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/doc/reference/en/master.xml,v retrieving revision 1.5 retrieving revision 1.6 diff -C2 -d -r1.5 -r1.6 *** master.xml 8 Apr 2005 19:23:36 -0000 1.5 --- master.xml 10 Apr 2005 14:37:18 -0000 1.6 *************** *** 8,11 **** --- 8,12 ---- <!ENTITY basic-mapping SYSTEM "modules/basic_mapping.xml"> <!ENTITY collection-mapping SYSTEM "modules/collection_mapping.xml"> + <!ENTITY association-mapping SYSTEM "modules/association_mapping.xml"> <!ENTITY component-mapping SYSTEM "modules/component_mapping.xml"> <!ENTITY inheritence-mapping SYSTEM "modules/inheritence_mapping.xml"> *************** *** 110,113 **** --- 111,116 ---- &configuration; &basic-mapping; + &collection-mapping; + &association-mapping; <index id="index"/> </book> \ No newline at end of file |
From: Michael D. <mik...@us...> - 2005-04-10 14:37:46
|
Update of /cvsroot/nhibernate/nhibernate/doc/reference/en/modules In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv14027/modules Modified Files: collection_mapping.xml Added Files: association_mapping.xml Log Message: started the shell on collections documentation Index: collection_mapping.xml =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/doc/reference/en/modules/collection_mapping.xml,v retrieving revision 1.1 retrieving revision 1.2 diff -C2 -d -r1.1 -r1.2 *** collection_mapping.xml 8 Apr 2005 19:23:35 -0000 1.1 --- collection_mapping.xml 10 Apr 2005 14:37:17 -0000 1.2 *************** *** 0 **** --- 1,257 ---- + <!-- + before committing make sure to comment out the DOCTYPE + It is in here to get intellisense with XMLSpy. The + HomeEdition is a free download. + + <!DOCTYPE chapter PUBLIC "-//OASIS//DTD DocBook XML V4.2//EN" + "../../support/docbook-dtd/docbookx.dtd"> + --> + <chapter id="collections"> + <title>Basic O/R Mapping</title> + <sect1 id="collections-persistent"> + <title>Persistent Collections</title> + <para> + This section does not contain much example .NET code. We assume you already know + how to use .NET's collections framework. If so, there's not really anything more + to know - with a single caveat, you may use .NET collections the same way you + always have. + </para> + <para> + NHibernate can persist instances of + <literal>System.Collections.IDictionary</literal>, + <literal>System.Collections.IList</literal>, + <literal>Iesi.Collections.ISet</literal>, + and an arry of persistent entities or values. Properties of type + <literal>System.Collections.ILst</literal> may also + be persisted with "bag" semantics. + </para> + <para> + Now the caveat: persistent collections do not retain any extra semantics added by the class + implementing the collection interface (eg. iteration order of a <literal>Iesi.Collections.ListSet</literal>. + The persistent collections actually behave like + <literal>System.Collections.Dictionary</literal>, + <literal>System.Collections.ArrayList</literal>, + <literal>Iesi.Collections.Set</literal> + respectively. Furthermore, the .NET type of a property holding a collection must be + the interface type (ie. <literal>IDictionary</literal>, <literal>IList</literal>, or + <literal>IList</literal>). This restriction exists because NHibernate replaces your + instances of <literal>IDictionary</literal>, <literal>IList</literal>, and + <literal>ISet</literal> with instances of its own persistent implemetations of those + collection interfaces. (So also be careful when using <literal>==</literal> on your + collections.) + </para> + + <programlisting><![CDATA[Cat cat = new DomesticCat(); + Cat kitten = new DomesticCat(); + ... + Iesi.Collections.ISet kittens = new Iesi.Collections.HashedSet(); + kittens.Add( kitten ); + cat.Kittens = kittens; + session.Save( cat ); + kittens = cat.Kittens; // Okay, kittens collection is an ISet + (Iesi.Collections.HashedSet)cat.Kittens; //Error! - a NHibernate.Collections.Set not Iesi.Collections.HashedSet]]></programlisting> + + <para> + Collections obey the usual rules for value types: no shared + references, created and deleted along with containing entity. Due to the underlying + relational model, they do not support null value semantics; NHibernate does not + distinguish between a null collection reference and an empty collection. + </para> + + <para> + Collections are automatically persisted when referenced by a persistent object + and automattically deleted when unreferenced. If a collection is passed from one + persistent object to another, its elements might be moved from one table to + another. You shouldn't have to worry much about any of this. Just use + NHibernate's collections the same way you use ordinary .NET collections, but + make sure you understand the semantic of bidirectional associations (discussed + later) before using them. + </para> + + <para> + Collection instances are distinguished in the database by a foreign key to + the owning entity. This foreign key is referred to as the + <emphasis>collection key</emphasis>. The collection key is mapped by + the <literal><key></literal> element. + </para> + + <para> + Collections may contain almost any other NHibernate type, including all basic types, + custome types, entity types and components. This is an important definition: An object + in a collection can either be handled with "pass by value" semantics (it therefore + fully depends on the collection owner) or it can be a reference to another entity + with its own lifecycle. Collections may not contain other collections. The contained type + is referred to as the <emphasis>collection element type</emphasis>. Collection elements + are mapped by <literal><element></literal>, <literal><composite-element></literal>, + <literal><one-to-many></literal>, <literal><many-to-many></literal>, or + <literal><many-to-any></literal>. The first two map elements with value semantics, + the other three are used to map entity associations. + </para> + + <para> + All collection types except <literal>ISet</literal> and bag have an <emphasis>index</emphasis> + column - a column that maps to an array or <literal>IList</literal> index or + <literal>IDictionary</literal>key. The index of a <literal>IDictionary</literal> may be of any + basic type, an entity type or even a composite type (it may not be a collection). The + index of an array or list is always of type <literal>Int32</literal>. Indexes are + mapped using <literal><index></literal>, <literal><index-many-to-many></literal>, + <literal><composite-index></literal>, or <literal><index-many-to-any></literal>. + </para> + + <para> + There are quite a range of mappings that can be generated for collections, + covering many common relational models. We suggest you experiment with the + schema generation tool to get a feeling for how various mapping declarations + translate to database tables. + </para> + </sect1> + <sect1 id="collections-mapping"> + <title>Mapping a Collection</title> + <para></para> + </sect1> + <sect1 id="collections-ofvalues"> + <title>Collections of Values and Many-To-Many Associations</title> + <para></para> + </sect1> + <sect1 id="collections-onetomany"> + <title>One-To-Many Associations</title> + <para></para> + </sect1> + <sect1 id="collections-lazy"> + <title>Lazy Initialization</title> + <para></para> + </sect1> + <sect1 id="collections-sorted"> + <title>Sorted Collections</title> + <para></para> + </sect1> + <sect1 id="collections-idbag"> + <title>Using an <idbag></title> + <para> + </para> + </sect1> + <sect1 id="collections-bidirectional"> + <title>Bidirectional Associations</title> + <para> + A <emphasis>bidirectional association</emphasis> allows navigation from both + "ends" of the association. Two kinds of bidirectional association are + supported: + + <variablelist> + <varlistentry> + <term>one-to-many</term> + <listitem> + <para> + <literal><set></literal> or <literal><bag></literal> at one + end, single-valued at the other + </para> + </listitem> + </varlistentry> + <varlistentry> + <term>many-to-many</term> + <listitem> + <para> + <literal><set></literal> or <literal><bag></literal> at both + ends. + </para> + </listitem> + </varlistentry> + </variablelist> + </para> + + <para> + Please note that NHibernate does not support bidirectional one-to-many associations + with an indexed collection (list, map, or array) as the "many" end, you have to + use a set or bag mapping. + </para> + + <para> + You may specify a bidirectional many-to-many association simply by mapping two + many-to-many associations to the same database table and declaring one end as + <emphasis>inverse</emphasis> (which end is your choice). Here's an example of + a bidirectional many-to-many association from a class back to <emphasis>itself</emphasis> + (each category can have many items and each item can be in many categories): + </para> + + <programlisting><![CDATA[<class name name="NHibernate.Auction.Category, NHibernate.Auction"> + <id name="Id" column="ID"/> + ... + <bag name="Items" table="CATEGORY_ITEM" lazy="true"> + <key column="CATEGORY_ID" /> + <many-to-many class="NHibernate.Auction.Category, NHibernate.Auction" column="ITEM_ID" /> + </bag> + </class> + + <class name="NHibernate.Auction.Item, NHibernate.Auction"> + <id name="Id" column="ID" /> + + <!-- inverse end --> + <bag name="Categories" table="CATEGORY_ITEM" inverse="true" lazy="true"> + <key column="ITEM_ID" /> + <many-to-many class="NHibernate.Auction.Category, NHibernate.Auction" column="CATEGORY_ID" /> + </bag> + </class> + ]]></programlisting> + + <para> + Changes made only to the inverse end of the association are <emphasis>not</emphasis> + persisted. This means that NHibernate has two representations in memory for every + bidirectional association, one link from A to B and another link from B to A. This + is easier to understand if you think about the object model and how we create a + many-to-many relationship in .NET: + </para> + + <programlisting><![CDATA[ + category.Items.Add( item ); // The category now "knows" about the relationship + item.Categories.Add( category ); // The item now "knows" about the relationship + + session.Update( item ); // No effect, nothing will be saved! + session.Update( category ); // The relationship will be saved + ]]></programlisting> + + <para> + The non-inverse side is used to save the in-memory representation to the database. + We would get an unnecessary INSERT/UPDATE and probably even a foreign key violation + if both would trigger changes! This same is of course also true for bidirectional + one-to-many associations. + </para> + + <para> + You may map a bidirectional one-to-many association by mapping a one-to-many association + to the same table column(s) as a many-to-one association and declaring the many-valued + end <literal>inverse="true"</literal>. + </para> + + <programlisting><![CDATA[<class name="Eg.Parent, Eg> + <id name="Id" column="id" /> + ... + <set name="Children" inverse="true" lazy="true"> + <key column="parent_id" /> + <one-to-many class="Eg.Child, Eg" /> + </set> + </class> + + <class name="Eg.Child, Eg"> + <id name="Id" column="id" /> + .... + <many-to-one name="Parent" class="Eg.Parent, Eg" column="parent_id" /> + </class>]]></programlisting> + + <para> + Mapping one end of an association with <literal>inverse="true"</literal> doesn't + affect the operation of cascades, both are different concepts! + </para> + </sect1> + <sect1 id="collections-ternary"> + <title>Ternary Associations</title> + <para></para> + </sect1> + <sect1 id="collections-heterogeneous"> + <title>Heterogeneous Associations</title> + <para></para> + </sect1> + <sect1 id="collections-example"> + <title>Collection examples</title> + <para></para> + </sect1> + </chapter> \ No newline at end of file --- NEW FILE: association_mapping.xml --- <!-- before committing make sure to comment out the DOCTYPE It is in here to get intellisense with XMLSpy. The HomeEdition is a free download. <!DOCTYPE chapter PUBLIC "-//OASIS//DTD DocBook XML V4.2//EN" "../../support/docbook-dtd/docbookx.dtd"> --> <chapter id="associations"> <title>Association Mappings</title> <sect1 id="assoc-intro"> <title>Introduction</title> <para> </para> </sect1> <sect1 id="assoc-unidirectional"> <title>Unidirectional associations</title> <para> </para> <sect2 id="assoc-unidirectional-m21"> <title>many to one</title> <para></para> </sect2> <sect2 id="assoc-unidirectional-121"> <title>one to one</title> <para></para> </sect2> <sect2 id="assoc-unidirectional-12m"> <title>one to many</title> <para></para> </sect2> </sect1> <sect1 id="assoc-unidirectional-join"> <title>Unidirectional associations with join tables</title> <para></para> <sect2 id="assoc-unidirectional-join-12m"> <title>one to many</title> <para></para> </sect2> <sect2 id="assoc-unidirectional-join-m21"> <title>many to one</title> <para></para> </sect2> <sect2 id="assoc-unidirectional-join-121"> <title>one to one</title> <para></para> </sect2> <sect2 id="assoc-unidirectional-join-m2m"> <title>many to many</title> <para></para> </sect2> </sect1> <sect1 id="assoc-bidirectional"> <title>Bidirectional associations</title> <para></para> <sect2 id="assoc-bidirectional-m21"> <title>one to many / many to one</title> <para></para> </sect2> <sect2 id="assoc-bidirectional-121"> <title>one to one</title> <para></para> </sect2> </sect1> <sect1 id="assoc-bidirectional-join"> <title>Bidirectional associations with join tables</title> <para></para> <sect2 id="assoc-bidirectional-join-12m"> <title>one to many / many to one</title> <para></para> </sect2> <sect2 id="assoc-bidirectional-join-121"> <title>one to one</title> <para></para> </sect2> <sect2 id="assoc-bidirectional-join-m2m"> <title>many to many</title> <para></para> </sect2> </sect1> </chapter> |
From: Sergey K. <jus...@us...> - 2005-04-09 12:51:47
|
Update of /cvsroot/nhibernate/nhibernate/src/NHibernate.Test/NHSpecificTest In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv7916/src/NHibernate.Test/NHSpecificTest Added Files: SetFixture.cs Log Message: Test case for the Set.InitializeFromCache bug --- NEW FILE: SetFixture.cs --- using System; using System.Collections; using NUnit.Framework; using NHibernate.Collection; using NHibernate.Engine; using NHibernate.Persister; using NHibernate.Type; namespace NHibernate.Test.NHSpecificTest { class CollectionSnapshotStub : ICollectionSnapshot { #region ICollectionSnapshot Members public bool Dirty { get { // TODO: Add CollectionSnapshotStub.Dirty getter implementation return false; } } public object Key { get { // TODO: Add CollectionSnapshotStub.Key getter implementation return null; } } public string Role { get { // TODO: Add CollectionSnapshotStub.Role getter implementation return null; } } public void SetDirty() { // TODO: Add CollectionSnapshotStub.SetDirty implementation } public bool WasDereferenced { get { // TODO: Add CollectionSnapshotStub.WasDereferenced getter implementation return false; } } public ICollection Snapshot { get { // TODO: Add CollectionSnapshotStub.Snapshot getter implementation return null; } } #endregion } class CollectionPersisterStub : ICollectionPersister { #region ICollectionPersister Members public System.Type OwnerClass { get { // TODO: Add CollectionPersisterStub.OwnerClass getter implementation return null; } } public bool HasCache { get { // TODO: Add CollectionPersisterStub.HasCache getter implementation return false; } } public NHibernate.Id.IIdentifierGenerator IdentifierGenerator { get { // TODO: Add CollectionPersisterStub.IdentifierGenerator getter implementation return null; } } public bool IsInverse { get { // TODO: Add CollectionPersisterStub.IsInverse getter implementation return false; } } public NHibernate.Type.IType IndexType { get { // TODO: Add CollectionPersisterStub.IndexType getter implementation return null; } } public bool HasIndex { get { // TODO: Add CollectionPersisterStub.HasIndex getter implementation return false; } } public bool IsOneToMany { get { // TODO: Add CollectionPersisterStub.IsOneToMany getter implementation return false; } } public System.Type ElementClass { get { // TODO: Add CollectionPersisterStub.ElementClass getter implementation return null; } } public NHibernate.Type.IType KeyType { get { // TODO: Add CollectionPersisterStub.KeyType getter implementation return null; } } public void InsertRows(PersistentCollection collection, object key, ISessionImplementor session) { // TODO: Add CollectionPersisterStub.InsertRows implementation } public bool IsLazy { get { // TODO: Add CollectionPersisterStub.IsLazy getter implementation return false; } } public NHibernate.Type.PersistentCollectionType CollectionType { get { // TODO: Add CollectionPersisterStub.CollectionType getter implementation return null; } } public void UpdateRows(PersistentCollection collection, object key, ISessionImplementor session) { // TODO: Add CollectionPersisterStub.UpdateRows implementation } public void DeleteRows(PersistentCollection collection, object key, ISessionImplementor session) { // TODO: Add CollectionPersisterStub.DeleteRows implementation } public void WriteElement(System.Data.IDbCommand st, object elt, bool writeOrder, ISessionImplementor session) { // TODO: Add CollectionPersisterStub.WriteElement implementation } public void Recreate(PersistentCollection collection, object key, ISessionImplementor session) { // TODO: Add CollectionPersisterStub.Recreate implementation } public bool HasOrdering { get { // TODO: Add CollectionPersisterStub.HasOrdering getter implementation return false; } } private IType elementType; public IType ElementType { get { return elementType; } set { elementType = value; } } public void Remove(object id, ISessionImplementor session) { // TODO: Add CollectionPersisterStub.Remove implementation } public object ReadElement(System.Data.IDataReader rs, object owner, ISessionImplementor session) { // TODO: Add CollectionPersisterStub.ReadElement implementation return null; } public string Role { get { // TODO: Add CollectionPersisterStub.Role getter implementation return null; } } public NHibernate.Metadata.ICollectionMetadata CollectionMetadata { get { // TODO: Add CollectionPersisterStub.CollectionMetadata getter implementation return null; } } public object ReadIndex(System.Data.IDataReader rs, ISessionImplementor session) { // TODO: Add CollectionPersisterStub.ReadIndex implementation return null; } public void WriteKey(System.Data.IDbCommand st, object key, bool writeOrder, ISessionImplementor session) { // TODO: Add CollectionPersisterStub.WriteKey implementation } public void Initialize(object key, object owner, ISessionImplementor session) { // TODO: Add CollectionPersisterStub.Initialize implementation } public object ReadKey(System.Data.IDataReader rs, ISessionImplementor session) { // TODO: Add CollectionPersisterStub.ReadKey implementation return null; } public NHibernate.Type.IType IdentifierType { get { // TODO: Add CollectionPersisterStub.IdentifierType getter implementation return null; } } public bool IsArray { get { // TODO: Add CollectionPersisterStub.IsArray getter implementation return false; } } public NHibernate.Cache.ICacheConcurrencyStrategy Cache { get { // TODO: Add CollectionPersisterStub.Cache getter implementation return null; } } public bool IsPrimitiveArray { get { // TODO: Add CollectionPersisterStub.IsPrimitiveArray getter implementation return false; } } public object ReadIdentifier(System.Data.IDataReader rs, ISessionImplementor session) { // TODO: Add CollectionPersisterStub.ReadIdentifier implementation return null; } public void WriteIndex(System.Data.IDbCommand st, object idx, bool writeOrder, ISessionImplementor session) { // TODO: Add CollectionPersisterStub.WriteIndex implementation } public object CollectionSpace { get { // TODO: Add CollectionPersisterStub.CollectionSpace getter implementation return null; } } public bool HasOrphanDelete { get { // TODO: Add CollectionPersisterStub.HasOrphanDelete getter implementation return false; } } public void WriteIdentifier(System.Data.IDbCommand st, object idx, bool writeOrder, ISessionImplementor session) { // TODO: Add CollectionPersisterStub.WriteIdentifier implementation } #endregion } [TestFixture] public class SetFixture { [Test] public void DisassembleAndAssemble() { Set set = new Set( null, new Iesi.Collections.ListSet() ); set.CollectionSnapshot = new CollectionSnapshotStub(); set.Add(10); set.Add(20); CollectionPersisterStub collectionPersister = new CollectionPersisterStub(); collectionPersister.ElementType = NHibernateUtil.Int32; object disassembled = set.Disassemble(collectionPersister); Set assembledSet = new Set( null ); assembledSet.InitializeFromCache( collectionPersister, disassembled, null ); Assert.AreEqual( 2, assembledSet.Count ); Assert.IsTrue( assembledSet.Contains( 10 ) ); Assert.IsTrue( assembledSet.Contains( 20 ) ); } } } |
From: Sergey K. <jus...@us...> - 2005-04-09 12:51:47
|
Update of /cvsroot/nhibernate/nhibernate/src/NHibernate.Test In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv7916/src/NHibernate.Test Modified Files: NHibernate.Test-1.1.csproj Log Message: Test case for the Set.InitializeFromCache bug Index: NHibernate.Test-1.1.csproj =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/src/NHibernate.Test/NHibernate.Test-1.1.csproj,v retrieving revision 1.69 retrieving revision 1.70 diff -C2 -d -r1.69 -r1.70 *** NHibernate.Test-1.1.csproj 31 Mar 2005 12:42:39 -0000 1.69 --- NHibernate.Test-1.1.csproj 9 Apr 2005 12:51:38 -0000 1.70 *************** *** 498,501 **** --- 498,506 ---- /> <File + RelPath = "NHSpecificTest\SetFixture.cs" + SubType = "Code" + BuildAction = "Compile" + /> + <File RelPath = "NHSpecificTest\SimpleComponentFixture.cs" SubType = "Code" |
From: Sergey K. <jus...@us...> - 2005-04-09 12:51:15
|
Update of /cvsroot/nhibernate/nhibernate/src/NHibernate/Collection In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv7576/src/NHibernate/Collection Modified Files: ArrayHolder.cs Bag.cs IdentifierBag.cs List.cs Map.cs PersistentCollection.cs Set.cs SortedMap.cs SortedSet.cs Log Message: Modified collection snapshots to be ICollections instead of objects (not so generic, but all of them are ICollections anyway). Fixed a bug in Set.InitializeFromCache Index: Map.cs =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/src/NHibernate/Collection/Map.cs,v retrieving revision 1.23 retrieving revision 1.24 diff -C2 -d -r1.23 -r1.24 *** Map.cs 30 Mar 2005 16:28:24 -0000 1.23 --- Map.cs 9 Apr 2005 12:51:06 -0000 1.24 *************** *** 23,27 **** /// <param name="persister"></param> /// <returns></returns> ! protected override object Snapshot( ICollectionPersister persister ) { Hashtable clonedMap = new Hashtable( map.Count ); --- 23,27 ---- /// <param name="persister"></param> /// <returns></returns> ! protected override ICollection Snapshot( ICollectionPersister persister ) { Hashtable clonedMap = new Hashtable( map.Count ); Index: PersistentCollection.cs =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/src/NHibernate/Collection/PersistentCollection.cs,v retrieving revision 1.25 retrieving revision 1.26 diff -C2 -d -r1.25 -r1.26 *** PersistentCollection.cs 29 Mar 2005 05:33:15 -0000 1.25 --- PersistentCollection.cs 9 Apr 2005 12:51:06 -0000 1.26 *************** *** 437,441 **** /// <param name="persister"></param> /// <returns></returns> ! protected abstract object Snapshot( ICollectionPersister persister ); /// <summary> --- 437,441 ---- /// <param name="persister"></param> /// <returns></returns> ! protected abstract ICollection Snapshot( ICollectionPersister persister ); /// <summary> *************** *** 466,470 **** /// <param name="persister"></param> /// <returns></returns> ! public object GetSnapshot( ICollectionPersister persister ) { return ( persister == null ) ? null : Snapshot( persister ); --- 466,470 ---- /// <param name="persister"></param> /// <returns></returns> ! public ICollection GetSnapshot( ICollectionPersister persister ) { return ( persister == null ) ? null : Snapshot( persister ); Index: List.cs =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/src/NHibernate/Collection/List.cs,v retrieving revision 1.21 retrieving revision 1.22 diff -C2 -d -r1.21 -r1.22 *** List.cs 14 Mar 2005 18:51:48 -0000 1.21 --- List.cs 9 Apr 2005 12:51:06 -0000 1.22 *************** *** 20,24 **** /// <param name="persister"></param> /// <returns></returns> ! protected override object Snapshot( ICollectionPersister persister ) { ArrayList clonedList = new ArrayList( list.Count ); --- 20,24 ---- /// <param name="persister"></param> /// <returns></returns> ! protected override ICollection Snapshot( ICollectionPersister persister ) { ArrayList clonedList = new ArrayList( list.Count ); Index: Bag.cs =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/src/NHibernate/Collection/Bag.cs,v retrieving revision 1.16 retrieving revision 1.17 diff -C2 -d -r1.16 -r1.17 *** Bag.cs 14 Mar 2005 18:51:48 -0000 1.16 --- Bag.cs 9 Apr 2005 12:51:06 -0000 1.17 *************** *** 168,172 **** /// <param name="persister"></param> /// <returns></returns> ! protected override object Snapshot( ICollectionPersister persister ) { ArrayList clonedList = new ArrayList( bag.Count ); --- 168,172 ---- /// <param name="persister"></param> /// <returns></returns> ! protected override ICollection Snapshot( ICollectionPersister persister ) { ArrayList clonedList = new ArrayList( bag.Count ); Index: ArrayHolder.cs =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/src/NHibernate/Collection/ArrayHolder.cs,v retrieving revision 1.19 retrieving revision 1.20 diff -C2 -d -r1.19 -r1.20 *** ArrayHolder.cs 14 Mar 2005 18:51:48 -0000 1.19 --- ArrayHolder.cs 9 Apr 2005 12:51:06 -0000 1.20 *************** *** 48,52 **** /// <param name="persister"></param> /// <returns></returns> ! protected override object Snapshot( ICollectionPersister persister ) { int length = /*(array==null) ? temp.Count :*/ array.Length; --- 48,52 ---- /// <param name="persister"></param> /// <returns></returns> ! protected override ICollection Snapshot( ICollectionPersister persister ) { int length = /*(array==null) ? temp.Count :*/ array.Length; Index: SortedSet.cs =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/src/NHibernate/Collection/SortedSet.cs,v retrieving revision 1.15 retrieving revision 1.16 diff -C2 -d -r1.15 -r1.16 *** SortedSet.cs 1 Mar 2005 16:24:44 -0000 1.15 --- SortedSet.cs 9 Apr 2005 12:51:06 -0000 1.16 *************** *** 23,27 **** /// <param name="persister"></param> /// <returns></returns> ! protected override object Snapshot( ICollectionPersister persister ) { SortedList clonedSet = new SortedList( comparer, internalSet.Count ); --- 23,27 ---- /// <param name="persister"></param> /// <returns></returns> ! protected override ICollection Snapshot( ICollectionPersister persister ) { SortedList clonedSet = new SortedList( comparer, internalSet.Count ); Index: SortedMap.cs =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/src/NHibernate/Collection/SortedMap.cs,v retrieving revision 1.10 retrieving revision 1.11 diff -C2 -d -r1.10 -r1.11 *** SortedMap.cs 1 Mar 2005 16:24:44 -0000 1.10 --- SortedMap.cs 9 Apr 2005 12:51:06 -0000 1.11 *************** *** 26,30 **** /// <param name="persister"></param> /// <returns></returns> ! protected override object Snapshot( ICollectionPersister persister ) { SortedList clonedMap = new SortedList( comparer ); --- 26,30 ---- /// <param name="persister"></param> /// <returns></returns> ! protected override ICollection Snapshot( ICollectionPersister persister ) { SortedList clonedMap = new SortedList( comparer ); Index: Set.cs =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/src/NHibernate/Collection/Set.cs,v retrieving revision 1.28 retrieving revision 1.29 diff -C2 -d -r1.28 -r1.29 *** Set.cs 29 Mar 2005 05:33:15 -0000 1.28 --- Set.cs 9 Apr 2005 12:51:06 -0000 1.29 *************** *** 10,14 **** /// <summary> /// .NET has no design equivalent for Java's Set so we are going to use the ! /// Iesi.Collections library. /// </summary> /// <remarks> --- 10,15 ---- /// <summary> /// .NET has no design equivalent for Java's Set so we are going to use the ! /// Iesi.Collections library. This class is internal to NHibernate and shouldn't ! /// be used by user code. /// </summary> /// <remarks> *************** *** 43,47 **** /// </summary> /// <param name="persister"></param> ! protected override object Snapshot( ICollectionPersister persister ) { Hashtable clonedMap = new Hashtable( internalSet.Count ); --- 44,48 ---- /// </summary> /// <param name="persister"></param> ! protected override ICollection Snapshot( ICollectionPersister persister ) { Hashtable clonedMap = new Hashtable( internalSet.Count ); *************** *** 109,116 **** /// <summary> ! /// /// </summary> /// <param name="session"></param> ! internal Set( ISessionImplementor session ) : base( session ) { } --- 110,117 ---- /// <summary> ! /// This constructor is NOT meant to be called from user code. /// </summary> /// <param name="session"></param> ! public Set( ISessionImplementor session ) : base( session ) { } *************** *** 118,121 **** --- 119,123 ---- /// <summary> /// Creates a new Set initialized to the values in the Map. + /// This constructor is NOT meant to be called from user code. /// </summary> /// <param name="session"></param> *************** *** 124,128 **** /// Only call this constructor if you consider the map initialized. /// </remarks> ! internal Set( ISessionImplementor session, ISet collection ) : base( session ) { internalSet = collection; --- 126,130 ---- /// Only call this constructor if you consider the map initialized. /// </remarks> ! public Set( ISessionImplementor session, ISet collection ) : base( session ) { internalSet = collection; *************** *** 141,145 **** BeforeInitialize( persister ); object[ ] array = ( object[ ] ) disassembled; ! for( int i = 0; i < array.Length; i += 2 ) { internalSet.Add( persister.ElementType.Assemble( array[ i ], Session, owner ) ); --- 143,147 ---- BeforeInitialize( persister ); object[ ] array = ( object[ ] ) disassembled; ! for( int i = 0; i < array.Length; i++ ) { internalSet.Add( persister.ElementType.Assemble( array[ i ], Session, owner ) ); Index: IdentifierBag.cs =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/src/NHibernate/Collection/IdentifierBag.cs,v retrieving revision 1.11 retrieving revision 1.12 diff -C2 -d -r1.11 -r1.12 *** IdentifierBag.cs 14 Mar 2005 18:51:48 -0000 1.11 --- IdentifierBag.cs 9 Apr 2005 12:51:06 -0000 1.12 *************** *** 430,434 **** /// <param name="persister"></param> /// <returns></returns> ! protected override object Snapshot( ICollectionPersister persister ) { IDictionary map = new Hashtable( values.Count ); --- 430,434 ---- /// <param name="persister"></param> /// <returns></returns> ! protected override ICollection Snapshot( ICollectionPersister persister ) { IDictionary map = new Hashtable( values.Count ); |
From: Sergey K. <jus...@us...> - 2005-04-09 12:51:15
|
Update of /cvsroot/nhibernate/nhibernate/src/NHibernate/Impl In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv7576/src/NHibernate/Impl Modified Files: CollectionEntry.cs Log Message: Modified collection snapshots to be ICollections instead of objects (not so generic, but all of them are ICollections anyway). Fixed a bug in Set.InitializeFromCache Index: CollectionEntry.cs =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/src/NHibernate/Impl/CollectionEntry.cs,v retrieving revision 1.8 retrieving revision 1.9 diff -C2 -d -r1.8 -r1.9 *** CollectionEntry.cs 14 Mar 2005 18:52:52 -0000 1.8 --- CollectionEntry.cs 9 Apr 2005 12:51:06 -0000 1.9 *************** *** 114,118 **** /// <summary>session-start/post-flush persistent state</summary> ! internal object snapshot; /// <summary>allow the snapshot to be serialized</summary> --- 114,118 ---- /// <summary>session-start/post-flush persistent state</summary> ! internal ICollection snapshot; /// <summary>allow the snapshot to be serialized</summary> *************** *** 306,310 **** /// <summary></summary> ! public object Snapshot { get { return snapshot; } --- 306,310 ---- /// <summary></summary> ! public ICollection Snapshot { get { return snapshot; } *************** *** 354,372 **** get { ! //TODO: implementation here is non-extensible ... ! //should use polymorphism ! // return initialized && snapshot!=null && ( ! // ( snapshot is IList && ( (IList) snapshot ).Count==0 ) || // if snapshot is a collection ! // ( snapshot is Map && ( (Map) snapshot ).Count==0 ) || // if snapshot is a map ! // (snapshot.GetType().IsArray && ( (Array) snapshot).Length==0 )// if snapshot is an array ! // ); ! ! // TODO: in .NET an IList, IDictionary, and Array are all collections so we might be able ! // to just cast it to a ICollection instead of all the diff collections. ! return initialized && snapshot != null && ( ! ( snapshot is IList && ( ( IList ) snapshot ).Count == 0 ) || // if snapshot is a collection ! ( snapshot is IDictionary && ( ( IDictionary ) snapshot ).Count == 0 ) || // if snapshot is a map ! ( snapshot.GetType().IsArray && ( ( Array ) snapshot ).Length == 0 ) // if snapshot is an array ! ); } } --- 354,358 ---- get { ! return initialized && snapshot != null && snapshot.Count == 0; } } |
From: Sergey K. <jus...@us...> - 2005-04-09 12:51:14
|
Update of /cvsroot/nhibernate/nhibernate/src/NHibernate/Engine In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv7576/src/NHibernate/Engine Modified Files: ICollectionSnapshot.cs Log Message: Modified collection snapshots to be ICollections instead of objects (not so generic, but all of them are ICollections anyway). Fixed a bug in Set.InitializeFromCache Index: ICollectionSnapshot.cs =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/src/NHibernate/Engine/ICollectionSnapshot.cs,v retrieving revision 1.6 retrieving revision 1.7 diff -C2 -d -r1.6 -r1.7 *** ICollectionSnapshot.cs 6 Feb 2005 01:58:57 -0000 1.6 --- ICollectionSnapshot.cs 9 Apr 2005 12:51:06 -0000 1.7 *************** *** 1,2 **** --- 1,4 ---- + using System.Collections; + namespace NHibernate.Engine { *************** *** 23,27 **** /// ie - the snapshot of an IList will return an IList. /// </remarks> ! object Snapshot { get; } /// <summary> --- 25,29 ---- /// ie - the snapshot of an IList will return an IList. /// </remarks> ! ICollection Snapshot { get; } /// <summary> |
From: Sergey K. <jus...@us...> - 2005-04-09 12:48:17
|
Update of /cvsroot/nhibernate/nhibernate/src/NHibernate.Test In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv5861/src/NHibernate.Test Modified Files: SQLFunctionsTest.cs Log Message: Abort transactions on failure Index: SQLFunctionsTest.cs =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/src/NHibernate.Test/SQLFunctionsTest.cs,v retrieving revision 1.8 retrieving revision 1.9 diff -C2 -d -r1.8 -r1.9 *** SQLFunctionsTest.cs 31 Mar 2005 12:42:39 -0000 1.8 --- SQLFunctionsTest.cs 9 Apr 2005 12:48:06 -0000 1.9 *************** *** 126,271 **** public void SQLFunctions() { ! ISession s = sessions.OpenSession(); ! ITransaction t = s.BeginTransaction(); ! Simple simple = new Simple(); ! simple.Name = "Simple 1"; ! s.Save( simple, (long)10 ); ! ! /* ! * TODO: once DB2Dialect is implemented uncomment this ! if( dialect is Dialect.DB2Dialect ) { ! s.Find("from s in class Simple where repeat('foo', 3) = 'foofoofoo'"); ! s.Find("from s in class Simple where repeat(s.Name, 3) = 'foofoofoo'"); ! s.Find("from s in class Simple where repeat( lower(s.Name), 3 + (1-1) / 2) = 'foofoofoo'"); ! } ! */ ! Assert.AreEqual( 1, s.Find("from s in class Simple where upper(s.Name) = 'SIMPLE 1'").Count ); ! Assert.AreEqual( 1, s.Find("from s in class Simple where not( upper(s.Name)='yada' or 1=2 or 'foo'='bar' or not('foo'='foo') or 'foo' like 'bar')").Count ); ! if( !(dialect is Dialect.MySQLDialect) && !(dialect is Dialect.SybaseDialect) && !(dialect is Dialect.MsSql2000Dialect) ) ! { ! // Dialect.MckoiDialect and Dialect.InterbaseDialect also included ! // My Sql has a funny concatenation operator ! Assert.AreEqual( 1, s.Find("from s in class Simple where lower(s.Name || ' foo')='simple 1 foo'").Count ); ! } ! if( (dialect is Dialect.SybaseDialect) ) ! { ! Assert.AreEqual( 1, s.Find("from s in class Simple where lower( concat(s.Name, ' foo') ) = 'simple 1 foo'").Count ); ! } ! if( (dialect is Dialect.MsSql2000Dialect) ) ! { ! Assert.AreEqual( 1, s.Find("from s in class Simple where lower( s.Name + ' foo' ) = 'simple 1 foo'").Count ); ! } ! /* ! * TODO: uncomment if MckoiDialect is ever implemented ! if( (dialect is Dialect.MckoiDialect) ) ! { ! Assert.AreEqual( 1, s.Find("from s in class Simple where lower( concat(s.Name, ' foo') ) = 'simple 1 foo'").Count ); ! } ! */ ! Simple other = new Simple(); ! other.Name = "Simple 2"; ! other.Count = 12; ! simple.Other = other; ! s.Save( other, (long)20 ); ! Assert.AreEqual( 1, s.Find("from s in class Simple where upper( s.Other.Name )='SIMPLE 2'").Count ); ! Assert.AreEqual( 0, s.Find("from s in class Simple where not (upper(s.Other.Name)='SIMPLE 2')").Count ); ! Assert.AreEqual( 1, s.Find("select distinct s from s in class Simple where ( ( s.Other.Count + 3) = (15*2)/2 and s.Count = 69) or ( (s.Other.Count + 2) / 7 ) = 2").Count ); ! Assert.AreEqual( 1, s.Find("select s from s in class Simple where ( ( s.Other.Count + 3) = (15*2)/2 and s.Count = 69) or ( (s.Other.Count + 2) / 7 ) = 2 order by s.Other.Count").Count ); ! Simple min = new Simple(); ! min.Count = -1; ! s.Save( min, (long)30 ); ! // && !(dialect is Dialect.HSQLDialect) ! // MySql has no subqueries ! if( !(dialect is Dialect.MySQLDialect) ) ! { ! Assert.AreEqual( 2, s.Find("from s in class Simple where s.Count > ( select min(sim.Count) from sim in class NHibernate.DomainModel.Simple )").Count ); ! t.Commit(); ! t = s.BeginTransaction(); ! Assert.AreEqual( 2, s.Find("from s in class Simple where s = some( select sim from sim in class NHibernate.DomainModel.Simple where sim.Count>=0) and s.Count >= 0").Count ); ! Assert.AreEqual( 1, s.Find("from s in class Simple where s = some( select sim from sim in class NHibernate.DomainModel.Simple where sim.Other.Count=s.Other.Count ) and s.Other.Count > 0").Count ); ! } ! IEnumerator enumer = s.Enumerable("select sum(s.Count) from s in class Simple group by s.Count having sum(s.Count) > 10 ").GetEnumerator(); ! Assert.IsTrue( enumer.MoveNext() ); ! Assert.AreEqual(12, (Int32)enumer.Current ); ! Assert.IsFalse( enumer.MoveNext() ); ! if( !(dialect is Dialect.MySQLDialect) ) ! { ! enumer = s.Enumerable("select s.Count from s in class Simple group by s.Count having s.Count = 12").GetEnumerator(); Assert.IsTrue( enumer.MoveNext() ); ! } ! enumer = s.Enumerable("select s.id, s.Count, count(t), max(t.Date) from s in class Simple, t in class Simple where s.Count = t.Count group by s.id, s.Count order by s.Count").GetEnumerator(); ! IQuery q = s.CreateQuery("from s in class Simple"); ! q.SetMaxResults(10); ! Assert.AreEqual( 3, q.List().Count ); ! q = s.CreateQuery("from s in class Simple"); ! q.SetMaxResults(1); ! Assert.AreEqual( 1, q.List().Count ); ! q = s.CreateQuery("from s in class Simple"); ! Assert.AreEqual( 3, q.List().Count ); ! q = s.CreateQuery("from s in class Simple where s.Name = ?"); ! q.SetString(0, "Simple 1"); ! Assert.AreEqual( 1, q.List().Count ); ! q = s.CreateQuery("from s in class Simple where s.Name = ? and upper(s.Name) = ?"); ! q.SetString( 1, "SIMPLE 1" ); ! q.SetString( 0, "Simple 1" ); ! q.SetFirstResult(0); ! Assert.IsTrue( q.Enumerable().GetEnumerator().MoveNext() ); ! q = s.CreateQuery("from s in class Simple where s.Name = :foo and upper(s.Name) = :bar or s.Count=:count or s.Count=:count + 1"); ! q.SetParameter("bar", "SIMPLE 1"); ! q.SetString("foo", "Simple 1"); ! q.SetInt32("count", 69); ! q.SetFirstResult(0); ! Assert.IsTrue( q.Enumerable().GetEnumerator().MoveNext() ); ! q = s.CreateQuery("select s.id from s in class Simple"); ! q.SetFirstResult(1); ! q.SetMaxResults(2); ! IEnumerable enumerable = q.Enumerable(); ! int i=0; ! foreach( object obj in enumerable ) ! { ! Assert.IsTrue( obj is Int64 ); ! i++; ! } ! Assert.AreEqual( 2, i ); ! q = s.CreateQuery("select all s, s.Other from s in class Simple where s = :s"); ! q.SetParameter("s", simple); ! Assert.AreEqual( 1, q.List().Count ); ! q = s.CreateQuery("from s in class Simple where s.Name in (:name_list) and s.Count > :count"); ! IList list = new ArrayList(2); ! list.Add("Simple 1"); ! list.Add("foo"); ! q.SetParameterList( "name_list", list ); ! q.SetParameter( "count", (int)-1 ); ! Assert.AreEqual( 1, q.List().Count ); ! s.Delete(other); ! s.Delete(simple); ! s.Delete(min); ! t.Commit(); ! s.Close(); ! } --- 126,271 ---- public void SQLFunctions() { ! using( ISession s = sessions.OpenSession() ) { ! ITransaction t = s.BeginTransaction(); ! Simple simple = new Simple(); ! simple.Name = "Simple 1"; ! s.Save( simple, (long)10 ); ! /* ! * TODO: once DB2Dialect is implemented uncomment this ! if( dialect is Dialect.DB2Dialect ) ! { ! s.Find("from s in class Simple where repeat('foo', 3) = 'foofoofoo'"); ! s.Find("from s in class Simple where repeat(s.Name, 3) = 'foofoofoo'"); ! s.Find("from s in class Simple where repeat( lower(s.Name), 3 + (1-1) / 2) = 'foofoofoo'"); ! } ! */ ! Assert.AreEqual( 1, s.Find("from s in class Simple where upper(s.Name) = 'SIMPLE 1'").Count ); ! Assert.AreEqual( 1, s.Find("from s in class Simple where not( upper(s.Name)='yada' or 1=2 or 'foo'='bar' or not('foo'='foo') or 'foo' like 'bar')").Count ); ! if( !(dialect is Dialect.MySQLDialect) && !(dialect is Dialect.SybaseDialect) && !(dialect is Dialect.MsSql2000Dialect) ) ! { ! // Dialect.MckoiDialect and Dialect.InterbaseDialect also included ! // My Sql has a funny concatenation operator ! Assert.AreEqual( 1, s.Find("from s in class Simple where lower(s.Name || ' foo')='simple 1 foo'").Count ); ! } ! if( (dialect is Dialect.SybaseDialect) ) ! { ! Assert.AreEqual( 1, s.Find("from s in class Simple where lower( concat(s.Name, ' foo') ) = 'simple 1 foo'").Count ); ! } ! if( (dialect is Dialect.MsSql2000Dialect) ) ! { ! Assert.AreEqual( 1, s.Find("from s in class Simple where lower( s.Name + ' foo' ) = 'simple 1 foo'").Count ); ! } ! /* ! * TODO: uncomment if MckoiDialect is ever implemented ! if( (dialect is Dialect.MckoiDialect) ) ! { ! Assert.AreEqual( 1, s.Find("from s in class Simple where lower( concat(s.Name, ' foo') ) = 'simple 1 foo'").Count ); ! } ! */ ! Simple other = new Simple(); ! other.Name = "Simple 2"; ! other.Count = 12; ! simple.Other = other; ! s.Save( other, (long)20 ); ! Assert.AreEqual( 1, s.Find("from s in class Simple where upper( s.Other.Name )='SIMPLE 2'").Count ); ! Assert.AreEqual( 0, s.Find("from s in class Simple where not (upper(s.Other.Name)='SIMPLE 2')").Count ); ! Assert.AreEqual( 1, s.Find("select distinct s from s in class Simple where ( ( s.Other.Count + 3) = (15*2)/2 and s.Count = 69) or ( (s.Other.Count + 2) / 7 ) = 2").Count ); ! Assert.AreEqual( 1, s.Find("select s from s in class Simple where ( ( s.Other.Count + 3) = (15*2)/2 and s.Count = 69) or ( (s.Other.Count + 2) / 7 ) = 2 order by s.Other.Count").Count ); ! Simple min = new Simple(); ! min.Count = -1; ! s.Save( min, (long)30 ); ! // && !(dialect is Dialect.HSQLDialect) ! // MySql has no subqueries ! if( !(dialect is Dialect.MySQLDialect) ) ! { ! Assert.AreEqual( 2, s.Find("from s in class Simple where s.Count > ( select min(sim.Count) from sim in class NHibernate.DomainModel.Simple )").Count ); ! t.Commit(); ! t = s.BeginTransaction(); ! Assert.AreEqual( 2, s.Find("from s in class Simple where s = some( select sim from sim in class NHibernate.DomainModel.Simple where sim.Count>=0) and s.Count >= 0").Count ); ! Assert.AreEqual( 1, s.Find("from s in class Simple where s = some( select sim from sim in class NHibernate.DomainModel.Simple where sim.Other.Count=s.Other.Count ) and s.Other.Count > 0").Count ); ! } ! IEnumerator enumer = s.Enumerable("select sum(s.Count) from s in class Simple group by s.Count having sum(s.Count) > 10 ").GetEnumerator(); Assert.IsTrue( enumer.MoveNext() ); ! Assert.AreEqual(12, (Int32)enumer.Current ); ! Assert.IsFalse( enumer.MoveNext() ); ! if( !(dialect is Dialect.MySQLDialect) ) ! { ! enumer = s.Enumerable("select s.Count from s in class Simple group by s.Count having s.Count = 12").GetEnumerator(); ! Assert.IsTrue( enumer.MoveNext() ); ! } ! enumer = s.Enumerable("select s.id, s.Count, count(t), max(t.Date) from s in class Simple, t in class Simple where s.Count = t.Count group by s.id, s.Count order by s.Count").GetEnumerator(); ! ! IQuery q = s.CreateQuery("from s in class Simple"); ! q.SetMaxResults(10); ! Assert.AreEqual( 3, q.List().Count ); ! q = s.CreateQuery("from s in class Simple"); ! q.SetMaxResults(1); ! Assert.AreEqual( 1, q.List().Count ); ! q = s.CreateQuery("from s in class Simple"); ! Assert.AreEqual( 3, q.List().Count ); ! q = s.CreateQuery("from s in class Simple where s.Name = ?"); ! q.SetString(0, "Simple 1"); ! Assert.AreEqual( 1, q.List().Count ); ! q = s.CreateQuery("from s in class Simple where s.Name = ? and upper(s.Name) = ?"); ! q.SetString( 1, "SIMPLE 1" ); ! q.SetString( 0, "Simple 1" ); ! q.SetFirstResult(0); ! Assert.IsTrue( q.Enumerable().GetEnumerator().MoveNext() ); ! q = s.CreateQuery("from s in class Simple where s.Name = :foo and upper(s.Name) = :bar or s.Count=:count or s.Count=:count + 1"); ! q.SetParameter("bar", "SIMPLE 1"); ! q.SetString("foo", "Simple 1"); ! q.SetInt32("count", 69); ! q.SetFirstResult(0); ! Assert.IsTrue( q.Enumerable().GetEnumerator().MoveNext() ); ! q = s.CreateQuery("select s.id from s in class Simple"); ! q.SetFirstResult(1); ! q.SetMaxResults(2); ! IEnumerable enumerable = q.Enumerable(); ! int i=0; ! foreach( object obj in enumerable ) ! { ! Assert.IsTrue( obj is Int64 ); ! i++; ! } ! Assert.AreEqual( 2, i ); ! q = s.CreateQuery("select all s, s.Other from s in class Simple where s = :s"); ! q.SetParameter("s", simple); ! Assert.AreEqual( 1, q.List().Count ); ! q = s.CreateQuery("from s in class Simple where s.Name in (:name_list) and s.Count > :count"); ! IList list = new ArrayList(2); ! list.Add("Simple 1"); ! list.Add("foo"); ! q.SetParameterList( "name_list", list ); ! q.SetParameter( "count", (int)-1 ); ! Assert.AreEqual( 1, q.List().Count ); ! s.Delete(other); ! s.Delete(simple); ! s.Delete(min); ! t.Commit(); ! } } |
From: Sergey K. <jus...@us...> - 2005-04-09 12:48:16
|
Update of /cvsroot/nhibernate/nhibernate/src/NHibernate.Test/ExpressionTest In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv5861/src/NHibernate.Test/ExpressionTest Modified Files: QueryByExampleTest.cs Log Message: Abort transactions on failure Index: QueryByExampleTest.cs =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/src/NHibernate.Test/ExpressionTest/QueryByExampleTest.cs,v retrieving revision 1.2 retrieving revision 1.3 diff -C2 -d -r1.2 -r1.3 *** QueryByExampleTest.cs 31 Mar 2005 12:42:39 -0000 1.2 --- QueryByExampleTest.cs 9 Apr 2005 12:48:06 -0000 1.3 *************** *** 32,46 **** public void TestSimpleQBE() { ! ISession s = sessions.OpenSession(); ! ITransaction t = s.BeginTransaction(); ! Componentizable master = GetMaster("hibernate", null, "ope%"); ! ICriteria crit = s.CreateCriteria(typeof(Componentizable)); ! Example ex = Example.create(master).EnableLike(); ! crit.Add(ex); ! IList result = crit.List(); ! Assertion.AssertNotNull(result); ! Assertion.AssertEquals(1, result.Count); ! t.Commit(); ! s.Close(); } --- 32,47 ---- public void TestSimpleQBE() { ! using( ISession s = sessions.OpenSession() ) ! using( ITransaction t = s.BeginTransaction() ) ! { ! Componentizable master = GetMaster("hibernate", null, "ope%"); ! ICriteria crit = s.CreateCriteria(typeof(Componentizable)); ! Example ex = Example.create(master).EnableLike(); ! crit.Add(ex); ! IList result = crit.List(); ! Assert.IsNotNull(result); ! Assert.AreEqual(1, result.Count); ! t.Commit(); ! } } *************** *** 49,68 **** public void TestJunctionNotExpressionQBE() { ! ISession s = sessions.OpenSession(); ! ITransaction t = s.BeginTransaction(); ! Componentizable master = GetMaster("hibernate", null, "ope%"); ! ICriteria crit = s.CreateCriteria(typeof(Componentizable)); ! Example ex = Example.create(master).EnableLike(); ! crit.Add(Expression.Expression.Or(Expression.Expression.Not(ex), ex)); ! IList result = crit.List(); ! Assertion.AssertNotNull(result); ! // if (!(GetDialect() ! // instanceof HSQLDialect) ) ! // assertEquals(2, result.size()); ! t.Commit(); ! s.Close(); } --- 50,70 ---- public void TestJunctionNotExpressionQBE() { ! using( ISession s = sessions.OpenSession() ) ! using( ITransaction t = s.BeginTransaction() ) ! { ! Componentizable master = GetMaster("hibernate", null, "ope%"); ! ICriteria crit = s.CreateCriteria(typeof(Componentizable)); ! Example ex = Example.create(master).EnableLike(); ! crit.Add(Expression.Expression.Or(Expression.Expression.Not(ex), ex)); ! IList result = crit.List(); ! Assert.IsNotNull(result); ! // if (!(GetDialect() ! // instanceof HSQLDialect) ) ! // assertEquals(2, result.size()); ! t.Commit(); ! } } *************** *** 70,119 **** public void TestExcludingQBE() { ! ISession s = sessions.OpenSession(); ! ITransaction t = s.BeginTransaction(); ! Componentizable master = GetMaster("hibernate", null, "ope%"); ! ICriteria crit = s.CreateCriteria(typeof(Componentizable)); ! Example ex = Example.create(master).EnableLike() ! .ExcludeProperty("Component.SubComponent"); ! crit.Add(ex); ! IList result = crit.List(); ! Assertion.AssertNotNull(result); ! Assertion.AssertEquals(3, result.Count); ! master = GetMaster("hibernate", "ORM tool", "fake stuff"); ! crit = s.CreateCriteria(typeof(Componentizable)); ! ex = Example.create(master).EnableLike() ! .ExcludeProperty("Component.SubComponent.SubName1"); ! crit.Add(ex); ! result = crit.List(); ! Assertion.AssertNotNull(result); ! Assertion.AssertEquals(1, result.Count); ! t.Commit(); ! s.Close(); } private void initData() { ! ISession s = sessions.OpenSession(); ! Componentizable master = GetMaster("hibernate", "ORM tool", "ORM tool1"); ! s.Save(master); ! s.Close(); ! s = sessions.OpenSession(); ! master = GetMaster("hibernate", "open source", "open source1"); ! s.Save(master); ! s.Close(); ! s = sessions.OpenSession(); ! master = GetMaster("hibernate", null, null); ! s.Save(master); ! s.Close(); } private void deleteData() { ! ISession s = sessions.OpenSession(); ! ITransaction t = s.BeginTransaction(); ! s.Delete("from Componentizable"); ! t.Commit(); ! s.Close(); } --- 72,131 ---- public void TestExcludingQBE() { ! using( ISession s = sessions.OpenSession() ) ! using( ITransaction t = s.BeginTransaction() ) ! { ! Componentizable master = GetMaster("hibernate", null, "ope%"); ! ICriteria crit = s.CreateCriteria(typeof(Componentizable)); ! Example ex = Example.create(master).EnableLike() ! .ExcludeProperty("Component.SubComponent"); ! crit.Add(ex); ! IList result = crit.List(); ! Assert.IsNotNull(result); ! Assert.AreEqual(3, result.Count); ! master = GetMaster("hibernate", "ORM tool", "fake stuff"); ! crit = s.CreateCriteria(typeof(Componentizable)); ! ex = Example.create(master).EnableLike() ! .ExcludeProperty("Component.SubComponent.SubName1"); ! crit.Add(ex); ! result = crit.List(); ! Assert.IsNotNull(result); ! Assert.AreEqual(1, result.Count); ! t.Commit(); ! } } private void initData() { ! using( ISession s = sessions.OpenSession() ) ! { ! Componentizable master = GetMaster("hibernate", "ORM tool", "ORM tool1"); ! s.Save(master); ! s.Flush(); ! } ! ! using( ISession s = sessions.OpenSession() ) ! { ! Componentizable master = GetMaster("hibernate", "open source", "open source1"); ! s.Save(master); ! s.Flush(); ! } ! ! using( ISession s = sessions.OpenSession() ) ! { ! Componentizable master = GetMaster("hibernate", null, null); ! s.Save(master); ! s.Flush(); ! } } private void deleteData() { ! using( ISession s = sessions.OpenSession() ) ! using( ITransaction t = s.BeginTransaction() ) ! { ! s.Delete("from Componentizable"); ! t.Commit(); ! } } |
From: Michael D. <mik...@us...> - 2005-04-08 19:23:44
|
Update of /cvsroot/nhibernate/nhibernate/doc/reference/en In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv10080/en Modified Files: master.xml Log Message: blank files for all documentation added Index: master.xml =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/doc/reference/en/master.xml,v retrieving revision 1.4 retrieving revision 1.5 diff -C2 -d -r1.4 -r1.5 *** master.xml 26 Mar 2005 22:44:13 -0000 1.4 --- master.xml 8 Apr 2005 19:23:36 -0000 1.5 *************** *** 2,9 **** <!DOCTYPE book PUBLIC "-//OASIS//DTD DocBook XML V4.2//EN" "../support/docbook-dtd/docbookx.dtd" [ <!ENTITY architecture SYSTEM "modules/architecture.xml"> <!ENTITY configuration SYSTEM "modules/configuration.xml"> <!ENTITY basic-mapping SYSTEM "modules/basic_mapping.xml"> ! ]> --- 2,24 ---- <!DOCTYPE book PUBLIC "-//OASIS//DTD DocBook XML V4.2//EN" "../support/docbook-dtd/docbookx.dtd" [ + <!ENTITY quickstart SYSTEM "modules/quickstart.xml"> <!ENTITY architecture SYSTEM "modules/architecture.xml"> <!ENTITY configuration SYSTEM "modules/configuration.xml"> + <!ENTITY persistent-classes SYSTEM "modules/persistent_classes.xml"> <!ENTITY basic-mapping SYSTEM "modules/basic_mapping.xml"> ! <!ENTITY collection-mapping SYSTEM "modules/collection_mapping.xml"> ! <!ENTITY component-mapping SYSTEM "modules/component_mapping.xml"> ! <!ENTITY inheritence-mapping SYSTEM "modules/inheritence_mapping.xml"> ! <!ENTITY manipulating-data SYSTEM "modules/mainpulating_data.xml"> ! <!ENTITY transactions SYSTEM "modules/transactions.xml"> ! <!ENTITY query-hql SYSTEM "modules/query_hql.xml"> ! <!ENTITY query-criteria SYSTEM "modules/query_criteria.xml"> ! <!ENTITY query-sql SYSTEM "modules/query_sql.xml"> ! <!ENTITY performance SYSTEM "modules/performance.xml"> ! <!ENTITY toolset-guide SYSTEM "modules/toolset_guide.xml"> ! <!ENTITY example-parentchild SYSTEM "modules/example-parentchild.xml"> ! <!ENTITY example-weblog SYSTEM "modules/example_weblog.xml"> ! <!ENTITY example-mappings SYSTEM "modules/example_mappings.xml"> ! <!ENTITY best-practices SYSTEM "modules/best_practices.xml"> ]> |
Update of /cvsroot/nhibernate/nhibernate/doc/reference/en/modules In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv10080/en/modules Added Files: best_practices.xml collection_mapping.xml component_mapping.xml example_mappings.xml example_parentchild.xml example_weblog.xml inheritance_mapping.xml manipulating_data.xml performance.xml persistent_classes.xml query_criteria.xml query_hql.xml query_sql.xml quickstart.xml toolset_guide.xml transactions.xml Log Message: blank files for all documentation added --- NEW FILE: manipulating_data.xml --- --- NEW FILE: example_parentchild.xml --- --- NEW FILE: query_hql.xml --- --- NEW FILE: collection_mapping.xml --- --- NEW FILE: query_criteria.xml --- --- NEW FILE: best_practices.xml --- --- NEW FILE: transactions.xml --- --- NEW FILE: toolset_guide.xml --- --- NEW FILE: persistent_classes.xml --- --- NEW FILE: example_mappings.xml --- --- NEW FILE: performance.xml --- --- NEW FILE: component_mapping.xml --- --- NEW FILE: example_weblog.xml --- --- NEW FILE: quickstart.xml --- --- NEW FILE: query_sql.xml --- --- NEW FILE: inheritance_mapping.xml --- |
From: Michael D. <mik...@us...> - 2005-04-08 04:27:36
|
Update of /cvsroot/nhibernate/nhibernate/src/NHibernate/Dialect In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv18585/Dialect Modified Files: SybaseDialect.cs Log Message: nh-235 Index: SybaseDialect.cs =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/src/NHibernate/Dialect/SybaseDialect.cs,v retrieving revision 1.13 retrieving revision 1.14 diff -C2 -d -r1.13 -r1.14 *** SybaseDialect.cs 6 Mar 2005 12:44:37 -0000 1.13 --- SybaseDialect.cs 8 Apr 2005 04:27:27 -0000 1.14 *************** *** 6,9 **** --- 6,34 ---- /// An SQL dialect compatible with Sybase. /// </summary> + /// <remarks> + /// <p> + /// This dialect probably will not work with schema-export. If anyone out there + /// can fill in the ctor with DbTypes to Strings that would be helpful. + /// </p> + /// The SybaseDialect defaults the following configuration properties: + /// <list type="table"> + /// <listheader> + /// <term>Property</term> + /// <description>Default Value</description> + /// </listheader> + /// <item> + /// <term>hibernate.use_outer_join</term> + /// <description><c>true</c></description> + /// </item> + /// <item> + /// <term>hibernate.connection.driver_class</term> + /// <description><see cref="NHibernate.Driver.SybaseClientDriver" /></description> + /// </item> + /// <item> + /// <term>hibernate.prepare_sql</term> + /// <description><c>false</c></description> + /// </item> + /// </list> + /// </remarks> public class SybaseDialect : Dialect { *************** *** 32,35 **** --- 57,62 ---- DefaultProperties[ Environment.UseOuterJoin ] = "true"; + DefaultProperties[ Environment.ConnectionDriver ] = "NHibernate.Driver.SybaseClientDriver"; + DefaultProperties[ Environment.PrepareSql ] = "false"; } |
From: Michael D. <mik...@us...> - 2005-04-08 04:27:36
|
Update of /cvsroot/nhibernate/nhibernate/src/NHibernate In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv18585 Modified Files: NHibernate-1.1.csproj Log Message: nh-235 Index: NHibernate-1.1.csproj =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/src/NHibernate/NHibernate-1.1.csproj,v retrieving revision 1.79 retrieving revision 1.80 diff -C2 -d -r1.79 -r1.80 *** NHibernate-1.1.csproj 30 Mar 2005 16:28:33 -0000 1.79 --- NHibernate-1.1.csproj 8 Apr 2005 04:27:27 -0000 1.80 *************** *** 700,703 **** --- 700,708 ---- /> <File + RelPath = "Driver\SybaseClientDriver.cs" + SubType = "Code" + BuildAction = "Compile" + /> + <File RelPath = "Engine\Cascades.cs" SubType = "Code" |
From: Michael D. <mik...@us...> - 2005-04-08 04:27:36
|
Update of /cvsroot/nhibernate/nhibernate/src/NHibernate/Driver In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv18585/Driver Modified Files: MySqlDataDriver.cs Added Files: SybaseClientDriver.cs Log Message: nh-235 Index: MySqlDataDriver.cs =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/src/NHibernate/Driver/MySqlDataDriver.cs,v retrieving revision 1.5 retrieving revision 1.6 diff -C2 -d -r1.5 -r1.6 *** MySqlDataDriver.cs 5 Apr 2005 14:22:27 -0000 1.5 --- MySqlDataDriver.cs 8 Apr 2005 04:27:27 -0000 1.6 *************** *** 1,4 **** using System; ! using System.Reflection; namespace NHibernate.Driver --- 1,4 ---- using System; ! using System.Data; namespace NHibernate.Driver *************** *** 55,59 **** /// that implements <see cref="IDbCommand"/> /// </summary> ! /// <value>The <see cref="MySql.Data.MySqlClient.MySqlCommand"/> type.</value> public override System.Type CommandType { --- 55,59 ---- /// that implements <see cref="IDbCommand"/> /// </summary> ! /// <value>The <c>MySql.Data.MySqlClient.MySqlCommand</c> type.</value> public override System.Type CommandType { *************** *** 65,69 **** /// that implements <see cref="IDbCommand"/> /// </summary> ! /// <value>The <see cref="MySql.Data.MySqlClient.MySqlConnection"/> type.</value> public override System.Type ConnectionType { --- 65,69 ---- /// that implements <see cref="IDbCommand"/> /// </summary> ! /// <value>The <c>MySql.Data.MySqlClient.MySqlConnection</c> type.</value> public override System.Type ConnectionType { --- NEW FILE: SybaseClientDriver.cs --- using System; using System.Data; namespace NHibernate.Driver { /// <summary> /// The SybaseClientDriver Driver provides a database driver for Sybase. /// </summary> /// <remarks> /// It has been reported to work with the <see cref="Dialect.MsSql2000Dialect"/>. /// </remarks> public class SybaseClientDriver : DriverBase { private System.Type connectionType; private System.Type commandType; /// <summary> /// Initializes a new instance of the <see cref="SybaseClientDriver"/> class. /// </summary> /// <exception cref="HibernateException"> /// Thrown when the Sybase.Data.AseClient assembly is not and can not be loaded. /// </exception> public SybaseClientDriver() { string assemblyName = "Sybase.Data.AseClient"; string connectionClassName = "Sybase.Data.AseClient.AseConnection"; string commandClassName = "Sybase.Data.AseClient.AseCommand"; // try to get the Types from an already loaded assembly connectionType = Util.ReflectHelper.TypeFromAssembly( connectionClassName, assemblyName ); commandType = Util.ReflectHelper.TypeFromAssembly( commandClassName, assemblyName ); if( connectionType == null || commandType == null ) { throw new HibernateException( "The IDbCommand and IDbConnection implementation in the Assembly Sybase.Data.AseClient.dll could not be found. " + "Please ensure that the Assemblies needed to communicate with Sybase " + "are in the Global Assembly Cache or in a location that NHibernate " + "can use System.Type.GetType(string) to load the types from." ); } } /// <summary> /// Gets the <see cref="System.Type"/> from the Sybase.Data.AseClient assembly /// that implements <see cref="IDbCommand"/> /// </summary> /// <value>The <c>Sybase.Data.AseClient.AseCommand</c>c> type.</value> public override System.Type CommandType { get { return commandType; } } /// <summary> /// Gets the <see cref="System.Type"/> from the Sybase.Data.AseClient assembly /// that implements <see cref="IDbCommand"/> /// </summary> /// <value>The <c>Sybase.Data.AseClient.AseConnection</c>c> type.</value> public override System.Type ConnectionType { get { return connectionType; } } /// <summary> /// Sybase.Data.AseClient uses named parameters in the sql. /// </summary> /// <value><c>true</c> - Sybase uses <c>@</c> in the sql.</value> public override bool UseNamedPrefixInSql { get { return true; } } /// <summary></summary> public override bool UseNamedPrefixInParameter { get { return true; } } /// <summary> /// Sybase.Data.AseClient use the <c>@</c> to locate parameters in sql. /// </summary> /// <value><c>@</c> is used to locate parameters in sql.</value> public override string NamedPrefix { get { return "@"; } } } } |
From: Michael D. <mik...@us...> - 2005-04-08 04:07:38
|
Update of /cvsroot/nhibernate/nhibernate/src/NHibernate.Test/TypesTest In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv9527/NHibernate.Test/TypesTest Modified Files: DecimalTypeFixture.cs Log Message: nh-248 Index: DecimalTypeFixture.cs =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/src/NHibernate.Test/TypesTest/DecimalTypeFixture.cs,v retrieving revision 1.4 retrieving revision 1.5 diff -C2 -d -r1.4 -r1.5 *** DecimalTypeFixture.cs 17 Jan 2005 03:40:54 -0000 1.4 --- DecimalTypeFixture.cs 8 Apr 2005 04:07:29 -0000 1.5 *************** *** 85,88 **** --- 85,98 ---- s.Close(); } + + [Test] + public void UnsavedValue() + { + + DecimalType type = (DecimalType)NHibernateUtil.Decimal; + object mappedValue = type.StringToObject( "0" ); + Assert.AreEqual( 0m, mappedValue); + Assert.IsTrue( type.Equals( mappedValue, 0m ), "'0' in the mapping file should have been converted to a 0m" ); + } } } |
From: Michael D. <mik...@us...> - 2005-04-08 04:07:38
|
Update of /cvsroot/nhibernate/nhibernate/src/NHibernate/Type In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv9527/NHibernate/Type Modified Files: DecimalType.cs Log Message: nh-248 Index: DecimalType.cs =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/src/NHibernate/Type/DecimalType.cs,v retrieving revision 1.8 retrieving revision 1.9 diff -C2 -d -r1.8 -r1.9 *** DecimalType.cs 31 Dec 2004 23:52:20 -0000 1.8 --- DecimalType.cs 8 Apr 2005 04:07:24 -0000 1.9 *************** *** 77,81 **** public object StringToObject( string xml ) { ! return long.Parse( xml ); } --- 77,81 ---- public object StringToObject( string xml ) { ! return Decimal.Parse( xml ); } |
From: Michael D. <mik...@us...> - 2005-04-06 18:25:43
|
Update of /cvsroot/nhibernate/nhibernate/doc/reference/en/modules In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv13902 Modified Files: basic_mapping.xml Log Message: finished some TODOs Index: basic_mapping.xml =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/doc/reference/en/modules/basic_mapping.xml,v retrieving revision 1.11 retrieving revision 1.12 diff -C2 -d -r1.11 -r1.12 *** basic_mapping.xml 26 Mar 2005 22:44:13 -0000 1.11 --- basic_mapping.xml 6 Apr 2005 18:25:27 -0000 1.12 *************** *** 1070,1074 **** update="true|false"<co id="manytoone6-co" /> insert="true|false"<co id="manytoone7-co" /> ! access="field|property|ClassName"<co id="manytoone7-co" /> /></programlisting> <calloutlist> --- 1070,1074 ---- update="true|false"<co id="manytoone6-co" /> insert="true|false"<co id="manytoone7-co" /> ! access="field|property|ClassName"<co id="manytoone8-co" /> /></programlisting> <calloutlist> *************** *** 1111,1115 **** </para> </callout> ! <callout arearefs="manytoone7-co" id="manytoone7"> <para> <literal>access</literal> (optional - defaults to --- 1111,1115 ---- </para> </callout> ! <callout arearefs="manytoone8-co" id="manytoone8"> <para> <literal>access</literal> (optional - defaults to *************** *** 1159,1163 **** <literal>one-to-one</literal> element. </para> ! <para>TODO: mapping sample</para> </sect2> <sect2 id="mapping-declaration-component"> --- 1159,1211 ---- <literal>one-to-one</literal> element. </para> ! <programlisting><one-to-one ! name="propertyName"<co id="onetoone1-co" /> ! class="ClassName"<co id="onetoone2-co" /> ! cascade="all|none|save-update|delete"<co id="onetoone3-co" /> ! constrained="true|false"<co id="onetoone4-co" /> ! outer-join="true|false|auto"<co id="onetoone5-co" /> ! access="field|property|ClassName"<co id="onetoone6-co" /> ! /></programlisting> ! <calloutlist> ! <callout arearefs="onetoone1-co" id="onetoone1"> ! <para> ! <literal>name</literal>: The name of the property. ! </para> ! </callout> ! <callout arearefs="onetoone2-co" id="onetoone2"> ! <para> ! <literal>class</literal> (optional - defaults to the property type ! determined by reflection): The name of the associated class. ! </para> ! </callout> ! <callout arearefs="onetoone3-co" id="onetoone3"> ! <para> ! <literal>cascade</literal> (optional) specifies which operations should ! be cascaded from the parent object to the associated object. ! </para> ! </callout> ! <callout arearefs="onetoone4-co" id="onetoone4"> ! <para> ! <literal>contstrainted</literal> (optional) specifies that a foreign key constraint ! on the primary key of the mapped table references the table of the associated ! class. This options affects the order in which <literal>Save()</literal> and ! <literal>Delete()</literal> are cascaded (and is also used by the schema export tool). ! </para> ! </callout> ! <callout arearefs="onetoone5-co" id="onetoone5"> ! <para> ! <literal>outer-join</literal> (optional - defaults to <literal>auto</literal>): ! Enable outer-join fetching for this association when <literal>hibernate.use_outer_join</literal> ! is set. ! </para> ! </callout> ! <callout arearefs="onetoone6-co" id="onetoone6"> ! <para> ! <literal>access</literal> (optional - defaults to <literal>property</literal>): The ! strategy NHibernate should use for accessing the property value. ! </para> ! </callout> ! </calloutlist> ! <!-- TODO: add details about the new property-ref attribute that Paul added --> </sect2> <sect2 id="mapping-declaration-component"> *************** *** 1177,1211 **** access="field|property|ClassName"<co id="component5-co" /> /></programlisting> ! <calloutlist> ! <callout arearefs="component1-co" id="component1"> ! <para> ! <literal>name</literal>: The name of the property. ! </para> ! </callout> ! <callout arearefs="component2-co" id="component2"> ! <para> ! <literal>class</literal> (optional - defaults to the property type ! determined by reflection): The name of the component (child) class. ! </para> ! </callout> ! <callout arearefs="component3-co" id="component3"> ! <para> ! <literal>insert</literal>: Do the mapped columns appear in SQL ! <literal>INSERT</literal>s? ! </para> ! </callout> ! <callout arearefs="component4-co" id="component4"> ! <para> ! <literal>update</literal>: Do the mapped columns appear in SQL ! <literal>UPDATE</literal>s? ! </para> ! </callout> ! <callout arearefs="component5-co" id="component5"> ! <para> ! <literal>access</literal> (optional - defaults to <literal>property</literal>): The ! strategy Hibernate should use for accessing the property value. ! </para> ! </callout> ! </calloutlist> </sect2> <sect2 id="mapping-declaration-subclass"> --- 1225,1259 ---- access="field|property|ClassName"<co id="component5-co" /> /></programlisting> ! <calloutlist> ! <callout arearefs="component1-co" id="component1"> ! <para> ! <literal>name</literal>: The name of the property. ! </para> ! </callout> ! <callout arearefs="component2-co" id="component2"> ! <para> ! <literal>class</literal> (optional - defaults to the property type ! determined by reflection): The name of the component (child) class. ! </para> ! </callout> ! <callout arearefs="component3-co" id="component3"> ! <para> ! <literal>insert</literal>: Do the mapped columns appear in SQL ! <literal>INSERT</literal>s? ! </para> ! </callout> ! <callout arearefs="component4-co" id="component4"> ! <para> ! <literal>update</literal>: Do the mapped columns appear in SQL ! <literal>UPDATE</literal>s? ! </para> ! </callout> ! <callout arearefs="component5-co" id="component5"> ! <para> ! <literal>access</literal> (optional - defaults to <literal>property</literal>): The ! strategy Hibernate should use for accessing the property value. ! </para> ! </callout> ! </calloutlist> </sect2> <sect2 id="mapping-declaration-subclass"> *************** *** 1217,1221 **** mapping strategy, the <literal><subclass></literal> declaration is used. </para> ! <para>TODO: mapping sample</para> </sect2> <sect2 id="mapping-declaration-joinedsubclass"> --- 1265,1305 ---- mapping strategy, the <literal><subclass></literal> declaration is used. </para> ! <programlisting><subclass ! name="ClassName"<co id="subclass1-co" /> ! discriminator-value="discriminator_value"<co id="subclass2-co" /> ! proxy="ProxyInterface"<co id="subclass3-co" /> ! dynamic-update="true|false" ! dynamic-insert="true|false" ! extends="BaseMappedClassName"> <co id="subclass4-co" /> ! ! <property ... / > ! ... ! <subclass/></programlisting> ! <calloutlist> ! <callout arearefs="subclass1-co" id="subclass1"> ! <para> ! <literal>name</literal>: The fully qualified .NET Type name of the persistent class. ! </para> ! </callout> ! <callout arearefs="subclass2-co" id="subclass2"> ! <para> ! <literal>discriminator-value</literal> (optional - defaults to the class name): A ! value that distinguishes individual subclasses. ! </para> ! </callout> ! <callout arearefs="subclass3-co" id="subclass3"> ! <para> ! <literal>proxy</literal> (optional): Specifies a class or interface to use ! for lazy initializing proxies. ! </para> ! </callout> ! <callout arearefs="subclass4-co" id="subclass4"> ! <para> ! <literal>extends</literal> (optional): Specifies the mapped class that this ! subclass is extending. This is only needed if <link linkend="mapping-modularfiles"> ! Modular Mapping Files</link> are used. ! </para> ! </callout> ! </calloutlist> </sect2> <sect2 id="mapping-declaration-joinedsubclass"> *************** *** 1227,1231 **** element. </para> ! <para>TODO: mapping sample</para> </sect2> <sect2 id="mapping-declaration-collections"> --- 1311,1358 ---- element. </para> ! ! <programlisting><joined-subclass ! name="ClassName"<co id="joinedsubclass1-co" /> ! table="tableName" <co id="joinedsubclass2-co" /> ! proxy="ProxyInterface"<co id="joinedsubclass3-co" /> ! dynamic-update="true|false" ! dynamic-insert="true|false" ! extends="BaseMappedClassName"> <co id="joinedsubclass4-co" /> ! ! <key ... > ! ! <property ... / > ! ... ! <joined-subclass/></programlisting> ! <calloutlist> ! <callout arearefs="joinedsubclass1-co" id="joinedsubclass1"> ! <para> ! <literal>name</literal>: The fully qualified .NET Type name of the persistent class. ! </para> ! </callout> ! <callout arearefs="joinedsubclass2-co" id="joinedsubclass2"> ! <para> ! <literal>table</literal>: The name of the table that holds the data specific to this class. ! </para> ! </callout> ! <callout arearefs="joinedsubclass3-co" id="joinedsubclass3"> ! <para> ! <literal>proxy</literal> (optional): Specifies a class or interface to use ! for lazy initializing proxies. ! </para> ! </callout> ! <callout arearefs="joinedsubclass4-co" id="joinedsubclass4"> ! <para> ! <literal>extends</literal> (optional): Specifies the mapped class that this ! joined-subclass is extending. This is only needed if ! <link linkend="mapping-modularfiles">Modular Mapping Files</link> are used. ! </para> ! </callout> ! </calloutlist> ! <para> ! No discriminator column is required for this mapping strategy. Each sublcass must, ! however, declare a table column holding the object identifier using the ! <literal><key></literal> element. ! </para> </sect2> <sect2 id="mapping-declaration-collections"> *************** *** 1239,1243 **** <sect2 id="mapping-declaration-import"> <title>import</title> ! <para>TODO: mapping sample</para> </sect2> </sect1> --- 1366,1395 ---- <sect2 id="mapping-declaration-import"> <title>import</title> ! <para> ! If your application has two persistent class with the same name, and you don't want to ! specify the fully qualified name in NHibernate queries, then classes may be "imported" ! explicity, rather than relying on <literal>auto-import="true"</literal>. Classes and interfaces ! that are not explicity mapped can be imported also. This is useful when you want to query for ! classes that implement a certain interface or want to use an unmapped class to put the results ! of the hql in. ! </para> ! <programlisting><import class="System.Object, System" /></programlisting> ! <programlisting><import ! class="className" <co id="import1-co" /> ! rename="newName" <co id="import2-co" /> ! /></programlisting> ! <calloutlist> ! <callout arearefs="import1-co" id="import1"> ! <para> ! <literal>class</literal>: The fully qualified .NET Type name of the persistent class (or interface). ! </para> ! </callout> ! <callout arearefs="import2-co" id="import2"> ! <para> ! <literal>rename</literal> (optional - defaults to the unqualified class name): A ! name that may be used in the query language. ! </para> ! </callout> ! </calloutlist> </sect2> </sect1> |
From: Michael D. <mik...@us...> - 2005-04-05 14:24:45
|
Update of /cvsroot/nhibernate/nhibernate/src/NHibernate/Impl In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv10119/NHibernate/Impl Modified Files: EnumerableImpl.cs Log Message: implemented standard IDisposable pattern. Index: EnumerableImpl.cs =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/src/NHibernate/Impl/EnumerableImpl.cs,v retrieving revision 1.9 retrieving revision 1.10 diff -C2 -d -r1.9 -r1.10 *** EnumerableImpl.cs 16 Jan 2005 19:55:42 -0000 1.9 --- EnumerableImpl.cs 5 Apr 2005 14:24:34 -0000 1.10 *************** *** 152,157 **** /// <summary> ! /// Releases resources that the EnumerableImpl acquired. /// </summary> /// <remarks> /// The command is closed and the reader is disposed. This allows other ADO.NET --- 152,182 ---- /// <summary> ! /// A flag to indicate if <c>Disose()</c> has been called. ! /// </summary> ! private bool _isAlreadyDisposed; ! ! /// <summary> ! /// Finalizer that ensures the object is correctly disposed of. /// </summary> + ~EnumerableImpl() + { + Dispose( false ); + } + + /// <summary> + /// Takes care of freeing the managed and unmanaged resources that + /// this class is responsible for. + /// </summary> + public void Dispose() + { + log.Debug( "running EnumerableImpl.Dispose()" ); + Dispose( true ); + } + + /// <summary> + /// Takes care of freeing the managed and unmanaged resources that + /// this class is responsible for. + /// </summary> + /// <param name="isDisposing">Indicates if this EnumerableImpl is being Disposed of or Finalized.</param> /// <remarks> /// The command is closed and the reader is disposed. This allows other ADO.NET *************** *** 159,172 **** /// EnumerableImpl. /// </remarks> ! public void Dispose() { ! log.Debug( "disposing of enumerator" ); ! // if there is still a possibility of moving next then we need to clean up ! // the resources - otherwise the cleanup has already been done. ! if( _hasNext ) { ! _currentResults = null; ! _sess.Batcher.CloseQueryCommand( _cmd, _reader ); } } --- 184,214 ---- /// EnumerableImpl. /// </remarks> ! protected virtual void Dispose(bool isDisposing) { ! if( _isAlreadyDisposed ) { ! // don't dispose of multiple times. ! return; } + + // free managed resources that are being managed by the EnumerableImpl if we + // know this call came through Dispose() + if( isDisposing ) + { + // if there is still a possibility of moving next then we need to clean up + // the resources - otherwise the cleanup has already been done by the + // PostMoveNext method. + if( _hasNext ) + { + _currentResults = null; + _sess.Batcher.CloseQueryCommand( _cmd, _reader ); + } + } + + // free unmanaged resources here + + _isAlreadyDisposed = true; + // nothing for Finalizer to do - so tell the GC to ignore it + GC.SuppressFinalize( this ); } |
Update of /cvsroot/nhibernate/nhibernate/src/NHibernate/Driver In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv9388/NHibernate/Driver Modified Files: DB2Driver.cs FirebirdDriver.cs MySqlDataDriver.cs NpgsqlDriver.cs OracleDataClientDriver.cs SqlClientDriver.cs SQLiteDriver.cs Log Message: NH-223: fixed how data provider assemblies are loaded to work with the gac instead of just local bin. Index: MySqlDataDriver.cs =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/src/NHibernate/Driver/MySqlDataDriver.cs,v retrieving revision 1.4 retrieving revision 1.5 diff -C2 -d -r1.4 -r1.5 *** MySqlDataDriver.cs 31 Dec 2004 17:25:35 -0000 1.4 --- MySqlDataDriver.cs 5 Apr 2005 14:22:27 -0000 1.5 *************** *** 1,2 **** --- 1,5 ---- + using System; + using System.Reflection; + namespace NHibernate.Driver { *************** *** 21,29 **** private System.Type commandType; ! /// <summary></summary> public MySqlDataDriver() { ! connectionType = System.Type.GetType( "MySql.Data.MySqlClient.MySqlConnection, MySql.Data" ); ! commandType = System.Type.GetType( "MySql.Data.MySqlClient.MySqlCommand, MySql.Data" ); if( connectionType == null || commandType == null ) --- 24,42 ---- private System.Type commandType; ! /// <summary> ! /// Initializes a new instance of the <see cref="MySqlDataDriver"/> class. ! /// </summary> ! /// <exception cref="HibernateException"> ! /// Thrown when the MySql.Data assembly is not and can not be loaded. ! /// </exception> public MySqlDataDriver() { ! string assemblyName = "MySql.Data"; ! string connectionClassName = "MySql.Data.MySqlClient.MySqlConnection"; ! string commandClassName = "MySql.Data.MySqlClient.MySqlCommand"; ! ! // try to get the Types from an already loaded assembly ! connectionType = Util.ReflectHelper.TypeFromAssembly( connectionClassName, assemblyName ); ! commandType = Util.ReflectHelper.TypeFromAssembly( commandClassName, assemblyName ); if( connectionType == null || commandType == null ) *************** *** 38,42 **** } ! /// <summary></summary> public override System.Type CommandType { --- 51,59 ---- } ! /// <summary> ! /// Gets the <see cref="System.Type"/> from the MySql.Data assembly ! /// that implements <see cref="IDbCommand"/> ! /// </summary> ! /// <value>The <see cref="MySql.Data.MySqlClient.MySqlCommand"/> type.</value> public override System.Type CommandType { *************** *** 44,48 **** } ! /// <summary></summary> public override System.Type ConnectionType { --- 61,69 ---- } ! /// <summary> ! /// Gets the <see cref="System.Type"/> from the MySql.Data assembly ! /// that implements <see cref="IDbCommand"/> ! /// </summary> ! /// <value>The <see cref="MySql.Data.MySqlClient.MySqlConnection"/> type.</value> public override System.Type ConnectionType { *************** *** 85,92 **** /// <summary> ! /// With the Gamma MySql.Data provider it is throwing an exception with the ! /// message "Expected End of data packet" when a select command is prepared. /// </summary> /// <value><c>false</c> - it is not supported.</value> public override bool SupportsPreparingCommands { --- 106,116 ---- /// <summary> ! /// MySql.Data does not support preparing of commands. /// </summary> /// <value><c>false</c> - it is not supported.</value> + /// <remarks> + /// With the Gamma MySql.Data provider it is throwing an exception with the + /// message "Expected End of data packet" when a select command is prepared. + /// </remarks> public override bool SupportsPreparingCommands { Index: SqlClientDriver.cs =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/src/NHibernate/Driver/SqlClientDriver.cs,v retrieving revision 1.7 retrieving revision 1.8 diff -C2 -d -r1.7 -r1.8 *** SqlClientDriver.cs 31 Dec 2004 17:26:01 -0000 1.7 --- SqlClientDriver.cs 5 Apr 2005 14:22:27 -0000 1.8 *************** *** 1,4 **** --- 1,5 ---- using System.Data; using System.Data.SqlClient; + using NHibernate.SqlCommand; using NHibernate.SqlTypes; *************** *** 11,20 **** public class SqlClientDriver : DriverBase { ! /// <summary></summary> public SqlClientDriver() { } ! /// <summary></summary> public override System.Type CommandType { --- 12,27 ---- public class SqlClientDriver : DriverBase { ! /// <summary> ! /// Initializes a new instance of the <see cref="SqlClientDriver"/> class. ! /// </summary> public SqlClientDriver() { } ! /// <summary> ! /// Gets the <see cref="System.Type"/> from the System.Data assembly ! /// that implements <see cref="IDbCommand"/> ! /// </summary> ! /// <value>The <see cref="System.Data.SqlClient.SqlCommand"/> type.</value> public override System.Type CommandType { *************** *** 22,38 **** } ! /// <summary></summary> public override System.Type ConnectionType { ! get { return typeof( SqlConnection ); } } ! /// <summary></summary> public override IDbConnection CreateConnection() { ! return new SqlConnection(); } ! /// <summary></summary> public override IDbCommand CreateCommand() { --- 29,57 ---- } ! /// <summary> ! /// Gets the <see cref="System.Type"/> from the System.Data assembly ! /// that implements <see cref="IDbConnection"/> ! /// </summary> ! /// <value>The <see cref="System.Data.SqlClient.SqlConnection"/> type.</value> public override System.Type ConnectionType { ! get { return typeof( System.Data.SqlClient.SqlConnection ); } } ! /// <summary> ! /// Creates an uninitialized <see cref="IDbConnection" /> object for ! /// the SqlClientDriver. ! /// </summary> ! /// <value>An unitialized <see cref="System.Data.SqlClient.SqlConnection"/> object.</value> public override IDbConnection CreateConnection() { ! return new System.Data.SqlClient.SqlConnection(); } ! /// <summary> ! /// Creates an uninitialized <see cref="IDbCommand" /> object for ! /// the SqlClientDriver. ! /// </summary> ! /// <value>An unitialized <see cref="System.Data.SqlClient.SqlCommand"/> object.</value> public override IDbCommand CreateCommand() { *************** *** 40,44 **** } ! /// <summary></summary> public override bool UseNamedPrefixInSql { --- 59,68 ---- } ! /// <summary> ! /// MsSql requires the use of a Named Prefix in the SQL statement. ! /// </summary> ! /// <remarks> ! /// <c>true</c> because MsSql uses "<c>@</c>". ! /// </remarks> public override bool UseNamedPrefixInSql { *************** *** 46,50 **** } ! /// <summary></summary> public override bool UseNamedPrefixInParameter { --- 70,79 ---- } ! /// <summary> ! /// MsSql requires the use of a Named Prefix in the Parameter. ! /// </summary> ! /// <remarks> ! /// <c>true</c> because MsSql uses "<c>@</c>". ! /// </remarks> public override bool UseNamedPrefixInParameter { *************** *** 52,56 **** } ! /// <summary></summary> public override string NamedPrefix { --- 81,90 ---- } ! /// <summary> ! /// The Named Prefix for parameters. ! /// </summary> ! /// <value> ! /// Sql Server uses <c>"@"</c>. ! /// </value> public override string NamedPrefix { Index: FirebirdDriver.cs =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/src/NHibernate/Driver/FirebirdDriver.cs,v retrieving revision 1.5 retrieving revision 1.6 diff -C2 -d -r1.5 -r1.6 *** FirebirdDriver.cs 31 Dec 2004 17:25:35 -0000 1.5 --- FirebirdDriver.cs 5 Apr 2005 14:22:27 -0000 1.6 *************** *** 2,6 **** { /// <summary> ! /// Summary description for FirebirdDriver. /// </summary> public class FirebirdDriver : DriverBase --- 2,6 ---- { /// <summary> ! /// A NHibernate Driver for using the FirebirdSql.Data.Firebird DataProvider. /// </summary> public class FirebirdDriver : DriverBase *************** *** 9,17 **** private System.Type commandType; ! /// <summary></summary> public FirebirdDriver() { ! connectionType = System.Type.GetType( "FirebirdSql.Data.Firebird.FbConnection, FirebirdSql.Data.Firebird" ); ! commandType = System.Type.GetType( "FirebirdSql.Data.Firebird.FbCommand, FirebirdSql.Data.Firebird" ); if( connectionType == null || commandType == null ) --- 9,27 ---- private System.Type commandType; ! /// <summary> ! /// Initializes a new instance of the <see cref="FirebirdDriver"/> class. ! /// </summary> ! /// <exception cref="HibernateException"> ! /// Thrown when the <c>FirebirdSql.Data.Firebird</c> assembly is not and can not be loaded. ! /// </exception> public FirebirdDriver() { ! string assemblyName = "FirebirdSql.Data.Firebird"; ! string connectionClassName = "FirebirdSql.Data.Firebird.FbConnection"; ! string commandClassName = "FirebirdSql.Data.Firebird.FbCommand"; ! ! // try to get the Types from an already loaded assembly ! connectionType = Util.ReflectHelper.TypeFromAssembly( connectionClassName, assemblyName ); ! commandType = Util.ReflectHelper.TypeFromAssembly( commandClassName, assemblyName ); if( connectionType == null || commandType == null ) Index: DB2Driver.cs =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/src/NHibernate/Driver/DB2Driver.cs,v retrieving revision 1.2 retrieving revision 1.3 diff -C2 -d -r1.2 -r1.3 *** DB2Driver.cs 31 Dec 2004 17:25:35 -0000 1.2 --- DB2Driver.cs 5 Apr 2005 14:22:26 -0000 1.3 *************** *** 12,21 **** /// <summary> ! /// /// </summary> public DB2Driver() { ! connectionType = System.Type.GetType( "IBM.Data.DB2.DB2Connection, IBM.Data.DB2" ); ! commandType = System.Type.GetType( "IBM.Data.DB2.DB2Command, IBM.Data.DB2" ); } --- 12,39 ---- /// <summary> ! /// Initializes a new instance of the <see cref="DB2Driver"/> class. /// </summary> + /// <exception cref="HibernateException"> + /// Thrown when the <c>IBM.Data.DB2</c> assembly is not and can not be loaded. + /// </exception> public DB2Driver() { ! string assemblyName = "IBM.Data.DB2"; ! string connectionClassName = "IBM.Data.DB2.DB2Connection"; ! string commandClassName = "IBM.Data.DB2.DB2Command"; ! ! // try to get the Types from an already loaded assembly ! connectionType = Util.ReflectHelper.TypeFromAssembly( connectionClassName, assemblyName ); ! commandType = Util.ReflectHelper.TypeFromAssembly( commandClassName, assemblyName ); ! ! if( connectionType == null || commandType == null ) ! { ! throw new HibernateException( ! "The IDbCommand and IDbConnection implementation in the Assembly IBM.Data.DB2 could not be found. " + ! "Please ensure that the Assemblies needed to communicate with IBM.Data.DB2 " + ! "are in the Global Assembly Cache or in a location that NHibernate " + ! "can use System.Type.GetType(string) to load the types from." ! ); ! } } Index: SQLiteDriver.cs =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/src/NHibernate/Driver/SQLiteDriver.cs,v retrieving revision 1.2 retrieving revision 1.3 diff -C2 -d -r1.2 -r1.3 *** SQLiteDriver.cs 1 Mar 2005 16:24:45 -0000 1.2 --- SQLiteDriver.cs 5 Apr 2005 14:22:27 -0000 1.3 *************** *** 24,34 **** /// <summary> ! /// /// </summary> public SQLiteDriver() { ! _connectionType = System.Type.GetType("Finisar.SQLite.SQLiteConnection, SQLite.NET"); ! _commandType = System.Type.GetType("Finisar.SQLite.SQLiteCommand, SQLite.NET"); ! if( _connectionType == null || _commandType == null ) --- 24,41 ---- /// <summary> ! /// Initializes a new instance of <see cref="SQLiteDriver"/>. /// </summary> + /// <exception cref="HibernateException"> + /// Thrown when the <c>SQLite.NET</c> assembly is not and can not be loaded. + /// </exception> public SQLiteDriver() { ! string assemblyName = "SQLite.NET"; ! string connectionClassName = "Finisar.SQLite.SQLiteConnection"; ! string commandClassName = "Finisar.SQLite.SQLiteCommand"; ! ! // try to get the Types from an already loaded assembly ! _connectionType = Util.ReflectHelper.TypeFromAssembly( connectionClassName, assemblyName ); ! _commandType = Util.ReflectHelper.TypeFromAssembly( commandClassName, assemblyName ); if( _connectionType == null || _commandType == null ) Index: NpgsqlDriver.cs =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/src/NHibernate/Driver/NpgsqlDriver.cs,v retrieving revision 1.3 retrieving revision 1.4 diff -C2 -d -r1.3 -r1.4 *** NpgsqlDriver.cs 31 Dec 2004 17:26:01 -0000 1.3 --- NpgsqlDriver.cs 5 Apr 2005 14:22:27 -0000 1.4 *************** *** 27,35 **** private System.Type commandType; ! /// <summary></summary> public NpgsqlDriver() { ! connectionType = System.Type.GetType( "Npgsql.NpgsqlConnection, Npgsql" ); ! commandType = System.Type.GetType( "Npgsql.NpgsqlCommand, Npgsql" ); if( connectionType == null || commandType == null ) --- 27,45 ---- private System.Type commandType; ! /// <summary> ! /// Initializes a new instance of the <see cref="NpgsqlDriver"/> class. ! /// </summary> ! /// <exception cref="HibernateException"> ! /// Thrown when the <c>Npgsql</c> assembly is not and can not be loaded. ! /// </exception> public NpgsqlDriver() { ! string assemblyName = "Npgsql"; ! string connectionClassName = "Npgsql.NpgsqlConnection"; ! string commandClassName = "Npgsql.NpgsqlCommand"; ! ! // try to get the Types from an already loaded assembly ! connectionType = Util.ReflectHelper.TypeFromAssembly( connectionClassName, assemblyName ); ! commandType = Util.ReflectHelper.TypeFromAssembly( commandClassName, assemblyName ); if( connectionType == null || commandType == null ) Index: OracleDataClientDriver.cs =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/src/NHibernate/Driver/OracleDataClientDriver.cs,v retrieving revision 1.1 retrieving revision 1.2 diff -C2 -d -r1.1 -r1.2 *** OracleDataClientDriver.cs 25 Jan 2005 13:37:09 -0000 1.1 --- OracleDataClientDriver.cs 5 Apr 2005 14:22:27 -0000 1.2 *************** *** 19,27 **** /// Initializes a new instance of <see cref="OracleDataClientDriver"/>. /// </summary> public OracleDataClientDriver() { ! connectionType = System.Type.GetType( "Oracle.DataAccess.Client.OracleConnection, Oracle.DataAccess" ); ! commandType =System. Type.GetType( "Oracle.DataAccess.Client.OracleCommand, Oracle.DataAccess" ); ! if( connectionType == null || commandType == null ) { --- 19,35 ---- /// Initializes a new instance of <see cref="OracleDataClientDriver"/>. /// </summary> + /// <exception cref="HibernateException"> + /// Thrown when the <c>Oracle.DataAccess</c> assembly is not and can not be loaded. + /// </exception> public OracleDataClientDriver() { ! string assemblyName = "Oracle.DataAccess"; ! string connectionClassName = "Oracle.DataAccess.Client.OracleConnection"; ! string commandClassName = "Oracle.DataAccess.Client.OracleCommand"; ! ! // try to get the Types from an already loaded assembly ! connectionType = Util.ReflectHelper.TypeFromAssembly( connectionClassName, assemblyName ); ! commandType = Util.ReflectHelper.TypeFromAssembly( commandClassName, assemblyName ); ! if( connectionType == null || commandType == null ) { |
From: Michael D. <mik...@us...> - 2005-04-05 14:21:33
|
Update of /cvsroot/nhibernate/nhibernate/src/NHibernate/Util In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv8929/NHibernate/Util Modified Files: ReflectHelper.cs Log Message: NH-223: added method to load a type from an assembly with its partial name. Index: ReflectHelper.cs =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/src/NHibernate/Util/ReflectHelper.cs,v retrieving revision 1.25 retrieving revision 1.26 diff -C2 -d -r1.25 -r1.26 *** ReflectHelper.cs 26 Mar 2005 13:24:37 -0000 1.25 --- ReflectHelper.cs 5 Apr 2005 14:21:21 -0000 1.26 *************** *** 12,15 **** --- 12,17 ---- public sealed class ReflectHelper { + private static readonly log4net.ILog log = log4net.LogManager.GetLogger( typeof( ReflectHelper ) ); + private ReflectHelper() { *************** *** 155,158 **** --- 157,207 ---- /// <summary> + /// Returns a <see cref="System.Type"/> from an already loaded Assembly or an + /// Assembly that is loaded with a partial name. + /// </summary> + /// <param name="className">The full name of the class.</param> + /// <param name="assemblyName"> + /// The name of the assembly. This can be the full assembly name or just the partial name. + /// </param> + /// <returns> + /// The <see cref="System.Type"/> for the class in the assembly or + /// <c>null</c> if a <see cref="System.Type"/> can't be found. + /// </returns> + /// <remarks> + /// Attempts to get a reference to the type from an already loaded assembly. If the + /// Type can be found then the Assembly is loaded using LoadWithPartialName. + /// </remarks> + public static System.Type TypeFromAssembly( string className, string assemblyName ) + { + try + { + // try to get the Types from an already loaded assembly + System.Type type = System.Type.GetType( className + ", " + assemblyName ); + + // if the type is null then the assembly is not loaded. + if( type==null ) + { + // use the partial name because we don't know the public key, version, culture-info of + // the assembly on the local machine. + Assembly assembly = Assembly.LoadWithPartialName( assemblyName ); + if( assembly!=null ) + { + type = assembly.GetType( className ); + } + } + + return type; + } + catch( Exception e ) + { + if( log.IsErrorEnabled ) + { + log.Error( className + ", " + assemblyName + " could not be loaded.", e ); + } + return null; + } + } + + /// <summary> /// Returns the value contained in the static field. /// </summary> |
From: Michael D. <mik...@us...> - 2005-04-05 14:21:33
|
Update of /cvsroot/nhibernate/nhibernate/src/NHibernate.Test/UtilityTest In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv8929/NHibernate.Test/UtilityTest Modified Files: ReflectHelperFixture.cs Log Message: NH-223: added method to load a type from an assembly with its partial name. Index: ReflectHelperFixture.cs =================================================================== RCS file: /cvsroot/nhibernate/nhibernate/src/NHibernate.Test/UtilityTest/ReflectHelperFixture.cs,v retrieving revision 1.2 retrieving revision 1.3 diff -C2 -d -r1.2 -r1.3 *** ReflectHelperFixture.cs 20 Nov 2004 15:20:10 -0000 1.2 --- ReflectHelperFixture.cs 5 Apr 2005 14:21:20 -0000 1.3 *************** *** 28,31 **** --- 28,48 ---- Assert.IsTrue( ReflectHelper.OverridesEquals( typeof(BRhf) ), "Base class overrides equals" ); } + + [Test] + public void NoTypeFoundReturnsNull() + { + System.Type noType = ReflectHelper.TypeFromAssembly( "noclass", "noassembly" ); + Assert.IsNull( noType ); + } + + [Test] + public void TypeFoundInNotLoadedAssembly() + { + System.Type httpRequest = ReflectHelper.TypeFromAssembly( "System.Web.HttpRequest", "System.Web" ); + Assert.IsNotNull( httpRequest ); + + System.Type sameType = ReflectHelper.TypeFromAssembly( "System.Web.HttpRequest", "System.Web" ); + Assert.AreEqual( httpRequest, sameType, "should be the exact same Type" ); + } } |