These old forums are deprecated now and set to read-only. We are waiting for you on our new forums!
More modern, Discourse-based and with GitHub/Google/Twitter authentication built-in.

All times are UTC - 5 hours [ DST ]



Forum locked This topic is locked, you cannot edit posts or make further replies.  [ 1 post ] 
Author Message
 Post subject: many-to-one relationship with join table
PostPosted: Mon Jun 30, 2008 12:01 pm 
Newbie

Joined: Mon Jun 30, 2008 11:43 am
Posts: 7
Is there a way to specify a many-to-one and one-to-many relationship using a joining table?

The relations are:
Owners - may or may not have cars.
Cars - may have zero or one owners.

I wanted to model this using a joining table (CarsForOwner) rather than having a nullable ownerId field in cars but I'm having trouble working out the nHibernate mappings for this.

The best I've been able to come is to have a many-to-many mapping in Car and hide the set from the rest of the code. Use a property for Owner that ensures 0 to 1 owners are in the set.

The problem with this solution is it prevents navigating the Owner property in HQL or criterias as a simple property.

NHibernate Version
1.2.1.4000

Mapping file
Code:
<?xml version="1.0" encoding="utf-8" ?>
<hibernate-mapping xmlns="urn:nhibernate-mapping-2.2"
                   default-access="field.camelcase"
                   default-lazy="false"
                   assembly="ManyToOne"
                   namespace="ManyToOne"
                   schema="dbo"
                   >
    <class name="Owner" table="Owners">
        <id name="Id" column="ownerId">
            <generator class="native"/>
        </id>
        <property name="Name"/>
    </class>

    <class name="Car" table="Cars">
        <id name="Id" column="carId">
            <generator class="native"/>
        </id>
        <property name="Model"/>
    </class>
</hibernate-mapping>


Test sql
Code:
CREATE TABLE Owners
(
    ownerId int identity(1,1) not null PRIMARY KEY,
    name nvarchar(255) not null
)

CREATE TABLE Cars
(
    carId int identity(1,1) not null PRIMARY KEY,
    model nvarchar(255) not null
)

CREATE TABLE CarsForOwner
(
    carId int not null PRIMARY KEY,
    ownerId int not null,
   
    CONSTRAINT FK_CarsForOwner_Owners
    FOREIGN KEY (ownerId)
    REFERENCES Owners (ownerId),

    CONSTRAINT FK_CarsForOwner_Cars
    FOREIGN KEY (carId)
    REFERENCES Cars (carId)
)
GO

INSERT INTO Owners ([name]) VALUES ('Fred')
INSERT INTO Owners ([name]) VALUES ('Bob')

INSERT INTO Cars (model) VALUES ('Toyota Yaris')
INSERT INTO Cars (model) VALUES ('Ford Mondao')
INSERT INTO Cars (model) VALUES ('MR2')
INSERT INTO Cars (model) VALUES ('Ownerless')

INSERT INTO CarsForOwner (carId, ownerId) VALUES (1, 1)
INSERT INTO CarsForOwner (carId, ownerId) VALUES (2, 1)
INSERT INTO CarsForOwner (carId, ownerId) VALUES (3, 2)
GO


Test code
Code:
class Program
{
    static void Main()
    {
        Configuration cfg = new Configuration();
        cfg.Configure();
        ISessionFactory factory = cfg.BuildSessionFactory();
        ISession session = factory.OpenSession();

        IList<Car> cars = session.CreateCriteria(typeof(Car)).List<Car>();
        foreach (Car c in cars) Console.WriteLine(c);
        Console.ReadKey();
    }
}

public class Owner
{
    private int? id;
    private string name;

    public int? Id
    {
        get { return id; }
        set { id = value; }
    }

    public string Name
    {
        get { return name; }
        set { name = value; }
    }

    public override string ToString()
    {
        return string.Format("{{ Id = {0}, Name = {1} }}", id, name);
    }
}

public class Car
{
    private int? id;
    private Owner owner;
    private string model;

    public int? Id
    {
        get { return id; }
        set { id = value; }
    }

    public Owner Owner
    {
        get { return owner; }
        set { owner = value; }
    }

    public string Model
    {
        get { return model; }
        set { model = value; }
    }

    public override string ToString()
    {
        return string.Format("{{ Id = {0}, Model = {1}, Owner = {2} }}", id, model, owner);
    }
}


Edit: just changed the subject to read many-to-one, as this is the relationship direction I'm most interested in, the one-to-many is simple.


Top
 Profile  
 
Display posts from previous:  Sort by  
Forum locked This topic is locked, you cannot edit posts or make further replies.  [ 1 post ] 

All times are UTC - 5 hours [ DST ]


You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum

Search for:
© Copyright 2014, Red Hat Inc. All rights reserved. JBoss and Hibernate are registered trademarks and servicemarks of Red Hat, Inc.