Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to enumerate column names with NHibernate?

I've got a class with a bunch of [ColumnName("foo")] NHibernate attributes. Is there an easy way to ask NHibernate to list all of the ColumnNames for a given class?

It sounds like it should be really easy but I'm just not seeing any kind of inspection in the NHibernate docs (or maybe I'm just blind today).

like image 781
Ken Avatar asked Dec 04 '22 15:12

Ken


2 Answers

I had this same problem, but found IClassMetadata doesn't have any column information, just property types, names, identifier, and table information.

What worked for me:

PersistentClass persistentClass = cfg.GetClassMapping(typeof(MyEntity));
Property property = persistentClass.GetProperty(propertyName);
property.ColumnIterator   // <-- the column(s) for the property
like image 115
scamp Avatar answered Dec 17 '22 15:12

scamp


How to get the database column names for an entity mapped by NHibernate:

using System;
using System.Collections.Generic;
using NHibernate;
using NHibernate.Persister.Entity;

namespace Stackoverflow.Example
{
    /// <summary>
    /// NHibernate helper class
    /// </summary>
    /// <remarks>
    /// Assumes you are using NHibernate version 3.1.0.4000 or greater (Not tested on previous versions)
    /// </remarks>
    public class NHibernateHelper
    {
        /// <summary>
        /// Gets the list of database column names for an entity
        /// </summary>
        /// <param name="sessionFactory">NHibernate SessionFactory</param>
        /// <param name="entity">A mapped entity</param>
        /// <returns>List of column names</returns>
        public static IEnumerable<string> GetPropertyColumnNames(ISessionFactory sessionFactory, object entity)
        {
            Type entityType = entity == null ? null : entity.GetType();

            List<string> columnNameList = null;

            // This has some cool methods and properties so check it out
            var metaData = entityType == null ? null : sessionFactory.GetClassMetadata(entityType.ToString());

            //- metaData validity check ... will be null if provided type is not mapped
            if (metaData != null)
            {
                // This has some even cooler methods and properties so definitely check this out
                var entityPersister = (AbstractEntityPersister) metaData;

                //- how to get the entity's identifier
                //- string entityIdentifier = metaData.IdentifierPropertyName;

                //- Get the database identifier
                //- can have multiple in case of composite keys
                IEnumerable<string> dbIdentifierNameList = entityPersister.KeyColumnNames;

                var propertyNameList = entityPersister.PropertyNames;

                // Adding the database identifier first
                columnNameList = new List<string>(dbIdentifierNameList);
                //- then add properties column names
                foreach (var propertyName in propertyNameList)
                {
                    var columnNameArray = entityPersister.GetPropertyColumnNames(propertyName);
                    columnNameList.AddRange(columnNameArray.Where(columnName => dbIdentifierNameList.Contains(columnName) == false));
                }
            }

            return columnNameList;
        }
    }
}   

Usage:

// Get your NHiberate SessionFactory wherever that is in your application
var sessionFactory = NHibernateHelper.SessionFactory;

// Get an entity that you know is mapped by NHibernate
var customer = new Customer();

// Get a list of the database column names for the entity
var columnNames = 
        Stackoverflow.Example.NHibernateHelper.GetPropertyColumnNames( sessionFactory, customer );

Bask in the glory of this awesomeness :)

like image 27
3 revs, 2 users 84% Avatar answered Dec 17 '22 14:12

3 revs, 2 users 84%