2

running a simple test with NUnit and FluentAssertion i have this messagge for failure:

Expected object to be 

Gedi.Domain.Object.Entity.Persona
{
   Annullato = False
   Descrizione = "Persona1"
   Id = 1
}, but found 

Gedi.Domain.Object.Entity.Persona
{
   Annullato = False
   Descrizione = "Persona1"
   Id = 1
}.

but I do not see differences. which may be the cause of failure?

this is the test method

public void CanSaveAndLoadDocumento()
    {
        //Arrange
        Documento documentoTarget = new Documento();
        Documento documentoActual;

        documentoTarget.Id = fixture.Create<int>();                 

        // Act
        using (IUnitOfWork uow = new UnitOfWork())
        {
            uow.Start();
            documentoTarget.Persona = uow.ServiceRepositoryFor<Persona>().GetById(1);
            uow.DocumentoRepository.Create(documentoTarget);
            uow.Commit();
            uow.CloseConnection();

            uow.Start();
            documentoActual = uow.DocumentoRepository.GetById(documentoTarget.Id);          
            uow.CloseConnection();
        }

        //Assert
        documentoActual.Persona.Should().Be(documentoTarget.Persona);

    }

Persona with ID = 1 is handwritten by me directly in database

this is the base repository i use with NHibernate

public abstract class RepositoryBase<TEntity, TKey> : IDisposable
    where TEntity : class, IKeyedEntity<TKey>
    where TKey : struct
{
    protected ISession _session;
    public RepositoryBase(ISession session)
    {
        _session = session;         
    }       
    public void Create(TEntity entity)
    {
        _session.SaveOrUpdate(entity);
    }       
    public TEntity GetById(TKey id)
    {
        return _session.Get<TEntity>(id);
    }
}

public class DocumentoRepository : RepositoryBase<Documento, int>
{
    public DocumentoRepository(ISession session)
        : base(session)
    {
    }
}
4

2 に答える 2

4

理由は単純です -キャッシュされたインスタンスを返す代わりに、エンティティDocumentoRepository.GetById(documentoTarget.Id)の新しいインスタンスを作成します。PersonaFluent アサーションは参照によって両方のエンティティを比較し、アサーション エラーが発生します。

Equalsクラスに andGetHashCodeを実装できますPersona。またはShouldBeEquivlentTo、オブジェクト グラフの同等性を主張するために使用します。

documentoActual.Persona.ShouldBeEquivlentTo(documentoTarget.Persona);
于 2014-08-08T10:15:39.633 に答える
-1

より良いバージョン: このように、すべてのプロパティが等しい場合、2 つのオブジェクトは等しい

public abstract class EquatableObject<TObject>: IEquatable<TObject>
    where TObject : class   
{
    protected EquatableObject()
    {           
    }

    public override int GetHashCode()
    {
        IEnumerable<FieldInfo> fields = GetFields();
        int startValue = 17;
        int multiplier = 59;
        int hashCode = startValue;

        foreach (FieldInfo field in fields)
        {
            object value = field.GetValue(this);
            if (value != null)
                hashCode = hashCode * multiplier + value.GetHashCode();
        }
        return hashCode;
    }

    public override bool Equals(object obj)
    {
        if (obj == null)
            return false;

        TObject other = obj as TObject;

        return Equals(other);

    }

    public virtual bool Equals(TObject other)
    {
        if (other == null)
            return false;

        Type t = GetType();
        Type otherType = other.GetType();

        if (t != otherType)
            return false;

        FieldInfo[] fields = t.GetFields(BindingFlags.Instance | BindingFlags.NonPublic | BindingFlags.Public);
        foreach (FieldInfo field in fields)
        {
            object value1 = field.GetValue(other);
            object value2 = field.GetValue(this);

            if (value1 == null)
            {
                if (value2 != null)
                    return false;
            }
            else if (!value1.Equals(value2))
                return false;
        }
        return true;

    }

    private IEnumerable<FieldInfo> GetFields()
    {
        Type t = GetType();
        List<FieldInfo> fields = new List<FieldInfo>();
        while (t != typeof(object))
        {
            fields.AddRange(t.GetFields(BindingFlags.Instance | BindingFlags.NonPublic | BindingFlags.Public));

            t = t.BaseType;
        }
        return fields;
    }
}

解決済み追加

public override bool Equals(object obj)
    {
        if (obj == null)
            return false;

        T other = obj as T;

        return Equals(other);

    }

私のクラスへ

于 2014-08-08T10:14:52.647 に答える