开发者

NHibernate convert subclass to parent class

开发者 https://www.devze.com 2023-01-12 02:07 出处:网络
开发者_StackOverflowSupposing the following entities : public class AppUser { public virtual int Id { get; set; }
开发者_StackOverflow

Supposing the following entities :

public class AppUser
{
    public virtual int Id { get; set; }
    public virtual string Login { get; set; }
}

// Mapped as joined-subclass
public class Person : AppUser 
{
    public virtual int Age { get; set; }
}

If I create 1 AppUser, and save it like this

var user = new AppUser() { Login = "test" };
session.Save( user ); // let's say Id = 1

How can I cast/convert/"promote" it to a Person, keeping the same ID ?

Now, i'm stuck with a row in my AppUser table, with Id = N. How can I populate the Person table with the same Id ? I can't delete the AppUser and recreate it as a Person, as AppUser may be referenced by foreign keys.

I could issue a "manual" SQL INSERT, but it's kind of ugly...

This is definitively a NHibernate question. I understand that from an OOP point of view, this makes little sense, hence the absence of other tags than nhibernate.


I don't believe nHibernate is going to be able to solve this problem for you. nHibernate is dealing with your data as an object and, especially with joined-subclass I don't believe there is anything built in that allows you to change the subclass type on the fly, or at least change the type and retain the original ID.

I think your best bet is to write a stored procedure that, given an ID and a NEW type, removes all entries from subclass tables and adds a new entry to the correct subclass table.

Once that proc runs, then reload the object in nHibernate (and make sure you have thrown away any cached data relating to it), it should now be of the correct type you want to work with, set its NEW properties and save it.

That way you have a relatively generic stored proc that just changes your subclass types, but you dont need to add all the crazy logic to handle various properties on your subclasses.


This has been discussed on SO before and I am quoting Jon Skeet for posterity:

No. A reference to a derived class must actually refer to an instance of the derived class (or null). Otherwise how would you expect it to behave?

For example:

object o = new object();
string s = (string) o;
int i = s.Length; // What can this sensibly do?

If you want to be able to convert an instance of the base type to the derived type, I suggest you write a method to create an appropriate derived type instance. Or look at your inheritance tree again and try to redesign so that you don't need to do this in the first place.

In Skeet's example, string's are objects and objects are not strings. So the "upcasting" would not work.

0

精彩评论

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