Themis, a bit dipper dive

I just committed some new code for Themis examples, which for now on, will be also an integration tests. The whole case is about values which are allowed for some roles.

Let’s take a case where there are two types of users: Admins and standard users, for the sake of briefness called Users. Let Admins are allowed to choice an offer type between Internal and External, and a standard user’s choice is narrowed to one value: Internal. How can a domain be modeled to handle it easily? First of all roles are needed:

public class AdminRoleDefinition : RoleDefinitionBase<Admin>
{
    public AdminRoleDefinition( )
    {
        ValueIsAllowed(OfferType.Internal);
        ValueIsAllowed(OfferType.External);
    }
}

public class UserRoleDefinition : RoleDefinitionBase<User>
{
    public UserRoleDefinition( )
    {
       ValueIsAllowed (OfferType.Internal);
    }
}

What’s the method ValueIsAllowed? It’s a simple, internal extension method, setting the possible value, using an markup demand.

public static class ServiceExtensions
{
    public static TValue[] GetAllowedValues<TValue>(this IDemandService @this, params object[] roles)
    {
        return @this.Evaluate<AllowedValueDemand<TValue>, TValue>(
                AllowedValueDemand<TValue>.Instance, roles);
    }
}

internal sealed class AllowedValueDemand<TValue> : IDemand<TValue>
{
    public static readonly AllowedValueDemand<TValue> Instance = new AllowedValueDemand<TValue>();
}

Having all this configured, now one can query a demand service for allowed values for a specific drop-down! It could be also done on the filtering basis with NHibernate, but it was an example how simply extensible Themis is.

NHibernate interceptor magic tricks, the example

Below, you can find the final example of working interceptor, which uses some methods described in text of the last few blog entries (1, 2, 3, 4 and 5). Scan the example and go below to get some explanation about it!

public class ExampleInterceptor : EmptyInterceptor
{
	private const int MaxStatements = 50;
	private static readonly ILog Logger = LogManager.GetLogger(typeof(UpdateInterceptor));

	private readonly InterfaceFinder _interfaceFinder;
	private readonly IUnityContainer _container;
	private ISession _session;

	private int _statementCount;

	public UpdateInterceptor(IUnityContainer container, InterfaceFinder interfaceFinder)
	{
		_container = container;
		_interfaceFinder = interfaceFinder;
	}

	public override void PostFlush(ICollection entities)
	{
		if (_session.Transaction == null)
		{
			throw new InvalidOperationException("Use transactions!");
		}
		base.PostFlush(entities);
	}

	public override void SetSession(ISession session)
	{
		base.SetSession(session);
		_session = session;
	}

	public override string GetEntityName(object entity)
	{
		if (entity == null)
		{
			return null;
		}

		var interfaceType = _interfaceFinder.GetDeepestInterface(entity);

		if (interfaceType == null)
		{
			return null;
		}

		return interfaceType.FullName;
	}

	public override SqlString OnPrepareStatement(SqlString sql)
	{
		if (_statementCount++ == MaxStatements)
		{
			Logger.WarnFormat("Max number of statements exceeded");
		}

		return base.OnPrepareStatement(sql);
	}

	public override object Instantiate(string clazz, EntityMode entityMode, object id)
	{
		if (entityMode == EntityMode.Poco)
		{
			var sessionFactory = _session.SessionFactory;
			var metadata = sessionFactory.GetAllClassMetadata()[clazz];
			var type = metadata.GetMappedClass(entityMode);

			if (type != null)
			{
				var instance = _container.Resolve(type);
				var classMetadata = sessionFactory.GetClassMetadata(clazz);

				classMetadata.SetIdentifier(instance, id, entityMode);

				return instance;
			}
		}

		return null;
	}
}

The constructor
As you’ve noticed, there is a dependency injection in here! Two arguments are: unity container instance; interface finder, which allows you to use interfaces with their implementation hierarchies. About the second, you can read here and here.

Post flush
does nothing more than ensuring that you’re running it in a transaction. Yep, one for all, all for one!

SetSession
remembers the session instance in a field.

GetEntityName
implementation indicates that there are some interfaces mapped, for instance IA and IB : IA. It allows the most nested interface to be easily find for the object type.

OnPrepareStatement
preserves a sane number of statements per session (hence, per request, because session per request scenario is considered).

Instantiate
is the final method. It uses the passed container to create an instance of the passed class. Having interfaces mapped, it’s must have since you cannot call new for interface :P

Unity registration
Having this interceptor we need a nice and easy way of registering any interceptor (which type is hold in _interceptorType field) in the container. That’s performed by the following unity extension:

public class NhUnityContainerExtension : UnityContainerExtension
{
	protected override void Initialize()
	{
		// ...
		// save configuration to container for any later use
		Context.Container.RegisterInstanceWithSingletonLifetimeManager(cfg);

		// build factory and register interceptor
		var factory = cfg.BuildSessionFactory();
		Context.Container.RegisterInstanceWithSingletonLifetimeManager(factory);
		Context.Container.RegisterTypeWithPerRequestLifetimeManager(typeof(IInterceptor), _interceptorType);

		var key =  NamedTypeBuildKey.Make<ISession>();
		// setup nhibernate session build plan policy
		Context.
			Policies.
			Set<IBuildPlanPolicy>(
				new DelegateBuildPlanPolicy(
					ctx =>
							{
								// create interceptor already registered
								var interceptor = BuilderContext.NewBuildUp<IInterceptor>(ctx);
								var buildUpFactory =
									BuilderContext.NewBuildUp<ISessionFactory>(ctx);
								return buildUpFactory.OpenSession(interceptor);
							}),
				key);

		// setup lifetime policy
		Context.
			Policies.
			Set<ILifetimePolicy>(CreatePerRequestLifeTimeManager(), key);
	}
		
	private LifetimeManager CreatePerRequestLifeTimeManager()
	{
		// ...
	}
}

If you know the architecture of Unity, this extension is pretty safe explanatory, event mine extension methods.

That’s the end of Interceptor journey. Happy Intercepting!

NHibernate interceptor magic tricks, pt. 5

The previous parts of NHibernate interceptor journey can be found here: 1, 2, 3, 4. In this last entry I will describe all methods not covered previously. The example will be added as a separate entry as it needs a few more tests to be done, but hey! Now you’ll know something about all methods of IInterceptor! So, let’s start!

When dirt is flushed
When a session is flushed, there is a dirty check which is performed for each entity stored in the first level cache (in other words: a session cache or a persistent context). The dirty check is done by raising a FlushEntityEvent. The event object contains all the needed information about entity and is processed by a chain of event listeners. There is one default event listener for this type of event, called DefaultFlushEntityEventListener. It’s the one which is responsible for checking whether a loaded entity needs an update. It’s out of scope of this post to go deeper into NH event model, hence finally, when an entity is marked as to be updated, an update action is created. During this process, under certain conditions,
bool IInterceptor.OnFlushDirty(object entity, object id, object[] currentState, object[] previousState, string[] propertyNames, IType[] types) method can be called. I tend to use event listeners rather than using this method, not dealing with flushing.

Lock ‘N Load!
This one will be pretty straightforward: bool IInterceptor.OnLoad(object entity, object id, object[] state, string[] propertyNames, IType[] types); is called each time an entity object is being preloaded (passing an event through all IPreLoadEventListener). There are two cases when this happens: an entity is being assembled from cache and when an entity is being just loaded from its db representation. The state passed as the table of objects, is the state retrieved from db/cache (the representation is the same: an array of objects), and if modified, will affect setting the properties of your entity. For instance if we change state[i] which represents a property of name propertyName[i] and is of type types[i], it will cause this property to set to the value. Even more, the new value will be saved as the original state of an entity and the dirty check will not mark an entity as dirty.

Format me this, format me that
SqlString OnPrepareStatement(SqlString sql) allows you to change the sql string which is being sent to the db. You may replace some parts, as well as create an interceptor which will write the whole SQL of your web app to the trace. It’s also the easiest way to check how many times you app hits db (if an interceptor is created and attached on per session basis and the session is created once, per request, then you can easly count SQL statements executed per request). The other, much nicer and elegant, way of logging all statements is attaching an appender to the right ILog. BTW, this is what NHProf does!

On save, save?
bool OnSave(object entity, object id, object[] state, string[] propertyNames, IType[] types) method is called when an entity is saved. As in many cases, the last three tables contains: object properties values, property names, types of the properties. The method returns bool, which indicates whether values from the state should be copied onto object properties. If you return false, although the state is changes, NHibernate will not be notified to copy these values. I tend to use proper event listeners IPreInsertEventListener and IPreUpdateEventListener rather then making IInterceptor more rigid.

Preflush, postflush, inflush, outflush…
void PreFlush(ICollection entities); and void PostFlush(ICollection entities); methods do what they destined to do. The first is called with an collection of all entities which state is going to be changed during the flush which is comming, the second, is called with an collection of all entities which state was flushed already. Want to customize logging for all objects flushed (NHibernate does it already!)? That’s the place you should go!

An example will be provided soon!

NHibernate interceptor magic tricks, pt. 4

It’s the very last but one entry of NHibernate IInterceptor series (the first three: 1, 2, 3). We traveled through a few first methods of IInterceptor. It’s time to end this travel.

Am I transient enough?
Being transient in NHibernate world means nothing more than being not-persistent ever. The entity which you create with your new operator is transient till you call ISession.Save(object entity) method onto it, hence making it persistent. The persistent entities are being tracked for changes, their state is being saved/updated. Creating a new entity object not attached to the session is nothing more than creating a new object. It’d be simply garbage collected if no attaching to the session, via the mentioned method, occurred. How NHibernate recognizes if an entity is transient? It uses a static (ugh, yeah, the static method!) ForeignKeys.IsTransient method, which first of all, delegates its execution to IInterceptor.IsTransient. If you find a more elegant and intelligent way of resolving ‘being transient’ than calling IEntityPersister.IsTransient here you are your entry point. I did not find it useful in my whole journey with NHibernate.

I am collection and I need some action to be performed onto me
The following three methods of IInterceptor:

  • void OnCollectionRecreate(object collection, object key)
  • void OnCollectionRemove(object collection, object key)
  • void OnCollectionUpdate(object collection, object key)

are called during flushing collections, when a session flush occurs. The first step of flush is flushing of entities, the second – flushing collections. When the collection flush occurs, for each collection, it is determined what kind of action should be executed against this collection. The three choices matches the names of the IInterceptor methods. It’s worth to know and read something more about IPersistentCollection interface which an implementation instance is passed as the first parameter. As it was in the IsTransient case, I did not use any of this methods either.

I am being deleted!
When a delete occurres, the very first thing NHibernate does, is calling IInterceptor.OnDelete(object entity, object id, object[] state, string[] propertyNames, IType[] types) method. It does not provide any flow control and is simply called by the default IDeleteEventListener before scheduling the real delete action. What one can do in here, is checking whether an entity can be deleted and, for instance, throw an exception if this operation is not permitted.

In the last entry I will provide the description of the last, few methods as well as an example of full-blown implementation of IInterceptor.

NHibernate interceptor magic tricks, pt. 3

The very last meeting with IInterceptor was ended by description of IInterceptor.GetEntityName(object entity); method. It’s time to step into the kingdom of almighty DI and IoC and learn how to combine it with NHibernate.
Instantiate me, now!
Imagine that you have a dependency passed as your entity constructor. Or you have some methods or properties which should be called immediately after one entity construction. (It’s out of the scope of this blog whether injection dependencies in your entities is good or bad. You can ask Google and check whether one or another solution fits for you.) One of the proposals of having an entity class with a non default constructor is providing a custom IByteCodeProvider. You can find this solution in here but I would recommend another one, if only entity creation bothers you (the mentioned IByteCodeProvider initializes much more NHibernate elements than you can imagine). The second approach is to use IInterceptor.Instantiate(string entityName, EntityMode entityMode, object id) method. As it was shown by Ayende in his MSDN article, the code should look like (I use in the example Unity container interface):

public class DependencyInjectionInterceptor : EmptyInterceptor
{
    private readonly IUnityContainer _container;
    private ISession _session;

    public DependencyInjectionInterceptor (IUnityContainer container)
    {
        _container = container;
    }

    public void SetSession(ISession session)
    {
        _session = session;
    }

    public override object Instantiate(string clazz, EntityMode entityMode, object id) 
    {
        if(entityMode == EntityMode.Poco)
        {
            var type = Type.GetType(clazz);
            if (type != null)
            {
               var instance = _container.Resolve(type);
               var md = _session.SessionFactory.GetClassMetadata(clazz);
               md.SetIdentifier(instance, id, entityMode);
               return instance;
            }
        }
        return base.Instantiate(clazz, entityMode, id);
  }
}

You can consider passing the ISessionFactory in the constructor as dependency, but as I tend to use IInterceptor one per session, I simply use the SetSession method and further, the SessionFactory property.

That would be all about a simple case of dependency injection with NHibernate (creating only your entities). It seems that there will be a few posts more about IInterceptor stuff ;-)

NHibernate interceptor magic tricks, pt. 2

In the previous post, I described the basics of NHibernate’s IInterceptor as well as using it to manage transaction-connected actions. It’s time to move on and know better the other methods of this interface.

Am I dirty? Yes I am!
The very next method is connected with the term: dirtyness. During a flush, which occurs from time to time (it’s a topic for another entry, but it’s well covered by plenty of other blogs and books), a NHibernate’s session performs a check, whether any of persistent objects loaded to the session context had any of its properties changed. Being dirty, especially for an entity, equals having any property changed. It’s obvious that running through all of the loaded entities can take time, so that’s another reason why you should bother how many objects are loaded during one request/session.
Ok, so what about IInterceptor.FindDirty method? When entity is checked for its dirtiness, the very first step is to do it via mentioned method. If the method returns a non null result, an array of ints, then the default check is not performed and it’s taken for granted, that properties with the identifiers hold by the result array are dirty. Their values will be used to finally generate the sql update script. If you return null, a standard mechanism will be used.

Excuse me sir, how can I get the car with this id?
When NHibernate tries to get an entity it goes through the following steps:

  1. try to hit session cache (persistence context)
  2. try to hit second level cache
  3. try to hit database

The interceptor’s method GetEntity is used between the first and the second step. If the entity was not loaded in previously by this session, the interceptor is asked to retrieve an entity. In majority of cases it does not do it. Then the second cache, if any is hit. What can it be used for? When a session is cleared, the first level cache is dropped. If it occurred frequently, the most commonly used entities could be stored in a session’s interceptor, to spare this poor db some hits.

Say my name, say my name
Entities names are very important part of NHibernate. It uses it with connection of identifiers to create a truly unique entity id (yep, there are some cases when you don’t use Guids). For instance, when you make an object persistent, and call ISession.Save(object entity) it’s hard to guess which entity do you save. To get this information the method of session is called. The very first step is to delegate it’s responsibility to the IInterceptor. If it returns null, the type of the entity is retrieved and is used to resolve the entity’s name. What can this method be used for? Imagine that your mapping describes not the class, but an interface. What object.GetType() will return? Your interface type? No! It will return the real type of the object, and when it is not mapped, an exception will occur. Having this method, you can easily combine a DI container used with your entities, having interfaces mapped instead of real classes.

Summing up
Now you know something about NHibernate’s dirty checks. You can also do some reaaaally interesting stuff with NHibernates caching. Finally, you’re partially prepared to introduce dependency injection into your domain mapped with NHibernate. To know how fully inject into your mapped domain, read the very next entry.