I have a Person class in Contacts subsystem. On the other hand in CRM subsystem, I have the notion of Customer.
In database design, I want to create a relationship between these notions. There are some possible ways:
Each customer is a person, thus customer should inherit from person and customer dies as soon as his person is removed (Composition). In this case, we create a one-to-one relationship between Id columns of the Customers table and People table, and we make the Id column of the People table an identity field, but we explicitly insert the scope_identity() in the Customers table.
Each customer has a person, thus customer and person have their own life-cycles (Aggregation) and can survive without the other. In this scenario, Customers table should have a foreign key to People table. The bad point here is that each Person can have many Customers which seems odd to me.
Which design is suggested as the best practice? I need solid objective answers. Thank you.
There are different cases when you may or may not give each table it's own ID.
In your case, it would be better if customer table does have it's own ID.
Example:
Own Id in a many to many relation defining table is redundant, when it doesn't have any extra column associated apart from the tables it is joining. Consider a Teacher and Student table relation. They have a many to many relation. If there is a table named TeacherStudentRelation having only foreign key to Teacher and Student table then it won't need any extra OwnId field.
But in your case, a Customer table surely would have extra information associated like balance, purchaseList or anything like that. And it is highly likely that you would search into Customer table for some data. Here an OwnId of customer table would let you to index that table.
Briefly, do give Customer table it's own Id.
IHMO, every entity must have a proper ID. You write about foreign key to refer Person as Customer, but this is another concept.
If Person is a base class about Customer, so, the ID field is the same and you don't explicit in Customer class because it inherit by Person.
In the first case (Person and Customer with FK) you have:
class Person {
private String id;
... and so on
... put here get and set property (as getId() / setId() and so on)
}
class Customer {
private String id; // this is different by id of Person class
private Person person;
... and so on
... put here get and set property (as getId() / setId() and so on)
}
In the second case (Customer extends Person) you have:
class Person {
private String id;
... and so on
... put here get and set property (as getId() / setId() and so on)
}
class Customer extends Person {
... other properties about Customer
... put here get and set property
}
Related
Given the following JPA model:
#Entity
public class Customer {
#Id
private long id;
#OneToOne(mappedBy="customer")
private ShippingAddress shippingAddress;
//...
}
#Entity
public class ShippingAddress {
#Id
private long id;
#OneToOne
private Customer customer;
//...
}
This will create a foreign key to the customer table in the shipping_address table i.e. shipping_address.customer_id.
From a database point-of-view, one would say that customer is the parent table and shipping_address is the child table, because
An address cannot exist without a customer
If a customer is deleted, their address must also be deleted
However, according to JPA, the owner of this relationship is ShippingAddress because the JavaDoc for mappedBy states
This element is only specified on the inverse (non-owning) side of the association.
I find it extremely confusing that the owner of the relationship according to JPA is what (from the database point-of-view) would be considered the child table. Is there a way to reconcile this apparent contradiction?
In short: as posted before here and here, the owning side of the relation is the one that holds the FK in the DB table.
You can read this excellent answer for a full explanation why.
I'm trying to design database for a class, in each class has many group or none, and each group has many student.
I drew two entity relation diagram like this.
For diagram 1 circle relation appear.
For diagram 2 to add student into class i have to add group so if class don't have group then i will can't add student into class. How can i design database for this situation ?
Your first diagram doesn't have circular functional dependencies. Read them from the "many" side to the "one" side:
Student -> Group (Belong to)
Student -> Group (Manage)
Group -> Student (Manage)
Group -> Class (Has)
Student -> Class (Belong to)
Class doesn't determine Student or Group, so there are no cyclic "references".
Circular relationships can be a warning that you need to watch out for possible anomalies - in this case, take care that students can't be associated with different classes via the two paths from Student to Class. As long as you take care that your data remains valid, circular relationships aren't a problem.
For your second diagram, you could adopt the convention that every class has at least one group (i.e. if there are no subgroups, the whole class counts as a group). In this way, every student is associated with a class via their group and you don't need to record that association directly.
These should be the tables in your DB:
Class table: Primary key would be ClassId.
Student table: Primary key Would be StudentId and FK(foreign key) would be ClassId.
Group table: Primary key would be GroupId, it would contain ClassId as FK.
Groups_Student table: This table contains the mapping of groups and students. So FK will be GroupId and StudentId.
The above design supports a student belonging to multiple groups or no groups at all. This assumes that a group is just associated with a single class. This also assumes that a student is just associated with a single class.
Lets say we have three tables: Cars, People, Companies.
We want the owner of the car to be a people or a company. The structure of the Cars table is: Car_id, Car_model, Owner_id
What is the best way to do that?
If you can't change the current structure of the cars table, then you could add new table called owners with the following columns:
number id -- unique key
number owner_id -- this is the actual owner id
char owner_type -- this is a value indicating whether the owner is a person or a company
You will then need to cross reference cars with owners and look at the value of owner_type to determine which table to get your owner data from.
EDIT
Forgot to mention (rather important):
In the cars table, populate the owner_id with the owners.id column.
What about having another field in Cars table as "Owner_type_id" which will determine if owner is a person or a company or any other thing. Of course, you should keep another table "Owner_Types" for this scenario to work.
As Igby mentioned, your existing structure is far from ideal, but if you're stuck with it, one option is to have a new Owner table that has the owner_id from the Car table as well as a person_id and a company_id, only one of which would need to be populated.
I have a question about entity creations that is specific to a student information system that i am building. i have created a Person table (id..) and i am trying to find out how i can handle my student, parent references. is it a good idea to create two separate tables (Student, Parent) that reference the Person table by FK relationship? All of the details about a Person (firstname, last name, SSN ...) have been set in the Person table but there are differences between a parent and student, how do you handle this in a database?
Since there are fundamental differences between parents and students, two tables would be the preferred solution. This way you can easily create a relation connecting the students and parents.
The other option is to use null values in the columns that do not apply for a given record. However, it will be more difficult to ensure that the relation always connects a student and parent.
I agree with Casey Robinson in that its a clean solution.
But if you already have a populated Person table which is being used by other code... in short you can't change the Person table then here is what I would suggest:
Create a table (studentParent) which will have two columns (student_id and parent_id) both foreign keys. The studentParent.student_id = Person.id of the student and studentParent.parent_id = Person.id of the parent.
This way you won't have to change the Person table. And will be able to create the parent, student relationship.
Without knowing more details it seems that two tables Person and Student should be sufficient. Have two columns in Student table like Student_id and Parent_id each of which is a FK to person_id in Person table. This is assuming you will need to know for only student which is a parent and not for every person. Also assuming that both student and parent are person.
I have a problem with a many-to-many relation in my tables, which is between an employee and instructor who work in a training centre. I cannot find the link between them, and I don't know how to get it. The employee fields are:
employee no.
employee name
company name
department job title
business area
mobile number
ext
ranking
The Instructors fields are
instructor name
institute
mobile number
email address
fees
in a many-to-many relationship the relationships will be in a 3rd table, something like
table EmployeeInstructor
EmployeeID
InstructorID
to find all the employees for a specific instructor, you'd use a join against all three tables.
Or more likely there will be classes involved --
Employee takes Class
Instructor teaches Class
so you'll have and EmployeeClass table,
an InstructorClass table,
and join through them. And Class needs to be unique, or else you'll need
Class is taught in Quarter on ClassSchedule
and end up joining EmplyeeClassSchedule to InstructorClassSchedule.
This ends up being one of your more interesting relational designs pretty quickly. If you google for "Terry Halpin" and "Object Role Modeling", this is used as an illustrative situation in the tutorial.
First of all, you will need a unique key in both tables. The employee number may work for the employee table, but you will need another for the instructor table. Personally, I tend to use auto incrementing identity fields called ID in my tables. This is the primary key.
Second, create a new table, InstructorEmployee. This table has two columns, InstructorID and EmployeeID. Both fields should be indexed. Now you can create an association between any Employee and any Instructor by creating a record which contains the two IDs.