Add column to database without defining it in model with Entity Framework - entity-framework-6

Is it possible to add a column (or execute some SQL) to a table when Entity Framework is instantiating a new database, without defining it in the Model used in DbSet ?
Iam building a prototype for a SaaS application with Entity Framework and Elastic Scale Client, and want to use Row Level Security, for that a need a column to identify my tenants. So i figured it would be nice if I could use just the EF initializer to add this column, when adding new tenants to the system.

As noted in the documentation here, you can execute sql when you have the DBContext.
From the docs:
using (var context = new BloggingContext())
{
context.Database.ExecuteSqlCommand(
"UPDATE dbo.Blogs SET Name = 'Another Name' WHERE BlogId = 1");
}
You could use this to modify the structure without having the actual structure defined in EF.

Related

ASP.NET Identity 2.0 DB First Approach: Adding new Columns

I am trying to use ASP.NET Identity 2.0 with existing database.
I have created an MVC project (which uses Individual Account Authentication), then I registered for a use in order to create the DB.
Then:
I created scripts for the necessary tables and added them to my own DB
I added ADO.NET Entity Data Model (database first) which include my tables plus identity tables.
I ran the application and registered for a user, everything is going fine.
Now, I need to add a relation to AspNetUser table.
I added the Column LocationId with the relationship in DB.
I Added the following to the Application User Class:
public virtual Region Region { get; set; }
Then, I updated my Model and run the application, when I tried to register for new user, I got the following error:
AspNet UserLogin: EntityType: EntitySet 'AspNetUserLogins' is based on type 'AspNet UserLogin' that has no keys defined.
How is it possible to continue using DB First Approach in this scenario?
Identity uses Code First approach for making Identity System make customization as more as possible and you are using DB first approach for your common data access. So there are 2 contexts, one is for your data and other is for you Identity. You need to write Identity classes and make a code first migration of Identity context class by typing in the Package Manager Console as:
`Enable-Migrations -ContextNameType [Your_Identity_Context]
This will enable code first migrations just for your Identity context type. If you want to add region property in your user table, then in 'ApplicationUser' (or any class derived from IdentityUser) add the required region property and then apply the migrations to update the user table in the database.
Generating SQL script and applying to the database is not a good approach.

Joining tables from two databases using entity framework

I am working on an ASP.NET MVC 4 web application. I am using Entity Framework as the data access layer, using database first approach (.edmx file).
Currently I have a problem in join tables that are defined inside two different databases (i.e. I have two .edmx files).
For example if I want to join tables I am performing the following query:-
public ActionResult AutoComplete(string term)
{
var tech = repository.AllFindTechnolog(term).Take(100);//Call to the first database
var resources = repository.GetResources(tech.Select(a => a.IT360ID.Value).ToArray(), false);//call to the second database
var query = from techItems in tech
join resourcesItems in resources
on techItems.IT360ID.Value equals resourcesItems.RESOURCEID // join based on db2ID
orderby techItems.PartialTag
select new //code goes here
return Json(query, JsonRequestBehavior.AllowGet);
}
I will have two separate calls to the database, and a join inside the application server, which is not the best performance-oriented solution. Ideally the joins will happen completely inside the database engine.
I know that a stored procedure will allow me to join tables from different databases purely on the server, but I do not want to use SP because it will make my code less maintainable and less testable.
So I am searching for a solution where I can do the join using entity framework and to result in a single database join?
If you want to do it with a single database call you will have to create a View in the database that joins the 2 tables from separate db's. Once the view is created you can add it to EF as a single object, which you can manipulate further and Query off of. The view will basically be a table and it will be easily maintable and easy to bind to a strongly typed model
Another way ,similiar like you have posted, you can query separate .edmx files and then join them.
Yes, there is 2 calls to the database but it shouldn't be that expensive and probably won't notice a difference.
using(var db = new MyEntities())
using (var db2 = new MyEntities2())
{
var one = db.Table1.AsEnumerable();
var two = db2.Table2.AsEnumerable();
var result = from o in one
join t in two on o.Id equals t.Id
// blah blah
}
#CSharper's answer is close. As #Oliver mentioned in the comments, IEnumerable loads the table into application memory, leading to crashes if you have a large database.
The solution is to use IQueryable, which can be called with LINQ - this produces SQL which is much faster.
// This is a generic method, modify to your needs
public ActionResult Details(int? id)
var one = db.Table1.AsQueryable();
var two = db2.Table2.AsQueryable();
// since you're using MVC EF, I assume you want to put this in a viewmodel
// (in this case ObjectCombined)
// assume "id" is passed as parameter
Object1 result1 = (from o in one where one.id == id select o).Single();
Object2 result2 = (from t in two where t.id == o.id select t).Single();
ObjectCombined result = new ObjectCombined(result1, result2);
return View(result);
}
Might I suggest that you look into using a synonym in your database. For instance, you can create a synonym to the resources table in the database that your tech table is located. This will ensure that you will not need to maintain 2 EDMX files. Instead you can have a single EDMX file and you can simply join your tech table to the synonym of the resource table and voila - you are on your way.
UPDATE: Please note that if you are using synonyms there is an extra bit of work you will need to do to the EDMX file to get it working in Entity Framework. Here is a blog post that was put out by a programmer who got it to work. Here is the original stackoverflow question she asked.
HAPPY CODING!!! :)
you can create a view or a stored procedure, your sql statement can then make cross db query just make sure your credentials can DML or DDL on both db. otherwise try the nested using entities that will make sure you will not get the linq bug when you dont declare the db entity inside a using statement.

How can I create and use views using EF6 Code First?

Is there actually any official strategy for creating and using views with EF6.1 Code First? I can reverse the database into Code First and get tables not views. I can import the database into Model First and get views and then do Generate DB from Model and my edmx is modified and the views are converted to tables. MSFT seems to have all but abandoned Model First, and the new Update 2 seems to have reverse engineering for Code First so I feel forced to convert to Code First but has the EF team given support for any reasonable approach to using views or stored Procedures in Code First? After all CF is supposed to create the DB but what - are you no longer supposed to use either of these SQL Server features in a .NET EF application?
For starters you can use views and stored procedures that are already created in the database. For views you don't have to do any mapping if you create a code like this:
public TestContext : DbContext
{
public DbSet<User> AdminUsers { get; set; }
}
And you have a view in the database named dbo.AdminUsers and it can be mapped to the class User (contains all required properties with the same name as the property).
For stored procedures you can use the SqlQuery function either through the Database property of the DbContext such as:
var userActivityReport = context.Database.SqlQuery<UserActivityReport>(
"dbo.GetUserActivityReport #p0, #p1", startDate, endDate);
Or through the SqlQuery function of the DbSet class:
var newUsers = context.Users.SqlQuery("dbo.GetNewUsers #p0", count);
If you want to create, modify or delete views and stored procedures via Entity Framework you can either use custom migration operations see http://dolinkamark.wordpress.com/2014/05/03/creating-a-custom-migration-operation-in-entity-framework/
For event better integration you can use the Public mapping API with a library provided by a community member: https://codefirstfunctions.codeplex.com/

ASP.NET MVC Model First Many To Many

I have some problems working with model first many to many relationship. Since I created many-many relationship between Town and Author via interface builder it created table TownAuthor with keys Towns_TownID and Authors_AuthorID but I want that just to be called TownID and AuthorID, how do I change that?
In Code first I would use that modelBuilder configuration in Context but I have no idea how to do this via model first...
You have to change the names of these columns in the Entity Designer DDL script (which is generated from the EDMX file and has ModelName.edmx.sql name) before executing it.
-- Creating table 'TownAuthor'
CREATE TABLE [dbo].[TownAuthor] (
[TownID] int NOT NULL,
[AuthorID] int NOT NULL
);
GO

LINQ Modelling Automagically Retrieving Data Via EntityRef

I'm using LINQ to model my database, but I'm writing it by hand (Steve Sanderson recommends this in his ASP.NET MVC book). What I need to know is what's happening when you create an EntityRef, and how it's referenced. If I create my queries manually (without using LINQ), but use LINQ to model it, and I bring back just the ID of something, then reference the actual table column using EntityRef in the view, does it do the join, or does it re-query the database for that bit of information?
To clear things up, if I have this in my repository:
public IEnumerable<MyTable> ListMyTable(int? myColumnVar)
{
string query = "SELECT * FROM MyTable WHERE MyColumn = {0}";
return this.ExecuteQuery<MyTable>(query, myColumnVar);
}
and then in my controller I do this:
IEnumerable<MyTable> mytables = _contractsControlService.ListMyTable(1);
return View(mytables);
then in my view I do things like
<%=tbl.Ref.MyColumn %>
I'm referencing something set out by the LINQ model, but isn't actually in the table output. How does it get that data?
To clear things up further, we're using systems which require ultimate speed, so the LINQ-to-SQL is too slow for us, hence why we're using direct queries in our repository. I wouldn't mind using this EntityRef business if only I knew what was happening underneath.
You have most likely used the Object Relational designer to create an entity class for the Ref entity and an association between the MyTable and the Ref entity. You can also do that manually by creating the appropriate entity classes and using attributes to map the classes to the database schema. You can read the details in How to: Customize Entity Classes by Using the Code Editor (LINQ to SQL) on MSDN.
In your generated (or handwritten) code you will find some attributes:
[Table(Name="dbo.Ref")]
public partial class Ref : INotifyPropertyChanging, INotifyPropertyChanged
and
public partial class MyTable: INotifyPropertyChanging, INotifyPropertyChanged
{
[Association(Name="Ref_MyTable", Storage="_Ref", ThisKey="RefId",
OtherKey="Id", IsForeignKey=true)]
public Ref Ref
{
get
...
The entity classes combined with the attributes enables the Linq-to-Sql framework to retrieve entity classes directly from the database.
If you want to monitor the SQL genereated by Linq-to-Sql you can assign the DataContext.Log property:
context.Log = Console.Out;
In your example, navigating from MyTable to Ref, probably generates SQL along these lines:
SELECT Id, Field1, Field2, Field3
FROM Ref
WHERE Id = #RefId

Resources