2010-09-20 6 views
14

Tengo una clase base DomainObject para todos mis objetos comerciales que estoy usando con NHibernate. Contiene la propiedad Id.¿Cómo obtengo el tipo de entidad en un objeto que puede ser un objeto proxy de NHibernate?

public abstract class DomainObject 
{ 
    public virtual int Id { get; private set; } 
} 

me gustaría escribir un IEqualityComparer a comparar mis objetos de dominio. Si dos objetos tienen el mismo Id y son del mismo tipo de objeto, deberían ser iguales. Sin embargo, cuando uso GetType() para obtener el tipo de objeto, devolverá el tipo de proxy NHibernate. Por lo que este código:

bool IEqualityComparer.Equals(object x, object y) 
{ 
    // null checking code skipped here 
    if(x is DomainObject && y is DomainObject) 
    { 
      return ((DomainObject) x).Id == ((DomainObject) y).Id 
        && x.GetType() == y.GetType(); 
    } 
    return x.Equals(y); 
} 

no funciona correctamente, ya que el tipo de x is Asset pero el tipo de y is AssetProxy21879bba3e9e47edbbdc2a546445c657.

Entonces, ¿cómo obtengo el tipo de entidad en un objeto que puede ser un objeto proxy de NHibernate? es decir, en el ejemplo anterior Asset en lugar de AssetProxy21879bba3e9e47edbbdc2a546445c657?

+0

Estoy 99% seguro de que esto es un duplicado, pero yo soy demasiado perezoso ahora a buscarla: -) –

+3

Por favor muéstrame el que se duplica, busqué en stackoverflow. –

Respuesta

20

Usted puede obtener el tipo real de un proxy con:

NHibernateUtil.GetClass(x); 

o puede agregar un método para DomainObject como:

public virtual Type GetTypeUnproxied() 
{ 
    return GetType(); 
} 

que en realidad es resbaladiza y no dependen directamente de NHibernate.

Alternativamente, se puede abordar el problema diciendo que necesita para obtener el objeto real, en lugar de la representación, la cual, si la sesión es práctico, se puede hacer con:

session.PersistenceContext.Unproxy(x); 

Como se mencionó en otra respuesta, si intenta implementar iguales, sería una buena idea consultar Sharp architecture implementation of Equals.

+1

Tenga en cuenta que si usa Castle Windsor, GetClass puede devolver el tipo Proxy.Vea este hilo para otra forma de resolverlo: http://stackoverflow.com/a/1420816/348841 –

2

Para obtener el objeto real en lugar de proxy que puede utilizar

session.PersistenceContext.Unproxy(proxyObject) 

pero creo que usted debe buscar en Sharp architecture implementation para iguala.

+0

Cabe señalar que probablemente esté más interesado en el método GetTypeUnproxied() en http://github.com/codai/Sharp-Architecture/blob/master/src/SharpArch/SharpArch.Core/DomainModel/BaseObject.cs - pero +1 para una buena referencia impl. – DanP

+0

En este caso, en realidad no tengo la sesión disponible para mí en este código. Gracias por la referencia a Equals en la arquitectura de Sharp, no se aplica a mí porque estoy escribiendo un equivalente para las pruebas, por lo que no tiene que manejar todos los casos, pero todavía era una buena referencia. Y gracias a Dan por el enlace al código GetTypeUnproxied(), eso es más de lo que me interesa. –

0

Puede implementar una propiedad de puerta trasera tal como se describe en here para obtener la instancia real no procesada.

-1

tomé un enfoque diferente en un proyecto de producción. Simplemente tengo un Hilow Id-generador global que genera el ID del único para todos los tipos entonces puedo:

// in DomainEntity 
public override bool Equals(object obj) 
{ 
    var other = obj as DomainEntity; 
    if (Id == 0) // IsTransient() 
     return ReferenceEquals(this, other); 
    else 
     return (other != null) && (Id == other.Id); 
} 

// Comparer 
bool IEqualityComparer.Equals(object x, object y) 
{ 
    return object.Equals(x, y); 
} 
Cuestiones relacionadas