set relationship in models without DB Context File - asp.net-mvc

I am developing an app where i am using MVC in Presentation layer so I have to define model classes in it.....and because of that I want relationship in that models.
How can we define relationship in model without Dbcontext class file.

I don't exactly understand what you are asking for, but I will take a shot.
EF creates relationships in models by having a reference to the related model(s).
Say you have models Cart and Item. A Cart can contain many Items, and any one Item can only belong to one Cart. This would be a one-to-many relationship.
public class Cart
{
public int CartId {get;set;}
//other properties
public List<Item> Items {get;set;}
}
public class Item
{
public int ItemId {get;set;}
// other properties
public Cart Cart {get;set;}
}
So from your Cart class you can fetch any Items it contains, and from any of those Items you can get the Cart that contains them.
Again, not sure if this is what you are asking for, and this is very quickly thrown together, but hopefully it helps.

Related

Asp.net MVC Entity Framework best way to retrieve data in many to many relationships

I have a question about the best way to retrieve data from many to many relationships that have been set up via entity framework.
As a simple example, let's say I have two models:
Items
Categories
Let's say that this is a many-to-many relationship in which an item can have many categories and a category can belong to many items.
As far as I understand, I do not need to create a third model for the Item-Category relationship as this is handled by the entity framework itself.
Thus, once everything is set up and I have used scaffolding on both of the models I end up with code similar to this:
public static ApplicationDbContext Create()
{
return new ApplicationDbContext();
}
public System.Data.Entity.DbSet<TShirtWSMVC.Models.Item> Items { get; set; }
public System.Data.Entity.DbSet<TShirtWSMVC.Models.Category> Categories { get; set; }
Now, I want to display to my view each item and its associated categories.
I am aware that I can code similar to:
dbContext.Database.SqlQuery(//Query the conjunction table here)
I could also make a method named AllCategoriesForItem(int itemID) inside the database context class.
I was wondering if there are better options? Such as when using dbContext.Items.ToList() it automatically retrieving the categories for each item so the Categories list for each item isn't null.
Alternatively, is there a way to have the ItemCategory table represented in the application db context?
Thanks.
namespace YourApp.Controllers
{
public class YourController: Controller
{
//your db context
private ApplicationDbContext db = new ApplicationDbContext();
public ActionResult Index()
{
var list = db.Items.Include(c => c.Categories);
return View(list.toList());
}
}
}
That's your controller, now you have to use it on your view.

Entity Framework Mapping. Multiple Foreign keys

I have two tables
People Relation
------------- -----------------
Id (int) Id (int)
Name (string) ParentPeopleId (int)
ChildPeopleId (int)
I need to get all people by Relation table with union all.
The relation table has two foreign keys. And there is one problem with mapping them. The mapping is one to many. People has many Relation, Relation has one People.
I mapped them like this:
HasRequired(r=> r.People).WithMany(p=>p.Relation).HasForeignKey(r=>r.ChildPeopleId);
So, how can I map the second foreign key?
Per each FK column in your Relations table you should have a navigation property in your Relation entity (this is not mandatory, but what is mandatory is have at least one navigation property between the entities involve in the relationship). In this case you have two relationships between People and Relations, and a navigation property represents one end in an relationship. Your model could be this way:
public class Relation
{
public int Id {get;set;}
public int ParentPeopleId {get;set;}
public int ChildPeopleId {get;set;}
public virtual People ParentPeople {get;set;}
public virtual People ChildPeople {get;set;}
}
public class People
{
public int Id {get;set;}
public string Name {get;set;}
public virtual ICollection<Relation> ParentRelations {get;set;}
public virtual ICollection<Relation> ChildRelations {get;set;}
}
And the Fluent Api configurations like this:
HasRequired(r=> r.ParentPeople ).WithMany(p=>p.ParentRelations ).HasForeignKey(r=>r.ParentPeopleId);
HasRequired(r=> r.ChildPeople).WithMany(p=>p.ChildRelations ).HasForeignKey(r=>r.ChildPeopleId );
Now if you don't want to work with one of the collection navigation properties in your People entity, you can create an unidirectional relationship. For example if you don't want ParenRelations navigation property, you can configure that relationship as follow:
HasRequired(r=> r.ParentPeople).WithMany().HasForeignKey(r=>r.ParentPeopleId);
Update
Let me start first with a suggestion. I thing your table Relation is not playing any role is you have only those columns. If a person con only have a parent I would change your model to the following:
public class People
{
public int Id {get;set;}
public string Name {get;set;}
public int ParentId {get;set;}
public virtual People Parent {get;set;}
public virtual ICollection<People> Children {get;set;}
}
And you relationship configuration would be:
HasOptional(r=> r.Parent).WithMany(p=>p.Children).HasForeignKey(r=>r.ParentId);
Now going back to your current model, EF sees your ChildPeopleId property as an simple scalar column, it doesn't know it's a FK column, that's way I suggested above map two relationship instead one.
Another thing, with the below line
var Peoplelist = MyDbContext.People.Include(p=>p.Relations.Select(r=>r.People)).ToList();
You are telling to EF that you want to load the Relation entities related to a People, but also you want to load the People related with each Relation, which is at the same time the same People where the Relation came from, so, you don't need to do the last select, if your data is properly related, that People navigation property is going to be loaded when you execute your query,so, that query should be this way:
var Peoplelist = MyDbContext.People.Include(p=>p.Relations).ToList();

MVC - Linking two Models using a foreign key

How would I add a foreign key linking my Club class and my ClubEvent class together in a one-to-many relationship where Club is the parent class and ClubEvent is the child.
These are the models I am using
public class Club
{
// Class to manage a single Club
[Key]
public int ClubID { get; set;
}//end Club
public class ClubEvent
{
[Key]
public int EventID { get; set; }
}
I want to connect these two tables so I can add events for a club so I can display only the relevant events for each club
This is pretty basic MVC, and if you need help with this stuff in the future please complete this tutorial: http://www.asp.net/mvc/overview/getting-started/getting-started-with-ef-using-mvc/creating-an-entity-framework-data-model-for-an-asp-net-mvc-application it is great!
Since ClubEvent is a 'child' of Club (meaning one club can have one or many events) you want to have the reference to the parent in the child. So, you will add a reference to clubEvent linking each instance of that object to the appropriate club. Add this to your ClubEvent Object..
public int ClubID {get; set;}
[ForeignKey("ClubID")]
public virtual Club Club {get;set;}
By adding the navigation property (virtual Club Club) you will be able to make a call to the parent object from the ClubEvent child. (club)this.ClubEvent.
displaying this is easily achieved by querying the ClubEvents table with the parent Club ID. Like:
var events = db.ClubEvents.Where(e => e.ClubID == id)
Where 'id' is the ClubID passed to the method in your controller.
Hope this helps, if you have any issues check this link out because it has great examples for every relation type in MVC.
http://www.asp.net/mvc/overview/getting-started/getting-started-with-ef-using-mvc/creating-a-more-complex-data-model-for-an-asp-net-mvc-application

How to delete all many-to-many relations without loading related entities in Entity Framework?

I have db scheme where Product table have many to many relation to Color table. I'm using EF and create POCO objects:
public class Product
{
public Guid Id {get;set;}
public ICollection<Color> Colors {get;set;}
}
public class Color
{
public Guid Id {get;set;}
public ICollection<Product> Products {get;set;}
}
In many situations it is necessary to delete all colors related to product and set new colors. So i want to delete all many to many relations whitout exactly knowing id of related colors. Is it possible to delete them without additional queries to db? I know i can just write stored procedure which will delete all relation with colors for specified product, but it will be better to find general approach through entity framework.
If you don't know keys of colors you cannot delete them without loading them first - EF deletes records one by one so it needs to know which record to delete.
The straight forward option is executing SQL DELETE directly:
dbContext.Database
.ExecuteSqlCommand("DELETE FROM dbo.ProductColors WHERE ProductId = #Id", product.Id);

ASP.NET MVC 2: Mechanics behind an Order / Order Line in a edit form

In this question I am looking for links/code to handle an IList<OrderLine> in an MVC 2 edit form. Specifically I am interested in sending a complete order to the client, then posting the edited order back to an object (to persist) using:
Html.EditorFor(m => m.orderlines[i]) (where orderlines is an enumerable object)
Editing an Order that has multiple order lines (two tables, Order and OrderLine, one to many) is apparently difficult. Is there any links/examples/patterns out there to advise how to create this form that edits an entity and related entities in a single form (in C# MVC 2)?
The IList is really throwing me for a loop. Should I have it there (while still having one form to edit one order)? How could you use the server side factory to create a blank OrderLine in the form while not posting the entire form back to the server? I am hoping we don't treat the individual order lines with individual save buttons, deletes, etc. (for example, they may open an order, delete all the lines, then click cancel, which shouldn't have altered the order itself in either the repository nor the database.
Example classes:
public class ViewModel {
public Order order {get;set;} // Only one order
}
public class Order {
public int ID {get;set;} // Order Identity
public string name {get;set;}
public IList<OrderLine> orderlines {get;set;} // Order has multiple lines
}
public class OrderLine {
public int orderID {get;set;} // references Order ID above
public int orderLineID {get;set;} // Order Line identity (need?)
public Product refProduct {get;set;} // Product value object
public int quantity {get;set;} // How many we want
public double price {get;set;} // Current sale price
}
You need to understand List<>/Array/IEnumerable model binding:
http://haacked.com/archive/2008/10/23/model-binding-to-a-list.aspx
http://blog.stevensanderson.com/2010/01/28/editing-a-variable-length-list-aspnet-mvc-2-style/
http://www.hanselman.com/blog/ASPNETWireFormatForModelBindingToArraysListsCollectionsDictionaries.aspx

Resources