I'm certainly in support of having a separate NHibernate.Core package.
I don't think it's necessary for every contrib package to reference
everything needed to get up and running. I think NHibernate users
aren't typically going to start with the idea that "I want this one
add-on", but will instead likely use NHibernate first and add things
on from there. If you consider people that are running different
databases, the necessity of multi-step installation seems more clear.
For example, to get a bare package running for PostgreSQL, you'd need
something like:
NHiberante.Core
NHibernate.ByteCode.Castle
NHibernate.Databases.PostgreSQL
We would actually want NHibernate.ByteCode.Castle to do some
configuration and set up the proxy factory factory setting for us. If
you had LinFu installed, and then were forced to install
NHibernate(+castle) because of a dependency, it might change your
LinFu proxy settings to Castle proxy settings.
Note that I changed the name of Castle, to ByteCode.Castle. If we
classify them into groups, it may become more clear how to use them.
For example, imagine we have this list:
NHibernate.Core
NHibernate.ByteCode.Castle
NHibernate.ByteCode.LinFu
NHibernate.ByteCode.Spring
NHibernate.Database.MsSql2008 (adds appropriate connection strings and
standard properties to user's config file)
NHibernate.Database.PostgreSQL
NHibernate.Database.SQLite
Any sort of introductory docs could simply state that the user needs
to select one of each... one ByteCode, one Database. At the very
least, when the user searches for NHibernate, they'll wonder what
these "ByteCode" and "Database" categories are, and that might prompt
them to read the description, letting them know what they need to
install. I actually think it's fair to use the descriptions of these
packages to convey information on requirements in our scenario.
Granted, you might still end up with a user just installing
"NHibernate" by name.
Here's a new idea. Make NHibernate a dummy package that isn't
actually needed for anything. All you would get is a file explaining
what other packages you need to install. Then there's no possibility
of people depending on the wrong packages. If needed though, I
generally support the use of castle as the default proxy provider.
I think it's important that the packages come with configuration.
It's not generally the assemblies themselves that are the hard part of
getting NH running, but the associated config. Once the user has
selected their two packages, they should only really need to change
the example connection string in the config and start writing some
code.
Patrick Earl
On Mon, Mar 14, 2011 at 8:15 AM, Stephen Bohlen <[email protected]> wrote:
> The intent was that Nhibernate.Core would be available for other package
> authors to reference in cases where they wanted fine-grained control over
> the 'composition' of their packages.
>
> The canonical example I had in mind when thinking this scenario out was that
> of Castle's ActiveRecord. It would (conceivably) be possible for the Castle
> ActiveRecord package to depend directly on Nhibernate.Castle (or, if Castle
> is to be the 'default', then on just the 'Nhibernate' package). But if the
> Castle.ActiveRecord package were to take this dependency in this manner then
> they would be at the mercy of the version of Castle that is specified in OUR
> packages rather than being able to state their version requirements for
> themselves.
>
> so...
>
> Castle.ActiveRecord
> --> Castle.Nhibernate
>
> ...or...
>
> Castle.ActiveRecord
> --> Nhibernate
>
> ...would force them to 'accept' the version constraints for Castle.Core that
> *we* define in the NH packages.
>
> But...
>
> Castle.ActiveRecord
> --> Nhibernate.Core
> --> Castle.Core
>
> ...would permit them to state their dependency on NH with whatever version
> constraints they wanted to enforce in their own packages.
>
> Its possible that this scenario is just an edge case and I (honestly) have
> trouble suggesting another use-case than just Castle.ActiveRecord so maybe
> this is over-thinking the problem and introducing unnecessary complexity.
>
> On the other hand, I wonder if its the case that a hypothetical future
> Nhibernate.Caches.MemCacheD package needs a dependency on 'Nhibernate' (with
> the default proxyfactoryfactory) rather than just on Nhibernate.Core. Maybe
> you're right that the dependency for *all* nhcontrib-style packages would be
> best-stated in terms of nh-with-the-default-proxy, but if so then suppose
> I've done the following:
>
> added Nhibernate.Linfu package b/c I *know* that's what I want
> add the Nhibernate.Caches.MemCacheD package b/c I want to use 2nd level
> caching
>
> When I get to step #2, this will (needlessly) bring in Nhibernate (with
> default proxyproxyfactory) which in turn (as suggested earlier) will
> probably 'pass-thru' to bring in the Nhibernate.Castle package
> unnecessarily. AFAIK NuGet doesn't let you state dependencies as "at least
> one of the following must be present: Nhibernate.Castle, Nhibernate.LinFu,
> or Nhibernate.Spring..." (which is sort of how I would think it would be
> best for the nhcontrib-style packages to state their dependencies).
>
> What do you (and others) think is the best way to address this --? If we
> think it best for these to take dependencies on just 'Nhiberate' (w. default
> proxyproxyfactory) and we consider the Castle.ActiveRecord scenario to be an
> unsupportable edge case then maybe Nhibernate.Core *can* just go away....
>
> Steve Bohlen
> [email protected]
> http://blog.unhandled-exceptions.com
> http://twitter.com/sbohlen