prestonsmith prestonsmith - 3 months ago 19
C# Question

"No persister for 'Class'" error when testing Fluent NHibernate with FakeItEasy

I'm writing some Persistence tests but am getting an error that NHibernate can't seem to work with FakeItEasy's fakes. Specifically the error is:


No persister for: Castle.Proxies.FacilityProxy


If I write the test like below it'll work fine and pass

[Test]
public void CanCorrectlyCreateFacilityTable()
{
new PersistenceSpecification<Facility>(session, new DataEqualityComparer())
.CheckProperty(f => f.Id, 1)
.CheckProperty(f => f.Name, _facility.Name)
.CheckReference(f => f.Owner, new Client())
.VerifyTheMappings();
}


However, if I create a fake:

IClient _client;
_client = A.Fake<Client>();
A.CallTo(() => _client.Name).Returns("Preston");


And pass that in to the test instead - it seems to fail with the error above:

[Test]
public void CanCorrectlyCreateFacilityTable()
{
new PersistenceSpecification<Facility>(session, new DataEqualityComparer())
.CheckProperty(f => f.Id, 1)
.CheckProperty(f => f.Name, _facility.Name)
.CheckReference(f => f.Owner, _client)
.VerifyTheMappings();
}


Does anyone know if there's a workaround or possible error on my end?

I've done a bit of research here but can't seem to find this question already asked. Most seem concerned with FakeItEasy's configuration or NHibernate's configuration - which don't seem to be the problem:
How do I test extension method of Nhibernate which does not return the value even after specifying return in fakeiteasy?
Can I sensibly mock this NHibernate query?

Answer

I'm not an NHibernate user, so may not be much help. You may already know that the reason you see this behaviour is that FakeItEasy creates Fakes by (using Castle.Core's DynamicProxy class in the process of) creating an entirely new class that extends the faked class (or implements the faked interface).

You didn't provide the definition of the Client class, but I'm guessing that some member on it is of type Facility, so when the... property (I'm guessing) is accessed in order to persist the object, the returned value is of type FacilityProxy, and NHibernate doesn't know what to do with it.

It seems to me that the accepted answer in Can I sensibly mock this NHibernate query? has the right idea: test with an object of the actual type that you want to persist.

If that's unpalatable, I guess the only things that I can suggest are:

  1. configuring the Facility-typed property (again, I assume a property) to return an actual Facility (and probably doing this for an assortment of other members), or
  2. teaching NHibernate about FacilityProxy, although this might be hard. I don't know NHibernate, but since you don't have access to the class at compile time, it may be tricky
Comments