James, I've just encountered the same exception after updating S#arp Architecture with Fluent NHibernate rev 285. All of the class maps within the S#arp Architecture demo project inherit from AutoMap<T> which was working alright with rev 207. For organization purposes, it's very convenient to be able to encapsulate changes to the conventions within separate auto maps, one for each divergent entity. For instance, if you have a Customer class which has a property which diverges from the convention, it's very convenient, and leads to clean organization, to be able to have a CustomerMap which inherits form AutoMap and defines where the conventions diverge.
With this said, I respect your wishes for where you want Fluent NHibernate to go and would like guidance on how you would propose organizing convention diversions so that they may be maintained in separate classes, one for each divergent entity. I'll be messing around with it for this evening and would love any insight you may have. Thank you, Billy McCafferty On Feb 3, 12:13 pm, Jimit <[email protected]> wrote: > The method MergeWithAutoMapsFromAssembly<T>() seemed to suggest the > style I used - that is, subclassing AutoMap<T> in an assembly. It did > discover my automaps fine, but then failed with the error described. > My domain has some very deep hierarchies and the fluent configuration > (using ForTypesThatDeriveFrom<T>) was getting rather wordy so I > seperated them into individual subclasses of AutoMap<T> and merged > them into my AutoPersistenceModel using > MergeWithAutoMapsFromAssembly<T>(). It seemed to work fine, until it > didn't. :) I think subclassing AutoMap<T> should be supported, if > nothing else than for consistency with ClassMap<T> for non-automapped > entities. > > Speaking of ForTypesThatDeriveFrom<T>, I think a non-generic overload > might come in handy. One use case (that's got me stumped at the moment > - having to use reflection) is setting conventions for the open form > of a generic base type, e.g EntityBase<,>. In my particular case, I > want to ignore certain properties in EntityBase<TEntity,TId> but don't > want to have to tell the Automapper to ignore it for each individual > TEntity. Any suggestions? > On a side note, you mentioned a check-in adding support for mapping > generic base classes > > On Feb 3, 4:32 pm, James Gregory <[email protected]> wrote: > > > Hi, > > You seem to be correct in your analysis. The reason this is happening is > > because it was never intended that people would subclass AutoMap<T>; > > alterations to classes are supposed to be done in the > > ForTypesThatDeriveFrom<T> call on the automapper, rather than in a subclass. > > > I realise this is probably quite annoying, but I'm not willing to endorse > > this style of automapping until I've done some investigation into it's > > implications. For the time being, I'd recommend either altering your code to > > use the recommended ForTypesThatDeriveFrom call, or altering the code > > yourself. > > > I will make a note to review this style to see if it's something we should > > officially support. > > > James > > > On Tue, Feb 3, 2009 at 4:25 PM, Jimit <[email protected]> wrote: > > > > Hi, > > > Sorry if this comes as a duplicate post. I think google might have > > > eaten my first so here it is again. > > > First off, mad props to all of you involved in the FNH - it rocks! > > > That said, I've come across what seems to be a bug in the method > > > FindMapping<T> of the AutoPersistenceModel class. Here's a sample > > > stack trace: > > > > TestCase 'Can_Write_XML_Mapping_Metadata_To_Folder' > > > failed: System.Reflection.TargetInvocationException : Exception has > > > been thrown by the target of an invocation. > > > ----> System.IndexOutOfRangeException :Indexwas outside thebounds > > > of the array. > > > at System.RuntimeMethodHandle._InvokeMethodFast(Object target, > > > Object > > > [] arguments, SignatureStruct& sig, MethodAttributes methodAttributes, > > > RuntimeTypeHandle typeOwner) > > > at System.RuntimeMethodHandle.InvokeMethodFast(Object target, > > > Object > > > [] arguments, Signature sig, MethodAttributes methodAttributes, > > > RuntimeTypeHandle typeOwner) > > > at System.Reflection.RuntimeMethodInfo.Invoke(Object obj, > > > BindingFlags invokeAttr, Binder binder, Object[] parameters, > > > CultureInfo culture, Boolean skipVisibilityChecks) > > > at System.Reflection.RuntimeMethodInfo.Invoke(Object obj, > > > BindingFlags invokeAttr, Binder binder, Object[] parameters, > > > CultureInfo culture) > > > at System.Reflection.MethodBase.Invoke(Object obj, Object[] > > > parameters) > > > at > > > > FluentNHibernate.InvocationHelper.InvokeGenericMethodWithDynamicTypeArgumen > > > ts > > > [T](T target, Expression`1 expression, Object[] methodArguments, Type > > > [] typeArguments) > > > at FluentNHibernate.AutoMap.AutoPersistenceModel.FindMapping(Type > > > type) > > > at FluentNHibernate.AutoMap.AutoPersistenceModel.CompileMappings() > > > C:\Projects\Dev\Source\Core\Tests\Unit Tests > > > \Core.Infrastructure.Data.NHibernate.Tests\MappingTests.cs(47,0): at > > > > Core.Infrastructure.Data.NHibernate.Tests.MappingTests.Can_Write_XML_Mappin > > > g_Metadata_To_Folder > > > () > > > --IndexOutOfRangeException > > > at > > > FluentNHibernate.AutoMap.AutoPersistenceModel.<FindMapping>b__7[T] > > > (IMapping t) > > > at System.Collections.Generic.List`1.Find(Predicate`1 match) > > > at FluentNHibernate.AutoMap.AutoPersistenceModel.FindMapping[T]() > > > > The test above simply instantiates a new AutoPersistenceModel, calls > > > MergeWithMappingsFromAssembly<T>() to add some custom mappings > > > (classes inheriting from Automap<T>), calls CompileMappings() and > > > attempts to write them to a folder using WriteMappingsTo(). > > > > I believe the culprit is this line in FindMapping<T>: > > > > // standard AutoMap<T> not found for the type, so looking > > > for one for it's base type. > > > return (IClassMap)_mappings.Find(t => t.GetType > > > ().GetGenericArguments()[0] == typeof(T).BaseType); > > > Because _mappings contains instances of classes that are derivatives > > > of AutoMap<T> and aren't actually generic types, the array returned > > > from Type.GetGenericArguments() contains no elements and thus you get > > > the IndexOutOfRangeException. > > > > I think the solution is to modify the predicate to allow for none > > > generic types by casting to Automap<T> first. --~--~---------~--~----~------------~-------~--~----~ You received this message because you are subscribed to the Google Groups "Fluent NHibernate" group. To post to this group, send email to [email protected] To unsubscribe from this group, send email to [email protected] For more options, visit this group at http://groups.google.com/group/fluent-nhibernate?hl=en -~----------~----~----~----~------~----~------~--~---
