开发者

Is it possible to have a OneToOne relation to a class hierarchy persisted using JoinedBase?

开发者 https://www.devze.com 2022-12-13 22:33 出处:网络
I\'d like one of my entities to have a one-to-one relationship with a class hierarchy. Think of it like a Strategy pattern, where each strategy needs different parameters to be persisted. I tried usin

I'd like one of my entities to have a one-to-one relationship with a class hierarchy. Think of it like a Strategy pattern, where each strategy needs different parameters to be persisted. I tried using a combination of OneToOne and JoinedBase/JoinedKey, but I've come across a problem.

With this combination, the primary key of the main entity also appears as the primary key of the table represent开发者_如何学Going the root class in the hierarchy, and as the primary key of the subclass:

        Order    --------------- TaxCalculator
([PrimaryKey]Id = 1234)        ([PrimaryKey(PrimaryKeyType.Foreign)]OrderId = 1234) 
                                      ^
                                      |
                                      |
                             UkTaxCalculator
                      ([JoinedKey]UkTaxCalculatorId = 1234)

I can persist this fine, but then I can't change which subclass of TaxCalculator I have. When I do something like:

order.TaxCalculator = new OverseasTaxCalculator(order);

then try to flush, then ActiveRecord/NHibernate (understandably) gets unhappy that there are now two TaxCalculators with Id = 1234.

I can get around this by replacing the OneToOne with a HasMany/BelongsTo, and hiding the multiplicity from users of the Order object, but I'm interested to know if it's possible to do this with OneToOne.

There's a full code example on github. This code throws an exception when the second SessionScope is disposed. If you clone the project, it should run out-of-the-box.


first of all i am sorry, but i did not tried my solution. It is to late and i really need my sleep ;-). I think the only way the one-to-one could work would be a 'table-per-hierarchy'-approach using a discriminator column instead of table-per-subclass. Maybe this will enable you to morph the existing object to another subclass. An other way, something like a polymorphic delete-orphan unfortunately is not supported as you stated. So i'll guess this would be your (very) last option.

But if this fails why don't you map it as a one-to-many instead of many-to-one with a foreign key in the order table, reusing the TaxCalculators? I would imagine them as quite static.

Interesting idea though: polymorphic delete-orphan.


We do something very similar to what you are trying to do. I think it's your combination of one-to-one and the joined key that's causing the problem. Try this:

[ActiveRecord, JoinedBase]
public class TaxCalculator
{
    protected int TaxCalculatorId;

    [PrimaryKey]
    public virtual int Id
    {
        get { return TaxCalculatorId; }
        set { TaxCalculatorId = value; }
    }

    // common tax calculation fields, methods etc...
}

[ActiveRecord]
public class OverseasTaxCalculator : TaxCalculator
{
    [JoinedKey]
    public override int Id
    {
        get { return TaxCalculatorId; }
        set { TaxCalculatorId = value; }
    }

    // overseas tax calculation specific methods, properties etc...
}
0

精彩评论

暂无评论...
验证码 换一张
取 消