Web API Entity Framework error - Item with idenity already exists in the metadata collection - entity-framework

I am experimenting with a Web API 2 project in Visual Studio 2012. I used the code first from existing DB option with EF6 to select one table and one view. I then tried to create a controller for the simple table using the profile for Web API 2 OData. The scaffolding of the controller fails telling me that "the item with identity 'Client Last Reveiwed On' already exists in the metadata collection". The problem is not only am I sure that field is unique for this project but that field is part of the view and not the table. Below is the model generated for the simple table (t_Client) that I was trying to create the controller for. As you can see the offending column is not part of the class. I will add below the definition for the column that VS/EF doesn't like which is in the class for the view.
Any ideas why this won't work?
Partial Public Class t_Client
<Key>
<DatabaseGenerated(DatabaseGeneratedOption.None)>
Public Property ClientID As Integer
<Required>
<StringLength(255)>
Public Property ClientName As String
Public Property isActive As Boolean
End Class
Here is the column that is defined in a separate view.
<Column("Client Last Reviewed On", TypeName:="date")>
Public Property Client_Last_Reviewed_On As Date?

I am not sure which of these steps fixed the issue but here are some notes on the topic.
Removing references to the model based on the SQL view eliminated errors.
I went into SQL and updated the view to contain a row number column.
Even with the row number column, EF tagged multiple columns as the key.
I manually edited the model to make the row number column the key.
I also had to update a cast the data type of a few columns in the SQL view to match reality, mainly bigint that was really just integer.
My guess is the fix was the well defined key.

Related

value from database computed property is Null in codefluent entity property

My MS SQL 2014 database table has a computed property column which uses a database function. Using SQL Server Management Studio, a query against the table lists the computed property values as expected.
The Codefluent model created via the import wizard shows the Entity with the computed column as a property. The underlying .cpf file defines the property with "d3p1:compute=" and the list of parameters that are used by the database function.
When an entity or the collection of entities is loaded, the properties which are used in the computed property have values, yet the computed property has a value of nothing/null.
How do I get Codefluent to read the computed value from the database table and have the value included in the entity's properties?
This is a bit tricky. First of all, you should declare the property like any other property. Then you must instruct the SQL producer to declare a formula on that column. You can do that with a custom 'compute' attribute in the SQL producer namespace. You can set it with the Visual Studio modeler like this:
In this example I've created an int property that is just another column value multiplied by 2.
Optionally, you can declare the property to be 'read on save' because most of the time, you want to read the computed value after a save, not only on load operations:
Once this is all done, this sample console app should display 30:
class Program
{
static void Main(string[] args)
{
var c = new Customer();
c.Name = "killroy";
c.Age = 15;
c.Save();
Console.WriteLine(c.Age2); // will display 30
}
}
If Simon Mouriers solution solves your problem than that is probably the best approach. However, there are 2 other options
RAW View Method
After you create a Codefluent Entities View click on the Edit Where button and it will allow you to create a RAW View
You can than specify the advanced property "UsedForMethods".
WARNING: Related entities will use the table instead of the view. This is by design and there is an article somewhere on the knowledge center on how to get around it. http://www.softfluent.com/product/codefluent-entities/knowledge-center/
Rename SQL Tables and Create a SQL View with the Same Name as the Original Table - This method is a hack, Softfluent discourages this approach, I love it because I know exactly what is happening under the scenes. I have used it with success in a scenario in which I needed soft deletes. I have automated the process with 2 stored procedures that handle the renaming. Using this approach requires running one of the stored procedures to undo the name changing prior to building the model. The other stored procedure handles the renaming after building the model. I'll post the stored procedures and how I use them within a couple of days.

Entity Framework : map duplicate tables to single entity at runtime?

I have a legacy database with a particular table -- I will call it ItemTable -- that can have billions of rows of data. To overcome database restrictions, we have decided to split the table into "silos" whenever the number of rows reaches 100,000,000. So, ItemTable will exist, then a procedure will run in the middle of the night to check the number of rows. If numberOfRows is > 100,000,000 then silo1_ItemTable will be created. Any Items added to the database from now on will be added to silo1_ItemTable (until it grows to big, then silo2_ItemTable will exist...)
ItemTable and silo1_ItemTable can be mapped to the same Item entity because the table structures are identical, but I am not sure how to set this mapping up at runtime, or how to specify the table name for my queries. All inserts should be added to the latest siloX_ItemTable, and all Reads should be from a specified siloX_ItemTable.
I have a separate siloTracker table that will give me the table name to insert/read the data from, but I am not sure how I can use this with entity framework...
Thoughts?
You could try to use the Entity Inheritance to get this. So you have a base class which has all the fields mapped to ItemTable and then you have descendant classes that inherit from ItemTable entity and is mapped to the silo tables in the db. Every time you create a new silo you create a new entity mapped to that silo table.
[Table("ItemTable")]
public class Item
{
//All the fields in the table goes here
}
[Table("silo1_ItemTable")]
public class Silo1Item : Item
{
}
[Table("silo2_ItemTable")]
public class Silo2Item : Item
{
}
You can find more information on this here
Other option is to create a view that creates a union of all those table and map your entity to that view.
As mentioned in my comment, to solve this problem I am using the SQLQuery method that is exposed by DBSet. Since all my item tables have the exact same schema, I can use the SQLQuery to define my own query and I can pass in the name of the table to the query. Tested on my system and it is working well.
See this link for an explanation of running raw queries with entity framework:
EF raw query documentation
If anyone has a better way to solve my question, please leave a comment.
[UPDATE]
I agree that stored procedures are also a great option, but for some reason my management is very resistant to make any changes to our database. It is easier for me (and our customers) to put the sql in code and acknowledge the fact that there is raw sql. At least I can hide it from the other layers rather easily.
[/UPDATE]
Possible solution for this problem may be using context initialization with DbCompiledModel param:
var builder = new DbModelBuilder(DbModelBuilderVersion.V6_0);
builder.Configurations.Add(new EntityTypeConfiguration<EntityName>());
builder.Entity<EntityName>().ToTable("TableNameDefinedInRuntime");
var dynamicContext = new MyDbContext(builder.Build(context.Database.Connection).Compile());
For some reason in EF6 it fails on second table request, but mapping inside context looks correct on the moment of execution.

Entity Framework 4 many to many relationship issue

Considering this database:
This is what EF generates:
I think that HeroesItem class, is useless, and there should be a navigation property Items on Hero class and a navigation property Heroes on Item class.
I saw this can be done easily with code first, but how to get it done using database first?
It can be done only if your HeroesItems table does not contain Id column and instead uses IdHero and IdItem as composite primary key. Once you add any additional column to junction table you must map it as entity to have control over that column.

Change Table and Column Name Mappings Entity Framework v4.3

I've got an application with a working Entity model generated from an existing database. I have to point my application at a new database, with the same schema, except that the table and column names are different.
For example, my current schema has tables named like "Answer". My new schema that I need to point to has the exact same table, except it is named "tblAnswer".
My columns have also changed. Where as a column used to be called "AnswerId", it's now "zAnswerId". Don't ask about the "z" prefix, it's a long story, but it's on every column.
So, what options do I have to point this existing Entity Model (generated from the database) to a new database and adjust the mappings? I've been experimenting with some of the techniques that are used for "Code First" mappings, as outlined in this guide, but haven't had any luck. I simply don't know if this is the right approach, or if there is something that makes more sense.
Suggestions? Thanks in advance.
You can change the database in the web.config file.
Use data annotations to use the different table and column names.
For example:
[Table("tblAnswer")]
class Answer
{
[Column("zAnswerId")]
public int AnswerId { get; set; }
}

Removing Entities from Database table via Navigation Property using RIA Services and Entity Framework

I have 3 normalised tables consisting of Employees, Departments and EmployeesToDepartments. I wish to be able to assign an Employee to one or more Department, hence the link table (EmployeesToDepartments). I can successfully query the database and extract the full hierarchy of entities via the Navigation properties using
this.ObjectContext.Employees.Include("EmployeesToDepartments").Include("EmployeesToDepartments.Department")
plus the [Include] attribute in the metadata, thus allowing me to access the Departments for a given Employee. Upon trying to remove a link between an [Employee] and [Department] in the [EmployeesToDepartments] table I was given a Foreign Key Constrain error.
I have simplified my model to include just one navigation property between [Employees] and [EmployeesToDepartments]. A Foreign Key constraint between[Employees].[ID] and [EmployeesToDepartments].[IDEmployee] was preventing me from updating the EmployeesToDepartments table. With this removed via a Relationship setting I can now update the table. I can now execute the following code
foreach (var rel in _employee.EmployeesToDepartments)
{
_employee.EmployeesToDepartments.Remove(rel);
}
_domainContext.SubmitChanges();
without error.
I was expecting to see the entries in the RelEmployeesToDepartments with the IDEmployee to have been deleted. What I see in the table are the value 0 where the IDEmployee previously was.
Is it possible to force a DELETE statement to be issued? Am I misunderstanding the basic concepts here?
Any help would be much appreciated.
Removing entities in navigation property only breaks the link between entities. You have to delete from the EntitySet to achive what you want.
ex)
myDomainContext.EmployeeDepartments.Remove(employeeDepartmentToRemove);
myDomainContext.SubmitChanges();