Home > Software engineering >  How to update Entity that have one-to-one relation?
How to update Entity that have one-to-one relation?

Time:02-15

I have entities as follows:

public class Device
{
    public long Guid { get; set; }
    public List<Computer> Computers { get; set; }
    public string ShopName { get; set; }
}

public class Computer
{
    public long Guid { get; set; }
    public long SerialNo { get; set; }
    public Device Device { get; set; }
    public Condition Condition { get; set; }
}

public class Condition
{
    public long Guid { get; set; }
    public bool hasDamage { get; set; }
    public bool IsSecondHand { get; set; }
    public Computer Computer { get; set; }
}

The request of my service is :

public class Request
{
    public long? DeviceGuid {get; set;}
    public long? SerialNo {get; set;}
    public bool? IsSecondHand {get; set;}
}

I want to update all the computers according to request

foreach (var requestItem in RequestList)
{
    var ComputerPredicate = PredicateBuilder.True<Computer>()
                                            .And(x => x.SerialNo== requestItem.SerialNo)
                                            .And(x => x.Device.Guid== requestItem.DeviceGuid);

    var computers = from computers in ISession.Query<Computer>()
                                              .Where(ComputerPredicate)
                    select computers;

    computers.Update(u => new Computer()
                        {
                            Condition = new Condition()
                                        {
                                            IsSecondHand = requestItem.IsSecondHand.GetValueOrDefault(false),
                                         } 
                        });

If Request.DeviceGuid is not null, I update the all computers belong to that device; if Request.SerialNo is not null I update only the computer. One of them always empty in each item of the list.

But I am getting an error

NHibernate.Exceptions.GenericADOException: 'could not execute update query[SQL: update COMPUTER set Condition.IsSecondHand=? where and serialno=?]'
PostgresException: 42703: column "condition" of relation "computer" does not exist

There is no relation in the SQL indeed.

There is another option that I can update successfully but I am not sure this is an effective way to do it:

var computerList = computers.ToList();

foreach (var computer in computerList)
{
    computer.Condition.IsSecondHand = requestItem.IsSecondHand.GetValueOrDefault(false);
    ISession.Save(computer)
}

So how can I handle this situation in most efficient way?

CodePudding user response:

Updates on relation entities are not supported by LINQ update in NHibernate. You can try to use subquery to find all entities you need to update. Something like:

var entitiesToUpdateSubQuery = session.Query<Computer>()
.Where(ComputerPredicate)
.Select(x => x.Condition); //<- Select entity  you need to update

session.Query<Condition>() //<- Write update query directly on entity you need to update
.Where(c => entitiesToUpdateSubQuery.Contains(c)) 
.Update(c => 
    new Condition()
        {
            IsSecondHand = requestItem.IsSecondHand.GetValueOrDefault(false),
        }
);
  • Related