Cascade deleting one-to-one linked entities in EntityDAC - delphi

Using Delphi XE5 and Devart EntityDAC ORM.
I have two entities linked one-to-one:
Project( Id, Name, ... ) and ProjectSchedule ( Id, ProjectId, ... );
In general schedule's fields may be easily inluded in Project table but I separated it for further possible needs. So, in Entity Developer I linked them as one-to-one relationship with Cascade=True and Delete_Rule=Cascade. Ok.
But when I try
project.DeleteAndSave( True );
I get and DB exception: FK violated. Child record found.
But if I change relationship to one-to-many the same works fine. But in this case access to schedule looks like
project.ProjectShedules.First
which is really terrible.
How to cascade delete an one-to-one related entities?

Related

Remove entries from a table that maintains a many to many relationship asp.net mvc entity framework

I am writing an application based on an existing database. I have two tables, a server table and a support table (people who support the specified server). These tables can have a many to many relationship, and as such I cannot maintain a foreign key within one of the tables pointing to another.
The solution that the person who designed the schema came up with was to add a third table, a server support junction, that has just two columns - ServerID and SupportID, both foreign keys pointing to their respective table.
When I import this database schema into Entity Framework, it gives me the following warning:
Warning 2 Error 6002: The
table/view 'dbo.Server_Support_Junction' does
not have a primary key defined. The key has been inferred and the definition
was created as a read-only table/view.
As such, the table does not appear in the edmx model and it does not create a class for the table.
As part of the application, I would like the DBA to be able to delete a server or a support (they leave the company/no longer support a certain server/etc). Is entity framework smart enough to see that this table is purely relational and will remove any connections when a support or server is deleted? Or must this be done explicitly?
If it must be done explicitly, what is a workaround for this? I tried adding a primary key called RelationID to the table, but it yelled at me saying that the primary key was not mapped or something.
Gert Arnold helped to find the solution. First, a primary key was added to the table consisting of both the Foreign keys, the SQL was:
ALTER TABLE dbo.Server_Support_Junction
ADD CONSTRAINT pk_ServerSupportJunc PRIMARY KEY (ServerID, SupportID)
I then updated the model by opening the edmx, right clicking on the blank space -> update model from database -> refresh -> finish.
To delete the relationship in the controller, the code was as follows:
Support support = db.Support.Find(id);
support.Servers.Clear();
db.Support.Remove(support);
db.SaveChanges();
Obviously you should do some error checking to make sure the entity was actually found, but that's the gist of it!
Special thanks to Gert Arnold!

Can EF6 use an existing table with GUIDs as the join/bridge table?

I have an existing database and one of the tables for the existing webforms application is a join or bridge table called PostCategory that links up Posts and Categories but it uses GUIDs to do that. It has GUIDs for CategoryID and PostID. When I tried use fluent mapping to point EF at that table I got the error that only ints can be used.
So I suspect the answer is no but I wanted to ask in case someone has done it. According to this post, it is possible with NHibernate but not EF.
This is not possible with EF because it doesn't support unique keys. Only primary keys can be used as principal in relation.
Now the post is from 2012 so I though maybe something has changed with EF6.

Simple one to many relation (association) fails in EF designer

I tried setting up a simple one-to-many relation in Entity Frameworks designer.
The tables are Category (1) and Transaction (N). Here's what I did:
Add "association"
End1 = Category, multiplicity 1, navigation property=Transaction
End2 = Transaction, multiplicity Many, navigation property = Category
Building it gave me the error "No mapping specified". Ok, makes sense. So I added this mapping:
Category
Category.CategoryID = Transaction.CategoryID
But the mapping designer also automatically adds a mapping for the Transaction table, which I cannot figure out how to delete or how to setup:
Transaction
Transaction.TransactionID = ???
Leaving it empty seems most valid, but that gives me: Error 3024 "Must specify mapping for all key properties (TransactionID)"
And trying to set it to a fake int property just hoping it's a compiler bug. But that gives me errors 3002 and 3003.
I dont get what to do. Isnt Associations meant to be used this way?
I suggest creating (or importing from the database) an entity for Catagory and an entity for Transaction. Add scalar properties to each as needed. Next, right-click on your entity, click Table Mapping, and map your entity properties to the table fields. For example, for the Category entity, map CategoryID field to a CategoryID property. Do the same for the other entity. THEN create the association.
Note that associations linked by exposed foreign keys do not have any mappings.
BTW, you'll probably want to add navigation properties as well.

Linq to SQL Entity Splitting

I've recently started playing around with the ASP.NET MVC NerdDinner sample, and as part of that you get to play around with Linq to SQL classes. This looks cool, so I decided to break away (perhaps a tad prematurely!) and try and create my own MVC application, but this time modelling my own simple database with Linq to SQL.
The problem I'm having is this. Consider these tables:
Car
Person
Passengers
The table CarPassengers is a mapping table between Car and Person (it has two columns: CarId, PersonId).
In Linq to SQL, I get a class for every table. But, what I really want is a class for Car that has the property CarPassengers, with each child being a Person, rather than the actual FK's (it's ok for selecting results, but to update Car with new Person objects, I have to first construct them - I can't just add an EntitySet of CarPassengers without first instantiating the child Person objects, I think).
I've been looking around and I've seen that the ADO.NET Entity Framework will allow me to achieve this using Entity Splitting, but I wondered if there's an easy way to accomplish the same thing in Linq to SQL, and if not, what the affects are in terms of integrating the .NET EF with my MVC app.
Any advice, comments, tips would be much appreciated.
Thank you!
If you define the FKs prior to adding them to the designer surface you will get the EntitySets added to the class in a manner close to what you expect. CarPassengers will exist but it will be an EntitySet of CarPassenger objects, not Persons. Those objects, however, will have an associated Person EntityRef. This will allow you to find the passengers in the car.
var car = db.Car.Where( c => c.CarId == id );
var passengers = db.Car.CarPassengers.Select( cp => cp.Person );
Adding new passengers works as well, but also involves another step.
var car = db.Car.Where( c => c.CarId == id );
var person = new Person { ... };
car.CarPassengers.Add( new CarPassenger { Person = person } );
If you don't have the FK relationships defined ahead of time, you can always add the associations manually in the designer. MSDN has a HowTo article on this topic.

How to get the foreign key in Entity Framework?

I am developing StudentApp in .NET 3.5 SP1 MVC Application.
I have two tables
Course
CourseID, course_Name
Students
studentID, student_Name, courseID(fk)
Now I made StudentApp.dbml which is having both table as entities.
As Foreign key will not be present in student entity,
I can not display courseID in student model, more over i can not generate add, edit, list views.
So tell me how to display courseID(fk) in student & i also want course name instead.
And also dropdownbox showing course name & storing courseID in edit view .
I'm pretty sure you have to load the foreign reference for each entity. Since I have no idea how you've constructed your API, I'll have to give you a pseudocode'ish example, but I think this is what you need to do.
List<Students> studList = [your_db_facade].SelectStudents() // Or however you retrieve your students
foreach (Students singleStudent in studList)
singleStudent.Context.CourseReference.Load() //CourseReference.Load() should be in the framework
Then you get the CourseID and name from the single student entity like
singleStudent.Course.CourseID
singleStudent.Course.course_Name
It could look slightly different for you, but I think the key to solving your problem is CourseReference.Load().
If your using LINQ-to-SQL and created a DBML file in Visual Studio then the foreign keys can be listed through the Course property in the Student object (automatically generated so since it is a one-to-many relationship from Student). Sort of like this:
var studentCourseIds =
from s in context.Students
select s.Course.CourseID;
Since your goal is to find the coursename then it is already accessible with Student.Course.course_Name.
Can you post your DBML? Also, DBML is used in LINQ to SQL (L2S) - EDMX is the mapping used in the ADO Entity Framework. Are you using LINQ to SQL or the Entity Framework (EF)?
No matter which one you are using - they both support Foreign Keys and you would get a property representing either side of the relationship - you don't need to do anything special (the Foreign Key must exist in the database, of course).
In EF, the foreign keys are called "navigtion properties" and they work a little differently to Foreign Keys in L2S. Nothing major, but updating them and "eager loading" are somewhat different.
Just drop the tables onto the map in the designer in Visual Studio (or generate using command line equivalents if you prefer).
Regarding Foreign Keys and Drop Down Lists (and other UI goodness) - I wrote a couple of blog entries on some approaches which might suit you. One part is located here and part two is located here.
if you create the correct relationship in your SQL server database, then when you add the tables to your DBML designer, the relationships will be copied across also and your code will link up automatically.

Resources